/* create a new GdaRow from the last read row */ static GdaRow * new_row (GdaDataSelect *imodel, GdaConnection *cnc, GdaOraclePStmt *ps) { GdaRow *prow; GList *nodes; gint i; prow = gda_row_new (((GdaDataSelect*) imodel)->prep_stmt->ncols); for (i = 0, nodes = ps->ora_values; nodes; i++, nodes = nodes->next) { GdaOracleValue *ora_value = (GdaOracleValue *) nodes->data; GValue *value = gda_row_get_value (prow, i); _gda_oracle_set_value (value, ora_value, cnc); } return prow; }
static GdaRow * create_new_row (GdaDataAccessWrapper *model) { gint i; GdaRow *row; row = gda_row_new (model->priv->nb_cols); for (i = 0; i < model->priv->nb_cols; i++) { GdaHolder *holder; GValue *dest; dest = gda_row_get_value (row, i); if (model->priv->rows_mapping) holder = gda_set_get_nth_holder ((GdaSet *) model->priv->iter, model->priv->rows_mapping [i]); else holder = gda_set_get_nth_holder ((GdaSet *) model->priv->iter, i); if (holder) { const GValue *cvalue = gda_holder_get_value (holder); if (cvalue) { gda_value_reset_with_type (dest, G_VALUE_TYPE ((GValue *) cvalue)); g_value_copy (cvalue, dest); } else gda_value_set_null (dest); } else gda_row_invalidate_value (row, dest); } gint *ptr; ptr = g_new (gint, 1); *ptr = model->priv->iter_row; g_hash_table_insert (model->priv->rows, ptr, row); /*g_print ("%s(%d)\n", __FUNCTION__, model->priv->iter_row);*/ return row; }
static GdaRow * new_row_from_mysql_stmt (GdaMysqlRecordset *imodel, G_GNUC_UNUSED gint rownum, GError **error) { //g_print ("%s(): NCOLS=%d ROWNUM=%d\n", __func__, ((GdaDataSelect *) imodel)->prep_stmt->ncols, rownum); int res; MYSQL_BIND *mysql_bind_result; g_return_val_if_fail (imodel->priv->mysql_stmt != NULL, NULL); mysql_bind_result = ((GdaMysqlPStmt *) ((GdaDataSelect *) imodel)->prep_stmt)->mysql_bind_result; g_assert (mysql_bind_result); res = mysql_stmt_fetch (imodel->priv->mysql_stmt); if (res == MYSQL_NO_DATA) { /* should not happen */ g_set_error (error, GDA_DATA_MODEL_ERROR, GDA_DATA_MODEL_ACCESS_ERROR, "%s", "No more data, please report this bug to " "http://bugzilla.gnome.org/ for the \"libgda\" product and the MySQL provider."); } else if (res == MYSQL_DATA_TRUNCATED) { GString *string; string = g_string_new ("Truncated data, please report this bug to " "http://bugzilla.gnome.org/ for the \"libgda\" product and the MySQL provider."); gint col; for (col = 0; col < ((GdaDataSelect *) imodel)->prep_stmt->ncols; ++col) { my_bool truncated; mysql_bind_result[col].error = &truncated; mysql_stmt_fetch_column (imodel->priv->mysql_stmt, &(mysql_bind_result[col]), (unsigned int)col, 0); if (truncated) g_string_append_printf (string, "\n column %d is truncated\n", col); mysql_bind_result[col].error = NULL; } g_set_error (error, GDA_DATA_MODEL_ERROR, GDA_DATA_MODEL_ACCESS_ERROR, "%s", string->str); g_string_free (string, TRUE); return NULL; } else if (res) { _gda_mysql_make_error (imodel->priv->cnc, NULL, imodel->priv->mysql_stmt, error); return NULL; } /* g_print ("%s: SQL=%s\n", __func__, ((GdaDataSelect *) imodel)->prep_stmt->sql); */ GdaRow *row = gda_row_new (((GdaDataSelect *) imodel)->prep_stmt->ncols); gint col; for (col = 0; col < ((GdaDataSelect *) imodel)->prep_stmt->ncols; ++col) { gint i = col; GValue *value = gda_row_get_value (row, i); GType type = ((GdaDataSelect *) imodel)->prep_stmt->types[i]; /*g_print ("%s: #%d : TYPE=%d, GTYPE=%s\n", __func__, i, mysql_bind_result[i].buffer_type, g_type_name (type));*/ my_bool is_null = FALSE; unsigned long length; g_memmove (&is_null, mysql_bind_result[i].is_null, sizeof (my_bool)); if (is_null) { gda_value_set_null (value); continue; } else gda_value_reset_with_type (value, type); switch (mysql_bind_result[i].buffer_type) { case MYSQL_TYPE_SHORT: { short int bvalue = 0; g_memmove (&bvalue, mysql_bind_result[i].buffer, sizeof (bvalue)); g_value_set_int (value, bvalue); break; } case MYSQL_TYPE_TINY: { signed char bvalue = 0; g_memmove (&bvalue, mysql_bind_result[i].buffer, sizeof (bvalue)); g_value_set_int (value, bvalue); break; } case MYSQL_TYPE_INT24: case MYSQL_TYPE_LONG: case MYSQL_TYPE_YEAR: { int bvalue = 0; g_memmove (&bvalue, mysql_bind_result[i].buffer, sizeof (bvalue)); if (type == G_TYPE_INT) g_value_set_int (value, bvalue); else if (type == G_TYPE_LONG) g_value_set_long (value, (long) bvalue); else if (type == G_TYPE_BOOLEAN) g_value_set_boolean (value, bvalue ? TRUE : FALSE); else { gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Type %s not mapped for value %d"), g_type_name (type), bvalue); } break; } case MYSQL_TYPE_LONGLONG: { long long bvalue = 0; g_memmove (&bvalue, mysql_bind_result[i].buffer, sizeof (bvalue)); if (type == G_TYPE_BOOLEAN) g_value_set_boolean (value, bvalue ? TRUE : FALSE); else if (type == G_TYPE_INT) g_value_set_int (value, bvalue); else if (type == G_TYPE_LONG) g_value_set_long (value, bvalue); else { gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Type %s not mapped for value %lld"), g_type_name (type), bvalue); } break; } case MYSQL_TYPE_NULL: gda_value_set_null (value); break; case MYSQL_TYPE_TIME: case MYSQL_TYPE_DATE: case MYSQL_TYPE_DATETIME: case MYSQL_TYPE_TIMESTAMP: { MYSQL_TIME bvalue = { 0, 0, 0, 0, 0, 0, 0, 0, 0 }; g_memmove (&bvalue, mysql_bind_result[i].buffer, sizeof (bvalue)); if (type == GDA_TYPE_TIME) { GdaTime time = { .hour = bvalue.hour, .minute = bvalue.minute, .second = bvalue.second, .fraction = bvalue.second_part, .timezone = 0 /* GMT */ }; gda_value_set_time (value, &time); } else if (type == G_TYPE_DATE) { GDate *date = g_date_new_dmy ((bvalue.day != 0) ? bvalue.day : 1, (bvalue.month != 0) ? bvalue.month : 1, (bvalue.year != 0) ? bvalue.year : 1970); g_value_take_boxed (value, date); } else if (type == GDA_TYPE_TIMESTAMP) { GdaTimestamp timestamp = { .year = bvalue.year, .month = bvalue.month, .day = bvalue.day, .hour = bvalue.hour, .minute = bvalue.minute, .second = bvalue.second, .fraction = bvalue.second_part, .timezone = 0 /* GMT */ }; gda_value_set_timestamp (value, ×tamp); } else { gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Type %s not mapped for value %d/%d/%d %d:%d:%d.%lu"), g_type_name (type), bvalue.year, bvalue.month, bvalue.day, bvalue.hour, bvalue.minute, bvalue.second, bvalue.second_part); } break; } case MYSQL_TYPE_FLOAT: { float bvalue = 0.; g_memmove (&bvalue, mysql_bind_result[i].buffer, sizeof (bvalue)); if (type == G_TYPE_FLOAT) g_value_set_float (value, (float) bvalue); else { gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Type %s not mapped for value %f"), g_type_name (type), bvalue); } break; } case MYSQL_TYPE_DOUBLE: { double bvalue = 0.0; g_memmove (&bvalue, mysql_bind_result[i].buffer, sizeof (bvalue)); if (type == G_TYPE_DOUBLE) g_value_set_double (value, bvalue); else { gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Type %s not mapped for value %f"), g_type_name (type), bvalue); } break; } case MYSQL_TYPE_STRING: case MYSQL_TYPE_VAR_STRING: case MYSQL_TYPE_BLOB: case MYSQL_TYPE_TINY_BLOB: case MYSQL_TYPE_MEDIUM_BLOB: case MYSQL_TYPE_LONG_BLOB: case MYSQL_TYPE_NEWDECIMAL: case MYSQL_TYPE_DECIMAL: case MYSQL_TYPE_BIT: { char *bvalue = NULL; g_memmove (&length, mysql_bind_result[i].length, sizeof (unsigned long)); if (length > 0) { bvalue = g_malloc (length + 1); memcpy (bvalue, mysql_bind_result[i].buffer, length); bvalue [length] = 0; } if (type == G_TYPE_STRING) g_value_set_string (value, bvalue); else if (type == GDA_TYPE_BINARY) { GdaBinary binary = { .data = (guchar*) bvalue, .binary_length = length }; gda_value_set_binary (value, &binary); } else if (type == GDA_TYPE_BLOB) { /* we don't use GdaMysqlBlobOp because it looks like the MySQL * API does not support BLOBs accessed in a random way, * so we return the whole BLOB at once */ GdaBlob blob = { {(guchar*) bvalue, length}, NULL }; gda_value_set_blob (value, &blob); } else if (type == GDA_TYPE_NUMERIC) { if (length > 0) { GdaNumeric *numeric; numeric = gda_numeric_new (); gda_numeric_set_from_string (numeric, bvalue); gda_numeric_set_precision (numeric, 6); gda_numeric_set_width (numeric, length); gda_value_set_numeric (value, numeric); gda_numeric_free (numeric); } } else if (type == G_TYPE_DOUBLE) { if (length > 0) g_value_set_double (value, g_ascii_strtod (bvalue, NULL)); else { /* error: wrong column type */ gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Invalid column bind data type. %d\n"), mysql_bind_result[i].buffer_type); break; } } else if (type == G_TYPE_INT) { if (length > 0) g_value_set_int (value, atoi (bvalue)); else { /* error: wrong column type */ gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Invalid column bind data type. %d\n"), mysql_bind_result[i].buffer_type); break; } } else if (type == G_TYPE_BOOLEAN) { if (length > 0) g_value_set_boolean (value, atoi (bvalue)); else { /* error: wrong column type */ gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Invalid column bind data type. %d\n"), mysql_bind_result[i].buffer_type); break; } } else { gda_row_invalidate_value (row, value); g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Type %s not mapped for value %s"), g_type_name (type), bvalue); } g_free (bvalue); break; }
GdaDataModel * gda_mysql_recordset_new_direct (GdaConnection *cnc, GdaDataModelAccessFlags flags, GType *col_types) { GdaMysqlRecordset *model; MysqlConnectionData *cdata; gint i; GdaDataModelAccessFlags rflags; GSList *columns = NULL; g_return_val_if_fail (GDA_IS_CONNECTION (cnc), NULL); cdata = (MysqlConnectionData*) gda_connection_internal_get_provider_data_error (cnc, NULL); if (!cdata) return NULL; /* determine access mode: RANDOM or CURSOR FORWARD are the only supported */ if (flags & GDA_DATA_MODEL_ACCESS_RANDOM) rflags = GDA_DATA_MODEL_ACCESS_RANDOM; else rflags = GDA_DATA_MODEL_ACCESS_CURSOR_FORWARD; /* create data model */ model = g_object_new (GDA_TYPE_MYSQL_RECORDSET, "connection", cnc, "model-usage", rflags, NULL); model->priv->cnc = cnc; g_object_ref (G_OBJECT(cnc)); /* columns & types */ model->priv->ncols = mysql_field_count (cdata->mysql); model->priv->types = g_new0 (GType, model->priv->ncols); /* create columns */ for (i = 0; i < model->priv->ncols; i++) columns = g_slist_prepend (columns, gda_column_new ()); columns = g_slist_reverse (columns); if (col_types) { for (i = 0; ; i++) { if (col_types [i] > 0) { if (col_types [i] == G_TYPE_NONE) break; if (i >= model->priv->ncols) { g_warning (_("Column %d out of range (0-%d), ignoring its specified type"), i, model->priv->ncols - 1); break; } else model->priv->types [i] = col_types [i]; } } } /* fill bind result */ MYSQL_RES *mysql_res = mysql_store_result (cdata->mysql); MYSQL_FIELD *mysql_fields = mysql_fetch_fields (mysql_res); GSList *list; ((GdaDataSelect *) model)->advertized_nrows = mysql_affected_rows (cdata->mysql); for (i=0, list = columns; i < model->priv->ncols; i++, list = list->next) { GdaColumn *column = GDA_COLUMN (list->data); /* use C API to set columns' information using gda_column_set_*() */ MYSQL_FIELD *field = &mysql_fields[i]; GType gtype = model->priv->types [i]; if (gtype == GDA_TYPE_NULL) { gtype = _gda_mysql_type_to_gda (cdata, field->type, field->charsetnr); model->priv->types [i] = gtype; } gda_column_set_g_type (column, gtype); gda_column_set_name (column, field->name); gda_column_set_description (column, field->name); } gda_data_select_set_columns (GDA_DATA_SELECT (model), columns); /* load ALL data */ MYSQL_ROW mysql_row; gint rownum; GdaServerProvider *prov; prov = gda_connection_get_provider (cnc); for (mysql_row = mysql_fetch_row (mysql_res), rownum = 0; mysql_row; mysql_row = mysql_fetch_row (mysql_res), rownum++) { GdaRow *row = gda_row_new (model->priv->ncols); gint col; for (col = 0; col < model->priv->ncols; col++) { gint i = col; GValue *value = gda_row_get_value (row, i); GType type = model->priv->types[i]; char *data = mysql_row[i]; if (!data || (type == GDA_TYPE_NULL)) continue; gda_value_reset_with_type (value, type); if (type == G_TYPE_STRING) g_value_set_string (value, data); else { GdaDataHandler *dh; gboolean valueset = FALSE; dh = gda_server_provider_get_data_handler_g_type (prov, cnc, type); if (dh) { GValue *tmpvalue; tmpvalue = gda_data_handler_get_value_from_str (dh, data, type); if (tmpvalue) { *value = *tmpvalue; g_free (tmpvalue); valueset = TRUE; } } if (!valueset) gda_row_invalidate_value (row, value); } } gda_data_select_take_row ((GdaDataSelect*) model, row, rownum); } mysql_free_result (mysql_res); return GDA_DATA_MODEL (model); }
static void data_model_errors_init (DataModelErrors *model, G_GNUC_UNUSED DataModelErrorsClass *klass) { gsize i; g_return_if_fail (IS_DATA_MODEL_ERRORS (model)); model->priv = g_new0 (DataModelErrorsPrivate, 1); /* columns */ model->priv->columns = NULL; for (i = 0; i < NCOLS; i++) { GdaColumn *col; gchar *str; col = gda_column_new (); gda_column_set_g_type (col, G_TYPE_STRING); str = g_strdup_printf ("col%" G_GSIZE_FORMAT, i); gda_column_set_name (col, str); gda_column_set_description (col, str); g_object_set (G_OBJECT (col), "id", str, NULL); g_free (str); model->priv->columns = g_slist_append (model->priv->columns, col); } /* rows */ model->priv->rows = g_ptr_array_new (); /* array of GdaRow pointers */ for (i = 0; i < (sizeof (data) / sizeof (ARow)); i++) { ARow *arow = &(data[i]); GdaRow *row = gda_row_new (NCOLS); GValue *value; value = gda_row_get_value (row, 0); if (arow->col0) { if (*arow->col0 == '-') G_VALUE_TYPE (value) = G_TYPE_INVALID; else { gda_value_reset_with_type (value, G_TYPE_STRING); g_value_set_string (value, arow->col0); } } value = gda_row_get_value (row, 1); if (arow->col1) { if (*arow->col1 == '-') G_VALUE_TYPE (value) = G_TYPE_INVALID; else { gda_value_reset_with_type (value, G_TYPE_STRING); g_value_set_string (value, arow->col1); } } value = gda_row_get_value (row, 2); if (arow->col2) { if (*arow->col2 == '-') G_VALUE_TYPE (value) = G_TYPE_INVALID; else { gda_value_reset_with_type (value, G_TYPE_STRING); g_value_set_string (value, arow->col2); } } value = gda_row_get_value (row, 3); if (arow->col3) { if (*arow->col3 == '-') G_VALUE_TYPE (value) = G_TYPE_INVALID; else { gda_value_reset_with_type (value, G_TYPE_STRING); g_value_set_string (value, arow->col3); } } g_ptr_array_add (model->priv->rows, row); } }
static GdaRow * fetch_next_sqlite_row (GdaSqliteRecordset *model, gboolean do_store, GError **error) { int rc; SqliteConnectionData *cdata; GdaSqlitePStmt *ps; GdaRow *prow = NULL; GdaConnection *cnc; glong length; cnc = gda_data_select_get_connection ((GdaDataSelect*) model); cdata = (SqliteConnectionData*) gda_connection_internal_get_provider_data_error (cnc, error); if (!cdata) return NULL; ps = GDA_SQLITE_PSTMT (GDA_DATA_SELECT (model)->prep_stmt); virt_cnc_set_working_obj (gda_data_select_get_connection ((GdaDataSelect*) model), model); if (model->priv->empty_forced) rc = SQLITE_DONE; else rc = SQLITE3_CALL (sqlite3_step) (ps->sqlite_stmt); switch (rc) { case SQLITE_ROW: { gint col, real_col; prow = gda_row_new (_GDA_PSTMT (ps)->ncols); for (col = 0; col < _GDA_PSTMT (ps)->ncols; col++) { GValue *value; GType type = _GDA_PSTMT (ps)->types [col]; real_col = col + ps->nb_rowid_columns; if (type == GDA_TYPE_NULL) { type = fuzzy_get_gtype (cdata, ps, col); if (type == GDA_TYPE_BLOB) { /* extra check: make sure we have a rowid for this blob, or fallback to binary */ if (ps->rowid_hash) { gint oidcol = 0; const char *ctable; ctable = SQLITE3_CALL (sqlite3_column_name) (ps->sqlite_stmt, real_col); if (ctable) oidcol = GPOINTER_TO_INT (g_hash_table_lookup (ps->rowid_hash, ctable)); if (oidcol == 0) { ctable = SQLITE3_CALL (sqlite3_column_table_name) (ps->sqlite_stmt, real_col); if (ctable) oidcol = GPOINTER_TO_INT (g_hash_table_lookup (ps->rowid_hash, ctable)); } if (oidcol == 0) type = GDA_TYPE_BINARY; } else type = GDA_TYPE_BINARY; } if (type != GDA_TYPE_NULL) { GdaColumn *column; _GDA_PSTMT (ps)->types [col] = type; column = gda_data_model_describe_column (GDA_DATA_MODEL (model), col); gda_column_set_g_type (column, type); column = (GdaColumn *) g_slist_nth_data (_GDA_PSTMT (ps)->tmpl_columns, col); gda_column_set_g_type (column, type); } } /* fill GValue */ value = gda_row_get_value (prow, col); GError *may_error; may_error = (GError*) SQLITE3_CALL (sqlite3_column_blob) (ps->sqlite_stmt, real_col); if (may_error && g_hash_table_lookup (error_blobs_hash, may_error)) { /*g_print ("Row invalidated: [%s]\n", may_error->message);*/ gda_row_invalidate_value_e (prow, value, may_error); g_hash_table_remove (error_blobs_hash, may_error); } else if (SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col) == NULL) { /* we have a NULL value */ gda_value_set_null (value); } else { gda_value_reset_with_type (value, type); if (type == GDA_TYPE_NULL) ; else if (type == G_TYPE_INT) { gint64 i; i = SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col); if ((i > G_MAXINT) || (i < G_MININT)) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "%s", _("Integer value is too big")); gda_row_invalidate_value_e (prow, value, lerror); } else g_value_set_int (value, (gint) i); } else if (type == G_TYPE_UINT) { guint64 i; i = (gint64) SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col); if (i > G_MAXUINT) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "%s", _("Integer value is too big")); gda_row_invalidate_value_e (prow, value, lerror); } else g_value_set_uint (value, (gint) i); } else if (type == G_TYPE_INT64) g_value_set_int64 (value, SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col)); else if (type == G_TYPE_UINT64) g_value_set_uint64 (value, (guint64) SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col)); else if (type == G_TYPE_DOUBLE) g_value_set_double (value, SQLITE3_CALL (sqlite3_column_double) (ps->sqlite_stmt, real_col)); else if (type == G_TYPE_STRING) g_value_set_string (value, (gchar *) SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col)); else if (type == GDA_TYPE_BINARY) { GdaBinary *bin; bin = gda_binary_new (); length = SQLITE3_CALL (sqlite3_column_bytes) (ps->sqlite_stmt, real_col); if (length > 0) { gda_binary_set_data (bin, SQLITE3_CALL (sqlite3_column_blob) (ps->sqlite_stmt, /* Flawfinder: ignore */ real_col), length); } gda_value_take_binary (value, bin); } else if (type == GDA_TYPE_BLOB) { GdaBlobOp *bop = NULL; gint oidcol = 0; if (ps->rowid_hash) { const char *ctable; ctable = SQLITE3_CALL (sqlite3_column_name) (ps->sqlite_stmt, real_col); if (ctable) oidcol = GPOINTER_TO_INT (g_hash_table_lookup (ps->rowid_hash, ctable)); if (oidcol == 0) { ctable = SQLITE3_CALL (sqlite3_column_table_name) (ps->sqlite_stmt, real_col); if (ctable) oidcol = GPOINTER_TO_INT (g_hash_table_lookup (ps->rowid_hash, ctable)); } } if (oidcol != 0) { gint64 rowid; rowid = SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, oidcol - 1); /* remove 1 because it was added in the first place */ bop = _gda_sqlite_blob_op_new (cnc, SQLITE3_CALL (sqlite3_column_database_name) (ps->sqlite_stmt, real_col), SQLITE3_CALL (sqlite3_column_table_name) (ps->sqlite_stmt, real_col), SQLITE3_CALL (sqlite3_column_origin_name) (ps->sqlite_stmt, real_col), rowid); } if (!bop) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "%s", _("Unable to open BLOB")); gda_row_invalidate_value_e (prow, value, lerror); } else { GdaBlob *blob; blob = gda_blob_new (); gda_blob_set_op (blob, bop); g_object_unref (bop); gda_value_take_blob (value, blob); } } else if (type == G_TYPE_BOOLEAN) g_value_set_boolean (value, SQLITE3_CALL (sqlite3_column_int) (ps->sqlite_stmt, real_col) == 0 ? FALSE : TRUE); else if (type == G_TYPE_DATE) { GDate date; if (!gda_parse_iso8601_date (&date, (gchar *) SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col))) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Invalid date '%s' (date format should be YYYY-MM-DD)"), (gchar *) SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col)); gda_row_invalidate_value_e (prow, value, lerror); } else g_value_set_boxed (value, &date); } else if (type == GDA_TYPE_TIME) { GdaTime timegda; if (!gda_parse_iso8601_time (&timegda, (gchar *) SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col))) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Invalid time '%s' (time format should be HH:MM:SS[.ms])"), (gchar *) SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col)); gda_row_invalidate_value_e (prow, value, lerror); } else { if (timegda.timezone == GDA_TIMEZONE_INVALID) timegda.timezone = 0; /* set to GMT */ gda_value_set_time (value, &timegda); } } else if (type == GDA_TYPE_TIMESTAMP) { GdaTimestamp timestamp; if (!gda_parse_iso8601_timestamp (×tamp, (gchar *) SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col))) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, _("Invalid timestamp '%s' (format should be YYYY-MM-DD HH:MM:SS[.ms])"), (gchar *) SQLITE3_CALL (sqlite3_column_text) (ps->sqlite_stmt, real_col)); gda_row_invalidate_value_e (prow, value, lerror); } else { if (timestamp.timezone == GDA_TIMEZONE_INVALID) timestamp.timezone = 0; /* set to GMT */ gda_value_set_timestamp (value, ×tamp); } } else if (type == G_TYPE_CHAR) { gint64 i; i = (gint64) SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col); if ((i > G_MAXINT8) || (i < G_MININT8)) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "%s", _("Integer value is too big")); gda_row_invalidate_value_e (prow, value, lerror); } else g_value_set_schar (value, (gchar) i); } else if (type == G_TYPE_UCHAR) { gint64 i; i = (gint64) SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col); if ((i > G_MAXUINT8) || (i < 0)) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "%s", _("Integer value is too big")); gda_row_invalidate_value_e (prow, value, lerror); } else g_value_set_uchar (value, (guchar) i); } else if (type == GDA_TYPE_SHORT) { gint64 i; i = (gint64) SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col); if ((i > G_MAXSHORT) || (i < G_MINSHORT)) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "%s", _("Integer value is too big")); gda_row_invalidate_value_e (prow, value, lerror); } else gda_value_set_short (value, (guchar) i); } else if (type == GDA_TYPE_USHORT) { gint64 i; i = (gint64) SQLITE3_CALL (sqlite3_column_int64) (ps->sqlite_stmt, real_col); if ((i > G_MAXUSHORT) || (i < 0)) { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "%s", _("Integer value is too big")); gda_row_invalidate_value_e (prow, value, lerror); } else gda_value_set_ushort (value, (guchar) i); } else { GError *lerror = NULL; g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_DATA_ERROR, "Unhandled type '%s' in SQLite recordset", gda_g_type_to_string (_GDA_PSTMT (ps)->types [col])); gda_row_invalidate_value_e (prow, value, lerror); } } } if (do_store) { /* insert row */ gda_data_select_take_row (GDA_DATA_SELECT (model), prow, model->priv->next_row_num); } model->priv->next_row_num ++; break; } case SQLITE_BUSY: /* nothing to do */ break; case SQLITE_DONE: GDA_DATA_SELECT (model)->advertized_nrows = model->priv->next_row_num; SQLITE3_CALL (sqlite3_reset) (ps->sqlite_stmt); break; case SQLITE_READONLY: case SQLITE_MISUSE: g_set_error (error, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_INTERNAL_ERROR, "%s", _("SQLite provider fatal internal error")); break; case SQLITE_ERROR: default: { GError *lerror = NULL; SQLITE3_CALL (sqlite3_reset) (ps->sqlite_stmt); if (rc == SQLITE_IOERR_TRUNCATE) g_set_error (&lerror, GDA_DATA_MODEL_ERROR, GDA_DATA_MODEL_TRUNCATED_ERROR, "%s", _("Truncated data")); else g_set_error (&lerror, GDA_SERVER_PROVIDER_ERROR, GDA_SERVER_PROVIDER_INTERNAL_ERROR, "%s", SQLITE3_CALL (sqlite3_errmsg) (cdata->connection)); gda_data_select_add_exception (GDA_DATA_SELECT (model), lerror); if (rc == SQLITE_ERROR) g_propagate_error (error, g_error_copy (lerror)); GDA_DATA_SELECT (model)->advertized_nrows = model->priv->next_row_num; break; } } virt_cnc_set_working_obj (gda_data_select_get_connection ((GdaDataSelect*) model), NULL); return prow; }