[SAMPLE APP][DATA-CONTROL-PROVIDER] Sql provider callback descriptions
authorMichal Skorupinski <m.skorupinsk@samsung.com>
Fri, 16 Oct 2015 15:19:48 +0000 (17:19 +0200)
committerMichal Skorupinski <m.skorupinsk@samsung.com>
Wed, 21 Oct 2015 13:22:15 +0000 (15:22 +0200)
Change-Id: I6fdea50ba1c93d05ad90fabfd16c9ec8a399d4a1
Signed-off-by: Michal Skorupinski <m.skorupinsk@samsung.com>
org.tizen.sampledescriptions/html/mobile_n/data_control_consumer_sd_mn.htm
org.tizen.sampledescriptions/html/mobile_n/data_control_provider_sd_mn.htm

index 7dbc797..4de0c88 100644 (file)
@@ -491,7 +491,7 @@ data_control_sql_select(data_control_h provider, char **column_list, int column_
 should be used. The <span style="font-family: Courier New,Courier,monospace">select_array</span> parameter is used as the text after the SELECT keyword in a sql query. The <span style="font-family: Courier New,Courier,monospace">select_array</span> is an array of strings. The <span style="font-family: Courier New,Courier,monospace"><a href = "#ui-struct-sql">column_name_entry</a></span> entry field in the sql view can be used as the input for the <span style="font-family: Courier New,Courier,monospace">select_array</span>. Note however that the string from the entry has to be converted (using the <span style="font-family: Courier New,Courier,monospace">elm_entry_markup_to_utf8()</span>) from markup to utf8 format. If not, some characters, e.g '&lt;', cannot be used. After the conversion, '\n' can be used as a delimiter when the text from the entry field is transformed into the array of strings. The <span style="font-family: Courier New,Courier,monospace">select_array_count</span> variable is the count of <span style="font-family: Courier New,Courier,monospace">select_array</span> elements. The <span style="font-family: Courier New,Courier,monospace">final_where</span> parameter is a string. It can contain any correct sql WHERE entry. The <span style="font-family: Courier New,Courier,monospace"><a href = "#ui-struct-sql">where_entry</a></span> entry field is used to provide an input for this parameter. Of course this text (like any text from an entry widget) has to be converted to utf8 as well. If one of the sort methods is chosen using the radiobuttons, a column name has to be provided using the <span style="font-family: Courier New,Courier,monospace"><a href = "#ui-struct-sql">sort_column_entry</a></span> field. The <span style="font-family: Courier New,Courier,monospace">order_text</span> parameter is a concatenation of the <span style="font-family: Courier New,Courier,monospace">order_text</span> string and an appropriate sort text, e.g. 'Num ASC'.
 </p>
 
-<p>Insert request</p>
+<p id = "consumer-sql-insert-request">Insert request</p>
 <p>Insert request uses a <span style="font-family: Courier New,Courier,monospace">bundle</span> structure to generate an sql query. The <span style="font-family: Courier New,Courier,monospace"><a href = "#ui-struct-sql">column_name_entry</a></span> and <span style="font-family: Courier New,Courier,monospace"><a href = "#ui-struct-sql">column_value_entry</a></span> entries are used to provide input. The obtained strings are then tokenized and added to the bundle as a key value pair. The first line of the <span style="font-family: Courier New,Courier,monospace"><a href = "#ui-struct-sql">column_name_entry</a></span> and  the first line of the <span style="font-family: Courier New,Courier,monospace"><a href = "#ui-struct-sql">value_name_entry</a></span> are used as the first pair and so on.</p>
 
 <p>Delete request</p>
index 249372e..f3f46a6 100644 (file)
@@ -274,6 +274,144 @@ static void __data_map_remove(int request_id, const char* key, const char *value
 }
 </pre>
 
+
+<h3>The SQL module</h3>
+<h4>Structure definitions</h4>
+
+<p>The map module uses the following structure to hold its data:</p>
+<pre class="prettyprint">
+static struct {
+&nbsp;&nbsp;&nbsp;data_control_provider_sql_cb sql_callback; /* Provider callbacks */
+&nbsp;&nbsp;&nbsp;sqlite3 *db; /* The map structure */
+} s_info;
+</pre>
+
+<h4>Initialization</h4>
+<p>The SQL module uses a SQLite database to hold data. As opposed to the map module, the SQL module uses an external file to store the data so it is not lost when the app is killed. Four callback are used to provide communication with the consumer application.</p>
+
+<p>The function below is used to initialize the SQL provider module.</p>
+<pre class="prettyprint">
+void sql_provider_init(void)
+{
+&nbsp;&nbsp;&nbsp;int result = __create_database(); /* Create and open a database file */
+
+&nbsp;&nbsp;&nbsp;/* Initialize the callback structure with function pointers */
+&nbsp;&nbsp;&nbsp;s_info.sql_callback.select_cb = __select_request_cb;
+&nbsp;&nbsp;&nbsp;s_info.sql_callback.insert_cb = __insert_request_cb;
+&nbsp;&nbsp;&nbsp;s_info.sql_callback.delete_cb = __delete_request_cb;
+&nbsp;&nbsp;&nbsp;s_info.sql_callback.update_cb = __update_request_cb;
+
+&nbsp;&nbsp;&nbsp;/* Register the callbacks */
+&nbsp;&nbsp;&nbsp;result = data_control_provider_sql_register_cb(&s_info.sql_callback, NULL);
+&nbsp;&nbsp;&nbsp;/* ... */
+}
+</pre>
+
+<h4>Callbacks</h4>
+
+<p>The callback invoked when an 'insert' request is sent:</p>
+<pre class="prettyprint">
+static void __insert_request_cb(int request_id, data_control_h provider, bundle *insert_data, void *user_data)
+{
+&nbsp;&nbsp;&nbsp;/* The insert_data argument contains a list of column name / value pairs. Check the <a href = "data_control_consumer_sd_mn.htm#consumer-sql-insert-request">consumer</a> app documentation for details.
+&nbsp;&nbsp;&nbsp;Based on the values stored in the bundle a SQL INSERT query is created. */
+&nbsp;&nbsp;&nbsp;command = data_control_provider_create_insert_statement(provider, insert_data);
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;/* The new row is added to the database using standard SQLite API's functions */
+&nbsp;&nbsp;&nbsp;ret = sqlite3_exec(s_info.db, command, NULL, NULL, NULL);
+&nbsp;&nbsp;&nbsp;/* ... */
+&nbsp;&nbsp;&nbsp;inserted_row_id = sqlite3_last_insert_rowid(s_info.db);
+
+&nbsp;&nbsp;&nbsp;/* The operation result is sent back to the consumer application */
+&nbsp;&nbsp;&nbsp;ret = data_control_provider_send_insert_result(request_id, inserted_row_id);
+
+&nbsp;&nbsp;&nbsp;/* ... */
+}
+</pre>
+
+<p>The callback invoked when a 'delete' request is sent:</p>
+<pre class="prettyprint">
+static void __delete_request_cb(int request_id, data_control_h provider, const char *where, void *user_data)
+{
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;/* The 'where' text is used to create a SQL DELETE query */
+&nbsp;&nbsp;&nbsp;command = data_control_provider_create_delete_statement(provider, where);
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;/* The new row is added to the database using standard SQLite API's functions */
+&nbsp;&nbsp;&nbsp;ret = sqlite3_exec(s_info.db, command, NULL, NULL, NULL);
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;/* The operation result is sent back to the consumer application */
+&nbsp;&nbsp;&nbsp;ret = data_control_provider_send_delete_result(request_id);
+&nbsp;&nbsp;&nbsp;/* ... */
+}
+</pre>
+
+<p>The callback invoked when a 'select' request is sent:</p>
+<pre class="prettyprint">
+static void __select_request_cb(int request_id, data_control_h provider, const char **column_list,
+&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;int column_count, const char *where, const char *order, void *user_data)
+{
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;/* A SQL SELECT query is created using the callback arguments. Note that some of the arguments can be NULL.
+&nbsp;&nbsp;&nbsp;The resulting query:
+&nbsp;&nbsp;&nbsp;SELECT column_list[0], column_list[1] .. column_list[column_count - 1] FROM Sample_Table WHERE where ORDER BY order;
+
+&nbsp;&nbsp;&nbsp;If the where string is NULL, there is no filter used and if order string is NULL there is no sorting applied.
+&nbsp;&nbsp;&nbsp;*/
+&nbsp;&nbsp;&nbsp;command = data_control_provider_create_select_statement(provider, column_list, column_count, where, order);
+&nbsp;&nbsp;&nbsp;if (!command) {
+&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;dlog_print(DLOG_ERROR, LOG_TAG, "command == NULL");
+&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;
+&nbsp;&nbsp;&nbsp;} else {
+&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;dlog_print(DLOG_ERROR, LOG_TAG, "command == %s", command);
+&nbsp;&nbsp;&nbsp;}
+
+&nbsp;&nbsp;&nbsp;/* A SQL statement object is created and sent to the consumer application */
+&nbsp;&nbsp;&nbsp;ret = sqlite3_prepare_v2(s_info.db, command, strlen(command), &sql_stmt, NULL);
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;ret = data_control_provider_send_select_result(request_id, (void *)sql_stmt);
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;sqlite3_finalize(sql_stmt);
+
+&nbsp;&nbsp;&nbsp;/* ... */
+}
+</pre>
+
+<p>The callback invoked when an 'update' request is sent:</p>
+<pre class="prettyprint">
+static void __update_request_cb(int request_id, data_control_h provider, bundle *update_data, const char *where, void *user_data)
+{
+&nbsp;&nbsp;&nbsp;int ret = -1;
+&nbsp;&nbsp;&nbsp;char *command = NULL;
+
+
+&nbsp;&nbsp;&nbsp;/* The SQL query is created using the bundle structure similar to the structure used in add query and where string similar to the one used in the delete query.
+&nbsp;&nbsp;&nbsp;The final query will look like this:
+&nbsp;&nbsp;&nbsp;UPDATE Sample_Table SET bundle_key1 = bundle_value_1, bundle_key1 = bundle_value_1, ..., columnN = valueN WHERE where
+
+&nbsp;&nbsp;&nbsp;*/
+&nbsp;&nbsp;&nbsp;command = data_control_provider_create_update_statement(provider, update_data, where);
+&nbsp;&nbsp;&nbsp;if (!command) {
+&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;dlog_print(DLOG_ERROR, LOG_TAG, "command == NULL");
+&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;return;
+&nbsp;&nbsp;&nbsp;}
+
+&nbsp;&nbsp;&nbsp;/* The generated command is then used as a SQLite query */
+&nbsp;&nbsp;&nbsp;ret = sqlite3_exec(s_info.db, command, NULL, NULL, NULL);
+&nbsp;&nbsp;&nbsp;/* ... */
+
+&nbsp;&nbsp;&nbsp;/* After the database update information about the update's result is sent to the consumer app*/
+&nbsp;&nbsp;&nbsp;ret = data_control_provider_send_update_result(request_id);
+&nbsp;&nbsp;&nbsp;/* ... */
+}
+</pre>
 <!-- ********************************************************************************** -->
 
 <script type="text/javascript" src="../scripts/jquery.zclip.min.js"></script>