View Javadoc
1   /*
2    * Licensed to the Apache Software Foundation (ASF) under one or more
3    * contributor license agreements.  See the NOTICE file distributed with
4    * this work for additional information regarding copyright ownership.
5    * The ASF licenses this file to You under the Apache License, Version 2.0
6    * (the "License"); you may not use this file except in compliance with
7    * the License.  You may obtain a copy of the License at
8    *
9    *     http://www.apache.org/licenses/LICENSE-2.0
10   *
11   * Unless required by applicable law or agreed to in writing, software
12   * distributed under the License is distributed on an "AS IS" BASIS,
13   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14   * See the License for the specific language governing permissions and
15   * limitations under the License.
16   */
17  
18  package org.apache.shardingsphere.sql.parser.sql92.visitor.statement.type;
19  
20  import org.antlr.v4.runtime.ParserRuleContext;
21  import org.antlr.v4.runtime.misc.Interval;
22  import org.apache.shardingsphere.sql.parser.api.ASTNode;
23  import org.apache.shardingsphere.sql.parser.api.visitor.statement.type.DDLStatementVisitor;
24  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.AddColumnSpecificationContext;
25  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.AddConstraintSpecificationContext;
26  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.AlterDefinitionClauseContext;
27  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.AlterTableContext;
28  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.CheckConstraintDefinitionContext;
29  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.ColumnDefinitionContext;
30  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.ConstraintDefinitionContext;
31  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.ConstraintNameContext;
32  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.CreateDefinitionClauseContext;
33  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.CreateDefinitionContext;
34  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.CreateTableContext;
35  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.DataTypeOptionContext;
36  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.DropColumnSpecificationContext;
37  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.DropConstraintSpecificationContext;
38  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.DropTableContext;
39  import org.apache.shardingsphere.sql.parser.autogen.SQL92StatementParser.ModifyColumnSpecificationContext;
40  import org.apache.shardingsphere.sql.parser.sql92.visitor.statement.SQL92StatementVisitor;
41  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.AlterDefinitionSegment;
42  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.CreateDefinitionSegment;
43  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.column.ColumnDefinitionSegment;
44  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.column.alter.AddColumnDefinitionSegment;
45  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.column.alter.DropColumnDefinitionSegment;
46  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.column.alter.ModifyColumnDefinitionSegment;
47  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.constraint.ConstraintDefinitionSegment;
48  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.constraint.ConstraintSegment;
49  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.constraint.alter.AddConstraintDefinitionSegment;
50  import org.apache.shardingsphere.sql.parser.statement.core.segment.ddl.constraint.alter.DropConstraintDefinitionSegment;
51  import org.apache.shardingsphere.sql.parser.statement.core.segment.dml.column.ColumnSegment;
52  import org.apache.shardingsphere.sql.parser.statement.core.segment.generic.DataTypeSegment;
53  import org.apache.shardingsphere.sql.parser.statement.core.segment.generic.table.SimpleTableSegment;
54  import org.apache.shardingsphere.sql.parser.statement.core.statement.type.ddl.table.AlterTableStatement;
55  import org.apache.shardingsphere.sql.parser.statement.core.statement.type.ddl.table.CreateTableStatement;
56  import org.apache.shardingsphere.sql.parser.statement.core.statement.type.ddl.table.DropTableStatement;
57  import org.apache.shardingsphere.sql.parser.statement.core.value.collection.CollectionValue;
58  import org.apache.shardingsphere.sql.parser.statement.core.value.identifier.IdentifierValue;
59  
60  import java.util.Collections;
61  
62  /**
63   * DDL statement visitor for SQL92.
64   */
65  public final class SQL92DDLStatementVisitor extends SQL92StatementVisitor implements DDLStatementVisitor {
66      
67      @SuppressWarnings("unchecked")
68      @Override
69      public ASTNode visitCreateTable(final CreateTableContext ctx) {
70          CreateTableStatement result = new CreateTableStatement();
71          result.setTable((SimpleTableSegment) visit(ctx.tableName()));
72          if (null != ctx.createDefinitionClause()) {
73              CollectionValue<CreateDefinitionSegment> createDefinitions = (CollectionValue<CreateDefinitionSegment>) visit(ctx.createDefinitionClause());
74              for (CreateDefinitionSegment each : createDefinitions.getValue()) {
75                  if (each instanceof ColumnDefinitionSegment) {
76                      result.getColumnDefinitions().add((ColumnDefinitionSegment) each);
77                  } else if (each instanceof ConstraintDefinitionSegment) {
78                      result.getConstraintDefinitions().add((ConstraintDefinitionSegment) each);
79                  }
80              }
81          }
82          return result;
83      }
84      
85      @Override
86      public ASTNode visitCreateDefinitionClause(final CreateDefinitionClauseContext ctx) {
87          CollectionValue<CreateDefinitionSegment> result = new CollectionValue<>();
88          for (CreateDefinitionContext each : ctx.createDefinition()) {
89              if (null != each.columnDefinition()) {
90                  result.getValue().add((ColumnDefinitionSegment) visit(each.columnDefinition()));
91              }
92              if (null != each.constraintDefinition()) {
93                  result.getValue().add((ConstraintDefinitionSegment) visit(each.constraintDefinition()));
94              }
95              if (null != each.checkConstraintDefinition()) {
96                  result.getValue().add((ConstraintDefinitionSegment) visit(each.checkConstraintDefinition()));
97              }
98          }
99          return result;
100     }
101     
102     @Override
103     public ASTNode visitColumnDefinition(final ColumnDefinitionContext ctx) {
104         ColumnSegment column = (ColumnSegment) visit(ctx.columnName());
105         DataTypeSegment dataType = (DataTypeSegment) visit(ctx.dataType());
106         boolean isPrimaryKey = ctx.dataTypeOption().stream().anyMatch(each -> null != each.primaryKey());
107         // TODO parse not null
108         ColumnDefinitionSegment result = new ColumnDefinitionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(), column, dataType, isPrimaryKey, false, getText(ctx));
109         for (DataTypeOptionContext each : ctx.dataTypeOption()) {
110             if (null != each.referenceDefinition()) {
111                 result.getReferencedTables().add((SimpleTableSegment) visit(each.referenceDefinition().tableName()));
112             }
113         }
114         return result;
115     }
116     
117     private String getText(final ParserRuleContext ctx) {
118         return ctx.start.getInputStream().getText(new Interval(ctx.start.getStartIndex(), ctx.stop.getStopIndex()));
119     }
120     
121     @Override
122     public ASTNode visitCheckConstraintDefinition(final CheckConstraintDefinitionContext ctx) {
123         return new ConstraintDefinitionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex());
124     }
125     
126     @Override
127     public ASTNode visitAddConstraintSpecification(final AddConstraintSpecificationContext ctx) {
128         return new AddConstraintDefinitionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(), (ConstraintDefinitionSegment) visit(ctx.constraintDefinition()));
129     }
130     
131     @Override
132     public ASTNode visitDropConstraintSpecification(final DropConstraintSpecificationContext ctx) {
133         return new DropConstraintDefinitionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(), (ConstraintSegment) visit(ctx.constraintDefinition().constraintName()));
134     }
135     
136     @SuppressWarnings("unchecked")
137     @Override
138     public ASTNode visitConstraintDefinition(final ConstraintDefinitionContext ctx) {
139         ConstraintDefinitionSegment result = new ConstraintDefinitionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex());
140         if (null != ctx.constraintName()) {
141             result.setConstraintName((ConstraintSegment) visit(ctx.constraintName()));
142         }
143         if (null != ctx.primaryKeyOption()) {
144             result.getPrimaryKeyColumns().addAll(((CollectionValue<ColumnSegment>) visit(ctx.primaryKeyOption().columnNames())).getValue());
145         }
146         if (null != ctx.foreignKeyOption()) {
147             result.setReferencedTable((SimpleTableSegment) visit(ctx.foreignKeyOption().referenceDefinition().tableName()));
148         }
149         return result;
150     }
151     
152     @Override
153     public ASTNode visitConstraintName(final ConstraintNameContext ctx) {
154         return new ConstraintSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(), (IdentifierValue) visit(ctx.identifier()));
155     }
156     
157     @SuppressWarnings("unchecked")
158     @Override
159     public ASTNode visitAlterTable(final AlterTableContext ctx) {
160         AlterTableStatement result = new AlterTableStatement();
161         result.setTable((SimpleTableSegment) visit(ctx.tableName()));
162         if (null != ctx.alterDefinitionClause()) {
163             for (AlterDefinitionSegment each : ((CollectionValue<AlterDefinitionSegment>) visit(ctx.alterDefinitionClause())).getValue()) {
164                 if (each instanceof AddColumnDefinitionSegment) {
165                     result.getAddColumnDefinitions().add((AddColumnDefinitionSegment) each);
166                 } else if (each instanceof ModifyColumnDefinitionSegment) {
167                     result.getModifyColumnDefinitions().add((ModifyColumnDefinitionSegment) each);
168                 } else if (each instanceof DropColumnDefinitionSegment) {
169                     result.getDropColumnDefinitions().add((DropColumnDefinitionSegment) each);
170                 } else if (each instanceof AddConstraintDefinitionSegment) {
171                     result.getAddConstraintDefinitions().add((AddConstraintDefinitionSegment) each);
172                 } else if (each instanceof DropConstraintDefinitionSegment) {
173                     result.getDropConstraintDefinitions().add((DropConstraintDefinitionSegment) each);
174                 }
175             }
176         }
177         return result;
178     }
179     
180     @SuppressWarnings("unchecked")
181     @Override
182     public ASTNode visitAlterDefinitionClause(final AlterDefinitionClauseContext ctx) {
183         CollectionValue<AlterDefinitionSegment> result = new CollectionValue<>();
184         if (null != ctx.addColumnSpecification()) {
185             result.getValue().addAll(((CollectionValue<AddColumnDefinitionSegment>) visit(ctx.addColumnSpecification())).getValue());
186         }
187         if (null != ctx.modifyColumnSpecification()) {
188             result.getValue().add((ModifyColumnDefinitionSegment) visit(ctx.modifyColumnSpecification()));
189         }
190         if (null != ctx.dropColumnSpecification()) {
191             result.getValue().add((DropColumnDefinitionSegment) visit(ctx.dropColumnSpecification()));
192         }
193         return result;
194     }
195     
196     @Override
197     public ASTNode visitAddColumnSpecification(final AddColumnSpecificationContext ctx) {
198         CollectionValue<AddColumnDefinitionSegment> result = new CollectionValue<>();
199         AddColumnDefinitionSegment addColumnDefinition = new AddColumnDefinitionSegment(
200                 ctx.columnDefinition().getStart().getStartIndex(), ctx.columnDefinition().getStop().getStopIndex(),
201                 Collections.singletonList((ColumnDefinitionSegment) visit(ctx.columnDefinition())));
202         result.getValue().add(addColumnDefinition);
203         return result;
204     }
205     
206     @Override
207     public ASTNode visitModifyColumnSpecification(final ModifyColumnSpecificationContext ctx) {
208         // TODO visit pk and table ref
209         return new ModifyColumnDefinitionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(), (ColumnDefinitionSegment) visit(ctx.columnDefinition()));
210     }
211     
212     @Override
213     public ASTNode visitDropColumnSpecification(final DropColumnSpecificationContext ctx) {
214         return new DropColumnDefinitionSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(), Collections.singleton((ColumnSegment) visit(ctx.columnName())));
215     }
216     
217     @SuppressWarnings("unchecked")
218     @Override
219     public ASTNode visitDropTable(final DropTableContext ctx) {
220         DropTableStatement result = new DropTableStatement();
221         result.getTables().addAll(((CollectionValue<SimpleTableSegment>) visit(ctx.tableNames())).getValue());
222         return result;
223     }
224 }