summaryrefslogtreecommitdiff
path: root/storage/connect
diff options
context:
space:
mode:
authorOlivier Bertrand <bertrandop@gmail.com>2015-05-05 11:37:21 +0200
committerOlivier Bertrand <bertrandop@gmail.com>2015-05-05 11:37:21 +0200
commit12bebceb8e37d7c8a57a56ea3391d2d76f74d5b4 (patch)
treede02f55359a55c727db5aa95ae38bb7962f36f59 /storage/connect
parent1b07ba57a4f05b53db48d89c5954448bbe4e64a3 (diff)
downloadmariadb-git-12bebceb8e37d7c8a57a56ea3391d2d76f74d5b4.tar.gz
- Fix a regression bug on (XML) HTML tables.
modified: tabxml.cpp added: xml_html.test xml_html.result beers.xml coffee.htm - Fix MDEV-7935 by suppressing error resetting code in delete_or_rename_table. However, the issue is that this code was added because without it an assertion was raised in some cases. Unfortunately I can't remember what were these cases. Therefore fixing it in this case will perhaps make a new crash happening on another cases. modified: ha_connect.cc - Add the UDF Json_Array_Delete. modified: jsonudf.cpp
Diffstat (limited to 'storage/connect')
-rw-r--r--storage/connect/ha_connect.cc9
-rw-r--r--storage/connect/jsonudf.cpp94
-rw-r--r--storage/connect/mysql-test/connect/r/xml_html.result32
-rw-r--r--storage/connect/mysql-test/connect/std_data/beers.xml16
-rw-r--r--storage/connect/mysql-test/connect/std_data/coffee.htm24
-rw-r--r--storage/connect/mysql-test/connect/t/xml_html.test39
-rw-r--r--storage/connect/tabxml.cpp5
7 files changed, 201 insertions, 18 deletions
diff --git a/storage/connect/ha_connect.cc b/storage/connect/ha_connect.cc
index 8b1ca3519ee..765c04bd2be 100644
--- a/storage/connect/ha_connect.cc
+++ b/storage/connect/ha_connect.cc
@@ -4632,8 +4632,13 @@ int ha_connect::delete_or_rename_table(const char *name, const char *to)
} // endif pos
- } else // Avoid infamous DBUG_ASSERT
- thd->get_stmt_da()->reset_diagnostics_area();
+ } // endif open_table_def
+
+// This below was done to avoid DBUG_ASSERT in some case that
+// we don't know anymore what they were. It was suppressed because
+// it did cause assertion in other cases (see MDEV-7935)
+// } else // Avoid infamous DBUG_ASSERT
+// thd->get_stmt_da()->reset_diagnostics_area();
free_table_share(share);
} else // Temporary file
diff --git a/storage/connect/jsonudf.cpp b/storage/connect/jsonudf.cpp
index 194cb6defd6..1afd79bec05 100644
--- a/storage/connect/jsonudf.cpp
+++ b/storage/connect/jsonudf.cpp
@@ -17,40 +17,45 @@
#include "json.h"
#define MEMFIX 512
+#define UDF_EXEC_ARGS \
+ UDF_INIT*, UDF_ARGS*, char*, unsigned long*, char*, char*
uint GetJsonGrpSize(void);
extern "C" {
DllExport my_bool Json_Value_init(UDF_INIT*, UDF_ARGS*, char*);
-DllExport char *Json_Value(UDF_INIT*, UDF_ARGS*, char*,
- unsigned long*, char *, char *);
+DllExport char *Json_Value(UDF_EXEC_ARGS);
DllExport void Json_Value_deinit(UDF_INIT*);
+
DllExport my_bool Json_Array_init(UDF_INIT*, UDF_ARGS*, char*);
-DllExport char *Json_Array(UDF_INIT*, UDF_ARGS*, char*,
- unsigned long*, char *, char *);
+DllExport char *Json_Array(UDF_EXEC_ARGS);
DllExport void Json_Array_deinit(UDF_INIT*);
+
DllExport my_bool Json_Array_Add_init(UDF_INIT*, UDF_ARGS*, char*);
-DllExport char *Json_Array_Add(UDF_INIT*, UDF_ARGS*, char*,
- unsigned long*, char *, char *);
+DllExport char *Json_Array_Add(UDF_EXEC_ARGS);
DllExport void Json_Array_Add_deinit(UDF_INIT*);
+
+DllExport my_bool Json_Array_Delete_init(UDF_INIT*, UDF_ARGS*, char*);
+DllExport char *Json_Array_Delete(UDF_EXEC_ARGS);
+DllExport void Json_Array_Delete_deinit(UDF_INIT*);
+
DllExport my_bool Json_Object_init(UDF_INIT*, UDF_ARGS*, char*);
-DllExport char *Json_Object(UDF_INIT*, UDF_ARGS*, char*,
- unsigned long*, char *, char *);
+DllExport char *Json_Object(UDF_EXEC_ARGS);
DllExport void Json_Object_deinit(UDF_INIT*);
+
DllExport my_bool Json_Object_Nonull_init(UDF_INIT*, UDF_ARGS*, char*);
-DllExport char *Json_Object_Nonull(UDF_INIT*, UDF_ARGS*, char*,
- unsigned long*, char *, char *);
+DllExport char *Json_Object_Nonull(UDF_EXEC_ARGS);
DllExport void Json_Object_Nonull_deinit(UDF_INIT*);
+
DllExport my_bool Json_Array_Grp_init(UDF_INIT*, UDF_ARGS*, char*);
DllExport void Json_Array_Grp_add(UDF_INIT *, UDF_ARGS *, char *, char *);
-DllExport char *Json_Array_Grp(UDF_INIT*, UDF_ARGS*, char*,
- unsigned long*, char *, char *);
+DllExport char *Json_Array_Grp(UDF_EXEC_ARGS);
DllExport void Json_Array_Grp_clear(UDF_INIT *, char *, char *);
DllExport void Json_Array_Grp_deinit(UDF_INIT*);
+
DllExport my_bool Json_Object_Grp_init(UDF_INIT*, UDF_ARGS*, char*);
DllExport void Json_Object_Grp_add(UDF_INIT *, UDF_ARGS *, char *, char *);
-DllExport char *Json_Object_Grp(UDF_INIT*, UDF_ARGS*, char*,
- unsigned long*, char *, char *);
+DllExport char *Json_Object_Grp(UDF_EXEC_ARGS);
DllExport void Json_Object_Grp_clear(UDF_INIT *, char *, char *);
DllExport void Json_Object_Grp_deinit(UDF_INIT*);
} // extern "C"
@@ -405,6 +410,67 @@ void Json_Array_Add_deinit(UDF_INIT* initid)
} // end of Json_Array_Add_deinit
/***********************************************************************/
+/* Add values to a Json array. */
+/***********************************************************************/
+my_bool Json_Array_Delete_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
+{
+ unsigned long reslen, memlen;
+
+ if (args->arg_count != 2) {
+ strcpy(message, "Json_Value_Delete must have 2 arguments");
+ return true;
+ } else if (!IsJson(args, 0)) {
+ strcpy(message, "Json_Value_Delete first argument must be a json item");
+ return true;
+ } else
+ CalcLen(args, false, reslen, memlen);
+
+ return JsonInit(initid, message, reslen, memlen);
+} // end of Json_Array_Delete_init
+
+char *Json_Array_Delete(UDF_INIT *initid, UDF_ARGS *args, char *result,
+ unsigned long *res_length, char *is_null, char *error)
+{
+ char *str;
+ int n;
+ PJVAL jvp;
+ PJAR arp;
+ PGLOBAL g = (PGLOBAL)initid->ptr;
+
+ PlugSubSet(g, g->Sarea, g->Sarea_Size);
+ jvp = MakeValue(g, args, 0);
+
+ if (jvp->GetValType() != TYPE_JAR) {
+ push_warning(current_thd, Sql_condition::WARN_LEVEL_WARN, 0,
+ "First argument is not an array");
+ str = args->args[0];
+ } else if (args->arg_type[1] != INT_RESULT) {
+ push_warning(current_thd, Sql_condition::WARN_LEVEL_WARN, 0,
+ "Second argument is not an integer");
+ str = args->args[0];
+ } else {
+ n = *(int*)args->args[1];
+ arp = jvp->GetArray();
+ arp->DeleteValue(n - 1);
+ arp->InitArray(g);
+
+ if (!(str = Serialize(g, arp, NULL, 0))) {
+ str = strcpy(result, g->Message);
+ push_warning(current_thd, Sql_condition::WARN_LEVEL_WARN, 0, str);
+ } // endif str
+
+ } // endif's
+
+ *res_length = strlen(str);
+ return str;
+} // end of Json_Array_Delete
+
+void Json_Array_Delete_deinit(UDF_INIT* initid)
+{
+ PlugExit((PGLOBAL)initid->ptr);
+} // end of Json_Array_Delete_deinit
+
+/***********************************************************************/
/* Make a Json Oject containing all the parameters. */
/***********************************************************************/
my_bool Json_Object_init(UDF_INIT *initid, UDF_ARGS *args, char *message)
diff --git a/storage/connect/mysql-test/connect/r/xml_html.result b/storage/connect/mysql-test/connect/r/xml_html.result
new file mode 100644
index 00000000000..7b5e0febe6e
--- /dev/null
+++ b/storage/connect/mysql-test/connect/r/xml_html.result
@@ -0,0 +1,32 @@
+Warnings:
+Warning 1105 No file name. Table will use t1.xml
+SET NAMES utf8;
+#
+# Testing HTML like XML file
+#
+CREATE TABLE beers (
+`Name` CHAR(16) FIELD_FORMAT='brandName',
+`Origin` CHAR(16) FIELD_FORMAT='origin',
+`Description` CHAR(32) FIELD_FORMAT='details')
+ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='beers.xml'
+TABNAME='table' OPTION_LIST='xmlsup=libxml2,rownode=tr,colnode=td';
+SELECT * FROM beers;
+Name Origin Description
+Huntsman Bath, UK Wonderful hop, light alcohol
+Tuborg Danmark In small bottles
+DROP TABLE beers;
+#
+# Testing HTML file
+#
+CREATE TABLE coffee (
+`Name` CHAR(16),
+`Cups` INT(8),
+`Type` CHAR(16),
+`Sugar` CHAR(4))
+ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='coffee.htm'
+TABNAME='TABLE' HEADER=1 OPTION_LIST='xmlsup=libxml2,Coltype=HTML';
+SELECT * FROM coffee;
+Name Cups Type Sugar
+T. Sexton 10 Espresso No
+J. Dinnen 5 Decaf Yes
+DROP TABLE coffee;
diff --git a/storage/connect/mysql-test/connect/std_data/beers.xml b/storage/connect/mysql-test/connect/std_data/beers.xml
new file mode 100644
index 00000000000..1abc77fe0f9
--- /dev/null
+++ b/storage/connect/mysql-test/connect/std_data/beers.xml
@@ -0,0 +1,16 @@
+<?xml version="1.0"?>
+<Beers>
+ <table>
+ <th><td>Name</td><td>Origin</td><td>Description</td></th>
+ <tr>
+ <td><brandName>Huntsman</brandName></td>
+ <td><origin>Bath, UK</origin></td>
+ <td><details>Wonderful hop, light alcohol</details></td>
+ </tr>
+ <tr>
+ <td><brandName>Tuborg</brandName></td>
+ <td><origin>Danmark</origin></td>
+ <td><details>In small bottles</details></td>
+ </tr>
+ </table>
+</Beers>
diff --git a/storage/connect/mysql-test/connect/std_data/coffee.htm b/storage/connect/mysql-test/connect/std_data/coffee.htm
new file mode 100644
index 00000000000..95a23d5c0ad
--- /dev/null
+++ b/storage/connect/mysql-test/connect/std_data/coffee.htm
@@ -0,0 +1,24 @@
+<TABLE summary="This table charts the number of cups of coffe
+ consumed by each senator, the type of coffee (decaf
+ or regular), and whether taken with sugar.">
+ <CAPTION>Cups of coffee consumed by each senator</CAPTION>
+ <TR>
+ <TH>Name</TH>
+ <TH>Cups</TH>
+ <TH>Type of Coffee</TH>
+ <TH>Sugar?</TH>
+ </TR>
+ <TR>
+ <TD>T. Sexton</TD>
+ <TD>10</TD>
+ <TD>Espresso</TD>
+ <TD>No</TD>
+ </TR>
+ <TR>
+ <TD>J. Dinnen</TD>
+ <TD>5</TD>
+ <TD>Decaf</TD>
+ <TD>Yes</TD>
+ </TR>
+</TABLE>
+
diff --git a/storage/connect/mysql-test/connect/t/xml_html.test b/storage/connect/mysql-test/connect/t/xml_html.test
new file mode 100644
index 00000000000..1c84b46ec38
--- /dev/null
+++ b/storage/connect/mysql-test/connect/t/xml_html.test
@@ -0,0 +1,39 @@
+--source have_libxml2.inc
+
+let $MYSQLD_DATADIR= `select @@datadir`;
+
+SET NAMES utf8;
+
+--copy_file $MTR_SUITE_DIR/std_data/beers.xml $MYSQLD_DATADIR/test/beers.xml
+--copy_file $MTR_SUITE_DIR/std_data/coffee.htm $MYSQLD_DATADIR/test/coffee.htm
+
+--echo #
+--echo # Testing HTML like XML file
+--echo #
+CREATE TABLE beers (
+`Name` CHAR(16) FIELD_FORMAT='brandName',
+`Origin` CHAR(16) FIELD_FORMAT='origin',
+`Description` CHAR(32) FIELD_FORMAT='details')
+ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='beers.xml'
+TABNAME='table' OPTION_LIST='xmlsup=libxml2,rownode=tr,colnode=td';
+SELECT * FROM beers;
+DROP TABLE beers;
+
+--echo #
+--echo # Testing HTML file
+--echo #
+CREATE TABLE coffee (
+`Name` CHAR(16),
+`Cups` INT(8),
+`Type` CHAR(16),
+`Sugar` CHAR(4))
+ENGINE=CONNECT TABLE_TYPE=XML FILE_NAME='coffee.htm'
+TABNAME='TABLE' HEADER=1 OPTION_LIST='xmlsup=libxml2,Coltype=HTML';
+SELECT * FROM coffee;
+DROP TABLE coffee;
+
+#
+# Clean up
+#
+--remove_file $MYSQLD_DATADIR/test/beers.xml
+--remove_file $MYSQLD_DATADIR/test/coffee.htm
diff --git a/storage/connect/tabxml.cpp b/storage/connect/tabxml.cpp
index 8ea44fed2be..1c1ff8a2ffe 100644
--- a/storage/connect/tabxml.cpp
+++ b/storage/connect/tabxml.cpp
@@ -1505,8 +1505,9 @@ bool XMLCOL::ParseXpath(PGLOBAL g, bool mode)
} else if (Type == 2) {
// HTML like table, columns are retrieved by position
new(this) XPOSCOL(Value); // Change the class of this column
- Tdbp->Hasnod = true;
- return false;
+ Inod = -1;
+// Tdbp->Hasnod = true;
+// return false;
} else if (Type == 0 && !mode) {
strcat(strcat(pbuf, "@"), Name);
} else { // Type == 1