📄 dbelement.c
字号:
default:// g_print("%s(): value = %s\n", __FUNCTION__, misc_binary_to_str(value, size)); sqlite3_bind_blob(pStmt, index, value, size, SQLITE_TRANSIENT); break; } return;}static voidbind_value_by_fid_2 (sqlite3_stmt *pStmt, guint32 fid, gconstpointer value, gint type, gint size){ gchar * name = NULL; gint index = 0; /* * use fid to fill pattern "$%03d" to location the * colum binding in a SQLite statement binary codes. */ name = sqlite3_mprintf("$%03d", fid); index = sqlite3_bind_parameter_index(pStmt, name); sqlite3_free(name);// g_print("%s(): fid = %d, type = %d, size = %d\n", __FUNCTION__, fid, type, size); switch (type) { case FIELD_TYPE_STRING:// g_print("%s(): value = %s\n", __FUNCTION__, value); sqlite3_bind_text(pStmt, index, (gchar *)value, strlen((gchar *)value), SQLITE_TRANSIENT); break; /* * INTEGER field SHOULD NOT treated as * binary or it will lead a logical error * when database manipulations. */ case FIELD_TYPE_INTEGER: sqlite3_bind_int(pStmt, index, *(gint *)value); break; default:// g_print("%s(): value = %s\n", __FUNCTION__, misc_binary_to_str(value, size)); sqlite3_bind_blob(pStmt, index, value, size, SQLITE_TRANSIENT); break; } return;}static voidbind_value_by_index (sqlite3_stmt *pStmt, guint32 index, gconstpointer value, gint type, gint size){/* g_print("%s(): index = %d, value = 0x%08x, type = %d, size = %d\n", __FUNCTION__, index, (guint32)value, type, size);*/ /* * use index to location the colum binding * in a SQLite statement binary codes. */ switch (type) { case FIELD_TYPE_STRING: sqlite3_bind_text(pStmt, index, (gchar *)value, strlen((gchar *)value), SQLITE_TRANSIENT); break; case FIELD_TYPE_INTEGER:/* g_print("%s(): value = %d\n", __FUNCTION__, *(gint32 *)value);*/ sqlite3_bind_int(pStmt, index, *(gint *)value); break; default:// g_print("%s(): value = %s\n", __FUNCTION__, misc_binary_to_str(value, size)); sqlite3_bind_blob(pStmt, index, value, size, SQLITE_TRANSIENT); break; } return;}static gpointerdump_field_value (sqlite3_stmt *pStmt, gint index){ gpointer value = NULL; /* * use index to location the colum binding * in a SQLite query returned results. */ switch (sqlite3_column_type(pStmt, index)) { case SQLITE_INTEGER: value = g_new0(gint, 1); *(gint *)value = (gint)sqlite3_column_int(pStmt, index); break; case SQLITE_FLOAT: value = g_new0(gfloat, 1); *(gfloat *)value = (gfloat)sqlite3_column_double(pStmt, index); break; case SQLITE_TEXT: value = g_strdup(sqlite3_column_text(pStmt, index)); break; default: { gssize len = 0; len = sqlite3_column_bytes(pStmt, index);/* g_print("%s(): default. len = %d\n", __FUNCTION__, len);*/ value = g_new0(gchar, len); memcpy(value, sqlite3_column_blob(pStmt, index), len); break; } } return value;}/** * @brief Add a #Record object into #RecordDBElement database. * * @param element the #RecordDBElement object * @param record the #Record object to be added * * @return DB_ERROR_NONE if operation was successfully. * * @note if primary field is NOT set in #Record object, * this routine will dispatch a unique ID for it, * and set as the value of primary field. */RecordDBErrorrecord_db_element_add_record (RecordDBElement *element, Record *record){ Iterator * iter = NULL; GString * sql_str = NULL; sqlite3_stmt * pStmt = NULL; sqlite3_stmt * pStmtExts[DB_FIELDS_NTYPES]; const FieldDescriptor * prifdesc = NULL; gconstpointer id = NULL; FieldSize prisize = 0; gint i; gint ret; g_return_val_if_fail(element, DB_ERROR_ARG_NULL); g_return_val_if_fail(record, DB_ERROR_ARG_NULL); memset(pStmtExts, 0, sizeof(pStmtExts)); /* * insert data for main table */ sql_str = g_string_new(""); g_string_append_printf(sql_str, "INSERT INTO %s_main ", element->db_elm_name); iter = record_get_ftids(record); if (iter) { GString * columns = NULL; GString * values = NULL; gssize pos; columns = g_string_new(""); values = g_string_new(""); for (iterator_to_first(iter); !iterator_at_last(iter); iterator_next(iter)) { guint32 ftid = *(guint32 *)iterator_current(iter); gchar * str = NULL; /* g_print("%s(): fid = %d\n", __FUNCTION__, fid);*/ str = sqlite3_mprintf("ftid%d, ", ftid); g_string_append(columns, str); sqlite3_free(str); str = sqlite3_mprintf(":%03d, ", ftid); g_string_append(values, str); sqlite3_free(str); } g_string_append(columns, "extflag"); g_string_append_printf(values, "%d", record_is_extended(record)); g_string_append_printf(sql_str, "( %s ) VALUES ( %s )", columns->str, values->str); g_string_free(columns, TRUE); g_string_free(values, TRUE); }/* g_print("%s(): main SQL: %s\n", __FUNCTION__, sql_str->str);*/ record_db_inner_trans_begin(element->db, DB_TRANS_DEFERRED); do { ret = sqlite3_prepare(element->db->database, sql_str->str, -1, &pStmt, 0); if (ret != SQLITE_OK) { g_print("%s(): sqlite3_prepare() failed: %s.\n", __FUNCTION__, sqlite3_errmsg(element->db->database)); goto failure; } for (iterator_to_first(iter); !iterator_at_last(iter); iterator_next(iter)) { const FieldDescriptor * fdesc = NULL; guint32 ftid = *(guint32 *)iterator_current(iter); if (ftid == element->db_elm_id_ftid) { continue; } fdesc = field_template_get(element->db_elm_template, ftid); if (fdesc) { gconstpointer value = NULL; FieldSize size = 0; value = record_get_field_default(record, ftid, &size); if (value == NULL) { continue; }/* g_print("%s(): ftid = %3d, value = 0x%08x, size = %d\n", __FUNCTION__, fdesc->identifier, (guint32)value, size);*/ bind_value_by_fid(pStmt, fdesc->identifier, value, fdesc->type, size); } } ret = sqlite3_step(pStmt); if (ret == SQLITE_ROW) { goto failure; } if (ret != SQLITE_DONE) { g_print("%s(): sqlite3_step() WARNING: main, %d[%s].\n", __FUNCTION__, sqlite3_errcode(element->db->database), sqlite3_errmsg(element->db->database)); if (ret == SQLITE_BUSY) { sqlite3_finalize(pStmt); goto failure; } } ret = sqlite3_finalize(pStmt); } while (ret == SQLITE_SCHEMA); iterator_free(iter, TRUE); if (TRUE) { prifdesc = field_template_get(element->db_elm_template, element->db_elm_id_ftid); id = record_get_field_default(record, element->db_elm_id_ftid, &prisize); /* * if "ID" field is NOT set, * query one by using _ROWID_ in sqlite3 * database. */ if (id == NULL) { guint32 lrid = sqlite3_last_insert_rowid(element->db->database); if (prifdesc->type == FIELD_TYPE_STRING || prifdesc->type == FIELD_TYPE_FLOAT || prifdesc->type == FIELD_TYPE_BINARY) { g_print("%s(): NULL primary field", __FUNCTION__); goto failure; }/* g_print("%s(): last row id = %d\n", __FUNCTION__, lrid);*/ record_set_field_default(record, element->db_elm_id_ftid, &lrid, sizeof(lrid)); id = record_get_field_default(record, element->db_elm_id_ftid, &prisize); } } /* * insert data into fidsmap table */ iter = record_get_ftids(record); if (iter && iterator_size(iter)) { g_string_assign(sql_str, ""); g_string_append_printf(sql_str, FIDSMAP_TABLE_INSERT_TEMPLATE, element->db_elm_name, element->db_elm_id_ftid); do { ret = sqlite3_prepare(element->db->database, sql_str->str, -1, &pStmt, 0); if (ret != SQLITE_OK) { g_print("%s(): sqlite3_prepare() failed: %s.\n", __FUNCTION__, sqlite3_errmsg(element->db->database)); goto failure; } for (iterator_to_first(iter); !iterator_at_last(iter); iterator_next(iter)) { const FieldDescriptor * fdesc = NULL; guint32 ftid = *(guint32 *)iterator_current(iter); guint32 fid = FIELD_ID_INVALID; if (ftid == element->db_elm_id_ftid || record_is_default_changed(record, ftid) == FALSE) { continue; } fid = record_get_default_fid(record, ftid); bind_value_by_index(pStmt, 1, id, prifdesc->type, prisize); sqlite3_bind_int(pStmt, 2, ftid); sqlite3_bind_int(pStmt, 3, fid); ret = sqlite3_step(pStmt); if (ret == SQLITE_ROW) { goto failure; } if (ret != SQLITE_DONE) { g_print("%s(): sqlite3_step() WARNING: main, %d[%s].\n", __FUNCTION__, sqlite3_errcode(element->db->database), sqlite3_errmsg(element->db->database)); if (ret == SQLITE_BUSY) { sqlite3_finalize(pStmt); goto failure; } } sqlite3_reset(pStmt); } ret = sqlite3_finalize(pStmt); } while (ret == SQLITE_SCHEMA); } iterator_free(iter, TRUE); /* * insert data into extend table */ iter = record_get_fids(record, FIELD_TEMPLATE_ID_INVALID, FID_ALL); if (iter && iterator_size(iter)) { do { /* * prepare for each type of extend field. */ for (i = 0; i < DB_FIELDS_NTYPES; i++) { if (element->db_elm_field_types & (1 << i)) { g_string_assign(sql_str, ""); g_string_append_printf(sql_str, EXTEND_TABLE_INSERT_TEMPLATE, element->db_elm_name, ftstrs[i], element->db_elm_id_ftid);/* g_print("%s(): ext SQL: %s\n", __FUNCTION__, sql_str->str);*/ ret = sqlite3_prepare(element->db->database, sql_str->str, -1, &pStmtExts[i], 0); if (ret != SQLITE_OK) { g_print("%s(): sqlite3_prepare() WARNING: ext, %d[%s].\n", __FUNCTION__, sqlite3_errcode(element->db->database), sqlite3_errmsg(element->db->database)); goto failure; } } else { pStmtExts[i] = NULL; } } for (iterator_to_first(iter); !iterator_at_last(iter); iterator_next(iter)) { const FieldDescriptor * fdesc = NULL; guint32 fid = *(guint32 *)iterator_current(iter); guint32 ftid = FID_GET_FTID(fid); sqlite3_stmt * pStmtExt = NULL; if (record_is_default_field(record, fid) == TRUE && record_get_label(record, fid) == NULL && record_get_desc(record, fid) == NULL) { continue; } fdesc = field_template_get(element->db_elm_template, ftid); if (fdesc) { gconstpointer value = NULL; const gchar * label = NULL; const gchar * desc = NULL; FieldSize size = 0; switch (fdesc->type) { case FIELD_TYPE_DATE: case FIELD_TYPE_BOOLEAN: case FIELD_TYPE_INTEGER: pStmtExt = pStmtExts[DB_FIELDS_INTEGER]; break; case FIELD_TYPE_FLOAT: pStmtExt = pStmtExts[DB_FIELDS_REAL]; break;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -