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.distsql.parser.core.kernel;
19  
20  import org.antlr.v4.runtime.tree.ParseTree;
21  import org.apache.groovy.parser.antlr4.util.StringUtils;
22  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementBaseVisitor;
23  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.AlgorithmDefinitionContext;
24  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.AlterComputeNodeContext;
25  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.AlterStorageUnitContext;
26  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.CheckPrivilegesContext;
27  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ConvertYamlConfigurationContext;
28  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.DatabaseNameContext;
29  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.DisableComputeNodeContext;
30  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.EnableComputeNodeContext;
31  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ExportDatabaseConfigurationContext;
32  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ExportMetaDataContext;
33  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ExportStorageNodesContext;
34  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.FromSegmentContext;
35  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.IgnoreBroadcastTablesContext;
36  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.IgnoreSingleAndBroadcastTablesContext;
37  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.IgnoreSingleTablesContext;
38  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ImportDatabaseConfigurationContext;
39  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ImportMetaDataContext;
40  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.InstanceIdContext;
41  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.LabelComputeNodeContext;
42  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.LockClusterContext;
43  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.PropertiesDefinitionContext;
44  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.PropertyContext;
45  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.RefreshDatabaseMetadataContext;
46  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.RefreshTableMetadataContext;
47  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.RegisterStorageUnitContext;
48  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.SetDistVariableContext;
49  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowComputeNodeInfoContext;
50  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowComputeNodeModeContext;
51  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowComputeNodesContext;
52  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowDistVariableContext;
53  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowDistVariablesContext;
54  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowKeyGenerateAlgorithmPluginsContext;
55  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowLoadBalanceAlgorithmPluginsContext;
56  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowLogicalTablesContext;
57  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowPluginImplementationsContext;
58  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowRulesUsedStorageUnitContext;
59  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowStorageUnitsContext;
60  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.ShowTableMetadataContext;
61  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.StorageUnitDefinitionContext;
62  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.StorageUnitsDefinitionContext;
63  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.UnlabelComputeNodeContext;
64  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.UnlockClusterContext;
65  import org.apache.shardingsphere.distsql.parser.autogen.KernelDistSQLStatementParser.UnregisterStorageUnitContext;
66  import org.apache.shardingsphere.distsql.segment.AlgorithmSegment;
67  import org.apache.shardingsphere.distsql.segment.DataSourceSegment;
68  import org.apache.shardingsphere.distsql.segment.HostnameAndPortBasedDataSourceSegment;
69  import org.apache.shardingsphere.distsql.segment.URLBasedDataSourceSegment;
70  import org.apache.shardingsphere.distsql.statement.ral.queryable.convert.ConvertYamlConfigurationStatement;
71  import org.apache.shardingsphere.distsql.statement.ral.queryable.export.ExportDatabaseConfigurationStatement;
72  import org.apache.shardingsphere.distsql.statement.ral.queryable.export.ExportMetaDataStatement;
73  import org.apache.shardingsphere.distsql.statement.ral.queryable.export.ExportStorageNodesStatement;
74  import org.apache.shardingsphere.distsql.statement.ral.queryable.show.ShowComputeNodeInfoStatement;
75  import org.apache.shardingsphere.distsql.statement.ral.queryable.show.ShowComputeNodeModeStatement;
76  import org.apache.shardingsphere.distsql.statement.ral.queryable.show.ShowComputeNodesStatement;
77  import org.apache.shardingsphere.distsql.statement.ral.queryable.show.ShowDistVariableStatement;
78  import org.apache.shardingsphere.distsql.statement.ral.queryable.show.ShowDistVariablesStatement;
79  import org.apache.shardingsphere.distsql.statement.ral.queryable.show.ShowPluginsStatement;
80  import org.apache.shardingsphere.distsql.statement.ral.queryable.show.ShowTableMetaDataStatement;
81  import org.apache.shardingsphere.distsql.statement.ral.updatable.AlterComputeNodeStatement;
82  import org.apache.shardingsphere.distsql.statement.ral.updatable.ImportDatabaseConfigurationStatement;
83  import org.apache.shardingsphere.distsql.statement.ral.updatable.ImportMetaDataStatement;
84  import org.apache.shardingsphere.distsql.statement.ral.updatable.LabelComputeNodeStatement;
85  import org.apache.shardingsphere.distsql.statement.ral.updatable.LockClusterStatement;
86  import org.apache.shardingsphere.distsql.statement.ral.updatable.RefreshDatabaseMetaDataStatement;
87  import org.apache.shardingsphere.distsql.statement.ral.updatable.RefreshTableMetaDataStatement;
88  import org.apache.shardingsphere.distsql.statement.ral.updatable.SetComputeNodeStateStatement;
89  import org.apache.shardingsphere.distsql.statement.ral.updatable.SetDistVariableStatement;
90  import org.apache.shardingsphere.distsql.statement.ral.updatable.UnlabelComputeNodeStatement;
91  import org.apache.shardingsphere.distsql.statement.ral.updatable.UnlockClusterStatement;
92  import org.apache.shardingsphere.distsql.statement.rdl.resource.unit.type.AlterStorageUnitStatement;
93  import org.apache.shardingsphere.distsql.statement.rdl.resource.unit.type.RegisterStorageUnitStatement;
94  import org.apache.shardingsphere.distsql.statement.rdl.resource.unit.type.UnregisterStorageUnitStatement;
95  import org.apache.shardingsphere.distsql.statement.rql.resource.ShowLogicalTablesStatement;
96  import org.apache.shardingsphere.distsql.statement.rql.resource.ShowStorageUnitsStatement;
97  import org.apache.shardingsphere.distsql.statement.rql.rule.database.ShowRulesUsedStorageUnitStatement;
98  import org.apache.shardingsphere.infra.database.core.metadata.database.enums.QuoteCharacter;
99  import org.apache.shardingsphere.sql.parser.api.ASTNode;
100 import org.apache.shardingsphere.sql.parser.api.visitor.SQLVisitor;
101 import org.apache.shardingsphere.sql.parser.statement.core.segment.dal.FromDatabaseSegment;
102 import org.apache.shardingsphere.sql.parser.statement.core.segment.generic.DatabaseSegment;
103 import org.apache.shardingsphere.sql.parser.statement.core.value.identifier.IdentifierValue;
104 import org.apache.shardingsphere.sql.parser.statement.core.value.literal.impl.StringLiteralValue;
105 
106 import java.util.Collection;
107 import java.util.Collections;
108 import java.util.Objects;
109 import java.util.Properties;
110 import java.util.stream.Collectors;
111 
112 /**
113  * SQL statement visitor for kernel DistSQL.
114  */
115 public final class KernelDistSQLStatementVisitor extends KernelDistSQLStatementBaseVisitor<ASTNode> implements SQLVisitor<ASTNode> {
116     
117     @Override
118     public ASTNode visitRegisterStorageUnit(final RegisterStorageUnitContext ctx) {
119         return new RegisterStorageUnitStatement(null != ctx.ifNotExists(), getStorageUnits(ctx.storageUnitsDefinition()), getExpectedPrivileges(ctx.checkPrivileges()));
120     }
121     
122     @Override
123     public ASTNode visitAlterStorageUnit(final AlterStorageUnitContext ctx) {
124         return new AlterStorageUnitStatement(getStorageUnits(ctx.storageUnitsDefinition()), getExpectedPrivileges(ctx.checkPrivileges()));
125     }
126     
127     private Collection<DataSourceSegment> getStorageUnits(final StorageUnitsDefinitionContext ctx) {
128         return ctx.storageUnitDefinition().stream().map(each -> (DataSourceSegment) visit(each)).collect(Collectors.toList());
129     }
130     
131     private Collection<String> getExpectedPrivileges(final CheckPrivilegesContext ctx) {
132         return null == ctx ? Collections.emptySet() : ctx.privilegeType().stream().map(this::getIdentifierValue).collect(Collectors.toSet());
133     }
134     
135     @Override
136     public ASTNode visitShowTableMetadata(final ShowTableMetadataContext ctx) {
137         Collection<String> tableNames = ctx.tableName().stream().map(this::getIdentifierValue).collect(Collectors.toSet());
138         return new ShowTableMetaDataStatement(tableNames, null == ctx.databaseName()
139                 ? null
140                 : new FromDatabaseSegment(ctx.FROM().getSymbol().getStartIndex(), (DatabaseSegment) visit(ctx.databaseName())));
141     }
142     
143     @Override
144     public ASTNode visitStorageUnitDefinition(final StorageUnitDefinitionContext ctx) {
145         String user = getIdentifierValue(ctx.user());
146         String password = null == ctx.password() ? "" : new StringLiteralValue(StringUtils.replaceStandardEscapes(ctx.password().getText())).getValue();
147         Properties props = getProperties(ctx.propertiesDefinition());
148         return null == ctx.urlSource()
149                 ? new HostnameAndPortBasedDataSourceSegment(getIdentifierValue(ctx.storageUnitName()),
150                         getIdentifierValue(ctx.simpleSource().hostname()), ctx.simpleSource().port().getText(), getIdentifierValue(ctx.simpleSource().dbName()), user, password, props)
151                 : new URLBasedDataSourceSegment(getIdentifierValue(ctx.storageUnitName()), getIdentifierValue(ctx.urlSource().url()), user, password, props);
152     }
153     
154     @Override
155     public ASTNode visitShowComputeNodes(final ShowComputeNodesContext ctx) {
156         return new ShowComputeNodesStatement();
157     }
158     
159     @Override
160     public ASTNode visitShowComputeNodeInfo(final ShowComputeNodeInfoContext ctx) {
161         return new ShowComputeNodeInfoStatement();
162     }
163     
164     @Override
165     public ASTNode visitShowComputeNodeMode(final ShowComputeNodeModeContext ctx) {
166         return new ShowComputeNodeModeStatement();
167     }
168     
169     @Override
170     public ASTNode visitEnableComputeNode(final EnableComputeNodeContext ctx) {
171         return buildSetComputeNodeStateStatement(ctx.ENABLE().getText().toUpperCase(), ctx.instanceId());
172     }
173     
174     @Override
175     public ASTNode visitDisableComputeNode(final DisableComputeNodeContext ctx) {
176         return buildSetComputeNodeStateStatement(ctx.DISABLE().getText().toUpperCase(), ctx.instanceId());
177     }
178     
179     @Override
180     public ASTNode visitLabelComputeNode(final LabelComputeNodeContext ctx) {
181         Collection<String> labels = ctx.label().stream().map(this::getIdentifierValue).collect(Collectors.toList());
182         return new LabelComputeNodeStatement(null != ctx.RELABEL(), getIdentifierValue(ctx.instanceId()), labels);
183     }
184     
185     @Override
186     public ASTNode visitUnlabelComputeNode(final UnlabelComputeNodeContext ctx) {
187         Collection<String> labels = ctx.label().stream().map(this::getIdentifierValue).collect(Collectors.toList());
188         return new UnlabelComputeNodeStatement(getIdentifierValue(ctx.instanceId()), labels);
189     }
190     
191     private SetComputeNodeStateStatement buildSetComputeNodeStateStatement(final String status, final InstanceIdContext instanceIdContext) {
192         return new SetComputeNodeStateStatement(status, getIdentifierValue(instanceIdContext));
193     }
194     
195     @Override
196     public ASTNode visitAlterComputeNode(final AlterComputeNodeContext ctx) {
197         return new AlterComputeNodeStatement(getIdentifierValue(ctx.instanceId()), getIdentifierValue(ctx.variableName()), getIdentifierValue(ctx.variableValues()));
198     }
199     
200     private Properties getProperties(final PropertiesDefinitionContext ctx) {
201         Properties result = new Properties();
202         if (null == ctx || null == ctx.properties()) {
203             return result;
204         }
205         for (PropertyContext each : ctx.properties().property()) {
206             result.setProperty(QuoteCharacter.unwrapAndTrimText(each.key.getText()), QuoteCharacter.unwrapAndTrimText(each.value.getText()));
207         }
208         return result;
209     }
210     
211     @Override
212     public ASTNode visitUnregisterStorageUnit(final UnregisterStorageUnitContext ctx) {
213         boolean ignoreSingleTables = ctx.ignoreTables() instanceof IgnoreSingleAndBroadcastTablesContext || ctx.ignoreTables() instanceof IgnoreSingleTablesContext;
214         boolean ignoreBroadcastTables = ctx.ignoreTables() instanceof IgnoreSingleAndBroadcastTablesContext || ctx.ignoreTables() instanceof IgnoreBroadcastTablesContext;
215         return new UnregisterStorageUnitStatement(null != ctx.ifExists(),
216                 ctx.storageUnitName().stream().map(ParseTree::getText).map(each -> new IdentifierValue(each).getValue()).collect(Collectors.toList()),
217                 ignoreSingleTables, ignoreBroadcastTables);
218     }
219     
220     @Override
221     public ASTNode visitShowStorageUnits(final ShowStorageUnitsContext ctx) {
222         FromDatabaseSegment fromDatabase = null == ctx.databaseName() ? null : new FromDatabaseSegment(ctx.FROM().getSymbol().getStartIndex(), (DatabaseSegment) visit(ctx.databaseName()));
223         String likePattern = null == ctx.showLike() ? null : getIdentifierValue(ctx.showLike().likePattern());
224         return new ShowStorageUnitsStatement(fromDatabase, likePattern);
225     }
226     
227     @Override
228     public ASTNode visitDatabaseName(final DatabaseNameContext ctx) {
229         return new DatabaseSegment(ctx.getStart().getStartIndex(), ctx.getStop().getStopIndex(), new IdentifierValue(ctx.getText()));
230     }
231     
232     @Override
233     public ASTNode visitSetDistVariable(final SetDistVariableContext ctx) {
234         return new SetDistVariableStatement(getIdentifierValue(ctx.variableName()), getIdentifierValue(ctx.variableValue()));
235     }
236     
237     @Override
238     public ASTNode visitShowLogicalTables(final ShowLogicalTablesContext ctx) {
239         FromDatabaseSegment fromDatabase = null == ctx.databaseName() ? null : new FromDatabaseSegment(ctx.FROM().getSymbol().getStartIndex(), (DatabaseSegment) visit(ctx.databaseName()));
240         return new ShowLogicalTablesStatement(null != ctx.FULL(), fromDatabase, null == ctx.showLike() ? null : getIdentifierValue(ctx.showLike().likePattern()));
241     }
242     
243     @Override
244     public ASTNode visitShowDistVariable(final ShowDistVariableContext ctx) {
245         return new ShowDistVariableStatement(Objects.requireNonNull(getIdentifierValue(ctx.variableName())).toUpperCase());
246     }
247     
248     @Override
249     public ASTNode visitShowDistVariables(final ShowDistVariablesContext ctx) {
250         return new ShowDistVariablesStatement(null == ctx.showLike() ? null : getIdentifierValue(ctx.showLike().likePattern()));
251     }
252     
253     @Override
254     public ASTNode visitRefreshDatabaseMetadata(final RefreshDatabaseMetadataContext ctx) {
255         return new RefreshDatabaseMetaDataStatement(null == ctx.databaseName() ? null : getIdentifierValue(ctx.databaseName()), null != ctx.FORCE());
256     }
257     
258     @Override
259     public ASTNode visitRefreshTableMetadata(final RefreshTableMetadataContext ctx) {
260         if (null == ctx.refreshScope()) {
261             return new RefreshTableMetaDataStatement();
262         }
263         String storageUnitName = null;
264         String schemaName = null;
265         String tableName = getIdentifierValue(ctx.refreshScope().tableName());
266         if (null != ctx.refreshScope().fromSegment()) {
267             FromSegmentContext fromSegment = ctx.refreshScope().fromSegment();
268             storageUnitName = getIdentifierValue(fromSegment.storageUnitName());
269             schemaName = null == fromSegment.schemaName() ? null : getIdentifierValue(fromSegment.schemaName());
270         }
271         return new RefreshTableMetaDataStatement(tableName, storageUnitName, schemaName);
272     }
273     
274     @Override
275     public ASTNode visitExportDatabaseConfiguration(final ExportDatabaseConfigurationContext ctx) {
276         return new ExportDatabaseConfigurationStatement(getIdentifierValue(ctx.filePath()),
277                 null == ctx.databaseName() ? null : new FromDatabaseSegment(ctx.FROM().getSymbol().getStartIndex(), (DatabaseSegment) visit(ctx.databaseName())));
278     }
279     
280     @Override
281     public ASTNode visitExportMetaData(final ExportMetaDataContext ctx) {
282         return new ExportMetaDataStatement(null == ctx.filePath() ? null : getIdentifierValue(ctx.filePath()));
283     }
284     
285     @Override
286     public ASTNode visitExportStorageNodes(final ExportStorageNodesContext ctx) {
287         return new ExportStorageNodesStatement(null == ctx.databaseName() ? null : getIdentifierValue(ctx.databaseName()), null == ctx.filePath() ? null : getIdentifierValue(ctx.filePath()));
288     }
289     
290     @Override
291     public ASTNode visitConvertYamlConfiguration(final ConvertYamlConfigurationContext ctx) {
292         return new ConvertYamlConfigurationStatement(getIdentifierValue(ctx.filePath()));
293     }
294     
295     @Override
296     public ASTNode visitShowRulesUsedStorageUnit(final ShowRulesUsedStorageUnitContext ctx) {
297         return new ShowRulesUsedStorageUnitStatement(getIdentifierValue(ctx.storageUnitName()),
298                 null == ctx.databaseName() ? null : new FromDatabaseSegment(ctx.FROM().getSymbol().getStartIndex(), (DatabaseSegment) visit(ctx.databaseName())));
299     }
300     
301     @Override
302     public ASTNode visitImportDatabaseConfiguration(final ImportDatabaseConfigurationContext ctx) {
303         return new ImportDatabaseConfigurationStatement(getIdentifierValue(ctx.filePath()));
304     }
305     
306     @Override
307     public ASTNode visitImportMetaData(final ImportMetaDataContext ctx) {
308         return new ImportMetaDataStatement(null == ctx.metaDataValue() ? null : QuoteCharacter.unwrapText(ctx.metaDataValue().getText()), getIdentifierValue(ctx.filePath()));
309     }
310     
311     @Override
312     public ASTNode visitAlgorithmDefinition(final AlgorithmDefinitionContext ctx) {
313         return new AlgorithmSegment(getIdentifierValue(ctx.algorithmTypeName()), buildProperties(ctx.propertiesDefinition()));
314     }
315     
316     private Properties buildProperties(final PropertiesDefinitionContext ctx) {
317         Properties result = new Properties();
318         if (null == ctx) {
319             return result;
320         }
321         for (PropertyContext each : ctx.properties().property()) {
322             result.setProperty(QuoteCharacter.unwrapAndTrimText(each.key.getText()), QuoteCharacter.unwrapAndTrimText(each.value.getText()));
323         }
324         return result;
325     }
326     
327     @Override
328     public ASTNode visitLockCluster(final LockClusterContext ctx) {
329         return new LockClusterStatement((AlgorithmSegment) visitAlgorithmDefinition(ctx.lockStrategy().algorithmDefinition()), Long.parseLong(getIdentifierValue(ctx.INT_())));
330     }
331     
332     @Override
333     public ASTNode visitUnlockCluster(final UnlockClusterContext ctx) {
334         return new UnlockClusterStatement(Long.parseLong(getIdentifierValue(ctx.INT_())));
335     }
336     
337     private String getIdentifierValue(final ParseTree context) {
338         return null == context ? null : new IdentifierValue(context.getText()).getValue();
339     }
340     
341     @Override
342     public ASTNode visitShowPluginImplementations(final ShowPluginImplementationsContext ctx) {
343         return new ShowPluginsStatement("COMMON", getIdentifierValue(ctx.pluginClass()));
344     }
345     
346     @Override
347     public ASTNode visitShowKeyGenerateAlgorithmPlugins(final ShowKeyGenerateAlgorithmPluginsContext ctx) {
348         return new ShowPluginsStatement("KEY_GENERATE_ALGORITHM");
349     }
350     
351     @Override
352     public ASTNode visitShowLoadBalanceAlgorithmPlugins(final ShowLoadBalanceAlgorithmPluginsContext ctx) {
353         return new ShowPluginsStatement("LOAD_BALANCE_ALGORITHM");
354     }
355 }