-/* $Id: cql.y,v 1.13 2006-12-14 09:05:18 adam Exp $
- Copyright (C) 2002-2006
- Index Data ApS
-
-This file is part of the YAZ toolkit.
-
-See the file LICENSE.
-
- bison parser for CQL grammar.
-*/
+/* This file is part of the YAZ toolkit.
+ * Copyright (C) 1995-2008 Index Data
+ * See the file LICENSE for details.
+ */
+/* bison parser for CQL grammar. */
%{
/**
* \file cql.c
%}
%pure_parser
-%token TERM AND OR NOT PROX GE LE NE
-%expect 9
+%token DOTTERM TERM AND OR NOT PROX GE LE NE EXACT SORTBY
%%
top: {
$$.rel = cql_node_mk_sc(((CQL_parser) parm)->nmem,
- "cql.serverChoice", "scr", 0);
+ "cql.serverChoice", "=", 0);
((CQL_parser) parm)->top = 0;
-} cqlQuery1 {
+} cqlQuery1 sortby {
cql_node_destroy($$.rel);
((CQL_parser) parm)->top = $2.cql;
}
;
+sortby: /* empty */
+| SORTBY sortSpec;
+
+sortSpec: sortSpec singleSpec
+| singleSpec;
+
+singleSpec: index modifiers ;
+
cqlQuery1: cqlQuery
| cqlQuery error {
cql_node_destroy($1.cql);
}
;
-cqlQuery:
+cqlQuery:
+ scopedClause
+ |
+ '>' searchTerm '=' searchTerm {
+ $$.rel = $0.rel;
+ } cqlQuery {
+ $$.cql = cql_apply_prefix(((CQL_parser) parm)->nmem,
+ $6.cql, $2.buf, $4.buf);
+ }
+| '>' searchTerm {
+ $$.rel = $0.rel;
+ } cqlQuery {
+ $$.cql = cql_apply_prefix(((CQL_parser) parm)->nmem,
+ $4.cql, 0, $2.buf);
+ }
+;
+
+scopedClause:
searchClause
|
- cqlQuery boolean modifiers {
+ scopedClause boolean modifiers {
$$.rel = $0.rel;
} searchClause {
struct cql_node *cn = cql_node_mk_boolean(((CQL_parser) parm)->nmem,
$$.cql = $3.cql;
}
|
- searchTerm {
- struct cql_node *st = cql_node_dup (((CQL_parser) parm)->nmem, $0.rel);
+searchTerm extraTerms {
+ struct cql_node *st = cql_node_dup(((CQL_parser) parm)->nmem, $0.rel);
+ st->u.st.extra_terms = $2.cql;
st->u.st.term = nmem_strdup(((CQL_parser)parm)->nmem, $1.buf);
$$.cql = st;
}
$$.cql = $5.cql;
cql_node_destroy($4.rel);
}
-| '>' searchTerm '=' searchTerm {
- $$.rel = $0.rel;
- } cqlQuery {
- $$.cql = cql_apply_prefix(((CQL_parser) parm)->nmem,
- $6.cql, $2.buf, $4.buf);
- }
-| '>' searchTerm {
- $$.rel = $0.rel;
- } cqlQuery {
- $$.cql = cql_apply_prefix(((CQL_parser) parm)->nmem,
- $4.cql, 0, $2.buf);
- }
;
+extraTerms:
+extraTerms TERM {
+ struct cql_node *st = cql_node_mk_sc(((CQL_parser) parm)->nmem,
+ /* index */ 0, /* rel */ 0, $2.buf);
+ st->u.st.extra_terms = $1.cql;
+ $$.cql = st;
+}
+|
+{ $$.cql = 0; }
+;
+
+
/* unary NOT search TERM here .. */
boolean:
modifiers: modifiers '/' searchTerm
{
struct cql_node *mod = cql_node_mk_sc(((CQL_parser)parm)->nmem,
- $3.buf, "=", 0);
+ $3.buf, 0, 0);
mod->u.st.modifiers = $1.cql;
$$.cql = mod;
| GE
| LE
| NE
+| EXACT
;
relation:
| GE
| LE
| NE
-| TERM
+| EXACT
+| DOTTERM
;
index:
searchTerm:
TERM
+| DOTTERM
| AND
| OR
| NOT
| PROX
+| SORTBY
;
%%
{
int c1;
putb(lval, cp, c);
- if (c == '>')
+ if (c == '=')
+ {
+ c1 = cp->getbyte(cp->client_data);
+ if (c1 == '=')
+ {
+ putb(lval, cp, c1);
+ return EXACT;
+ }
+ else
+ cp->ungetbyte(c1, cp->client_data);
+ }
+ else if (c == '>')
{
c1 = cp->getbyte(cp->client_data);
if (c1 == '=')
while ((c = cp->getbyte(cp->client_data)) != 0 && c != '"')
{
if (c == '\\')
+ {
+ putb(lval, cp, c);
c = cp->getbyte(cp->client_data);
- putb(lval, cp, c);
+ if (!c)
+ break;
+ }
+ putb(lval, cp, c);
}
putb(lval, cp, 0);
+ return TERM;
}
else
{
- while (c != 0 && !strchr(" \n()=<>/", c))
- {
- if (c == '\\')
- c = cp->getbyte(cp->client_data);
- putb(lval, cp, c);
+ int relation_like = 0;
+ while (c != 0 && !strchr(" \n()=<>/", c))
+ {
+ if (c == '.')
+ relation_like = 1;
+ if (c == '\\')
+ {
+ putb(lval, cp, c);
+ c = cp->getbyte(cp->client_data);
+ if (!c)
+ break;
+ }
+ putb(lval, cp, c);
c = cp->getbyte(cp->client_data);
- }
+ }
+ putb(lval, cp, 0);
#if YYDEBUG
- printf ("got %s\n", lval->buf);
+ printf ("got %s\n", lval->buf);
#endif
- if (c != 0)
- cp->ungetbyte(c, cp->client_data);
- if (!cql_strcmp(lval->buf, "and"))
+ if (c != 0)
+ cp->ungetbyte(c, cp->client_data);
+ if (!cql_strcmp(lval->buf, "and"))
{
lval->buf = "and";
- return AND;
+ return AND;
}
- if (!cql_strcmp(lval->buf, "or"))
+ if (!cql_strcmp(lval->buf, "or"))
{
lval->buf = "or";
- return OR;
+ return OR;
}
- if (!cql_strcmp(lval->buf, "not"))
+ if (!cql_strcmp(lval->buf, "not"))
{
lval->buf = "not";
- return NOT;
+ return NOT;
}
- if (!cql_strcmp(lval->buf, "prox"))
+ if (!cql_strcmp(lval->buf, "prox"))
{
lval->buf = "prox";
- return PROX;
+ return PROX;
+ }
+ if (!cql_strcmp(lval->buf, "sortby"))
+ {
+ lval->buf = "sortby";
+ return SORTBY;
}
+ if (!cql_strcmp(lval->buf, "all"))
+ relation_like = 1;
+ if (!cql_strcmp(lval->buf, "any"))
+ relation_like = 1;
+ if (relation_like)
+ return DOTTERM;
}
return TERM;
}