Skip to content
Oracle Database

Oracle Error PLS-00103

Encountered the symbol ... when expecting one of the following

Applies to: Oracle Database 19c, 21c, 23ai and 26ai (same form)
Last technically reviewed 24 October 2026 on Oracle Database Error Messages reference (26ai, 21c and 19c); not run locally
The full message
PLS-00103: Encountered the symbol "BEGIN" when expecting one of the following:
Other forms of this message
Under ORA-06550, with the list of tokens that would have been valid (shortened)
ORA-06550: line 6, column 24:
PLS-00103: Encountered the symbol "BEGIN" when expecting one of the following:
( ) - + case mod new not null <an identifier>
<a double-quoted delimited-identifier> <a bind variable>
...
Any other token in place of BEGIN
PLS-00103: Encountered the symbol "CREATE" when expecting one of the following:
Error code
PLS-00103
Product
Oracle Database
Versions
Oracle Database 19c, 21c, 23ai and 26ai (same form)
Last reviewed
24 October 2026

What it means

PLS-00103 is a PL/SQL syntax error: while parsing, the compiler met a token (the "symbol") that cannot appear at that point, and it lists the tokens it would have accepted instead.

The PL/SQL parser reads your code token by token. When the next token does not fit the grammar, it stops and reports PLS-00103, naming the token it found and listing what could legally come next. In an anonymous block the error appears under ORA-06550 with a line and column; for a stored unit it is in SHOW ERRORS and USER_ERRORS.

The key to reading it is in Oracle's action text: check the previous tokens as well as the one in the message, because the line and column refer to the end of the faulty construct. A missing semicolon at the end of line 2 is reported at the first token of line 3, which is why the line named often looks correct. The expected-token list is a hint: if it contains ;, a statement before the reported position was not ended.

