Error detection inside Prox done. Returning a precise error message through JSON: done.
Change-Id: I2a1d079a03f6aece3283eb9805600e9dde9a3701
diff --git a/src/main/antlr/cosmas/c2ps_opPROX.g b/src/main/antlr/cosmas/c2ps_opPROX.g
index 4e80d82..9b6c5cb 100644
--- a/src/main/antlr/cosmas/c2ps_opPROX.g
+++ b/src/main/antlr/cosmas/c2ps_opPROX.g
@@ -96,9 +96,9 @@
proxDist
@init{ int countM=0; int countD=0; int countV=0;}
:
- (m=proxMeasure {countM++;}|d=proxDirection {countD++;}|v=proxDistValue {countV++;} )+
+ ((m=proxMeasure {countM++;})|(d=proxDirection {countD++;})|(v=proxDistValue {countV++;}) )+
- -> {c2ps_opPROX.encodeDIST(DIST, DIR, $d.tree, $m.tree, $v.tree, $proxDist.text, $proxDist.index, countD, countM, countV)};
+ -> {c2ps_opPROX.encodeDIST(DIST, DIR, $d.tree, $m.tree, $v.tree, $proxDist.text, countD, countM, countV)};
// new rule accepts only '+' and '-'; default tree for direction is
diff --git a/src/main/java/de/ids_mannheim/korap/query/parse/cosmas/c2ps_opPROX.java b/src/main/java/de/ids_mannheim/korap/query/parse/cosmas/c2ps_opPROX.java
index efad8a3..2f81b5c 100644
--- a/src/main/java/de/ids_mannheim/korap/query/parse/cosmas/c2ps_opPROX.java
+++ b/src/main/java/de/ids_mannheim/korap/query/parse/cosmas/c2ps_opPROX.java
@@ -13,93 +13,107 @@
public class c2ps_opPROX
{
-
- /* duplicateOptions:
- * detect if any prox option appears twice or more.
- * Return true of false.
- * 19.12.23/FB
- */
+ final static int typeERROR = 1; // type of an Error CommonToken.
+ final static int ERR_MEAS_NULL = 300;
+ final static int ERR_MEAS_TOOGREAT = 301;
+ final static int ERR_VAL_NULL = 302;
+ final static int ERR_VAL_TOOGREAT = 303;
+ final static int ERR_DIR_TOOGREAT = 304;
- private static boolean duplicateOptions(String text)
+ private static CommonTree buildErrorTree_Prox(String text, int errCode, int typeDIST)
{
-
- return false;
- }
+ CommonTree
+ errorTree = new CommonTree(new CommonToken(typeDIST, "DIST"));
+ CommonTree
+ errorNode = new CommonTree(new CommonToken(typeERROR, "ERROR"));
+ CommonTree
+ errorPos = new CommonTree(new CommonToken(typeERROR, Integer.toString(errCode)));
+ CommonTree
+ errorArg = new CommonTree(new CommonToken(1, text));
+ CommonTree
+ errorMes;
+ String
+ mess;
+ switch( errCode )
+ {
+ case ERR_MEAS_NULL:
+ mess = String.format("Abstandsoperator an der Stelle '%s' es fehlt eine der folgenden Angaben: w,s,p!", text);
+ errorMes = new CommonTree(new CommonToken(typeERROR, mess));
+ break;
+ case ERR_MEAS_TOOGREAT:
+ mess = String.format("Abstandsoperator an der Stelle '%s': Bitte nur 1 der folgenden Angaben einsetzen: w,s,p! " +
+ "Falls Mehrfachangabe erwünscht, dann durch Kommata trennen (z.B.: /+w2,s0).", text);
+ errorMes = new CommonTree(new CommonToken(typeERROR, mess));
+ break;
+ case ERR_VAL_NULL:
+ mess = String.format("Abstandsoperator an der Stelle '%s': Bitte einen numerischen Wert einsetzen (z.B. /+w5)! ", text);
+ errorMes = new CommonTree(new CommonToken(typeERROR, mess));
+ break;
+ case ERR_VAL_TOOGREAT:
+ mess = String.format("Abstandsoperator an der Stelle '%s': Bitte nur 1 numerischen Wert einsetzen (z.B. /+w5)! ", text);
+ errorMes = new CommonTree(new CommonToken(typeERROR, mess));
+ break;
+ case ERR_DIR_TOOGREAT:
+ mess = String.format("Abstandsoperator an der Stelle '%s': Bitte nur 1 Angabe '+' oder '-' oder keine! ", text);
+ errorMes = new CommonTree(new CommonToken(typeERROR, mess));
+ break;
+ default:
+ mess = String.format("Abstandsoperator an der Stelle '%s': unbekannter Fehler. Korrekte Syntax z.B.: /+w2 oder /w10,s0.", text);
+
+ errorMes = new CommonTree(new CommonToken(typeERROR, mess));
+ }
+
+ errorTree.addChild(errorNode);
+ errorNode.addChild(errorPos);
+ errorNode.addChild(errorArg);
+ errorNode.addChild(errorMes);
+
+ return errorTree;
+ }
+
/* encodeDIST():
* - returns a CommonTree built from the Direction/Measure/Distance value.
* - accepts options in any order.
* - creates CommonTree in that order: Direction .. Distance value .. Measure.
* - sets default direction to BOTH if not set yet.
+ * - unfortunatly, in ANTLR3 it seems that there is no way inside the Parser Grammar to get
+ * the absolute token position from the beginning of the query. Something like $ProxDist.pos or
+ * $start.pos is not available, so we have no info in this function about the position at which
+ * an error occurs.
+ * - For multiple prox options, e.g. /w2,s2,p0, this function if called 3 times.
+ * Arguments:
+ * countD : how many occurences of distance: + or - or nothing. If 0 insert the default BOTH.
+ * countM : how many occurences of measure: w,s,p,t: should be 1.
+ * countV : how many occurences of distance value: should be 1.
* 28.11.23/FB
*/
- public static Object encodeDIST(int typeDIST, int typeDIR, Object ctDir, Object ctMeas, Object ctVal, String text, int start,
+ public static Object encodeDIST(int typeDIST, int typeDIR, Object ctDir, Object ctMeas, Object ctVal, String text,
int countD, int countM, int countV)
{
- boolean multiple = false;
CommonTree tree1 = (CommonTree)ctDir;
CommonTree tree2 = (CommonTree)ctMeas;
CommonTree tree3 = (CommonTree)ctVal;
- //String text = "for debugging only";
- int pos = -1;
- System.err.printf("Debug: encodeDIST: scanned input='%s' start=%d countM=%d countD=%d countV=%d.\n",
- text, start, countM, countD, countV);
-
- if( duplicateOptions(text) == true )
- {
- CommonTree errorTree, errorNode, errorPos, errorArg, errorMes;
-
- errorTree = new CommonTree(new CommonToken(typeDIST, "DIST"));
- errorNode = new CommonTree(new CommonToken(1, "ERROR"));
- errorPos = new CommonTree(new CommonToken(1, "15"));
- errorArg = new CommonTree(new CommonToken(1, text));
- errorMes = new CommonTree(new CommonToken(1, "Operator PROX/Abstand darf nur höchsten 1 Abstandswert, Abstandstyp und" +
- " Abstandsrichtung enthalten!"));
-
- errorTree.addChild(errorNode);
- errorNode.addChild(errorPos);
- errorNode.addChild(errorArg);
- errorNode.addChild(errorMes);
-
- System.err.printf("Debug: encodeDIST: parse error found, returning error tree: %s.\n",
- errorTree.toStringTree());
-
- return errorTree;
-
- /* throwing an Exception is only part of the solution,
- * but how to stop parsing and return the error code properly - 07.12.23/DB
- *
- String mess = String.format("line 0:%d %s expecting only 1 of 'wsp'!\n",
- 2345, text);
- //de.ids_mannheim.korap.query.serialize.Antlr3AbstractQueryProcessor.reportError(mess);
- //reportError(mess);
- C2RecognitionException re = new C2RecognitionException(text);
- re.c = '/';
- re.charPositionInLine = 15; //tokenPos;
- re.index = 1;
- re.line = 0;
-
- throw re;
- */
- }
-
- System.err.printf("Debug: encodeDIST: ctDir='%s': %d ctMeas='%s': %d ctVal='%s': %d.\n",
- tree1 != null ? tree1.toStringTree() : "null",
- tree1 != null ? tree1.getChildCount() : 0,
- tree2 != null ? tree2.toStringTree() : "null",
- tree2 != null ? tree2.getChildCount() : 0,
- tree3 != null ? tree3.toStringTree() : "null",
- tree3 != null ? tree3.getChildCount() : 0);
+ //System.err.printf("Debug: encodeDIST: scanned input='%s' countM=%d countD=%d countV=%d.\n",
+ // text, countM, countD, countV);
- // if direction is not specified, return default = BOTH:
- if( ctDir == null )
+ if( countM == 0 )
+ return buildErrorTree_Prox(text, ERR_MEAS_NULL, typeDIST);
+ if( countM > 1 )
+ return buildErrorTree_Prox(text, ERR_MEAS_TOOGREAT, typeDIST);
+ if( countV == 0 )
+ return buildErrorTree_Prox(text, ERR_VAL_NULL, typeDIST);
+ if( countV > 1 )
+ return buildErrorTree_Prox(text, ERR_VAL_TOOGREAT, typeDIST);
+
+ if( countD == 0 )
{
- CommonTree treeDIR = new CommonTree(new CommonToken(typeDIR, (String)"DIR"));
- //CommonToken tok = new CommonToken(typeDIR, "BOTH");
+ // if direction is not specified (ctDir == null or countD==0), return default = BOTH:
+ CommonTree treeDIR = new CommonTree(new CommonToken(typeDIR, (String)"DIR"));
CommonTree treeBOTH = new CommonTree(new CommonToken(typeDIR, "BOTH"));
treeDIR.addChild(treeBOTH);
@@ -107,7 +121,10 @@
treeDIR.toStringTree());
tree1 = treeDIR;
}
+ else if( countD > 1 )
+ return buildErrorTree_Prox(text, ERR_DIR_TOOGREAT, typeDIST);
+ // create DIST tree:
CommonTree
tree = new CommonTree(new CommonToken(typeDIST, "DIST"));
@@ -115,8 +132,7 @@
tree.addChild(tree3); // tree3 before tree2 expected by serialization.
tree.addChild(tree2);
- System.err.printf("Debug: encodeDIST: returning '%s'.\n",
- tree.toStringTree());
+ System.err.printf("Debug: encodeDIST: returning '%s'.\n", tree.toStringTree());
return tree;
} // encodeDIST
diff --git a/src/main/java/de/ids_mannheim/korap/query/serialize/Cosmas2QueryProcessor.java b/src/main/java/de/ids_mannheim/korap/query/serialize/Cosmas2QueryProcessor.java
index 8d42718..381c35e 100644
--- a/src/main/java/de/ids_mannheim/korap/query/serialize/Cosmas2QueryProcessor.java
+++ b/src/main/java/de/ids_mannheim/korap/query/serialize/Cosmas2QueryProcessor.java
@@ -20,6 +20,7 @@
import org.antlr.runtime.ANTLRStringStream;
import org.antlr.runtime.FailedPredicateException;
import org.antlr.runtime.RecognitionException;
+import org.antlr.runtime.Token;
import org.antlr.runtime.tree.Tree;
import org.antlr.v4.runtime.tree.ParseTree;
import org.slf4j.Logger;
@@ -1822,14 +1823,6 @@
org.antlr.runtime.CommonTokenStream tokens =
new org.antlr.runtime.CommonTokenStream(lex); // v3
- System.out.printf("parseCosmasQuery: tokens = %d\n", tokens.size());
- System.out.printf("parseCosmasQuery: tokens[] = ");
-
- for(int i=0; i<tokens.size(); i++)
- System.out.printf("%s ", tokens.get(i).toString());
-
- System.out.println();
-
parser = new c2psParser(tokens);
// Use custom error reporters