Changeset: 90eeac6503b8 for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=90eeac6503b8
Modified Files:
        sql/server/rel_exp.c
        sql/server/rel_select.c
        sql/test/miscellaneous/Tests/groupby_error.sql
        sql/test/miscellaneous/Tests/groupby_error.stable.err
        sql/test/miscellaneous/Tests/groupby_error.stable.out
Branch: linear-hashing
Log Message:

Handle IN subqueries with prepared statements and cleanup


diffs (141 lines):

diff --git a/sql/server/rel_exp.c b/sql/server/rel_exp.c
--- a/sql/server/rel_exp.c
+++ b/sql/server/rel_exp.c
@@ -782,7 +782,8 @@ exp_rel(mvc *sql, sql_rel *rel)
        assert(rel);
        if (is_project(rel->op)) {
                sql_exp *last = rel->exps->t->data;
-               e->tpe = *exp_subtype(last);
+               sql_subtype *t = exp_subtype(last);
+               e->tpe = t ? *t : (sql_subtype) {0};
        }
        return e;
 }
diff --git a/sql/server/rel_select.c b/sql/server/rel_select.c
--- a/sql/server/rel_select.c
+++ b/sql/server/rel_select.c
@@ -1251,7 +1251,9 @@ exp_fix_scale(mvc *sql, sql_subtype *ct,
 static int
 rel_set_type_param(mvc *sql, sql_subtype *type, sql_rel *rel, sql_exp 
*rel_exp, int upcast)
 {
-       if (!type || !rel_exp || (rel_exp->type != e_atom && rel_exp->type != 
e_column))
+       sql_rel *r = rel;
+
+       if (!type || !rel_exp || (rel_exp->type != e_atom && rel_exp->type != 
e_column && rel_exp->type == e_psm && rel_exp->flag != PSM_REL))
                return -1;
 
        /* use largest numeric types */
@@ -1264,19 +1266,19 @@ rel_set_type_param(mvc *sql, sql_subtype
        if (upcast && type->type->eclass == EC_FLT) 
                type = sql_bind_localtype("dbl");
 
-       if ((rel_exp->type == e_atom || rel_exp->type == e_column) && 
(rel_exp->l || rel_exp->r || rel_exp->f)) {
+       if (rel_exp->type == e_psm)
+               r = (sql_rel*) rel_exp->l;
+
+       if ((rel_exp->type == e_atom && (rel_exp->l || rel_exp->r || 
rel_exp->f)) || rel_exp->type == e_column || rel_exp->type == e_psm) {
                /* it's not a parameter set possible parameters below */
                const char *relname = exp_relname(rel_exp), *expname = 
exp_name(rel_exp);
-               if (rel_set_type_recurse(sql, type, rel, &relname, &expname) < 
0)
+               if (rel_set_type_recurse(sql, type, r, &relname, &expname) < 0)
                        return -1;
-       }
-       if (exp_subtype(rel_exp))
-               return 0;
-       if (set_type_param(sql, type, rel_exp->flag) == 0) {
-               rel_exp->tpe = *type;
-               return 0;
-       }
-       return -1;
+       } else if (set_type_param(sql, type, rel_exp->flag) != 0)
+               return -1;
+
+       rel_exp->tpe = *type;
+       return 0;
 }
 
 /* try to do an in-place conversion
@@ -5314,7 +5316,7 @@ rel_select_exp(sql_query *query, sql_rel
                list *te = NULL;
                sql_exp *ce = rel_column_exp(query, &inner, n->data.sym, 
sql_sel | group_totals);
 
-               if (ce && exp_subtype(ce)) {
+               if (ce && (exp_subtype(ce) || (ce->type == e_atom && !ce->l && 
!ce->f))) {
                        pexps = append(pexps, ce);
                        rel = inner;
                        continue;
diff --git a/sql/test/miscellaneous/Tests/groupby_error.sql 
b/sql/test/miscellaneous/Tests/groupby_error.sql
--- a/sql/test/miscellaneous/Tests/groupby_error.sql
+++ b/sql/test/miscellaneous/Tests/groupby_error.sql
@@ -15,9 +15,11 @@ SELECT ALL * FROM tab0 AS cor0 WHERE col
 
 prepare select col0 from tab0 where (?) in (select col0 from tab0);
 prepare select col0 from tab0 where (?,?) in (select col0,col1 from tab0);
-
+prepare select col0 from tab0 where (col1,col1) in (select col0,? from tab0);
+prepare select col0 from tab0 where (col1,col1) in (select ?,? from tab0);
+prepare select col0 from tab0 where (col0) in (?);
+prepare select col0 from tab0 where (col0) in (?,?);
 
-prepare select col0 from tab0 where (col0) in (?);
-
+prepare select col0 from tab0 where (?) in (?); --error
 
 ROLLBACK;
diff --git a/sql/test/miscellaneous/Tests/groupby_error.stable.err 
b/sql/test/miscellaneous/Tests/groupby_error.stable.err
--- a/sql/test/miscellaneous/Tests/groupby_error.stable.err
+++ b/sql/test/miscellaneous/Tests/groupby_error.stable.err
@@ -31,6 +31,10 @@ MAPI  = (monetdb) /var/tmp/mtest-13678/.
 QUERY = SELECT parent."sys_id" FROM "kagami_dump"."test_task" parent INNER 
JOIN "kagami_dump"."test_task" child ON child."parent" = parent."sys_id" GROUP 
BY parent."sys_id" HAVING count(child."sys_id") >= 1 ORDER BY parent."number"; 
--error, parent."number" requires an aggregate function
 ERROR = !SELECT: no such column 'parent.number'
 CODE  = 42S22
+MAPI  = (monetdb) /var/tmp/mtest-19682/.s.monetdb.38130
+QUERY = prepare select col0 from tab0 where (?) in (?); --error
+ERROR = !Cannot have a parameter (?) on both sides of an expression
+CODE  = 42000
 
 # 10:56:47 >  
 # 10:56:47 >  "Done."
diff --git a/sql/test/miscellaneous/Tests/groupby_error.stable.out 
b/sql/test/miscellaneous/Tests/groupby_error.stable.out
--- a/sql/test/miscellaneous/Tests/groupby_error.stable.out
+++ b/sql/test/miscellaneous/Tests/groupby_error.stable.out
@@ -103,6 +103,23 @@ stdout of test 'groupby_error` in direct
 [ "int",       32,     0,      "",     "tab0", "col0"  ]
 [ "int",       32,     0,      NULL,   NULL,   NULL    ]
 [ "int",       32,     0,      NULL,   NULL,   NULL    ]
+#prepare select col0 from tab0 where (col1,col1) in (select col0,? from tab0);
+#prepare select col0 from tab0 where (col1,col1) in (select col0,? from tab0);
+% .prepare,    .prepare,       .prepare,       .prepare,       .prepare,       
.prepare # table_name
+% type,        digits, scale,  schema, table,  column # name
+% varchar,     int,    int,    str,    str,    str # type
+% 3,   3,      1,      0,      4,      4 # length
+[ "int",       32,     0,      "",     "tab0", "col0"  ]
+[ "int",       32,     0,      NULL,   NULL,   NULL    ]
+#prepare select col0 from tab0 where (col1,col1) in (select ?,? from tab0);
+#prepare select col0 from tab0 where (col1,col1) in (select ?,? from tab0);
+% .prepare,    .prepare,       .prepare,       .prepare,       .prepare,       
.prepare # table_name
+% type,        digits, scale,  schema, table,  column # name
+% varchar,     int,    int,    str,    str,    str # type
+% 3,   3,      1,      0,      4,      4 # length
+[ "int",       32,     0,      "",     "tab0", "col0"  ]
+[ "int",       32,     0,      NULL,   NULL,   NULL    ]
+[ "int",       32,     0,      NULL,   NULL,   NULL    ]
 #prepare select col0 from tab0 where (col0) in (?);
 #prepare select col0 from tab0 where (col0) in (?);
 % .prepare,    .prepare,       .prepare,       .prepare,       .prepare,       
.prepare # table_name
@@ -111,6 +128,15 @@ stdout of test 'groupby_error` in direct
 % 3,   3,      1,      0,      4,      4 # length
 [ "int",       32,     0,      "",     "tab0", "col0"  ]
 [ "int",       32,     0,      NULL,   NULL,   NULL    ]
+#prepare select col0 from tab0 where (col0) in (?,?);
+#prepare select col0 from tab0 where (col0) in (?,?);
+% .prepare,    .prepare,       .prepare,       .prepare,       .prepare,       
.prepare # table_name
+% type,        digits, scale,  schema, table,  column # name
+% varchar,     int,    int,    str,    str,    str # type
+% 3,   3,      1,      0,      4,      4 # length
+[ "int",       32,     0,      "",     "tab0", "col0"  ]
+[ "int",       32,     0,      NULL,   NULL,   NULL    ]
+[ "int",       32,     0,      NULL,   NULL,   NULL    ]
 #ROLLBACK;
 
 # 10:56:47 >  
_______________________________________________
checkin-list mailing list
checkin-list@monetdb.org
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to