Common causes

  • A missing semicolon at the end of the previous declaration or statement.
  • A missing or mismatched keyword: THEN after IF, LOOP or END LOOP, END IF, or the END of a block, procedure or CASE.
  • A reserved word used as a variable, parameter or column alias name without double quotation marks (Oracle's example uses BEGIN).
  • A DDL statement such as CREATE TABLE written directly in a block; PL/SQL static SQL does not include DDL, so the parser does not expect CREATE there.
  • An unbalanced quotation mark or parenthesis, which makes the parser read later code as part of a string or expression.
  • Syntax from another language, such as = for assignment where PL/SQL uses :=.

Diagnose it

Read-only These queries only read the data dictionary (USER_, ALL_ and DBA_ views) and dynamic performance views (V$). They do not change data, privileges or settings, so they are safe to run first. DBA_ and V$ views need the matching privileges.

Read backwards from the reported position

Go to the line and column given, then look at the tokens just before it: the end of the previous line, the last IF, LOOP or BEGIN that has not been closed. Compare the token named in the message with the expected list: the first thing you can add from that list before the symbol is usually the fix.

List the syntax errors of a stored unit

SELECT name, type, line, position, text
FROM all_errors
WHERE owner = 'SHOP'
  AND name = 'CLOSE_MONTH'
ORDER BY sequence;
What to look for

Each error with line and position. Fix the first one and recompile: a single syntax error often produces several follow-on messages.

Show the lines before the error

SELECT line, text
FROM all_source
WHERE owner = 'SHOP'
  AND name = 'CLOSE_MONTH'
  AND type = 'PROCEDURE'
  AND line BETWEEN 10 AND 15   -- a few lines up to the reported one
ORDER BY line;
What to look for

The code leading up to the error, where the missing or extra token usually is.

How to fix it

Each fix is labelled with what it changes. Try read-only checks and the least invasive fix first, and test changes outside production.

Add the missing semicolon or closing keyword

Changes schema

End every declaration and statement with a semicolon, and close every IF with END IF, every LOOP with END LOOP and every block with END. Then recreate the unit.

CREATE OR REPLACE PROCEDURE shop.close_month (p_month IN DATE)
IS
  v_count NUMBER;   -- the semicolon was missing here
BEGIN
  SELECT COUNT(*) INTO v_count
  FROM shop.orders
  WHERE order_date >= TRUNC(p_month, 'MM')
    AND order_date <  ADD_MONTHS(TRUNC(p_month, 'MM'), 1);
  IF v_count = 0 THEN
    RAISE_APPLICATION_ERROR(-20030, 'No orders in this month');
  END IF;
END close_month;
/

Rename identifiers that are reserved words

Changes schema

Rename the variable (for example v_begin instead of begin). Oracle's reference shows that a reserved word can be used only as a quoted identifier, which then has to be quoted and spelt with the same case everywhere, so renaming is the better fix.

Run DDL through EXECUTE IMMEDIATE

Changes schema

DDL is not static SQL in PL/SQL, so it must be run as dynamic SQL. Check first whether the DDL belongs in a deployment script rather than in application code at all.

BEGIN
  EXECUTE IMMEDIATE 'CREATE TABLE shop.month_close_log (closed_on DATE, order_count NUMBER)';
END;
/

Examples

A reserved word used as a name

Not reproduced here: no Oracle Database is installed for this site. This is the documented example and result from Oracle's PL/SQL Language Reference (lexical units); the list of expected tokens is shortened here.

DECLARE
  "HELLO" VARCHAR2(10) := 'hello';   -- HELLO is not a reserved word
  "BEGIN" VARCHAR2(10) := 'begin';   -- BEGIN is a reserved word
BEGIN
  DBMS_OUTPUT.PUT_LINE(Hello);   -- double quotation marks are optional
  DBMS_OUTPUT.PUT_LINE(BEGIN);   -- double quotation marks are required
END;
/
Expected result (documented format, not run)
ORA-06550: line 6, column 24:
PLS-00103: Encountered the symbol "BEGIN" when expecting one of the following:
( ) - + case mod new not null <an identifier>
<a double-quoted delimited-identifier> <a bind variable>
...

A missing semicolon is reported on the next line

Not reproduced here: no Oracle Database is installed for this site. The message form follows Oracle's documented PLS-00103 examples; the position and the expected-token list (omitted) are illustrative. The error points at BEGIN on line 3 although the mistake is the missing semicolon on line 2, as Oracle's action text describes.

DECLARE
  v_count NUMBER
BEGIN
  SELECT COUNT(*) INTO v_count FROM orders;
END;
/
Expected result (documented format, not run)
ORA-06550: line 3, column 1:
PLS-00103: Encountered the symbol "BEGIN" when expecting one of the following:
...

CREATE TABLE written directly in a block

Not reproduced here: no Oracle Database is installed for this site. The message form follows Oracle's documented PLS-00103 examples; the position and the omitted token list are illustrative. Use EXECUTE IMMEDIATE for DDL inside PL/SQL.

BEGIN
  CREATE TABLE month_close_log (closed_on DATE);
END;
/
Expected result (documented format, not run)
ORA-06550: line 2, column 3:
PLS-00103: Encountered the symbol "CREATE" when expecting one of the following:
...

How to prevent it

Use an editor or IDE that highlights PL/SQL syntax and matches BEGIN/END and IF/END IF, and compile small pieces often. Use a naming convention (v_, p_, l_ prefixes) that keeps variables from colliding with reserved words.

Keep DDL in deployment scripts rather than in PL/SQL, and when it must be dynamic, build it with EXECUTE IMMEDIATE.

Common questions

How do I fix PLS-00103 encountered the symbol?

Go to the line and column given and look just before it: most often a semicolon, THEN, END IF or END is missing on the previous line. The symbol named is where the parser noticed; the expected list shows what could have come next.

Why does the error point to a line that looks correct?

Oracle documents that the line and column refer to the end of the faulty construct. The parser only notices the problem at the next token, which is often on the following line.

What does "when expecting one of the following" mean?

It is the list of tokens that would have been valid at that position. If it includes a semicolon, a statement before that point was not ended; if it includes an identifier, a name is missing or a reserved word was used as one.

Learn more on CodeWithSQL

Official documentation

Last technically reviewed 24 October 2026; examples and diagnostics run on Oracle Database Error Messages reference (26ai, 21c and 19c); not run locally. Messages and explanations follow Oracle's Database Error Messages reference; no Oracle Database was available, so the examples were not run locally.

Still stuck on an Oracle error?

Browse the full Oracle error library, or get hands-on help from an experienced SQL professional.