提交 64f1d744 编写于 作者: S Serge Rider 提交者: GitHub

Merge pull request #12411 from dbeaver/sql-multi-word-rules-feature#11829

#11829 DB2: Special rule for ROW BEGIN/END

Former-commit-id: a9387b0b
......@@ -122,7 +122,8 @@ public class DB2Constants {
"RESULT", "RESULT_SET_LOCATOR", "RETURN", "RETURNS", "ROUTINE", "ROW", "RRN", "RUN", "SAVEPOINT", "SCRATCHPAD", "SECOND",
"SECONDS", "SECQTY", "SECURITY", "SENSITIVE", "SIGNAL", "SIMPLE", "SOURCE", "SPECIFIC", "SQLID", "STANDARD", "START",
"STARTING", "STATIC", "STAY", "STOGROUP", "STORES", "STYLE", "SUBPAGES", "SYNONYM", "SYSTEM", "TABLESPACE",
"TRIGGER", "TYPE", "UNDO", "UNTIL", "VALIDPROC", "VARIABLE", "VARIANT", "VCAT", "VOLATILE", "VOLUMES", "WHILE", "WLM" };
"TRIGGER", "TYPE", "UNDO", "UNTIL", "VALIDPROC", "VARIABLE", "VARIANT", "VCAT", "VOLATILE", "VOLUMES", "WHILE", "WLM",
"IMPLICITLY", "HIDDEN" };
public static final DBDPseudoAttribute PSEUDO_ATTR_RID_BIT = new DBDPseudoAttribute(DBDPseudoAttributeType.ROWID,
"RID_BIT()", "RID_BIT($alias)", "RID_BIT", "Unique physical row identifier", false);
......
......@@ -22,6 +22,7 @@ import org.jkiss.code.Nullable;
import org.jkiss.dbeaver.DBException;
import org.jkiss.dbeaver.Log;
import org.jkiss.dbeaver.ext.db2.model.DB2Routine;
import org.jkiss.dbeaver.model.DBPDataSourceContainer;
import org.jkiss.dbeaver.model.DBPEvaluationContext;
import org.jkiss.dbeaver.model.data.DBDBinaryFormatter;
import org.jkiss.dbeaver.model.exec.jdbc.JDBCDatabaseMetaData;
......@@ -31,12 +32,18 @@ import org.jkiss.dbeaver.model.exec.jdbc.JDBCStatement;
import org.jkiss.dbeaver.model.impl.data.formatters.BinaryFormatterHexString;
import org.jkiss.dbeaver.model.impl.jdbc.JDBCDataSource;
import org.jkiss.dbeaver.model.impl.jdbc.JDBCSQLDialect;
import org.jkiss.dbeaver.model.sql.parser.rules.SQLMultiWordRule;
import org.jkiss.dbeaver.model.sql.parser.tokens.SQLTokenType;
import org.jkiss.dbeaver.model.struct.rdb.DBSProcedure;
import org.jkiss.dbeaver.model.struct.rdb.DBSProcedureType;
import org.jkiss.dbeaver.model.text.parser.TPRule;
import org.jkiss.dbeaver.model.text.parser.TPRuleProvider;
import org.jkiss.dbeaver.model.text.parser.TPTokenDefault;
import org.jkiss.utils.CommonUtils;
import java.sql.SQLException;
import java.util.Arrays;
import java.util.List;
import java.util.Set;
/**
......@@ -45,15 +52,12 @@ import java.util.Set;
* @author Denis Forveille
*
*/
public class DB2SQLDialect extends JDBCSQLDialect {
public class DB2SQLDialect extends JDBCSQLDialect implements TPRuleProvider {
private static final Log log = Log.getLog(DB2SQLDialect.class);
public static final String[] EXEC_KEYWORDS = new String[]{"CALL"};
private static final String[][] DB2_BEGIN_END_BLOCK = new String[][]{
};
private static final boolean LOAD_ROUTINES_FROM_SYSCAT = false;
public DB2SQLDialect() {
......@@ -146,13 +150,17 @@ public class DB2SQLDialect extends JDBCSQLDialect {
return BinaryFormatterHexString.INSTANCE;
}
@Override
public String[][] getBlockBoundStrings() {
return DB2_BEGIN_END_BLOCK;
}
@Override
public String getScriptDelimiterRedefiner() {
return "DELIMITER";
}
@Override
public void extendRules(@Nullable DBPDataSourceContainer dataSource, @NotNull List<TPRule> rules, @NotNull RulePosition position) {
if (position == RulePosition.KEYWORDS) {
final TPTokenDefault keywordToken = new TPTokenDefault(SQLTokenType.T_KEYWORD);
rules.add(new SQLMultiWordRule(new String[]{"ROW", "BEGIN"}, keywordToken));
rules.add(new SQLMultiWordRule(new String[]{"ROW", "END"}, keywordToken));
}
}
}
/*
* DBeaver - Universal Database Manager
* Copyright (C) 2010-2021 DBeaver Corp and others
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.jkiss.dbeaver.model.sql.parser.rules;
import org.eclipse.core.runtime.Assert;
import org.jkiss.dbeaver.model.text.parser.TPCharacterScanner;
import org.jkiss.dbeaver.model.text.parser.TPRule;
import org.jkiss.dbeaver.model.text.parser.TPToken;
import org.jkiss.dbeaver.model.text.parser.TPTokenAbstract;
/**
* Rule for matching tokens consisting of several words separated by one or more whitespaces.
*/
public class SQLMultiWordRule implements TPRule {
private final String[] parts;
private final TPToken token;
public SQLMultiWordRule(String[] parts, TPToken token) {
this.parts = parts;
this.token = token;
Assert.isLegal(parts.length > 1, "Multi-word rule should consist of two or more parts");
}
@Override
public TPToken evaluate(TPCharacterScanner scanner) {
int ch = scanner.read();
int read = 1;
outer:
for (int partIndex = 0; partIndex < parts.length; partIndex++) {
if (ch == TPCharacterScanner.EOF || !Character.isUnicodeIdentifierStart(ch)) {
break;
}
for (char partCh : parts[partIndex].toCharArray()) {
if (ch == TPCharacterScanner.EOF || !Character.isUnicodeIdentifierPart(ch) || Character.toUpperCase(partCh) != Character.toUpperCase(ch)) {
break outer;
}
ch = scanner.read();
read++;
}
if (partIndex == parts.length - 1 && !Character.isUnicodeIdentifierPart(ch)) {
// Accept rule if last part is preceded by non-identifier character
scanner.unread();
return token;
}
if (ch == TPCharacterScanner.EOF || !Character.isWhitespace(ch)) {
// Require at least one whitespace character between parts
break;
}
while (ch != TPCharacterScanner.EOF && Character.isWhitespace(ch)) {
ch = scanner.read();
read++;
}
}
while (read > 0) {
scanner.unread();
read--;
}
return TPTokenAbstract.UNDEFINED;
}
}
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册