add support for LIMIT clause in SQL engine

This commit is contained in:
Brian Bruns 2016-08-30 08:43:34 -04:00
parent 2355aec912
commit 23bab7c2d6
5 changed files with 37 additions and 11 deletions

View File

@ -43,6 +43,8 @@ typedef struct {
unsigned char *kludge_ttable_pg;
long max_rows;
char error_msg[1024];
int limit;
long row_count;
} MdbSQL;
typedef struct {
@ -99,6 +101,7 @@ extern void mdb_sql_bind_all(MdbSQL *sql);
extern int mdb_sql_fetch_row(MdbSQL *sql, MdbTableDef *table);
extern int mdb_sql_add_temp_col(MdbSQL *sql, MdbTableDef *ttable, int col_num, char *name, int col_type, int col_size, int is_fixed);
extern void mdb_sql_bind_column(MdbSQL *sql, int colnum, void *varaddr, int *len_ptr);
extern int mdb_sql_add_limit(MdbSQL *sql, char *limit);
#ifdef __cplusplus
}

View File

@ -45,12 +45,14 @@ null { return NUL; }
(<=) { return LTEQ; }
(>=) { return GTEQ; }
like { return LIKE; }
limit { return LIMIT; }
[ \t\r] ;
\"[^"]*\"\" {
yyless(yyleng-1);
yymore();
}
\"[^"]*\" {
int ip, op, ilen;
ilen = strlen(yytext);

View File

@ -429,6 +429,17 @@ int mdb_sql_add_column(MdbSQL *sql, char *column_name)
sql->num_columns++;
return 0;
}
int mdb_sql_add_limit(MdbSQL *sql, char *limit)
{
sql->limit = atoi(limit);
return 0;
}
int mdb_sql_add_function1(MdbSQL *sql, char *func_name, char *arg1)
{
fprintf(stderr, "calling function %s with %s", func_name, arg1);
return 0;
}
int mdb_sql_add_table(MdbSQL *sql, char *table_name)
{
MdbSQLTable *t;
@ -509,6 +520,8 @@ void mdb_sql_reset(MdbSQL *sql)
sql->all_columns = 0;
sql->max_rows = -1;
sql->row_count = 0;
sql->limit = 0;
}
static void print_break(int sz, int first)
{
@ -762,7 +775,14 @@ mdb_sql_bind_all(MdbSQL *sql)
int
mdb_sql_fetch_row(MdbSQL *sql, MdbTableDef *table)
{
return mdb_fetch_row(table);
int rc = mdb_fetch_row(table);
if (rc) {
if (sql->row_count + 1 > sql->limit) {
return 0;
}
sql->row_count++;
}
return rc;
}
void

View File

@ -42,7 +42,7 @@ static MdbSQL *g_sql;
%token <name> IDENT NAME PATH STRING NUMBER
%token SELECT FROM WHERE CONNECT DISCONNECT TO LIST TABLES AND OR NOT
%token SELECT FROM WHERE CONNECT DISCONNECT TO LIST TABLES AND OR NOT LIMIT
%token DESCRIBE TABLE
%token LTEQ GTEQ LIKE IS NUL
@ -60,7 +60,7 @@ stmt:
;
query:
SELECT column_list FROM table where_clause {
SELECT column_list FROM table where_clause limit_clause {
mdb_sql_select(_mdb_sql(NULL));
}
| CONNECT TO database {
@ -82,6 +82,11 @@ where_clause:
| WHERE sarg_list
;
limit_clause:
/* empty */
| LIMIT NUMBER { mdb_sql_add_limit(_mdb_sql(NULL), $2); free($2); }
;
sarg_list:
sarg
| '(' sarg_list ')'

View File

@ -253,7 +253,6 @@ dump_results(FILE *out, MdbSQL *sql, char *delimiter)
{
unsigned int j;
MdbSQLColumn *sqlcol;
unsigned long row_count = 0;
if (headers) {
for (j=0;j<sql->num_columns-1;j++) {
@ -266,8 +265,7 @@ dump_results(FILE *out, MdbSQL *sql, char *delimiter)
fprintf(out,"\n");
fflush(out);
}
while(mdb_fetch_row(sql->cur_table)) {
row_count++;
while(mdb_sql_fetch_row(sql, sql->cur_table)) {
for (j=0;j<sql->num_columns-1;j++) {
sqlcol = g_ptr_array_index(sql->columns,j);
fprintf(out, "%s%s", (char*)(sql->bound_values[j]),
@ -279,7 +277,7 @@ dump_results(FILE *out, MdbSQL *sql, char *delimiter)
fflush(out);
}
if (footers) {
print_rows_retrieved(out, row_count);
print_rows_retrieved(out, sql->row_count);
}
}
@ -288,7 +286,6 @@ dump_results_pp(FILE *out, MdbSQL *sql)
{
unsigned int j;
MdbSQLColumn *sqlcol;
unsigned long row_count = 0;
/* print header */
if (headers) {
@ -316,8 +313,7 @@ dump_results_pp(FILE *out, MdbSQL *sql)
fflush(out);
/* print each row */
while(mdb_fetch_row(sql->cur_table)) {
row_count++;
while(mdb_sql_fetch_row(sql, sql->cur_table)) {
for (j=0;j<sql->num_columns;j++) {
sqlcol = g_ptr_array_index(sql->columns,j);
print_value(out, sql->bound_values[j],sqlcol->disp_size,!j);
@ -334,7 +330,7 @@ dump_results_pp(FILE *out, MdbSQL *sql)
fprintf(out,"\n");
fflush(out);
if (footers) {
print_rows_retrieved(out, row_count);
print_rows_retrieved(out, sql->row_count);
}
}