001package gudusoft.gsqlparser.sqlcmds;
002
003import gudusoft.gsqlparser.EFindSqlStateType;
004import gudusoft.gsqlparser.ESqlStatementType;
005import gudusoft.gsqlparser.TBaseType;
006import gudusoft.gsqlparser.TCustomSqlStatement;
007import gudusoft.gsqlparser.TSourceToken;
008import gudusoft.gsqlparser.stmt.TUnknownSqlStatement;
009import gudusoft.gsqlparser.stmt.oceanbase.TAlterOutlineSqlStatement;
010import gudusoft.gsqlparser.stmt.oceanbase.TAlterTablegroupSqlStatement;
011import gudusoft.gsqlparser.stmt.oceanbase.TCreateOutlineSqlStatement;
012import gudusoft.gsqlparser.stmt.oceanbase.TCreateTablegroupSqlStatement;
013import gudusoft.gsqlparser.stmt.oceanbase.TDropOutlineSqlStatement;
014import gudusoft.gsqlparser.stmt.oceanbase.TDropTablegroupSqlStatement;
015
016/**
017 * OceanBase Oracle-mode SQL command resolver — Phase 4 Batch 6+.
018 *
019 * <p>Extends the stock {@link TSqlCmdsOracle} to add recognition for
020 * OceanBase-specific DDL that parses through the Oracle-mode fork:
021 * currently the {@code CREATE/ALTER/DROP TABLEGROUP} family (Batch 6).
022 *
023 * <p>This class keeps OceanBase-specific prefix registrations out of the
024 * shared {@link TSqlCmdsOracle} so base-Oracle semantics remain
025 * unchanged and backportable. {@link gudusoft.gsqlparser.parser.OceanBaseOracleSqlParser}
026 * selects this subclass in its constructor.
027 *
028 * @since 4.0.1.4
029 */
030public class TSqlCmdsOceanbaseOracle extends TSqlCmdsOracle {
031
032    public TSqlCmdsOceanbaseOracle() {
033        super();
034        // Inherit Oracle vendor identity — OceanBaseOracleSqlParser already
035        // rebinds vendor via the AST NodeFactory path, so we do NOT override
036        // it here (see Phase 3 notes in OceanBaseOracleSqlParser).
037    }
038
039    @Override
040    protected void initializeCommands() {
041        // Step 1 — inherit the full Oracle command surface verbatim.
042        super.initializeCommands();
043
044        // Step 2 — register OceanBase tablegroup DDL prefixes so the
045        // Oracle-mode splitter recognizes them as statement boundaries.
046        // Phase 4 Batch 6.
047        addCmd(TBaseType.rrw_create, "tablegroup", " ", " ", " ", " ", " ",
048                ESqlStatementType.sstoceanbase_create_tablegroup);
049        addCmd(TBaseType.rrw_alter,  "tablegroup", " ", " ", " ", " ", " ",
050                ESqlStatementType.sstoceanbase_alter_tablegroup);
051        addCmd(TBaseType.rrw_drop,   "tablegroup", " ", " ", " ", " ", " ",
052                ESqlStatementType.sstoceanbase_drop_tablegroup);
053
054        // Phase 4 Batch 8 — OUTLINE DDL does NOT need new addCmd entries
055        // here: Oracle base already registers CREATE/ALTER/DROP OUTLINE
056        // with the sstoracle*outline enum values. We reuse those enums
057        // per ADR-8 and the issql override below intercepts them to swap
058        // in the OceanBase statement classes.
059
060        // CREATE OR REPLACE OUTLINE — Oracle base only registers
061        // CREATE OUTLINE; the OR REPLACE variant needs explicit entry.
062        addCmd(TBaseType.rrw_create, "or", "replace", "outline", " ", " ", " ",
063                ESqlStatementType.sstoraclecreateoutline);
064
065        // Phase 4 Batch 7 — CREATE [GLOBAL|LOCAL] INDEX Oracle-mode
066        // support deferred. See FORK_DIVERGENCE.md.
067    }
068
069    /**
070     * Intercept the {@link TUnknownSqlStatement} produced by
071     * {@link TSqlCmdsOracle#issql} for the OceanBase tablegroup types
072     * and swap in the proper statement class so downstream tools switch
073     * on the real type rather than the opaque unknown shell.
074     */
075    @Override
076    public TCustomSqlStatement issql(TSourceToken token,
077                                     EFindSqlStateType state,
078                                     TCustomSqlStatement currentStatement) {
079        TCustomSqlStatement ret = super.issql(token, state, currentStatement);
080        if (ret instanceof TUnknownSqlStatement) {
081            switch (ret.sqlstatementtype) {
082                case sstoceanbase_create_tablegroup:
083                    return new TCreateTablegroupSqlStatement(this.vendor);
084                case sstoceanbase_alter_tablegroup:
085                    return new TAlterTablegroupSqlStatement(this.vendor);
086                case sstoceanbase_drop_tablegroup:
087                    return new TDropTablegroupSqlStatement(this.vendor);
088                // Phase 4 Batch 8 — OUTLINE DDL reuses Oracle's existing
089                // sstoracle*outline enum values (which Oracle's issql
090                // switch default-cases into TUnknownSqlStatement). Swap
091                // to the OceanBase statement classes here.
092                case sstoraclecreateoutline:
093                    return new TCreateOutlineSqlStatement(this.vendor);
094                case sstoraclealteroutline:
095                    return new TAlterOutlineSqlStatement(this.vendor);
096                case sstoracledropoutline:
097                    return new TDropOutlineSqlStatement(this.vendor);
098                default:
099                    break;
100            }
101        }
102        return ret;
103    }
104}