The R Project SVN R-packages

Rev

Rev 3397 | Rev 3684 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
3397 mrmanese 1
#include <stdio.h>
2
#include <string.h>
3
#include "sqlite_dataframe.h"
4
 
5
 
6
SEXP sdf_import_sqlite_table(SEXP _dbfilename, SEXP _tblname, SEXP _sdfiname) {
7
    sqlite3 *db;
8
    sqlite3_stmt *stmt;
9
    int res, nrows, ncols, buflen0, buflen1, buflen3, i;
10
    int tblname_len, colname_len, iname_len;
11
    char *dbfilename, *tblname, *iname, *type;
12
    const char *colname;
13
    SEXP ret = NULL;
14
 
15
    dbfilename = CHAR_ELT(_dbfilename, 0);
16
    tblname = CHAR_ELT(_tblname, 0);
17
    /* determine if we were passed a real sqlite db */
18
    db = _is_sqlitedb(dbfilename);
19
 
20
    if (!db) {
21
        Rprintf("Error: %s is not a SQLite database.\n", dbfilename);
22
        return R_NilValue;
23
    }
24
 
25
    /* check if the table exists in the db */
26
    sprintf(g_sql_buf[0], "select count(*) from [%s]", tblname);
27
    res = sqlite3_prepare(db, g_sql_buf[0], -1, &stmt, 0);
28
    if (_sqlite_error(res)) { 
29
        sqlite3_finalize(stmt); sqlite3_close(db);
30
        return R_NilValue; 
31
    }
32
    sqlite3_step(stmt);
33
    nrows = sqlite3_column_int(stmt, 0);
34
    sqlite3_finalize(stmt); sqlite3_close(db);
35
    if (nrows == 0) {
36
        Rprintf("Error: Table contains no rows. Aborting import operation.\n");
37
        return R_NilValue;
38
    }
39
 
40
    /* we have to attach it so we can transfer easily */
41
 
42
    /* unload sdf's if we run to the MAX_ATTACHED limit */
43
    _prepare_attach2();
44
 
45
    /* attach the table to be imported */
46
    sprintf(g_sql_buf[0], "attach '%s' as [@@import@@]", dbfilename);
47
    res = _sqlite_exec(g_sql_buf[0]);
48
    if (_sqlite_error(res)) return R_NilValue;
49
 
50
 
51
    /* create the sdf where the data will be imported to */
3419 mrmanese 52
    iname = _create_sdf_skeleton1(_sdfiname, NULL, FALSE);
3397 mrmanese 53
    if (iname == NULL) goto sdf_import_sqlite_table__out;
54
 
55
    iname_len = strlen(iname);  /* needed for buf resizing below */
56
    tblname_len = strlen(tblname);
57
 
58
    /* get column types and names */
59
    sprintf(g_sql_buf[0], "select * from [@@import@@].[%s]", tblname);
60
    res = sqlite3_prepare(g_workspace, g_sql_buf[0], -1, &stmt, 0);
61
    _sqlite_error(res);
62
    sqlite3_step(stmt);
63
    ncols = sqlite3_column_count(stmt);
64
 
65
    /* create the sql scripts to execute: the create table and the insert-select */
66
    buflen0 = sprintf(g_sql_buf[0], "create table [%s].sdf_data([row name] text", iname);
67
    buflen1 = sprintf(g_sql_buf[1], "select cumsum(1)");
68
    buflen3 = sprintf(g_sql_buf[3], "from [@@import@@].[%s] ", tblname);
69
    for (i = 0; i < ncols; i++) {
70
        type = _str_tolower(g_sql_buf[2], sqlite3_column_decltype(stmt, i));
71
        colname = sqlite3_column_name(stmt, i);
72
        colname_len = strlen(colname);
73
        if (strstr(type, "int")) {
74
            _expand_buf(0, buflen0 + strlen(colname) + 10);
75
            buflen0 += sprintf(g_sql_buf[0]+buflen0, ",[%s] int", colname);
76
 
77
            _expand_buf(1, buflen1 + colname_len + 10);
78
            buflen1 += sprintf(g_sql_buf[1]+buflen1, ",[%s]", colname);
79
        } else if (strstr(type, "char") || strcmp(type, "text")) {
80
            _expand_buf(0, buflen0 + strlen(colname) + 10);
81
            buflen0 += sprintf(g_sql_buf[0]+buflen0, ",[%s] int", colname);
82
 
83
            _expand_buf(1, buflen1 + colname_len + iname_len + 20);
84
            buflen1 += sprintf(g_sql_buf[1]+buflen1, ",[%s].[factor %s].level",
85
                   iname, colname);
86
 
87
            /* create factor table */
88
            _create_factor_table2(iname, "factor", colname);
89
 
90
            /* insert factor levels and labels */
91
            sprintf(g_sql_buf[2], "insert into [%s].[factor %s] (label, level)"
92
                   " select distinct [%s], cumsum(1) from [@@import@@].[%s]", 
93
                   iname, colname, colname, tblname);
94
            res = _sqlite_exec(g_sql_buf[2]);
95
            _sqlite_error(res);
96
 
97
            /* add join clause to from clause */
98
            _expand_buf(3, buflen3 + colname_len * 3 + iname_len * 2 + strlen(tblname) + 32);
99
            buflen3 += sprintf(g_sql_buf[3] + buflen3, " join [%s].[factor %s] "
100
                    "on [@@import@@].[%s].[%s] = [%s].[factor %s].label",
101
                    iname, colname, tblname, colname, iname, colname);
102
        } else if (strcmp(type, "blob") || !*type) {
103
            /* not supported */
104
            Rprintf("Warning: skipping column %s because it is a blob.\n", colname);
105
        } else { /* numeric / float / real / ... */
106
            _expand_buf(0, buflen0 + strlen(colname) + 10);
107
            buflen0 += sprintf(g_sql_buf[0]+buflen0, ",[%s] double", colname);
108
 
109
            _expand_buf(1, buflen1 + colname_len + 10);
110
            buflen1 += sprintf(g_sql_buf[1]+buflen1, ",[%s]", colname);
111
        }
112
    }
113
 
114
    sqlite3_finalize(stmt);
115
 
116
    /* execute create script */
117
    _expand_buf(0, buflen0 + 10);
118
    sprintf(g_sql_buf[0] + buflen0, ")");
119
    res = _sqlite_exec(g_sql_buf[0]);
120
    if (_sqlite_error(res)) {
121
        sdf_detach_sdf(mkString(iname));
122
        goto sdf_import_sqlite_table__out;
123
    }
124
 
125
    _expand_buf(0, buflen1 + buflen3 + iname_len + 32 );
126
    sprintf(g_sql_buf[0], "insert into [%s].sdf_data %s %s", iname, g_sql_buf[1], g_sql_buf[3]);
127
    res = _sqlite_exec(g_sql_buf[0]);
128
    if (_sqlite_error(res)) {
129
        sdf_detach_sdf(mkString(iname));
130
        goto sdf_import_sqlite_table__out;
131
    }
132
 
133
    /* create sexp sdf */
134
    ret = _create_sdf_sexp(iname);
135
 
136
sdf_import_sqlite_table__out:
137
    _sqlite_exec("detach [@@import@@]");
138
    return ret;
139
}