mirror of
https://github.com/MariaDB/server.git
synced 2025-08-08 11:22:35 +03:00
Commit updating CONNECT from the 10.1 version
This commit is contained in:
@@ -28,8 +28,8 @@ tabvct.cpp tabvir.cpp tabxcl.cpp valblk.cpp value.cpp xindex.cpp xobject.cpp
|
|||||||
|
|
||||||
array.h blkfil.h block.h catalog.h checklvl.h colblk.h connect.h csort.h
|
array.h blkfil.h block.h catalog.h checklvl.h colblk.h connect.h csort.h
|
||||||
engmsg.h filamap.h filamdbf.h filamfix.h filamtxt.h filamvct.h filamzip.h
|
engmsg.h filamap.h filamdbf.h filamfix.h filamtxt.h filamvct.h filamzip.h
|
||||||
filter.h global.h ha_connect.h inihandl.h json.h maputil.h msgid.h mycat.h
|
filter.h global.h ha_connect.h inihandl.h json.h jsonudf.h maputil.h msgid.h
|
||||||
myconn.h myutil.h os.h osutil.h plgcnx.h plgdbsem.h preparse.h reldef.h
|
mycat.h myconn.h myutil.h os.h osutil.h plgcnx.h plgdbsem.h preparse.h reldef.h
|
||||||
resource.h tabcol.h tabdos.h tabfix.h tabfmt.h tabjson.h tabmul.h tabmysql.h
|
resource.h tabcol.h tabdos.h tabfix.h tabfmt.h tabjson.h tabmul.h tabmysql.h
|
||||||
taboccur.h tabpivot.h tabsys.h tabtbl.h tabutil.h tabvct.h tabvir.h tabxcl.h
|
taboccur.h tabpivot.h tabsys.h tabtbl.h tabutil.h tabvct.h tabvir.h tabxcl.h
|
||||||
user_connect.h valblk.h value.h xindex.h xobject.h xtable.h)
|
user_connect.h valblk.h value.h xindex.h xobject.h xtable.h)
|
||||||
@@ -48,7 +48,7 @@ IF(UNIX)
|
|||||||
# Bar: -Wfatal-errors removed (does not present in gcc on solaris10)
|
# Bar: -Wfatal-errors removed (does not present in gcc on solaris10)
|
||||||
if(WITH_WARNINGS)
|
if(WITH_WARNINGS)
|
||||||
add_definitions(-Wall -Wextra -Wmissing-declarations)
|
add_definitions(-Wall -Wextra -Wmissing-declarations)
|
||||||
message(STATUS "CONNECT: GCC: All warnings enabled")
|
#message(STATUS "CONNECT: GCC: All warnings enabled")
|
||||||
else()
|
else()
|
||||||
add_definitions(-Wall -Wmissing-declarations)
|
add_definitions(-Wall -Wmissing-declarations)
|
||||||
add_definitions(-Wno-write-strings)
|
add_definitions(-Wno-write-strings)
|
||||||
@@ -69,7 +69,7 @@ IF(UNIX)
|
|||||||
# These switches are for C++ only
|
# These switches are for C++ only
|
||||||
# add_definitions(-Wno-reorder)
|
# add_definitions(-Wno-reorder)
|
||||||
|
|
||||||
message(STATUS "CONNECT: GCC: Some warnings disabled")
|
#message(STATUS "CONNECT: GCC: Some warnings disabled")
|
||||||
endif(WITH_WARNINGS)
|
endif(WITH_WARNINGS)
|
||||||
|
|
||||||
add_definitions( -DUNIX -DLINUX -DUBUNTU )
|
add_definitions( -DUNIX -DLINUX -DUBUNTU )
|
||||||
|
@@ -735,17 +735,12 @@ static void SetSwapValue(PVAL valp, char *kp)
|
|||||||
/* IndexRead: fetch a record having the index value. */
|
/* IndexRead: fetch a record having the index value. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
RCODE CntIndexRead(PGLOBAL g, PTDB ptdb, OPVAL op,
|
RCODE CntIndexRead(PGLOBAL g, PTDB ptdb, OPVAL op,
|
||||||
const void *key, int len, bool mrr)
|
const key_range *kr, bool mrr)
|
||||||
{
|
{
|
||||||
char *kp= (char*)key;
|
|
||||||
int n, x;
|
int n, x;
|
||||||
short lg;
|
|
||||||
bool rcb;
|
|
||||||
RCODE rc;
|
RCODE rc;
|
||||||
PVAL valp;
|
|
||||||
PCOL colp;
|
|
||||||
XXBASE *xbp;
|
XXBASE *xbp;
|
||||||
PTDBDOX tdbp;
|
PTDBDOX tdbp;
|
||||||
|
|
||||||
if (!ptdb)
|
if (!ptdb)
|
||||||
return RC_FX;
|
return RC_FX;
|
||||||
@@ -757,13 +752,13 @@ RCODE CntIndexRead(PGLOBAL g, PTDB ptdb, OPVAL op,
|
|||||||
return RC_FX;
|
return RC_FX;
|
||||||
} else if (x == 2) {
|
} else if (x == 2) {
|
||||||
// Remote index
|
// Remote index
|
||||||
if (ptdb->ReadKey(g, op, key, len))
|
if (ptdb->ReadKey(g, op, kr))
|
||||||
return RC_FX;
|
return RC_FX;
|
||||||
|
|
||||||
goto rnd;
|
goto rnd;
|
||||||
} else if (x == 3) {
|
} else if (x == 3) {
|
||||||
if (key)
|
if (kr)
|
||||||
((PTDBASE)ptdb)->SetRecpos(g, *(int*)key);
|
((PTDBASE)ptdb)->SetRecpos(g, *(int*)kr->key);
|
||||||
|
|
||||||
if (op == OP_SAME)
|
if (op == OP_SAME)
|
||||||
return RC_NF;
|
return RC_NF;
|
||||||
@@ -790,7 +785,14 @@ RCODE CntIndexRead(PGLOBAL g, PTDB ptdb, OPVAL op,
|
|||||||
|
|
||||||
xbp= (XXBASE*)tdbp->To_Kindex;
|
xbp= (XXBASE*)tdbp->To_Kindex;
|
||||||
|
|
||||||
if (key) {
|
if (kr) {
|
||||||
|
char *kp= (char*)kr->key;
|
||||||
|
int len= kr->length;
|
||||||
|
short lg;
|
||||||
|
bool rcb;
|
||||||
|
PVAL valp;
|
||||||
|
PCOL colp;
|
||||||
|
|
||||||
for (n= 0; n < tdbp->Knum; n++) {
|
for (n= 0; n < tdbp->Knum; n++) {
|
||||||
colp= (PCOL)tdbp->To_Key_Col[n];
|
colp= (PCOL)tdbp->To_Key_Col[n];
|
||||||
|
|
||||||
@@ -832,10 +834,10 @@ RCODE CntIndexRead(PGLOBAL g, PTDB ptdb, OPVAL op,
|
|||||||
|
|
||||||
kp+= valp->GetClen();
|
kp+= valp->GetClen();
|
||||||
|
|
||||||
if (len == kp - (char*)key) {
|
if (len == kp - (char*)kr->key) {
|
||||||
n++;
|
n++;
|
||||||
break;
|
break;
|
||||||
} else if (len < kp - (char*)key) {
|
} else if (len < kp - (char*)kr->key) {
|
||||||
strcpy(g->Message, "Key buffer is too small");
|
strcpy(g->Message, "Key buffer is too small");
|
||||||
return RC_FX;
|
return RC_FX;
|
||||||
} // endif len
|
} // endif len
|
||||||
|
@@ -36,7 +36,7 @@ bool CntRewindTable(PGLOBAL g, PTDB tdbp);
|
|||||||
int CntCloseTable(PGLOBAL g, PTDB tdbp, bool nox, bool abort);
|
int CntCloseTable(PGLOBAL g, PTDB tdbp, bool nox, bool abort);
|
||||||
int CntIndexInit(PGLOBAL g, PTDB tdbp, int id, bool sorted);
|
int CntIndexInit(PGLOBAL g, PTDB tdbp, int id, bool sorted);
|
||||||
RCODE CntReadNext(PGLOBAL g, PTDB tdbp);
|
RCODE CntReadNext(PGLOBAL g, PTDB tdbp);
|
||||||
RCODE CntIndexRead(PGLOBAL g, PTDB, OPVAL op, const void *k, int n, bool mrr);
|
RCODE CntIndexRead(PGLOBAL g, PTDB, OPVAL op, const key_range *kr, bool mrr);
|
||||||
RCODE CntWriteRow(PGLOBAL g, PTDB tdbp);
|
RCODE CntWriteRow(PGLOBAL g, PTDB tdbp);
|
||||||
RCODE CntUpdateRow(PGLOBAL g, PTDB tdbp);
|
RCODE CntUpdateRow(PGLOBAL g, PTDB tdbp);
|
||||||
RCODE CntDeleteRow(PGLOBAL g, PTDB tdbp, bool all);
|
RCODE CntDeleteRow(PGLOBAL g, PTDB tdbp, bool all);
|
||||||
@@ -60,7 +60,7 @@ class TDBDOX: public TDBDOS {
|
|||||||
friend int MakeIndex(PGLOBAL, PTDB, PIXDEF);
|
friend int MakeIndex(PGLOBAL, PTDB, PIXDEF);
|
||||||
friend int CntCloseTable(PGLOBAL, PTDB, bool, bool);
|
friend int CntCloseTable(PGLOBAL, PTDB, bool, bool);
|
||||||
friend int CntIndexInit(PGLOBAL, PTDB, int, bool);
|
friend int CntIndexInit(PGLOBAL, PTDB, int, bool);
|
||||||
friend RCODE CntIndexRead(PGLOBAL, PTDB, OPVAL, const void*, int, bool);
|
friend RCODE CntIndexRead(PGLOBAL, PTDB, OPVAL, const key_range*, bool);
|
||||||
friend RCODE CntDeleteRow(PGLOBAL, PTDB, bool);
|
friend RCODE CntDeleteRow(PGLOBAL, PTDB, bool);
|
||||||
friend int CntIndexRange(PGLOBAL, PTDB, const uchar**, uint*,
|
friend int CntIndexRange(PGLOBAL, PTDB, const uchar**, uint*,
|
||||||
bool*, key_part_map*);
|
bool*, key_part_map*);
|
||||||
|
@@ -1404,8 +1404,13 @@ void ZLBFAM::Rewind(void)
|
|||||||
// We must be positioned after the header block
|
// We must be positioned after the header block
|
||||||
if (CurBlk >= 0) { // Nothing to do if no block read yet
|
if (CurBlk >= 0) { // Nothing to do if no block read yet
|
||||||
if (!Optimized) { // If optimized, fseek will be done in ReadBuffer
|
if (!Optimized) { // If optimized, fseek will be done in ReadBuffer
|
||||||
|
size_t st;
|
||||||
|
|
||||||
rewind(Stream);
|
rewind(Stream);
|
||||||
fread(Zlenp, sizeof(int), 1, Stream);
|
|
||||||
|
if (!(st = fread(Zlenp, sizeof(int), 1, Stream)) && trace)
|
||||||
|
htrc("fread error %d in Rewind", errno);
|
||||||
|
|
||||||
fseek(Stream, *Zlenp + sizeof(int), SEEK_SET);
|
fseek(Stream, *Zlenp + sizeof(int), SEEK_SET);
|
||||||
OldBlk = -1;
|
OldBlk = -1;
|
||||||
} // endif Optimized
|
} // endif Optimized
|
||||||
|
@@ -169,9 +169,9 @@
|
|||||||
#define JSONMAX 10 // JSON Default max grp size
|
#define JSONMAX 10 // JSON Default max grp size
|
||||||
|
|
||||||
extern "C" {
|
extern "C" {
|
||||||
char version[]= "Version 1.03.0007 October 20, 2015";
|
char version[]= "Version 1.04.0005 November 20, 2015";
|
||||||
#if defined(__WIN__)
|
#if defined(__WIN__)
|
||||||
char compver[]= "Version 1.03.0007 " __DATE__ " " __TIME__;
|
char compver[]= "Version 1.04.0005 " __DATE__ " " __TIME__;
|
||||||
char slash= '\\';
|
char slash= '\\';
|
||||||
#else // !__WIN__
|
#else // !__WIN__
|
||||||
char slash= '/';
|
char slash= '/';
|
||||||
@@ -1114,7 +1114,7 @@ int GetIntegerTableOption(PGLOBAL g, PTOS options, char *opname, int idef)
|
|||||||
else if (!stricmp(opname, "Compressed"))
|
else if (!stricmp(opname, "Compressed"))
|
||||||
opval= (options->compressed);
|
opval= (options->compressed);
|
||||||
|
|
||||||
if (opval == NO_IVAL) {
|
if (opval == (ulonglong)NO_IVAL) {
|
||||||
char *pv;
|
char *pv;
|
||||||
|
|
||||||
if ((pv= GetListOption(g, opname, options->oplist)))
|
if ((pv= GetListOption(g, opname, options->oplist)))
|
||||||
@@ -1135,9 +1135,9 @@ PTOS ha_connect::GetTableOptionStruct(TABLE_SHARE *s)
|
|||||||
TABLE_SHARE *tsp= (tshp) ? tshp : (s) ? s : table_share;
|
TABLE_SHARE *tsp= (tshp) ? tshp : (s) ? s : table_share;
|
||||||
|
|
||||||
return (tsp && (!tsp->db_plugin ||
|
return (tsp && (!tsp->db_plugin ||
|
||||||
!stricmp(plugin_name(tsp->db_plugin)->str, "connect") ||
|
!stricmp(plugin_name(tsp->db_plugin)->str, "connect") ||
|
||||||
!stricmp(plugin_name(tsp->db_plugin)->str, "partition")))
|
!stricmp(plugin_name(tsp->db_plugin)->str, "partition")))
|
||||||
? tsp->option_struct : NULL;
|
? tsp->option_struct : NULL;
|
||||||
} // end of GetTableOptionStruct
|
} // end of GetTableOptionStruct
|
||||||
|
|
||||||
/****************************************************************************/
|
/****************************************************************************/
|
||||||
@@ -2191,99 +2191,159 @@ int ha_connect::ScanRecord(PGLOBAL g, uchar *)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
int ha_connect::CheckRecord(PGLOBAL g, const uchar *, uchar *newbuf)
|
int ha_connect::CheckRecord(PGLOBAL g, const uchar *, uchar *newbuf)
|
||||||
{
|
{
|
||||||
return ScanRecord(g, newbuf);
|
return ScanRecord(g, newbuf);
|
||||||
} // end of dummy CheckRecord
|
} // end of dummy CheckRecord
|
||||||
|
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Return true if this field is used in current indexing. */
|
||||||
|
/***********************************************************************/
|
||||||
|
bool ha_connect::IsIndexed(Field *fp)
|
||||||
|
{
|
||||||
|
if (active_index < MAX_KEY) {
|
||||||
|
KEY_PART_INFO *kpart;
|
||||||
|
KEY *kfp= &table->key_info[active_index];
|
||||||
|
uint rem= kfp->user_defined_key_parts;
|
||||||
|
|
||||||
|
for (kpart= kfp->key_part; rem; rem--, kpart++)
|
||||||
|
if (kpart->field == fp)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
} // endif active_index
|
||||||
|
|
||||||
|
return false;
|
||||||
|
} // end of IsIndexed
|
||||||
|
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Return the where clause for remote indexed read. */
|
/* Return the where clause for remote indexed read. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
bool ha_connect::MakeKeyWhere(PGLOBAL g, PSTRG qry, OPVAL op, char q,
|
bool ha_connect::MakeKeyWhere(PGLOBAL g, PSTRG qry, OPVAL vop, char q,
|
||||||
const void *key, int klen)
|
const key_range *kr)
|
||||||
{
|
{
|
||||||
const uchar *ptr;
|
const uchar *ptr;
|
||||||
uint rem, len, stlen; //, prtlen;
|
//uint i, rem, len, klen, stlen;
|
||||||
bool nq, oom, b= false;
|
uint i, rem, len, stlen;
|
||||||
Field *fp;
|
bool nq, both, oom= false;
|
||||||
KEY *kfp;
|
OPVAL op;
|
||||||
KEY_PART_INFO *kpart;
|
Field *fp;
|
||||||
|
const key_range *ranges[2];
|
||||||
|
my_bitmap_map *old_map;
|
||||||
|
KEY *kfp;
|
||||||
|
KEY_PART_INFO *kpart;
|
||||||
|
|
||||||
if (active_index == MAX_KEY)
|
if (active_index == MAX_KEY)
|
||||||
return false;
|
return false;
|
||||||
else if (!key) {
|
|
||||||
strcpy(g->Message, "MakeKeyWhere: No key");
|
|
||||||
return true;
|
|
||||||
} // endif key
|
|
||||||
|
|
||||||
oom= qry->Append(" WHERE (");
|
ranges[0]= kr;
|
||||||
kfp= &table->key_info[active_index];
|
ranges[1]= (end_range && !eq_range) ? &save_end_range : NULL;
|
||||||
rem= kfp->user_defined_key_parts,
|
|
||||||
len= klen,
|
|
||||||
ptr= (const uchar *)key;
|
|
||||||
|
|
||||||
for (kpart= kfp->key_part; rem; rem--, kpart++) {
|
if (!ranges[0] && !ranges[1]) {
|
||||||
fp= kpart->field;
|
strcpy(g->Message, "MakeKeyWhere: No key");
|
||||||
stlen= kpart->store_length;
|
return true;
|
||||||
// prtlen= MY_MIN(stlen, len);
|
} else
|
||||||
nq= fp->str_needs_quotes();
|
both= ranges[0] && ranges[1];
|
||||||
|
|
||||||
if (b)
|
kfp= &table->key_info[active_index];
|
||||||
oom|= qry->Append(" AND ");
|
old_map= dbug_tmp_use_all_columns(table, table->write_set);
|
||||||
else
|
|
||||||
b= true;
|
|
||||||
|
|
||||||
oom|= qry->Append(q);
|
for (i = 0; i <= 1; i++) {
|
||||||
oom|= qry->Append((PSZ)fp->field_name);
|
if (ranges[i] == NULL)
|
||||||
oom|= qry->Append(q);
|
continue;
|
||||||
|
|
||||||
switch (op) {
|
if (both && i > 0)
|
||||||
case OP_EQ:
|
oom|= qry->Append(") AND (");
|
||||||
case OP_GT:
|
else
|
||||||
case OP_GE:
|
oom|= qry->Append(" WHERE (");
|
||||||
case OP_LT:
|
|
||||||
case OP_LE:
|
|
||||||
oom |= qry->Append((PSZ)GetValStr(op, false));
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
oom|= qry->Append(" ??? ");
|
|
||||||
} // endwitch op
|
|
||||||
|
|
||||||
if (nq)
|
// klen= len= ranges[i]->length;
|
||||||
oom|= qry->Append('\'');
|
len= ranges[i]->length;
|
||||||
|
rem= kfp->user_defined_key_parts;
|
||||||
|
ptr= ranges[i]->key;
|
||||||
|
|
||||||
if (kpart->key_part_flag & HA_VAR_LENGTH_PART) {
|
for (kpart= kfp->key_part; rem; rem--, kpart++) {
|
||||||
String varchar;
|
fp= kpart->field;
|
||||||
uint var_length= uint2korr(ptr);
|
stlen= kpart->store_length;
|
||||||
|
nq= fp->str_needs_quotes();
|
||||||
|
|
||||||
varchar.set_quick((char*) ptr+HA_KEY_BLOB_LENGTH,
|
if (kpart != kfp->key_part)
|
||||||
var_length, &my_charset_bin);
|
oom|= qry->Append(" AND ");
|
||||||
oom|= qry->Append(varchar.ptr(), varchar.length());
|
|
||||||
} else {
|
|
||||||
char strbuff[MAX_FIELD_WIDTH];
|
|
||||||
String str(strbuff, sizeof(strbuff), kpart->field->charset()), *res;
|
|
||||||
|
|
||||||
res= fp->val_str(&str, ptr);
|
if (q) {
|
||||||
oom|= qry->Append(res->ptr(), res->length());
|
oom|= qry->Append(q);
|
||||||
} // endif flag
|
oom|= qry->Append((PSZ)fp->field_name);
|
||||||
|
oom|= qry->Append(q);
|
||||||
|
} else
|
||||||
|
oom|= qry->Append((PSZ)fp->field_name);
|
||||||
|
|
||||||
if (nq)
|
switch (ranges[i]->flag) {
|
||||||
oom|= qry->Append('\'');
|
case HA_READ_KEY_EXACT:
|
||||||
|
// op= (stlen >= len || !nq || fp->result_type() != STRING_RESULT)
|
||||||
|
// ? OP_EQ : OP_LIKE;
|
||||||
|
op= OP_EQ;
|
||||||
|
break;
|
||||||
|
case HA_READ_AFTER_KEY:
|
||||||
|
op= (stlen >= len) ? (!i ? OP_GT : OP_LE) : OP_GE;
|
||||||
|
break;
|
||||||
|
case HA_READ_KEY_OR_NEXT:
|
||||||
|
op= OP_GE;
|
||||||
|
break;
|
||||||
|
case HA_READ_BEFORE_KEY:
|
||||||
|
op= (stlen >= len) ? OP_LT : OP_LE;
|
||||||
|
break;
|
||||||
|
case HA_READ_KEY_OR_PREV:
|
||||||
|
op= OP_LE;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
sprintf(g->Message, "cannot handle flag %d", ranges[i]->flag);
|
||||||
|
goto err;
|
||||||
|
} // endswitch flag
|
||||||
|
|
||||||
if (stlen >= len)
|
oom|= qry->Append((PSZ)GetValStr(op, false));
|
||||||
break;
|
|
||||||
|
|
||||||
len-= stlen;
|
if (nq)
|
||||||
|
oom|= qry->Append('\'');
|
||||||
|
|
||||||
/* For nullable columns, null-byte is already skipped before, that is
|
if (kpart->key_part_flag & HA_VAR_LENGTH_PART) {
|
||||||
ptr was incremented by 1. Since store_length still counts null-byte,
|
String varchar;
|
||||||
we need to subtract 1 from store_length. */
|
uint var_length= uint2korr(ptr);
|
||||||
ptr+= stlen - MY_TEST(kpart->null_bit);
|
|
||||||
} // endfor kpart
|
varchar.set_quick((char*)ptr + HA_KEY_BLOB_LENGTH,
|
||||||
|
var_length, &my_charset_bin);
|
||||||
|
oom|= qry->Append(varchar.ptr(), varchar.length(), nq);
|
||||||
|
} else {
|
||||||
|
char strbuff[MAX_FIELD_WIDTH];
|
||||||
|
String str(strbuff, sizeof(strbuff), kpart->field->charset()), *res;
|
||||||
|
|
||||||
|
res= fp->val_str(&str, ptr);
|
||||||
|
oom|= qry->Append(res->ptr(), res->length(), nq);
|
||||||
|
} // endif flag
|
||||||
|
|
||||||
|
if (nq)
|
||||||
|
oom |= qry->Append('\'');
|
||||||
|
|
||||||
|
if (stlen >= len)
|
||||||
|
break;
|
||||||
|
|
||||||
|
len-= stlen;
|
||||||
|
|
||||||
|
/* For nullable columns, null-byte is already skipped before, that is
|
||||||
|
ptr was incremented by 1. Since store_length still counts null-byte,
|
||||||
|
we need to subtract 1 from store_length. */
|
||||||
|
ptr+= stlen - MY_TEST(kpart->null_bit);
|
||||||
|
} // endfor kpart
|
||||||
|
|
||||||
|
} // endfor i
|
||||||
|
|
||||||
if ((oom|= qry->Append(")")))
|
if ((oom|= qry->Append(")")))
|
||||||
strcpy(g->Message, "Out of memory");
|
strcpy(g->Message, "Out of memory");
|
||||||
|
|
||||||
return oom;
|
dbug_tmp_restore_column_map(table->write_set, old_map);
|
||||||
|
return oom;
|
||||||
|
|
||||||
|
err:
|
||||||
|
dbug_tmp_restore_column_map(table->write_set, old_map);
|
||||||
|
return true;
|
||||||
} // end of MakeKeyWhere
|
} // end of MakeKeyWhere
|
||||||
|
|
||||||
|
|
||||||
@@ -2483,9 +2543,11 @@ PFIL ha_connect::CondFilter(PGLOBAL g, Item *cond)
|
|||||||
case MYSQL_TYPE_YEAR:
|
case MYSQL_TYPE_YEAR:
|
||||||
case MYSQL_TYPE_NEWDATE:
|
case MYSQL_TYPE_NEWDATE:
|
||||||
return NULL;
|
return NULL;
|
||||||
|
default:
|
||||||
|
break;
|
||||||
} // endswitch type
|
} // endswitch type
|
||||||
|
|
||||||
if (trace) {
|
if (trace) {
|
||||||
htrc("Field index=%d\n", pField->field->field_index);
|
htrc("Field index=%d\n", pField->field->field_index);
|
||||||
htrc("Field name=%s\n", pField->field->field_name);
|
htrc("Field name=%s\n", pField->field->field_name);
|
||||||
} // endif trace
|
} // endif trace
|
||||||
@@ -2562,8 +2624,9 @@ PFIL ha_connect::CondFilter(PGLOBAL g, Item *cond)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Check the WHERE condition and return a MYSQL/ODBC/WQL filter. */
|
/* Check the WHERE condition and return a MYSQL/ODBC/WQL filter. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond)
|
PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, const Item *cond)
|
||||||
{
|
{
|
||||||
|
AMT tty = filp->Type;
|
||||||
char *body= filp->Body;
|
char *body= filp->Body;
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
bool ismul= false, x= (tty == TYPE_AM_MYX || tty == TYPE_AM_XDBC);
|
bool ismul= false, x= (tty == TYPE_AM_MYX || tty == TYPE_AM_XDBC);
|
||||||
@@ -2596,7 +2659,7 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond)
|
|||||||
|
|
||||||
List<Item>* arglist= cond_item->argument_list();
|
List<Item>* arglist= cond_item->argument_list();
|
||||||
List_iterator<Item> li(*arglist);
|
List_iterator<Item> li(*arglist);
|
||||||
Item *subitem;
|
const Item *subitem;
|
||||||
|
|
||||||
p1= body + strlen(body);
|
p1= body + strlen(body);
|
||||||
strcpy(p1, "(");
|
strcpy(p1, "(");
|
||||||
@@ -2604,7 +2667,7 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond)
|
|||||||
|
|
||||||
for (i= 0; i < arglist->elements; i++)
|
for (i= 0; i < arglist->elements; i++)
|
||||||
if ((subitem= li++)) {
|
if ((subitem= li++)) {
|
||||||
if (!CheckCond(g, filp, tty, subitem)) {
|
if (!CheckCond(g, filp, subitem)) {
|
||||||
if (vop == OP_OR || nonul)
|
if (vop == OP_OR || nonul)
|
||||||
return NULL;
|
return NULL;
|
||||||
else
|
else
|
||||||
@@ -2626,26 +2689,27 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond)
|
|||||||
|
|
||||||
} else if (cond->type() == COND::FUNC_ITEM) {
|
} else if (cond->type() == COND::FUNC_ITEM) {
|
||||||
unsigned int i;
|
unsigned int i;
|
||||||
// int n;
|
|
||||||
bool iscol, neg= FALSE;
|
bool iscol, neg= FALSE;
|
||||||
Item_func *condf= (Item_func *)cond;
|
Item_func *condf= (Item_func *)cond;
|
||||||
Item* *args= condf->arguments();
|
Item* *args= condf->arguments();
|
||||||
|
|
||||||
if (trace)
|
if (trace)
|
||||||
htrc("Func type=%d argnum=%d\n", condf->functype(),
|
htrc("Func type=%d argnum=%d\n", condf->functype(),
|
||||||
condf->argument_count());
|
condf->argument_count());
|
||||||
|
|
||||||
// neg= condf->
|
|
||||||
|
|
||||||
switch (condf->functype()) {
|
switch (condf->functype()) {
|
||||||
case Item_func::EQUAL_FUNC:
|
case Item_func::EQUAL_FUNC:
|
||||||
case Item_func::EQ_FUNC: vop= OP_EQ; break;
|
case Item_func::EQ_FUNC: vop= OP_EQ; break;
|
||||||
case Item_func::NE_FUNC: vop= OP_NE; break;
|
case Item_func::NE_FUNC: vop= OP_NE; break;
|
||||||
case Item_func::LT_FUNC: vop= OP_LT; break;
|
case Item_func::LT_FUNC: vop= OP_LT; break;
|
||||||
case Item_func::LE_FUNC: vop= OP_LE; break;
|
case Item_func::LE_FUNC: vop= OP_LE; break;
|
||||||
case Item_func::GE_FUNC: vop= OP_GE; break;
|
case Item_func::GE_FUNC: vop= OP_GE; break;
|
||||||
case Item_func::GT_FUNC: vop= OP_GT; break;
|
case Item_func::GT_FUNC: vop= OP_GT; break;
|
||||||
case Item_func::IN_FUNC: vop= OP_IN;
|
case Item_func::LIKE_FUNC: vop= OP_LIKE; break;
|
||||||
|
case Item_func::ISNOTNULL_FUNC:
|
||||||
|
neg = true;
|
||||||
|
case Item_func::ISNULL_FUNC: vop= OP_NULL; break;
|
||||||
|
case Item_func::IN_FUNC: vop= OP_IN;
|
||||||
case Item_func::BETWEEN:
|
case Item_func::BETWEEN:
|
||||||
ismul= true;
|
ismul= true;
|
||||||
neg= ((Item_func_opt_neg *)condf)->negated;
|
neg= ((Item_func_opt_neg *)condf)->negated;
|
||||||
@@ -2658,7 +2722,7 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond)
|
|||||||
else if (ismul && tty == TYPE_AM_WMI)
|
else if (ismul && tty == TYPE_AM_WMI)
|
||||||
return NULL; // Not supported by WQL
|
return NULL; // Not supported by WQL
|
||||||
|
|
||||||
if (x && (neg || !(vop == OP_EQ || vop == OP_IN)))
|
if (x && (neg || !(vop == OP_EQ || vop == OP_IN || vop == OP_NULL)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
for (i= 0; i < condf->argument_count(); i++) {
|
for (i= 0; i < condf->argument_count(); i++) {
|
||||||
@@ -2679,9 +2743,10 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond)
|
|||||||
|
|
||||||
if (x && i)
|
if (x && i)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
else if (pField->field->table != table)
|
||||||
if (pField->field->table != table)
|
return NULL; // Field does not belong to this table
|
||||||
return NULL; // Field does not belong to this table
|
else if (tty != TYPE_AM_WMI && IsIndexed(pField->field))
|
||||||
|
return NULL; // Will be handled by ReadKey
|
||||||
else
|
else
|
||||||
fop= GetFieldOptionStruct(pField->field);
|
fop= GetFieldOptionStruct(pField->field);
|
||||||
|
|
||||||
@@ -2712,7 +2777,7 @@ PCFIL ha_connect::CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond)
|
|||||||
strcat(body, fnm);
|
strcat(body, fnm);
|
||||||
} else if (args[i]->type() == COND::FUNC_ITEM) {
|
} else if (args[i]->type() == COND::FUNC_ITEM) {
|
||||||
if (tty == TYPE_AM_MYSQL) {
|
if (tty == TYPE_AM_MYSQL) {
|
||||||
if (!CheckCond(g, filp, tty, args[i]))
|
if (!CheckCond(g, filp, args[i]))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
} else
|
} else
|
||||||
@@ -2901,14 +2966,17 @@ const COND *ha_connect::cond_push(const COND *cond)
|
|||||||
goto fin;
|
goto fin;
|
||||||
|
|
||||||
if (b) {
|
if (b) {
|
||||||
PCFIL filp= (PCFIL)PlugSubAlloc(g, NULL, sizeof(CONDFIL));
|
PCFIL filp;
|
||||||
|
|
||||||
|
if ((filp= tdbp->GetCondFil()) && filp->Cond == cond &&
|
||||||
|
filp->Idx == active_index && filp->Type == tty)
|
||||||
|
goto fin; // Already done
|
||||||
|
|
||||||
|
filp= new(g) CONDFIL(cond, active_index, tty);
|
||||||
filp->Body= (char*)PlugSubAlloc(g, NULL, (x) ? 128 : 0);
|
filp->Body= (char*)PlugSubAlloc(g, NULL, (x) ? 128 : 0);
|
||||||
*filp->Body= 0;
|
*filp->Body= 0;
|
||||||
filp->Op= OP_XX;
|
|
||||||
filp->Cmds= NULL;
|
|
||||||
|
|
||||||
if (CheckCond(g, filp, tty, (Item *)cond)) {
|
if (CheckCond(g, filp, cond)) {
|
||||||
if (trace)
|
if (trace)
|
||||||
htrc("cond_push: %s\n", filp->Body);
|
htrc("cond_push: %s\n", filp->Body);
|
||||||
|
|
||||||
@@ -3372,13 +3440,13 @@ int ha_connect::index_end()
|
|||||||
/****************************************************************************/
|
/****************************************************************************/
|
||||||
/* This is internally called by all indexed reading functions. */
|
/* This is internally called by all indexed reading functions. */
|
||||||
/****************************************************************************/
|
/****************************************************************************/
|
||||||
int ha_connect::ReadIndexed(uchar *buf, OPVAL op, const uchar *key, uint key_len)
|
int ha_connect::ReadIndexed(uchar *buf, OPVAL op, const key_range *kr)
|
||||||
{
|
{
|
||||||
int rc;
|
int rc;
|
||||||
|
|
||||||
//statistic_increment(ha_read_key_count, &LOCK_status);
|
//statistic_increment(ha_read_key_count, &LOCK_status);
|
||||||
|
|
||||||
switch (CntIndexRead(xp->g, tdbp, op, key, (int)key_len, mrr)) {
|
switch (CntIndexRead(xp->g, tdbp, op, kr, mrr)) {
|
||||||
case RC_OK:
|
case RC_OK:
|
||||||
xp->fnd++;
|
xp->fnd++;
|
||||||
rc= MakeRecord((char*)buf);
|
rc= MakeRecord((char*)buf);
|
||||||
@@ -3444,7 +3512,12 @@ int ha_connect::index_read(uchar * buf, const uchar * key, uint key_len,
|
|||||||
htrc("%p index_read: op=%d\n", this, op);
|
htrc("%p index_read: op=%d\n", this, op);
|
||||||
|
|
||||||
if (indexing > 0) {
|
if (indexing > 0) {
|
||||||
rc= ReadIndexed(buf, op, key, key_len);
|
start_key.key= key;
|
||||||
|
start_key.length= key_len;
|
||||||
|
start_key.flag= find_flag;
|
||||||
|
start_key.keypart_map= 0;
|
||||||
|
|
||||||
|
rc= ReadIndexed(buf, op, &start_key);
|
||||||
|
|
||||||
if (rc == HA_ERR_INTERNAL_ERROR) {
|
if (rc == HA_ERR_INTERNAL_ERROR) {
|
||||||
nox= true; // To block making indexes
|
nox= true; // To block making indexes
|
||||||
@@ -3750,7 +3823,7 @@ void ha_connect::position(const uchar *)
|
|||||||
//if (((PTDBASE)tdbp)->GetDef()->Indexable())
|
//if (((PTDBASE)tdbp)->GetDef()->Indexable())
|
||||||
my_store_ptr(ref, ref_length, (my_off_t)((PTDBASE)tdbp)->GetRecpos());
|
my_store_ptr(ref, ref_length, (my_off_t)((PTDBASE)tdbp)->GetRecpos());
|
||||||
|
|
||||||
if (trace)
|
if (trace > 1)
|
||||||
htrc("position: pos=%d\n", ((PTDBASE)tdbp)->GetRecpos());
|
htrc("position: pos=%d\n", ((PTDBASE)tdbp)->GetRecpos());
|
||||||
|
|
||||||
DBUG_VOID_RETURN;
|
DBUG_VOID_RETURN;
|
||||||
@@ -4034,7 +4107,27 @@ bool ha_connect::check_privileges(THD *thd, PTOS options, char *dbn)
|
|||||||
case TAB_MAC:
|
case TAB_MAC:
|
||||||
case TAB_WMI:
|
case TAB_WMI:
|
||||||
case TAB_OEM:
|
case TAB_OEM:
|
||||||
return check_access(thd, FILE_ACL, db, NULL, NULL, 0, 0);
|
#ifdef NO_EMBEDDED_ACCESS_CHECKS
|
||||||
|
return false;
|
||||||
|
#endif
|
||||||
|
/*
|
||||||
|
If table or table->mdl_ticket is NULL - it's a DLL, e.g. CREATE TABLE.
|
||||||
|
if the table has an MDL_EXCLUSIVE lock - it's a DDL too, e.g. the
|
||||||
|
insert step of CREATE ... SELECT.
|
||||||
|
|
||||||
|
Otherwise it's a DML, the table was normally opened, locked,
|
||||||
|
privilege were already checked, and table->grant.privilege is set.
|
||||||
|
With SQL SECURITY DEFINER, table->grant.privilege has definer's privileges.
|
||||||
|
*/
|
||||||
|
if (!table || !table->mdl_ticket || table->mdl_ticket->get_type() == MDL_EXCLUSIVE)
|
||||||
|
return check_access(thd, FILE_ACL, db, NULL, NULL, 0, 0);
|
||||||
|
if (table->grant.privilege & FILE_ACL)
|
||||||
|
return false;
|
||||||
|
status_var_increment(thd->status_var.access_denied_errors);
|
||||||
|
my_error(access_denied_error_code(thd->password), MYF(0),
|
||||||
|
thd->security_ctx->priv_user, thd->security_ctx->priv_host,
|
||||||
|
(thd->password ? ER(ER_YES) : ER(ER_NO)));
|
||||||
|
return true;
|
||||||
|
|
||||||
// This is temporary until a solution is found
|
// This is temporary until a solution is found
|
||||||
case TAB_TBL:
|
case TAB_TBL:
|
||||||
@@ -4421,15 +4514,16 @@ int ha_connect::external_lock(THD *thd, int lock_type)
|
|||||||
xmod= MODE_ANY; // For info commands
|
xmod= MODE_ANY; // For info commands
|
||||||
DBUG_RETURN(rc);
|
DBUG_RETURN(rc);
|
||||||
} // endif MODE_ANY
|
} // endif MODE_ANY
|
||||||
|
else
|
||||||
DBUG_ASSERT(table && table->s);
|
|
||||||
|
|
||||||
if (check_privileges(thd, options, table->s->db.str)) {
|
if (check_privileges(thd, options, table->s->db.str)) {
|
||||||
strcpy(g->Message, "This operation requires the FILE privilege");
|
strcpy(g->Message, "This operation requires the FILE privilege");
|
||||||
htrc("%s\n", g->Message);
|
htrc("%s\n", g->Message);
|
||||||
DBUG_RETURN(HA_ERR_INTERNAL_ERROR);
|
DBUG_RETURN(HA_ERR_INTERNAL_ERROR);
|
||||||
} // endif check_privileges
|
} // endif check_privileges
|
||||||
|
|
||||||
|
|
||||||
|
DBUG_ASSERT(table && table->s);
|
||||||
|
|
||||||
// Table mode depends on the query type
|
// Table mode depends on the query type
|
||||||
newmode= CheckMode(g, thd, newmode, &xcheck, &cras);
|
newmode= CheckMode(g, thd, newmode, &xcheck, &cras);
|
||||||
|
|
||||||
@@ -5068,7 +5162,6 @@ static int connect_assisted_discovery(handlerton *, THD* thd,
|
|||||||
hdr= (int)topt->header;
|
hdr= (int)topt->header;
|
||||||
tbl= topt->tablist;
|
tbl= topt->tablist;
|
||||||
col= topt->colist;
|
col= topt->colist;
|
||||||
lrecl= (int)topt->lrecl;
|
|
||||||
|
|
||||||
if (topt->oplist) {
|
if (topt->oplist) {
|
||||||
host= GetListOption(g, "host", topt->oplist, "localhost");
|
host= GetListOption(g, "host", topt->oplist, "localhost");
|
||||||
@@ -5684,6 +5777,14 @@ int ha_connect::create(const char *name, TABLE *table_arg,
|
|||||||
PGLOBAL g= xp->g;
|
PGLOBAL g= xp->g;
|
||||||
|
|
||||||
DBUG_ENTER("ha_connect::create");
|
DBUG_ENTER("ha_connect::create");
|
||||||
|
/*
|
||||||
|
This assignment fixes test failures if some
|
||||||
|
"ALTER TABLE t1 ADD KEY(a)" query exits on ER_ACCESS_DENIED_ERROR
|
||||||
|
(e.g. on missing FILE_ACL). All following "CREATE TABLE" failed with
|
||||||
|
"ERROR 1105: CONNECT index modification should be in-place"
|
||||||
|
TODO: check with Olivier.
|
||||||
|
*/
|
||||||
|
g->Xchk= NULL;
|
||||||
int sqlcom= thd_sql_command(table_arg->in_use);
|
int sqlcom= thd_sql_command(table_arg->in_use);
|
||||||
PTOS options= GetTableOptionStruct(table_arg->s);
|
PTOS options= GetTableOptionStruct(table_arg->s);
|
||||||
|
|
||||||
@@ -6173,10 +6274,6 @@ bool ha_connect::FileExists(const char *fn, bool bf)
|
|||||||
int n;
|
int n;
|
||||||
struct stat info;
|
struct stat info;
|
||||||
|
|
||||||
if (check_access(ha_thd(), FILE_ACL, table->s->db.str,
|
|
||||||
NULL, NULL, 0, 0))
|
|
||||||
return true;
|
|
||||||
|
|
||||||
#if defined(__WIN__)
|
#if defined(__WIN__)
|
||||||
s= "\\";
|
s= "\\";
|
||||||
#else // !__WIN__
|
#else // !__WIN__
|
||||||
@@ -6662,10 +6759,10 @@ maria_declare_plugin(connect)
|
|||||||
PLUGIN_LICENSE_GPL,
|
PLUGIN_LICENSE_GPL,
|
||||||
connect_init_func, /* Plugin Init */
|
connect_init_func, /* Plugin Init */
|
||||||
connect_done_func, /* Plugin Deinit */
|
connect_done_func, /* Plugin Deinit */
|
||||||
0x0103, /* version number (1.03) */
|
0x0104, /* version number (1.04) */
|
||||||
NULL, /* status variables */
|
NULL, /* status variables */
|
||||||
connect_system_variables, /* system variables */
|
connect_system_variables, /* system variables */
|
||||||
"1.03.0007", /* string version */
|
"1.04.0003", /* string version */
|
||||||
MariaDB_PLUGIN_MATURITY_GAMMA /* maturity */
|
MariaDB_PLUGIN_MATURITY_BETA /* maturity */
|
||||||
}
|
}
|
||||||
maria_declare_plugin_end;
|
maria_declare_plugin_end;
|
||||||
|
@@ -241,11 +241,12 @@ public:
|
|||||||
int MakeRecord(char *buf);
|
int MakeRecord(char *buf);
|
||||||
int ScanRecord(PGLOBAL g, uchar *buf);
|
int ScanRecord(PGLOBAL g, uchar *buf);
|
||||||
int CheckRecord(PGLOBAL g, const uchar *oldbuf, uchar *newbuf);
|
int CheckRecord(PGLOBAL g, const uchar *oldbuf, uchar *newbuf);
|
||||||
int ReadIndexed(uchar *buf, OPVAL op, const uchar* key= NULL,
|
int ReadIndexed(uchar *buf, OPVAL op, const key_range *kr= NULL);
|
||||||
uint key_len= 0);
|
bool IsIndexed(Field *fp);
|
||||||
bool MakeKeyWhere(PGLOBAL g, PSTRG qry, OPVAL op, char q,
|
bool MakeKeyWhere(PGLOBAL g, PSTRG qry, OPVAL op, char q,
|
||||||
const void *key, int klen);
|
const key_range *kr);
|
||||||
inline char *Strz(LEX_STRING &ls);
|
inline char *Strz(LEX_STRING &ls);
|
||||||
|
key_range start_key;
|
||||||
|
|
||||||
|
|
||||||
/** @brief
|
/** @brief
|
||||||
@@ -374,7 +375,7 @@ public:
|
|||||||
condition stack.
|
condition stack.
|
||||||
*/
|
*/
|
||||||
virtual const COND *cond_push(const COND *cond);
|
virtual const COND *cond_push(const COND *cond);
|
||||||
PCFIL CheckCond(PGLOBAL g, PCFIL filp, AMT tty, Item *cond);
|
PCFIL CheckCond(PGLOBAL g, PCFIL filp, const Item *cond);
|
||||||
const char *GetValStr(OPVAL vop, bool neg);
|
const char *GetValStr(OPVAL vop, bool neg);
|
||||||
PFIL CondFilter(PGLOBAL g, Item *cond);
|
PFIL CondFilter(PGLOBAL g, Item *cond);
|
||||||
//PFIL CheckFilter(PGLOBAL g);
|
//PFIL CheckFilter(PGLOBAL g);
|
||||||
|
@@ -1,5 +1,5 @@
|
|||||||
/*************** json CPP Declares Source Code File (.H) ***************/
|
/*************** json CPP Declares Source Code File (.H) ***************/
|
||||||
/* Name: json.cpp Version 1.1 */
|
/* Name: json.cpp Version 1.2 */
|
||||||
/* */
|
/* */
|
||||||
/* (C) Copyright to the author Olivier BERTRAND 2014 - 2015 */
|
/* (C) Copyright to the author Olivier BERTRAND 2014 - 2015 */
|
||||||
/* */
|
/* */
|
||||||
@@ -31,11 +31,12 @@
|
|||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Parse a json string. */
|
/* Parse a json string. */
|
||||||
|
/* Note: when pretty is not known, the caller set pretty to 3. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
PJSON ParseJson(PGLOBAL g, char *s, int len, int pretty, bool *comma)
|
PJSON ParseJson(PGLOBAL g, char *s, int len, int *ptyp, bool *comma)
|
||||||
{
|
{
|
||||||
int i, rc;
|
int i, rc, pretty = (ptyp) ? *ptyp : 3;
|
||||||
bool b = false;
|
bool b = false, pty[3] = {true, true, true};
|
||||||
PJSON jsp = NULL;
|
PJSON jsp = NULL;
|
||||||
STRG src;
|
STRG src;
|
||||||
|
|
||||||
@@ -48,6 +49,10 @@ PJSON ParseJson(PGLOBAL g, char *s, int len, int pretty, bool *comma)
|
|||||||
src.str = s;
|
src.str = s;
|
||||||
src.len = len;
|
src.len = len;
|
||||||
|
|
||||||
|
// Trying to guess the pretty format
|
||||||
|
if (s[0] == '[' && (s[1] == '\n' || (s[1] == '\r' && s[2] == '\n')))
|
||||||
|
pty[0] = false;
|
||||||
|
|
||||||
// Save stack and allocation environment and prepare error return
|
// Save stack and allocation environment and prepare error return
|
||||||
if (g->jump_level == MAX_JUMP) {
|
if (g->jump_level == MAX_JUMP) {
|
||||||
strcpy(g->Message, MSG(TOO_MANY_JUMPS));
|
strcpy(g->Message, MSG(TOO_MANY_JUMPS));
|
||||||
@@ -58,21 +63,19 @@ PJSON ParseJson(PGLOBAL g, char *s, int len, int pretty, bool *comma)
|
|||||||
goto err;
|
goto err;
|
||||||
} // endif rc
|
} // endif rc
|
||||||
|
|
||||||
for (i = 0; i < len; i++)
|
for (i = 0; i < len; i++)
|
||||||
switch (s[i]) {
|
switch (s[i]) {
|
||||||
case '[':
|
case '[':
|
||||||
if (jsp) {
|
if (jsp)
|
||||||
strcpy(g->Message, "More than one item in file");
|
goto tryit;
|
||||||
goto err;
|
else if (!(jsp = ParseArray(g, ++i, src, pty)))
|
||||||
} else if (!(jsp = ParseArray(g, ++i, src)))
|
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case '{':
|
case '{':
|
||||||
if (jsp) {
|
if (jsp)
|
||||||
strcpy(g->Message, "More than one item in file");
|
goto tryit;
|
||||||
goto err;
|
else if (!(jsp = ParseObject(g, ++i, src, pty)))
|
||||||
} else if (!(jsp = ParseObject(g, ++i, src)))
|
|
||||||
goto err;
|
goto err;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@@ -82,20 +85,16 @@ PJSON ParseJson(PGLOBAL g, char *s, int len, int pretty, bool *comma)
|
|||||||
case '\r':
|
case '\r':
|
||||||
break;
|
break;
|
||||||
case ',':
|
case ',':
|
||||||
if (jsp && pretty == 1) {
|
if (jsp && (pretty == 1 || pretty == 3)) {
|
||||||
if (comma)
|
if (comma)
|
||||||
*comma = true;
|
*comma = true;
|
||||||
|
|
||||||
|
pty[0] = pty[2] = false;
|
||||||
break;
|
break;
|
||||||
} // endif pretty
|
} // endif pretty
|
||||||
|
|
||||||
sprintf(g->Message, "Unexpected ',' (pretty=%d)", pretty);
|
sprintf(g->Message, "Unexpected ',' (pretty=%d)", pretty);
|
||||||
goto err;
|
goto err;
|
||||||
case '"':
|
|
||||||
if (!(jsp = ParseValue(g, i, src)))
|
|
||||||
goto err;
|
|
||||||
|
|
||||||
break;
|
|
||||||
case '(':
|
case '(':
|
||||||
b = true;
|
b = true;
|
||||||
break;
|
break;
|
||||||
@@ -106,18 +105,41 @@ PJSON ParseJson(PGLOBAL g, char *s, int len, int pretty, bool *comma)
|
|||||||
} // endif b
|
} // endif b
|
||||||
|
|
||||||
default:
|
default:
|
||||||
sprintf(g->Message, "Bad '%c' character near %.*s",
|
if (jsp)
|
||||||
s[i], ARGS);
|
goto tryit;
|
||||||
goto err;
|
else if (!(jsp = ParseValue(g, i, src, pty)))
|
||||||
}; // endswitch s[i]
|
goto err;
|
||||||
|
|
||||||
if (!jsp)
|
break;
|
||||||
sprintf(g->Message, "Invalid Json string '%.*s'", 50, s);
|
}; // endswitch s[i]
|
||||||
|
|
||||||
|
if (!jsp)
|
||||||
|
sprintf(g->Message, "Invalid Json string '%.*s'", 50, s);
|
||||||
|
else if (ptyp && pretty == 3) {
|
||||||
|
*ptyp = 3; // Not recognized pretty
|
||||||
|
|
||||||
|
for (i = 0; i < 3; i++)
|
||||||
|
if (pty[i]) {
|
||||||
|
*ptyp = i;
|
||||||
|
break;
|
||||||
|
} // endif pty
|
||||||
|
|
||||||
|
} // endif ptyp
|
||||||
|
|
||||||
g->jump_level--;
|
g->jump_level--;
|
||||||
return jsp;
|
return jsp;
|
||||||
|
|
||||||
err:
|
tryit:
|
||||||
|
if (pty[0] && (!pretty || pretty > 2)) {
|
||||||
|
if ((jsp = ParseArray(g, (i = 0), src, pty)) && ptyp && pretty == 3)
|
||||||
|
*ptyp = (pty[0]) ? 0 : 3;
|
||||||
|
|
||||||
|
g->jump_level--;
|
||||||
|
return jsp;
|
||||||
|
} else
|
||||||
|
strcpy(g->Message, "More than one item in file");
|
||||||
|
|
||||||
|
err:
|
||||||
g->jump_level--;
|
g->jump_level--;
|
||||||
return NULL;
|
return NULL;
|
||||||
} // end of ParseJson
|
} // end of ParseJson
|
||||||
@@ -125,11 +147,12 @@ PJSON ParseJson(PGLOBAL g, char *s, int len, int pretty, bool *comma)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Parse a JSON Array. */
|
/* Parse a JSON Array. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
PJAR ParseArray(PGLOBAL g, int& i, STRG& src)
|
PJAR ParseArray(PGLOBAL g, int& i, STRG& src, bool *pty)
|
||||||
{
|
{
|
||||||
char *s = src.str;
|
char *s = src.str;
|
||||||
int len = src.len;
|
int len = src.len;
|
||||||
int level = 0;
|
int level = 0;
|
||||||
|
bool b = (!i);
|
||||||
PJAR jarp = new(g) JARRAY;
|
PJAR jarp = new(g) JARRAY;
|
||||||
PJVAL jvp = NULL;
|
PJVAL jvp = NULL;
|
||||||
|
|
||||||
@@ -151,25 +174,32 @@ PJAR ParseArray(PGLOBAL g, int& i, STRG& src)
|
|||||||
|
|
||||||
jarp->InitArray(g);
|
jarp->InitArray(g);
|
||||||
return jarp;
|
return jarp;
|
||||||
case ' ':
|
case '\n':
|
||||||
|
if (!b)
|
||||||
|
pty[0] = pty[1] = false;
|
||||||
|
case '\r':
|
||||||
|
case ' ':
|
||||||
case '\t':
|
case '\t':
|
||||||
case '\n':
|
|
||||||
case '\r':
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
if (level == 2) {
|
if (level == 2) {
|
||||||
sprintf(g->Message, "Unexpected value near %.*s", ARGS);
|
sprintf(g->Message, "Unexpected value near %.*s", ARGS);
|
||||||
return NULL;
|
return NULL;
|
||||||
} else if ((jvp = ParseValue(g, i, src))) {
|
} else if ((jvp = ParseValue(g, i, src, pty)))
|
||||||
jarp->AddValue(g, jvp);
|
jarp->AddValue(g, jvp);
|
||||||
level = 2;
|
else
|
||||||
} else
|
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
level = 2;
|
level = (b) ? 1 : 2;
|
||||||
break;
|
break;
|
||||||
}; // endswitch s[i]
|
}; // endswitch s[i]
|
||||||
|
|
||||||
|
if (b) {
|
||||||
|
// Case of Pretty == 0
|
||||||
|
jarp->InitArray(g);
|
||||||
|
return jarp;
|
||||||
|
} // endif b
|
||||||
|
|
||||||
strcpy(g->Message, "Unexpected EOF in array");
|
strcpy(g->Message, "Unexpected EOF in array");
|
||||||
return NULL;
|
return NULL;
|
||||||
} // end of ParseArray
|
} // end of ParseArray
|
||||||
@@ -177,7 +207,7 @@ PJAR ParseArray(PGLOBAL g, int& i, STRG& src)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Parse a JSON Object. */
|
/* Parse a JSON Object. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
PJOB ParseObject(PGLOBAL g, int& i, STRG& src)
|
PJOB ParseObject(PGLOBAL g, int& i, STRG& src, bool *pty)
|
||||||
{
|
{
|
||||||
PSZ key;
|
PSZ key;
|
||||||
char *s = src.str;
|
char *s = src.str;
|
||||||
@@ -204,7 +234,7 @@ PJOB ParseObject(PGLOBAL g, int& i, STRG& src)
|
|||||||
break;
|
break;
|
||||||
case ':':
|
case ':':
|
||||||
if (level == 1) {
|
if (level == 1) {
|
||||||
if (!(jpp->Val = ParseValue(g, ++i, src)))
|
if (!(jpp->Val = ParseValue(g, ++i, src, pty)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
level = 2;
|
level = 2;
|
||||||
@@ -229,10 +259,11 @@ PJOB ParseObject(PGLOBAL g, int& i, STRG& src)
|
|||||||
} // endif level
|
} // endif level
|
||||||
|
|
||||||
return jobp;
|
return jobp;
|
||||||
case ' ':
|
case '\n':
|
||||||
|
pty[0] = pty[1] = false;
|
||||||
|
case '\r':
|
||||||
|
case ' ':
|
||||||
case '\t':
|
case '\t':
|
||||||
case '\n':
|
|
||||||
case '\r':
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
sprintf(g->Message, "Unexpected character '%c' near %.*s",
|
sprintf(g->Message, "Unexpected character '%c' near %.*s",
|
||||||
@@ -247,7 +278,7 @@ PJOB ParseObject(PGLOBAL g, int& i, STRG& src)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Parse a JSON Value. */
|
/* Parse a JSON Value. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
PJVAL ParseValue(PGLOBAL g, int& i, STRG& src)
|
PJVAL ParseValue(PGLOBAL g, int& i, STRG& src, bool *pty)
|
||||||
{
|
{
|
||||||
char *strval, *s = src.str;
|
char *strval, *s = src.str;
|
||||||
int n, len = src.len;
|
int n, len = src.len;
|
||||||
@@ -255,10 +286,11 @@ PJVAL ParseValue(PGLOBAL g, int& i, STRG& src)
|
|||||||
|
|
||||||
for (; i < len; i++)
|
for (; i < len; i++)
|
||||||
switch (s[i]) {
|
switch (s[i]) {
|
||||||
case ' ':
|
case '\n':
|
||||||
|
pty[0] = pty[1] = false;
|
||||||
|
case '\r':
|
||||||
|
case ' ':
|
||||||
case '\t':
|
case '\t':
|
||||||
case '\n':
|
|
||||||
case '\r':
|
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
goto suite;
|
goto suite;
|
||||||
@@ -267,12 +299,12 @@ PJVAL ParseValue(PGLOBAL g, int& i, STRG& src)
|
|||||||
suite:
|
suite:
|
||||||
switch (s[i]) {
|
switch (s[i]) {
|
||||||
case '[':
|
case '[':
|
||||||
if (!(jvp->Jsp = ParseArray(g, ++i, src)))
|
if (!(jvp->Jsp = ParseArray(g, ++i, src, pty)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case '{':
|
case '{':
|
||||||
if (!(jvp->Jsp = ParseObject(g, ++i, src)))
|
if (!(jvp->Jsp = ParseObject(g, ++i, src, pty)))
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@@ -319,7 +351,6 @@ PJVAL ParseValue(PGLOBAL g, int& i, STRG& src)
|
|||||||
|
|
||||||
}; // endswitch s[i]
|
}; // endswitch s[i]
|
||||||
|
|
||||||
jvp->Size = 1;
|
|
||||||
return jvp;
|
return jvp;
|
||||||
|
|
||||||
err:
|
err:
|
||||||
@@ -481,9 +512,9 @@ PVAL ParseNumeric(PGLOBAL g, int& i, STRG& src)
|
|||||||
|
|
||||||
valp = AllocateValue(g, &dv, TYPE_DOUBLE, nd);
|
valp = AllocateValue(g, &dv, TYPE_DOUBLE, nd);
|
||||||
} else {
|
} else {
|
||||||
int iv = strtol(buf, NULL, 10);
|
long long iv = strtoll(buf, NULL, 10);
|
||||||
|
|
||||||
valp = AllocateValue(g, &iv, TYPE_INT);
|
valp = AllocateValue(g, &iv, TYPE_BIGINT);
|
||||||
} // endif has
|
} // endif has
|
||||||
|
|
||||||
i--; // Unstack following character
|
i--; // Unstack following character
|
||||||
@@ -501,35 +532,44 @@ PVAL ParseNumeric(PGLOBAL g, int& i, STRG& src)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Serialize a JSON tree: */
|
/* Serialize a JSON tree: */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
PSZ Serialize(PGLOBAL g, PJSON jsp, FILE *fs, int pretty)
|
PSZ Serialize(PGLOBAL g, PJSON jsp, char *fn, int pretty)
|
||||||
{
|
{
|
||||||
bool b = false, err = true;
|
bool b = false, err = true;
|
||||||
JOUT *jp;
|
JOUT *jp;
|
||||||
|
FILE *fs = NULL;
|
||||||
|
|
||||||
g->Message[0] = 0;
|
g->Message[0] = 0;
|
||||||
|
|
||||||
if (!jsp) {
|
if (!jsp) {
|
||||||
strcpy(g->Message, "Null json tree");
|
strcpy(g->Message, "Null json tree");
|
||||||
return NULL;
|
return NULL;
|
||||||
} else if (!fs) {
|
} else if (!fn) {
|
||||||
// Serialize to a string
|
// Serialize to a string
|
||||||
jp = new(g) JOUTSTR(g);
|
jp = new(g) JOUTSTR(g);
|
||||||
b = pretty == 1;
|
b = pretty == 1;
|
||||||
} else if (pretty == 2) {
|
} else {
|
||||||
// Serialize to a pretty file
|
if (!(fs = fopen(fn, "wb"))) {
|
||||||
jp = new(g) JOUTPRT(g, fs);
|
sprintf(g->Message, MSG(OPEN_MODE_ERROR),
|
||||||
} else {
|
"w", (int)errno, fn);
|
||||||
// Serialize to a flat file
|
strcat(strcat(g->Message, ": "), strerror(errno));
|
||||||
jp = new(g) JOUTFILE(g, fs);
|
return g->Message;
|
||||||
b = pretty == 1;
|
} else if (pretty >= 2) {
|
||||||
} // endif's
|
// Serialize to a pretty file
|
||||||
|
jp = new(g)JOUTPRT(g, fs);
|
||||||
|
} else {
|
||||||
|
// Serialize to a flat file
|
||||||
|
b = true;
|
||||||
|
jp = new(g)JOUTFILE(g, fs, pretty);
|
||||||
|
} // endif's
|
||||||
|
|
||||||
|
} // endif's
|
||||||
|
|
||||||
switch (jsp->GetType()) {
|
switch (jsp->GetType()) {
|
||||||
case TYPE_JAR:
|
case TYPE_JAR:
|
||||||
err = SerializeArray(jp, (PJAR)jsp, b);
|
err = SerializeArray(jp, (PJAR)jsp, b);
|
||||||
break;
|
break;
|
||||||
case TYPE_JOB:
|
case TYPE_JOB:
|
||||||
err = (b && jp->WriteChr('\t'));
|
err = ((b && jp->Prty()) && jp->WriteChr('\t'));
|
||||||
err |= SerializeObject(jp, (PJOB)jsp);
|
err |= SerializeObject(jp, (PJOB)jsp);
|
||||||
break;
|
break;
|
||||||
case TYPE_JVAL:
|
case TYPE_JVAL:
|
||||||
@@ -540,7 +580,7 @@ PSZ Serialize(PGLOBAL g, PJSON jsp, FILE *fs, int pretty)
|
|||||||
} // endswitch Type
|
} // endswitch Type
|
||||||
|
|
||||||
if (fs) {
|
if (fs) {
|
||||||
fputc('\n', fs);
|
fputs(EL, fs);
|
||||||
fclose(fs);
|
fclose(fs);
|
||||||
return (err) ? g->Message : NULL;
|
return (err) ? g->Message : NULL;
|
||||||
} else if (!err) {
|
} else if (!err) {
|
||||||
@@ -565,29 +605,40 @@ bool SerializeArray(JOUT *js, PJAR jarp, bool b)
|
|||||||
{
|
{
|
||||||
bool first = true;
|
bool first = true;
|
||||||
|
|
||||||
|
if (b) {
|
||||||
|
if (js->Prty()) {
|
||||||
|
if (js->WriteChr('['))
|
||||||
|
return true;
|
||||||
|
else if (js->Prty() == 1 && (js->WriteStr(EL) || js->WriteChr('\t')))
|
||||||
|
return true;
|
||||||
|
|
||||||
if (js->WriteChr('['))
|
} // endif Prty
|
||||||
return true;
|
|
||||||
else if (b && (js->WriteStr(EL) || js->WriteChr('\t')))
|
} else if (js->WriteChr('['))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
for (int i = 0; i < jarp->size(); i++) {
|
for (int i = 0; i < jarp->size(); i++) {
|
||||||
if (first)
|
if (first)
|
||||||
first = false;
|
first = false;
|
||||||
else if (js->WriteChr(','))
|
else if ((!b || js->Prty()) && js->WriteChr(','))
|
||||||
return true;
|
|
||||||
else if (b && (js->WriteStr(EL) || js->WriteChr('\t')))
|
|
||||||
return true;
|
return true;
|
||||||
|
else if (b) {
|
||||||
|
if (js->Prty() < 2 && js->WriteStr(EL))
|
||||||
|
return true;
|
||||||
|
else if (js->Prty() == 1 && js->WriteChr('\t'))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
} // endif b
|
||||||
|
|
||||||
if (SerializeValue(js, jarp->GetValue(i)))
|
if (SerializeValue(js, jarp->GetValue(i)))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
} // endfor i
|
} // endfor i
|
||||||
|
|
||||||
if (b && js->WriteStr(EL))
|
if (b && js->Prty() == 1 && js->WriteStr(EL))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
return js->WriteChr(']');
|
return ((!b || js->Prty()) && js->WriteChr(']'));
|
||||||
} // end of SerializeArray
|
} // end of SerializeArray
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -647,8 +698,8 @@ bool SerializeValue(JOUT *js, PJVAL jvp)
|
|||||||
|
|
||||||
} // endswitch Type
|
} // endswitch Type
|
||||||
|
|
||||||
strcpy(js->g->Message, "Unrecognized value");
|
strcpy(js->g->Message, "Unrecognized value");
|
||||||
return true;
|
return true;
|
||||||
} // end of SerializeValue
|
} // end of SerializeValue
|
||||||
|
|
||||||
/* -------------------------- Class JOUTSTR -------------------------- */
|
/* -------------------------- Class JOUTSTR -------------------------- */
|
||||||
@@ -866,6 +917,20 @@ PJPR JOBJECT::AddPair(PGLOBAL g, PSZ key)
|
|||||||
return jpp;
|
return jpp;
|
||||||
} // end of AddPair
|
} // end of AddPair
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Return all keys as an array. */
|
||||||
|
/***********************************************************************/
|
||||||
|
PJAR JOBJECT::GetKeyList(PGLOBAL g)
|
||||||
|
{
|
||||||
|
PJAR jarp = new(g) JARRAY();
|
||||||
|
|
||||||
|
for (PJPR jpp = First; jpp; jpp = jpp->Next)
|
||||||
|
jarp->AddValue(g, new(g) JVALUE(g, jpp->GetKey()));
|
||||||
|
|
||||||
|
jarp->InitArray(g);
|
||||||
|
return jarp;
|
||||||
|
} // end of GetKeyList
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Get the value corresponding to the given key. */
|
/* Get the value corresponding to the given key. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -903,12 +968,30 @@ PSZ JOBJECT::GetText(PGLOBAL g, PSZ text)
|
|||||||
return text + n;
|
return text + n;
|
||||||
} // end of GetValue;
|
} // end of GetValue;
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Merge two objects. */
|
||||||
|
/***********************************************************************/
|
||||||
|
bool JOBJECT::Merge(PGLOBAL g, PJSON jsp)
|
||||||
|
{
|
||||||
|
if (jsp->GetType() != TYPE_JOB) {
|
||||||
|
strcpy(g->Message, "Second argument is not an object");
|
||||||
|
return true;
|
||||||
|
} // endif Type
|
||||||
|
|
||||||
|
PJOB jobp = (PJOB)jsp;
|
||||||
|
|
||||||
|
for (PJPR jpp = jobp->First; jpp; jpp = jpp->Next)
|
||||||
|
SetValue(g, jpp->GetVal(), jpp->GetKey());
|
||||||
|
|
||||||
|
return false;
|
||||||
|
} // end of Marge;
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Set or add a value corresponding to the given key. */
|
/* Set or add a value corresponding to the given key. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
void JOBJECT::SetValue(PGLOBAL g, PJVAL jvp, PSZ key)
|
void JOBJECT::SetValue(PGLOBAL g, PJVAL jvp, PSZ key)
|
||||||
{
|
{
|
||||||
PJPR jp;
|
PJPR jp;
|
||||||
|
|
||||||
for (jp = First; jp; jp = jp->Next)
|
for (jp = First; jp; jp = jp->Next)
|
||||||
if (!strcmp(jp->Key, key)) {
|
if (!strcmp(jp->Key, key)) {
|
||||||
@@ -923,6 +1006,23 @@ void JOBJECT::SetValue(PGLOBAL g, PJVAL jvp, PSZ key)
|
|||||||
|
|
||||||
} // end of SetValue
|
} // end of SetValue
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Delete a value corresponding to the given key. */
|
||||||
|
/***********************************************************************/
|
||||||
|
void JOBJECT::DeleteKey(PSZ key)
|
||||||
|
{
|
||||||
|
PJPR jp, *pjp = &First;
|
||||||
|
|
||||||
|
for (jp = First; jp; jp = jp->Next)
|
||||||
|
if (!strcmp(jp->Key, key)) {
|
||||||
|
*pjp = jp->Next;
|
||||||
|
Size--;
|
||||||
|
break;
|
||||||
|
} else
|
||||||
|
pjp = &jp->Next;
|
||||||
|
|
||||||
|
} // end of DeleteKey
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* True if void or if all members are nulls. */
|
/* True if void or if all members are nulls. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -943,23 +1043,25 @@ bool JOBJECT::IsNull(void)
|
|||||||
void JARRAY::InitArray(PGLOBAL g)
|
void JARRAY::InitArray(PGLOBAL g)
|
||||||
{
|
{
|
||||||
int i;
|
int i;
|
||||||
PJVAL jvp;
|
PJVAL jvp, *pjvp = &First;
|
||||||
|
|
||||||
for (Size = 0, jvp = First; jvp; jvp = jvp->Next)
|
for (Size = 0, jvp = First; jvp; jvp = jvp->Next)
|
||||||
if (!jvp->Del)
|
if (!jvp->Del)
|
||||||
Size++;
|
Size++;
|
||||||
|
|
||||||
if (!Size) {
|
if (Size > Alloc) {
|
||||||
return;
|
|
||||||
} else if (Size > Alloc) {
|
|
||||||
// No need to realloc after deleting values
|
// No need to realloc after deleting values
|
||||||
Mvals = (PJVAL*)PlugSubAlloc(g, NULL, Size * sizeof(PJVAL));
|
Mvals = (PJVAL*)PlugSubAlloc(g, NULL, Size * sizeof(PJVAL));
|
||||||
Alloc = Size;
|
Alloc = Size;
|
||||||
} // endif Size
|
} // endif Size
|
||||||
|
|
||||||
for (i = 0, jvp = First; jvp; jvp = jvp->Next)
|
for (i = 0, jvp = First; jvp; jvp = jvp->Next)
|
||||||
if (!jvp->Del)
|
if (!jvp->Del) {
|
||||||
Mvals[i++] = jvp;
|
Mvals[i++] = jvp;
|
||||||
|
pjvp = &jvp->Next;
|
||||||
|
Last = jvp;
|
||||||
|
} else
|
||||||
|
*pjvp = jvp->Next;
|
||||||
|
|
||||||
} // end of InitArray
|
} // end of InitArray
|
||||||
|
|
||||||
@@ -975,31 +1077,66 @@ PJVAL JARRAY::GetValue(int i)
|
|||||||
} // end of GetValue
|
} // end of GetValue
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Add a Value to the Arrays Value list. */
|
/* Add a Value to the Array Value list. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
PJVAL JARRAY::AddValue(PGLOBAL g, PJVAL jvp)
|
PJVAL JARRAY::AddValue(PGLOBAL g, PJVAL jvp, int *x)
|
||||||
{
|
{
|
||||||
if (!jvp)
|
if (!jvp)
|
||||||
jvp = new(g) JVALUE;
|
jvp = new(g) JVALUE;
|
||||||
|
|
||||||
if (Last)
|
if (x) {
|
||||||
Last->Next = jvp;
|
int i = 0, n = *x;
|
||||||
else
|
PJVAL jp, *jpp = &First;
|
||||||
First = jvp;
|
|
||||||
|
for (jp = First; jp && i < n; i++, jp = *(jpp = &jp->Next));
|
||||||
|
|
||||||
|
(*jpp) = jvp;
|
||||||
|
|
||||||
|
if (!(jvp->Next = jp))
|
||||||
|
Last = jvp;
|
||||||
|
|
||||||
|
} else {
|
||||||
|
if (!First)
|
||||||
|
First = jvp;
|
||||||
|
else if (Last == First)
|
||||||
|
First->Next = Last = jvp;
|
||||||
|
else
|
||||||
|
Last->Next = jvp;
|
||||||
|
|
||||||
|
Last = jvp;
|
||||||
|
} // endif x
|
||||||
|
|
||||||
Last = jvp;
|
|
||||||
return jvp;
|
return jvp;
|
||||||
} // end of AddValue
|
} // end of AddValue
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Add a Value to the Arrays Value list. */
|
/* Merge two arrays. */
|
||||||
|
/***********************************************************************/
|
||||||
|
bool JARRAY::Merge(PGLOBAL g, PJSON jsp)
|
||||||
|
{
|
||||||
|
if (jsp->GetType() != TYPE_JAR) {
|
||||||
|
strcpy(g->Message, "Second argument is not an array");
|
||||||
|
return true;
|
||||||
|
} // endif Type
|
||||||
|
|
||||||
|
PJAR arp = (PJAR)jsp;
|
||||||
|
|
||||||
|
for (int i = 0; i < jsp->size(); i++)
|
||||||
|
AddValue(g, arp->GetValue(i));
|
||||||
|
|
||||||
|
InitArray(g);
|
||||||
|
return false;
|
||||||
|
} // end of Merge
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Set the nth Value of the Array Value list. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
bool JARRAY::SetValue(PGLOBAL g, PJVAL jvp, int n)
|
bool JARRAY::SetValue(PGLOBAL g, PJVAL jvp, int n)
|
||||||
{
|
{
|
||||||
int i = 0;
|
int i = 0;
|
||||||
PJVAL jp, *jpp = &First;
|
PJVAL jp, *jpp = &First;
|
||||||
|
|
||||||
for (i = 0, jp = First; i < n; i++, jp = *(jpp = &jp->Next))
|
for (jp = First; i < n; i++, jp = *(jpp = &jp->Next))
|
||||||
if (!jp)
|
if (!jp)
|
||||||
*jpp = jp = new(g) JVALUE;
|
*jpp = jp = new(g) JVALUE;
|
||||||
|
|
||||||
@@ -1048,6 +1185,17 @@ JVALUE::JVALUE(PGLOBAL g, PVAL valp) : JSON()
|
|||||||
Del = false;
|
Del = false;
|
||||||
} // end of JVALUE constructor
|
} // end of JVALUE constructor
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Constructor for a given string. */
|
||||||
|
/***********************************************************************/
|
||||||
|
JVALUE::JVALUE(PGLOBAL g, PSZ strp) : JSON()
|
||||||
|
{
|
||||||
|
Jsp = NULL;
|
||||||
|
Value = AllocateValue(g, strp, TYPE_STRING);
|
||||||
|
Next = NULL;
|
||||||
|
Del = false;
|
||||||
|
} // end of JVALUE constructor
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Returns the type of the Value's value. */
|
/* Returns the type of the Value's value. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -1092,6 +1240,14 @@ int JVALUE::GetInteger(void)
|
|||||||
return (Value) ? Value->GetIntValue() : 0;
|
return (Value) ? Value->GetIntValue() : 0;
|
||||||
} // end of GetInteger
|
} // end of GetInteger
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Return the Value's Big integer value. */
|
||||||
|
/***********************************************************************/
|
||||||
|
long long JVALUE::GetBigint(void)
|
||||||
|
{
|
||||||
|
return (Value) ? Value->GetBigintValue() : 0;
|
||||||
|
} // end of GetBigint
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Return the Value's Double value. */
|
/* Return the Value's Double value. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -1128,13 +1284,44 @@ PSZ JVALUE::GetText(PGLOBAL g, PSZ text)
|
|||||||
return text;
|
return text;
|
||||||
} // end of GetText
|
} // end of GetText
|
||||||
|
|
||||||
|
void JVALUE::SetValue(PJSON jsp)
|
||||||
|
{
|
||||||
|
if (jsp && jsp->GetType() == TYPE_JVAL) {
|
||||||
|
Jsp = jsp->GetJsp();
|
||||||
|
Value = jsp->GetValue();
|
||||||
|
} else {
|
||||||
|
Jsp = jsp;
|
||||||
|
Value = NULL;
|
||||||
|
} // endif Type
|
||||||
|
|
||||||
|
} // end of SetValue;
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Set the Value's value as the given integer. */
|
/* Set the Value's value as the given integer. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
void JVALUE::SetInteger(PGLOBAL g, int n)
|
void JVALUE::SetInteger(PGLOBAL g, int n)
|
||||||
{
|
{
|
||||||
Value = AllocateValue(g, &n, TYPE_INT);
|
Value = AllocateValue(g, &n, TYPE_INT);
|
||||||
} // end of AddInteger
|
Jsp = NULL;
|
||||||
|
} // end of SetInteger
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Set the Value's Boolean value as a tiny integer. */
|
||||||
|
/***********************************************************************/
|
||||||
|
void JVALUE::SetTiny(PGLOBAL g, char n)
|
||||||
|
{
|
||||||
|
Value = AllocateValue(g, &n, TYPE_TINY);
|
||||||
|
Jsp = NULL;
|
||||||
|
} // end of SetInteger
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Set the Value's value as the given big integer. */
|
||||||
|
/***********************************************************************/
|
||||||
|
void JVALUE::SetBigint(PGLOBAL g, long long ll)
|
||||||
|
{
|
||||||
|
Value = AllocateValue(g, &ll, TYPE_BIGINT);
|
||||||
|
Jsp = NULL;
|
||||||
|
} // end of SetBigint
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Set the Value's value as the given DOUBLE. */
|
/* Set the Value's value as the given DOUBLE. */
|
||||||
@@ -1142,15 +1329,17 @@ void JVALUE::SetInteger(PGLOBAL g, int n)
|
|||||||
void JVALUE::SetFloat(PGLOBAL g, double f)
|
void JVALUE::SetFloat(PGLOBAL g, double f)
|
||||||
{
|
{
|
||||||
Value = AllocateValue(g, &f, TYPE_DOUBLE, 6);
|
Value = AllocateValue(g, &f, TYPE_DOUBLE, 6);
|
||||||
} // end of AddFloat
|
Jsp = NULL;
|
||||||
|
} // end of SetFloat
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Set the Value's value as the given string. */
|
/* Set the Value's value as the given string. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
void JVALUE::SetString(PGLOBAL g, PSZ s)
|
void JVALUE::SetString(PGLOBAL g, PSZ s, short c)
|
||||||
{
|
{
|
||||||
Value = AllocateValue(g, s, TYPE_STRING);
|
Value = AllocateValue(g, s, TYPE_STRING, c);
|
||||||
} // end of AddFloat
|
Jsp = NULL;
|
||||||
|
} // end of SetString
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* True when its JSON or normal value is null. */
|
/* True when its JSON or normal value is null. */
|
||||||
|
@@ -1,5 +1,5 @@
|
|||||||
/**************** json H Declares Source Code File (.H) ****************/
|
/**************** json H Declares Source Code File (.H) ****************/
|
||||||
/* Name: json.h Version 1.1 */
|
/* Name: json.h Version 1.2 */
|
||||||
/* */
|
/* */
|
||||||
/* (C) Copyright to the author Olivier BERTRAND 2014 - 2015 */
|
/* (C) Copyright to the author Olivier BERTRAND 2014 - 2015 */
|
||||||
/* */
|
/* */
|
||||||
@@ -16,8 +16,9 @@
|
|||||||
enum JTYP {TYPE_STRG = 1,
|
enum JTYP {TYPE_STRG = 1,
|
||||||
TYPE_DBL = 2,
|
TYPE_DBL = 2,
|
||||||
TYPE_BOOL = 4,
|
TYPE_BOOL = 4,
|
||||||
TYPE_INTG = 7,
|
TYPE_BINT = 5,
|
||||||
TYPE_JSON = 12,
|
TYPE_INTG = 7,
|
||||||
|
TYPE_JSON = 12,
|
||||||
TYPE_JAR,
|
TYPE_JAR,
|
||||||
TYPE_JOB,
|
TYPE_JOB,
|
||||||
TYPE_JVAL};
|
TYPE_JVAL};
|
||||||
@@ -40,13 +41,13 @@ typedef struct {
|
|||||||
int len;
|
int len;
|
||||||
} STRG, *PSG;
|
} STRG, *PSG;
|
||||||
|
|
||||||
PJSON ParseJson(PGLOBAL g, char *s, int n, int prty, bool *b = NULL);
|
PJSON ParseJson(PGLOBAL g, char *s, int n, int *prty = NULL, bool *b = NULL);
|
||||||
PJAR ParseArray(PGLOBAL g, int& i, STRG& src);
|
PJAR ParseArray(PGLOBAL g, int& i, STRG& src, bool *pty);
|
||||||
PJOB ParseObject(PGLOBAL g, int& i, STRG& src);
|
PJOB ParseObject(PGLOBAL g, int& i, STRG& src, bool *pty);
|
||||||
PJVAL ParseValue(PGLOBAL g, int& i, STRG& src);
|
PJVAL ParseValue(PGLOBAL g, int& i, STRG& src, bool *pty);
|
||||||
char *ParseString(PGLOBAL g, int& i, STRG& src);
|
char *ParseString(PGLOBAL g, int& i, STRG& src);
|
||||||
PVAL ParseNumeric(PGLOBAL g, int& i, STRG& src);
|
PVAL ParseNumeric(PGLOBAL g, int& i, STRG& src);
|
||||||
PSZ Serialize(PGLOBAL g, PJSON jsp, FILE *fs, int pretty);
|
PSZ Serialize(PGLOBAL g, PJSON jsp, char *fn, int pretty);
|
||||||
bool SerializeArray(JOUT *js, PJAR jarp, bool b);
|
bool SerializeArray(JOUT *js, PJAR jarp, bool b);
|
||||||
bool SerializeObject(JOUT *js, PJOB jobp);
|
bool SerializeObject(JOUT *js, PJOB jobp);
|
||||||
bool SerializeValue(JOUT *js, PJVAL jvp);
|
bool SerializeValue(JOUT *js, PJVAL jvp);
|
||||||
@@ -56,14 +57,16 @@ bool SerializeValue(JOUT *js, PJVAL jvp);
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
class JOUT : public BLOCK {
|
class JOUT : public BLOCK {
|
||||||
public:
|
public:
|
||||||
JOUT(PGLOBAL gp) : BLOCK() {g = gp;}
|
JOUT(PGLOBAL gp) : BLOCK() {g = gp; Pretty = 3;}
|
||||||
|
|
||||||
virtual bool WriteStr(const char *s) = 0;
|
virtual bool WriteStr(const char *s) = 0;
|
||||||
virtual bool WriteChr(const char c) = 0;
|
virtual bool WriteChr(const char c) = 0;
|
||||||
virtual bool Escape(const char *s) = 0;
|
virtual bool Escape(const char *s) = 0;
|
||||||
|
int Prty(void) {return Pretty;}
|
||||||
|
|
||||||
// Member
|
// Member
|
||||||
PGLOBAL g;
|
PGLOBAL g;
|
||||||
|
int Pretty;
|
||||||
}; // end of class JOUT
|
}; // end of class JOUT
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -88,7 +91,7 @@ class JOUTSTR : public JOUT {
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
class JOUTFILE : public JOUT {
|
class JOUTFILE : public JOUT {
|
||||||
public:
|
public:
|
||||||
JOUTFILE(PGLOBAL g, FILE *str) : JOUT(g) {Stream = str;}
|
JOUTFILE(PGLOBAL g, FILE *str, int pty) : JOUT(g) {Stream = str; Pretty = pty;}
|
||||||
|
|
||||||
virtual bool WriteStr(const char *s);
|
virtual bool WriteStr(const char *s);
|
||||||
virtual bool WriteChr(const char c);
|
virtual bool WriteChr(const char c);
|
||||||
@@ -103,7 +106,7 @@ class JOUTFILE : public JOUT {
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
class JOUTPRT : public JOUTFILE {
|
class JOUTPRT : public JOUTFILE {
|
||||||
public:
|
public:
|
||||||
JOUTPRT(PGLOBAL g, FILE *str) : JOUTFILE(g, str) {M = 0; B = false;}
|
JOUTPRT(PGLOBAL g, FILE *str) : JOUTFILE(g, str, 2) {M = 0; B = false;}
|
||||||
|
|
||||||
virtual bool WriteStr(const char *s);
|
virtual bool WriteStr(const char *s);
|
||||||
virtual bool WriteChr(const char c);
|
virtual bool WriteChr(const char c);
|
||||||
@@ -118,7 +121,8 @@ class JOUTPRT : public JOUTFILE {
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
class JPAIR : public BLOCK {
|
class JPAIR : public BLOCK {
|
||||||
friend class JOBJECT;
|
friend class JOBJECT;
|
||||||
friend PJOB ParseObject(PGLOBAL, int&, STRG&);
|
friend class JSNX;
|
||||||
|
friend PJOB ParseObject(PGLOBAL, int&, STRG&, bool*);
|
||||||
friend bool SerializeObject(JOUT *, PJOB);
|
friend bool SerializeObject(JOUT *, PJOB);
|
||||||
public:
|
public:
|
||||||
JPAIR(PSZ key) : BLOCK() {Key = key; Val = NULL; Next = NULL;}
|
JPAIR(PSZ key) : BLOCK() {Key = key; Val = NULL; Next = NULL;}
|
||||||
@@ -145,28 +149,32 @@ class JSON : public BLOCK {
|
|||||||
virtual JTYP GetType(void) {return TYPE_JSON;}
|
virtual JTYP GetType(void) {return TYPE_JSON;}
|
||||||
virtual JTYP GetValType(void) {X return TYPE_JSON;}
|
virtual JTYP GetValType(void) {X return TYPE_JSON;}
|
||||||
virtual void InitArray(PGLOBAL g) {X}
|
virtual void InitArray(PGLOBAL g) {X}
|
||||||
virtual PJVAL AddValue(PGLOBAL g, PJVAL jvp = NULL) {X return NULL;}
|
//virtual PJVAL AddValue(PGLOBAL g, PJVAL jvp = NULL, int *x = NULL) {X return NULL;}
|
||||||
virtual PJPR AddPair(PGLOBAL g, PSZ key) {X return NULL;}
|
virtual PJPR AddPair(PGLOBAL g, PSZ key) {X return NULL;}
|
||||||
virtual PJVAL GetValue(const char *key) {X return NULL;}
|
virtual PJAR GetKeyList(PGLOBAL g) {X return NULL;}
|
||||||
|
virtual PJVAL GetValue(const char *key) {X return NULL;}
|
||||||
virtual PJOB GetObject(void) {return NULL;}
|
virtual PJOB GetObject(void) {return NULL;}
|
||||||
virtual PJAR GetArray(void) {return NULL;}
|
virtual PJAR GetArray(void) {return NULL;}
|
||||||
virtual PJVAL GetValue(int i) {X return NULL;}
|
virtual PJVAL GetValue(int i) {X return NULL;}
|
||||||
virtual PVAL GetValue(void) {X return NULL;}
|
virtual PVAL GetValue(void) {X return NULL;}
|
||||||
virtual PJSON GetJson(void) {X return NULL;}
|
virtual PJSON GetJsp(void) { X return NULL; }
|
||||||
|
virtual PJSON GetJson(void) { X return NULL; }
|
||||||
virtual PJPR GetFirst(void) {X return NULL;}
|
virtual PJPR GetFirst(void) {X return NULL;}
|
||||||
virtual int GetInteger(void) {X return 0;}
|
virtual int GetInteger(void) {X return 0;}
|
||||||
virtual double GetFloat() {X return 0.0;}
|
virtual double GetFloat() {X return 0.0;}
|
||||||
virtual PSZ GetString() {X return NULL;}
|
virtual PSZ GetString() {X return NULL;}
|
||||||
virtual PSZ GetText(PGLOBAL g, PSZ text) {X return NULL;}
|
virtual PSZ GetText(PGLOBAL g, PSZ text) {X return NULL;}
|
||||||
virtual bool SetValue(PGLOBAL g, PJVAL jvp, int i) {X return true;}
|
virtual bool Merge(PGLOBAL g, PJSON jsp) { X return true; }
|
||||||
|
virtual bool SetValue(PGLOBAL g, PJVAL jvp, int i) { X return true; }
|
||||||
virtual void SetValue(PGLOBAL g, PJVAL jvp, PSZ key) {X}
|
virtual void SetValue(PGLOBAL g, PJVAL jvp, PSZ key) {X}
|
||||||
virtual void SetValue(PVAL valp) {X}
|
virtual void SetValue(PVAL valp) {X}
|
||||||
virtual void SetValue(PJSON jsp) {X}
|
virtual void SetValue(PJSON jsp) {X}
|
||||||
virtual void SetString(PGLOBAL g, PSZ s) {X}
|
virtual void SetString(PGLOBAL g, PSZ s, short c) {X}
|
||||||
virtual void SetInteger(PGLOBAL g, int n) {X}
|
virtual void SetInteger(PGLOBAL g, int n) {X}
|
||||||
virtual void SetFloat(PGLOBAL g, double f) {X}
|
virtual void SetFloat(PGLOBAL g, double f) {X}
|
||||||
virtual bool DeleteValue(int i) {X return true;}
|
virtual void DeleteKey(char *k) {X}
|
||||||
virtual bool IsNull(void) {X return true;}
|
virtual bool DeleteValue(int i) {X return true;}
|
||||||
|
virtual bool IsNull(void) {X return true;}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
int Size;
|
int Size;
|
||||||
@@ -176,8 +184,9 @@ class JSON : public BLOCK {
|
|||||||
/* Class JOBJECT: contains a list of value pairs. */
|
/* Class JOBJECT: contains a list of value pairs. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
class JOBJECT : public JSON {
|
class JOBJECT : public JSON {
|
||||||
friend PJOB ParseObject(PGLOBAL, int&, STRG&);
|
friend PJOB ParseObject(PGLOBAL, int&, STRG&, bool*);
|
||||||
friend bool SerializeObject(JOUT *, PJOB);
|
friend bool SerializeObject(JOUT *, PJOB);
|
||||||
|
friend class JSNX;
|
||||||
public:
|
public:
|
||||||
JOBJECT(void) : JSON() {First = Last = NULL;}
|
JOBJECT(void) : JSON() {First = Last = NULL;}
|
||||||
|
|
||||||
@@ -189,9 +198,12 @@ class JOBJECT : public JSON {
|
|||||||
virtual PJPR AddPair(PGLOBAL g, PSZ key);
|
virtual PJPR AddPair(PGLOBAL g, PSZ key);
|
||||||
virtual PJOB GetObject(void) {return this;}
|
virtual PJOB GetObject(void) {return this;}
|
||||||
virtual PJVAL GetValue(const char* key);
|
virtual PJVAL GetValue(const char* key);
|
||||||
virtual PSZ GetText(PGLOBAL g, PSZ text);
|
virtual PJAR GetKeyList(PGLOBAL g);
|
||||||
virtual void SetValue(PGLOBAL g, PJVAL jvp, PSZ key);
|
virtual PSZ GetText(PGLOBAL g, PSZ text);
|
||||||
virtual bool IsNull(void);
|
virtual bool Merge(PGLOBAL g, PJSON jsp);
|
||||||
|
virtual void SetValue(PGLOBAL g, PJVAL jvp, PSZ key);
|
||||||
|
virtual void DeleteKey(char *k);
|
||||||
|
virtual bool IsNull(void);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
PJPR First;
|
PJPR First;
|
||||||
@@ -202,7 +214,7 @@ class JOBJECT : public JSON {
|
|||||||
/* Class JARRAY. */
|
/* Class JARRAY. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
class JARRAY : public JSON {
|
class JARRAY : public JSON {
|
||||||
friend PJAR ParseArray(PGLOBAL, int&, STRG&);
|
friend PJAR ParseArray(PGLOBAL, int&, STRG&, bool*);
|
||||||
public:
|
public:
|
||||||
JARRAY(void) : JSON() {Alloc = 0; First = Last = NULL; Mvals = NULL;}
|
JARRAY(void) : JSON() {Alloc = 0; First = Last = NULL; Mvals = NULL;}
|
||||||
|
|
||||||
@@ -211,10 +223,11 @@ class JARRAY : public JSON {
|
|||||||
virtual void Clear(void) {First = Last = NULL; Size = 0;}
|
virtual void Clear(void) {First = Last = NULL; Size = 0;}
|
||||||
virtual JTYP GetType(void) {return TYPE_JAR;}
|
virtual JTYP GetType(void) {return TYPE_JAR;}
|
||||||
virtual PJAR GetArray(void) {return this;}
|
virtual PJAR GetArray(void) {return this;}
|
||||||
virtual PJVAL AddValue(PGLOBAL g, PJVAL jvp = NULL);
|
PJVAL AddValue(PGLOBAL g, PJVAL jvp = NULL, int *x = NULL);
|
||||||
virtual void InitArray(PGLOBAL g);
|
virtual void InitArray(PGLOBAL g);
|
||||||
virtual PJVAL GetValue(int i);
|
virtual PJVAL GetValue(int i);
|
||||||
virtual bool SetValue(PGLOBAL g, PJVAL jvp, int i);
|
virtual bool Merge(PGLOBAL g, PJSON jsp);
|
||||||
|
virtual bool SetValue(PGLOBAL g, PJVAL jvp, int i);
|
||||||
virtual bool DeleteValue(int n);
|
virtual bool DeleteValue(int n);
|
||||||
virtual bool IsNull(void);
|
virtual bool IsNull(void);
|
||||||
|
|
||||||
@@ -231,7 +244,8 @@ class JARRAY : public JSON {
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
class JVALUE : public JSON {
|
class JVALUE : public JSON {
|
||||||
friend class JARRAY;
|
friend class JARRAY;
|
||||||
friend PJVAL ParseValue(PGLOBAL, int&, STRG&);
|
friend class JSNX;
|
||||||
|
friend PJVAL ParseValue(PGLOBAL, int&, STRG&, bool*);
|
||||||
friend bool SerializeValue(JOUT *, PJVAL);
|
friend bool SerializeValue(JOUT *, PJVAL);
|
||||||
public:
|
public:
|
||||||
JVALUE(void) : JSON()
|
JVALUE(void) : JSON()
|
||||||
@@ -239,6 +253,7 @@ class JVALUE : public JSON {
|
|||||||
JVALUE(PJSON jsp) : JSON()
|
JVALUE(PJSON jsp) : JSON()
|
||||||
{Jsp = jsp; Value = NULL; Next = NULL; Del = false;}
|
{Jsp = jsp; Value = NULL; Next = NULL; Del = false;}
|
||||||
JVALUE(PGLOBAL g, PVAL valp);
|
JVALUE(PGLOBAL g, PVAL valp);
|
||||||
|
JVALUE(PGLOBAL g, PSZ strp);
|
||||||
|
|
||||||
using JSON::GetValue;
|
using JSON::GetValue;
|
||||||
using JSON::SetValue;
|
using JSON::SetValue;
|
||||||
@@ -249,17 +264,21 @@ class JVALUE : public JSON {
|
|||||||
virtual PJOB GetObject(void);
|
virtual PJOB GetObject(void);
|
||||||
virtual PJAR GetArray(void);
|
virtual PJAR GetArray(void);
|
||||||
virtual PVAL GetValue(void) {return Value;}
|
virtual PVAL GetValue(void) {return Value;}
|
||||||
virtual PJSON GetJson(void) {return (Jsp ? Jsp : this);}
|
virtual PJSON GetJsp(void) {return Jsp;}
|
||||||
virtual int GetInteger(void);
|
virtual PJSON GetJson(void) { return (Jsp ? Jsp : this); }
|
||||||
virtual double GetFloat(void);
|
virtual int GetInteger(void);
|
||||||
|
virtual long long GetBigint(void);
|
||||||
|
virtual double GetFloat(void);
|
||||||
virtual PSZ GetString(void);
|
virtual PSZ GetString(void);
|
||||||
virtual PSZ GetText(PGLOBAL g, PSZ text);
|
virtual PSZ GetText(PGLOBAL g, PSZ text);
|
||||||
virtual void SetValue(PVAL valp) {Value = valp;}
|
virtual void SetValue(PJSON jsp);
|
||||||
virtual void SetValue(PJSON jsp) {Jsp = jsp;}
|
virtual void SetValue(PVAL valp) { Value = valp; Jsp = NULL; }
|
||||||
virtual void SetString(PGLOBAL g, PSZ s);
|
virtual void SetString(PGLOBAL g, PSZ s, short c = 0);
|
||||||
virtual void SetInteger(PGLOBAL g, int n);
|
virtual void SetInteger(PGLOBAL g, int n);
|
||||||
virtual void SetFloat(PGLOBAL g, double f);
|
virtual void SetBigint(PGLOBAL g, longlong ll);
|
||||||
virtual bool IsNull(void);
|
virtual void SetFloat(PGLOBAL g, double f);
|
||||||
|
virtual void SetTiny(PGLOBAL g, char f);
|
||||||
|
virtual bool IsNull(void);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
PJSON Jsp; // To the json value
|
PJSON Jsp; // To the json value
|
||||||
|
File diff suppressed because it is too large
Load Diff
292
storage/connect/jsonudf.h
Normal file
292
storage/connect/jsonudf.h
Normal file
@@ -0,0 +1,292 @@
|
|||||||
|
/******************** tabjson H Declares Source Code File (.H) *******************/
|
||||||
|
/* Name: jsonudf.h Version 1.2 */
|
||||||
|
/* */
|
||||||
|
/* (C) Copyright to the author Olivier BERTRAND 2015 */
|
||||||
|
/* */
|
||||||
|
/* This file contains the JSON UDF function and class declares. */
|
||||||
|
/*********************************************************************************/
|
||||||
|
#include "global.h"
|
||||||
|
#include "plgdbsem.h"
|
||||||
|
#include "block.h"
|
||||||
|
#include "osutil.h"
|
||||||
|
#include "maputil.h"
|
||||||
|
#include "json.h"
|
||||||
|
|
||||||
|
#define UDF_EXEC_ARGS \
|
||||||
|
UDF_INIT*, UDF_ARGS*, char*, unsigned long*, char*, char*
|
||||||
|
|
||||||
|
/*********************************************************************************/
|
||||||
|
/* The JSON tree node. Can be an Object or an Array. */
|
||||||
|
/*********************************************************************************/
|
||||||
|
typedef struct _jnode {
|
||||||
|
PSZ Key; // The key used for object
|
||||||
|
OPVAL Op; // Operator used for this node
|
||||||
|
PVAL CncVal; // To cont value used for OP_CNC
|
||||||
|
PVAL Valp; // The internal array VALUE
|
||||||
|
int Rank; // The rank in array
|
||||||
|
int Rx; // Read row number
|
||||||
|
int Nx; // Next to read row number
|
||||||
|
} JNODE, *PJNODE;
|
||||||
|
|
||||||
|
typedef class JSNX *PJSNX;
|
||||||
|
typedef class JOUTPATH *PJTP;
|
||||||
|
typedef class JOUTALL *PJTA;
|
||||||
|
|
||||||
|
extern "C" {
|
||||||
|
DllExport my_bool jsonvalue_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jsonvalue(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jsonvalue_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_array_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_array(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_array_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_array_add_values_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_array_add_values(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_array_add_values_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_array_add_init(UDF_INIT*, UDF_ARGS*, 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_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_EXEC_ARGS);
|
||||||
|
DllExport void json_object_nonull_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_object_key_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_object_key(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_object_key_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_object_add_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_object_add(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_object_add_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_object_delete_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_object_delete(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_object_delete_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_object_list_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_object_list(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_object_list_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_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_EXEC_ARGS);
|
||||||
|
DllExport void json_object_grp_clear(UDF_INIT *, char *, char *);
|
||||||
|
DllExport void json_object_grp_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_item_merge_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_item_merge(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_item_merge_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_get_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_get_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_get_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jsonget_string_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jsonget_string(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jsonget_string_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jsonget_int_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport long long jsonget_int(UDF_INIT*, UDF_ARGS*, char*, char*);
|
||||||
|
DllExport void jsonget_int_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jsonget_real_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport double jsonget_real(UDF_INIT*, UDF_ARGS*, char*, char*);
|
||||||
|
DllExport void jsonget_real_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jsoncontains_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport long long jsoncontains(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jsoncontains_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jsonlocate_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jsonlocate(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jsonlocate_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_locate_all_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_locate_all(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_locate_all_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jsoncontains_path_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport long long jsoncontains_path(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jsoncontains_path_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_set_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_set_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_set_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_insert_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_insert_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_insert_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_update_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_update_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_update_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_file_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_file(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_file_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jfile_make_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jfile_make(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jfile_make_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_array_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_array(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_array_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_array_add_values_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_array_add_values(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_array_add_values_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_array_add_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_array_add(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_array_add_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_array_delete_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_array_delete(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_array_delete_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_object_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_object(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_object_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_object_nonull_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_object_nonull(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_object_nonull_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_object_key_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_object_key(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_object_key_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_object_add_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_object_add(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_object_add_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_object_delete_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_object_delete(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_object_delete_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_object_list_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_object_list(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_object_list_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_get_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_get_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_get_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_item_merge_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_item_merge(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_item_merge_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_set_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_set_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_set_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_insert_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_insert_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_insert_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_update_item_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_update_item(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_update_item_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool jbin_file_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *jbin_file(UDF_EXEC_ARGS);
|
||||||
|
DllExport void jbin_file_deinit(UDF_INIT*);
|
||||||
|
|
||||||
|
DllExport my_bool json_serialize_init(UDF_INIT*, UDF_ARGS*, char*);
|
||||||
|
DllExport char *json_serialize(UDF_EXEC_ARGS);
|
||||||
|
DllExport void json_serialize_deinit(UDF_INIT*);
|
||||||
|
} // extern "C"
|
||||||
|
|
||||||
|
/*********************************************************************************/
|
||||||
|
/* Structure JPN. Used to make the locate path. */
|
||||||
|
/*********************************************************************************/
|
||||||
|
typedef struct _jpn {
|
||||||
|
enum JTYP Type;
|
||||||
|
PSZ Key;
|
||||||
|
int N;
|
||||||
|
} JPN, *PJPN;
|
||||||
|
|
||||||
|
/*********************************************************************************/
|
||||||
|
/* Class JSNX: JSON access method. */
|
||||||
|
/*********************************************************************************/
|
||||||
|
class JSNX : public BLOCK {
|
||||||
|
public:
|
||||||
|
// Constructors
|
||||||
|
JSNX(PGLOBAL g, PJSON row, int type, int len = 64, int prec = 0, my_bool wr = false);
|
||||||
|
|
||||||
|
// Implementation
|
||||||
|
int GetPrecision(void) {return Prec;}
|
||||||
|
PVAL GetValue(void) {return Value;}
|
||||||
|
|
||||||
|
// Methods
|
||||||
|
my_bool SetJpath(PGLOBAL g, char *path, my_bool jb = false);
|
||||||
|
my_bool ParseJpath(PGLOBAL g);
|
||||||
|
void ReadValue(PGLOBAL g);
|
||||||
|
PJVAL GetRowValue(PGLOBAL g, PJSON row, int i, my_bool b = true);
|
||||||
|
PJVAL GetJson(PGLOBAL g);
|
||||||
|
my_bool CheckPath(PGLOBAL g);
|
||||||
|
my_bool WriteValue(PGLOBAL g, PJVAL jvalp);
|
||||||
|
char *Locate(PGLOBAL g, PJSON jsp, PJVAL jvp, int k = 1);
|
||||||
|
char *LocateAll(PGLOBAL g, PJSON jsp, PJVAL jvp, int mx = 10);
|
||||||
|
|
||||||
|
protected:
|
||||||
|
my_bool SetArrayOptions(PGLOBAL g, char *p, int i, PSZ nm);
|
||||||
|
PVAL GetColumnValue(PGLOBAL g, PJSON row, int i);
|
||||||
|
PVAL ExpandArray(PGLOBAL g, PJAR arp, int n);
|
||||||
|
PVAL CalculateArray(PGLOBAL g, PJAR arp, int n);
|
||||||
|
PVAL MakeJson(PGLOBAL g, PJSON jsp);
|
||||||
|
void SetJsonValue(PGLOBAL g, PVAL vp, PJVAL val, int n);
|
||||||
|
PJSON GetRow(PGLOBAL g);
|
||||||
|
my_bool LocateArray(PJAR jarp);
|
||||||
|
my_bool LocateObject(PJOB jobp);
|
||||||
|
my_bool LocateValue(PJVAL jvp);
|
||||||
|
my_bool LocateArrayAll(PJAR jarp);
|
||||||
|
my_bool LocateObjectAll(PJOB jobp);
|
||||||
|
my_bool LocateValueAll(PJVAL jvp);
|
||||||
|
my_bool CompareTree(PJSON jp1, PJSON jp2);
|
||||||
|
my_bool AddPath(void);
|
||||||
|
|
||||||
|
// Default constructor not to be used
|
||||||
|
JSNX(void) {}
|
||||||
|
|
||||||
|
// Members
|
||||||
|
PJSON Row;
|
||||||
|
PJVAL Jvalp;
|
||||||
|
PJPN Jpnp;
|
||||||
|
JOUTSTR *Jp;
|
||||||
|
JNODE *Nodes; // The intermediate objects
|
||||||
|
PVAL Value;
|
||||||
|
PVAL MulVal; // To value used by multiple column
|
||||||
|
char *Jpath; // The json path
|
||||||
|
int Buf_Type;
|
||||||
|
int Long;
|
||||||
|
int Prec;
|
||||||
|
int Nod; // The number of intermediate objects
|
||||||
|
int Xnod; // Index of multiple values
|
||||||
|
int K; // Kth item to locate
|
||||||
|
int I; // Index of JPN
|
||||||
|
int Imax; // Max number of JPN's
|
||||||
|
int B; // Index base
|
||||||
|
my_bool Xpd; // True for expandable column
|
||||||
|
my_bool Parsed; // True when parsed
|
||||||
|
my_bool Found; // Item found by locate
|
||||||
|
my_bool Wr; // Write mode
|
||||||
|
my_bool Jb; // Must return json item
|
||||||
|
}; // end of class JSNX
|
@@ -89,6 +89,7 @@
|
|||||||
#if defined(XML_SUPPORT)
|
#if defined(XML_SUPPORT)
|
||||||
#include "tabxml.h"
|
#include "tabxml.h"
|
||||||
#endif // XML_SUPPORT
|
#endif // XML_SUPPORT
|
||||||
|
#include "mycat.h"
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Extern static variables. */
|
/* Extern static variables. */
|
||||||
@@ -299,13 +300,13 @@ int GetIndexType(TABTYPE type)
|
|||||||
xtyp= 1;
|
xtyp= 1;
|
||||||
break;
|
break;
|
||||||
case TAB_MYSQL:
|
case TAB_MYSQL:
|
||||||
// case TAB_ODBC:
|
case TAB_ODBC:
|
||||||
xtyp= 2;
|
xtyp= 2;
|
||||||
break;
|
break;
|
||||||
case TAB_VIR:
|
case TAB_VIR:
|
||||||
xtyp= 3;
|
xtyp= 3;
|
||||||
break;
|
break;
|
||||||
case TAB_ODBC:
|
// case TAB_ODBC:
|
||||||
default:
|
default:
|
||||||
xtyp= 0;
|
xtyp= 0;
|
||||||
break;
|
break;
|
||||||
|
@@ -74,6 +74,7 @@ struct ha_table_option_struct {
|
|||||||
|
|
||||||
typedef class ha_connect *PHC;
|
typedef class ha_connect *PHC;
|
||||||
|
|
||||||
|
char *GetPluginDir(void);
|
||||||
TABTYPE GetTypeID(const char *type);
|
TABTYPE GetTypeID(const char *type);
|
||||||
bool IsFileType(TABTYPE type);
|
bool IsFileType(TABTYPE type);
|
||||||
bool IsExactType(TABTYPE type);
|
bool IsExactType(TABTYPE type);
|
||||||
|
@@ -30,3 +30,30 @@ SELECT id, TIME(tim) FROM t1 LIMIT 1;
|
|||||||
id TIME(tim)
|
id TIME(tim)
|
||||||
1 09:35:08.000000
|
1 09:35:08.000000
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
|
#
|
||||||
|
# Testing use of dates in where clause (MDEV-8926)
|
||||||
|
#
|
||||||
|
CREATE TABLE t1 (col1 DATE) ENGINE=CONNECT TABLE_TYPE=CSV;
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 No file name. Table will use t1.csv
|
||||||
|
INSERT INTO t1 VALUES('2015-01-01'),('2015-02-01'),('2015-03-01'),('2015-04-01');
|
||||||
|
SELECT * FROM t1 WHERE col1 = '2015-02-01';
|
||||||
|
col1
|
||||||
|
2015-02-01
|
||||||
|
SELECT * FROM t1 WHERE col1 > '2015-02-01';
|
||||||
|
col1
|
||||||
|
2015-03-01
|
||||||
|
2015-04-01
|
||||||
|
SELECT * FROM t1 WHERE col1 >= '2015-02-01';
|
||||||
|
col1
|
||||||
|
2015-02-01
|
||||||
|
2015-03-01
|
||||||
|
2015-04-01
|
||||||
|
SELECT * FROM t1 WHERE col1 < '2015-02-01';
|
||||||
|
col1
|
||||||
|
2015-01-01
|
||||||
|
SELECT * FROM t1 WHERE col1 <= '2015-02-01';
|
||||||
|
col1
|
||||||
|
2015-01-01
|
||||||
|
2015-02-01
|
||||||
|
DROP TABLE t1;
|
||||||
|
@@ -1,3 +1,4 @@
|
|||||||
|
set sql_mode="";
|
||||||
#
|
#
|
||||||
# Testing FILE privilege
|
# Testing FILE privilege
|
||||||
#
|
#
|
||||||
@@ -46,7 +47,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -70,6 +71,7 @@ DROP USER user@localhost;
|
|||||||
#
|
#
|
||||||
# Beginning of grant.inc
|
# Beginning of grant.inc
|
||||||
#
|
#
|
||||||
|
CREATE USER user@localhost;
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -130,7 +132,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -164,6 +166,7 @@ DROP USER user@localhost;
|
|||||||
#
|
#
|
||||||
# Beginning of grant.inc
|
# Beginning of grant.inc
|
||||||
#
|
#
|
||||||
|
CREATE USER user@localhost;
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -224,7 +227,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -258,6 +261,7 @@ DROP USER user@localhost;
|
|||||||
#
|
#
|
||||||
# Beginning of grant.inc
|
# Beginning of grant.inc
|
||||||
#
|
#
|
||||||
|
CREATE USER user@localhost;
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -318,7 +322,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -352,6 +356,7 @@ DROP USER user@localhost;
|
|||||||
#
|
#
|
||||||
# Beginning of grant.inc
|
# Beginning of grant.inc
|
||||||
#
|
#
|
||||||
|
CREATE USER user@localhost;
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -412,7 +417,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -446,6 +451,7 @@ DROP USER user@localhost;
|
|||||||
#
|
#
|
||||||
# Beginning of grant.inc
|
# Beginning of grant.inc
|
||||||
#
|
#
|
||||||
|
CREATE USER user@localhost;
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -506,7 +512,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -537,3 +543,4 @@ DROP USER user@localhost;
|
|||||||
#
|
#
|
||||||
# End of grant.inc
|
# End of grant.inc
|
||||||
#
|
#
|
||||||
|
set sql_mode=default;
|
||||||
|
@@ -1,8 +1,10 @@
|
|||||||
#
|
#
|
||||||
# Checking FILE privileges
|
# Checking FILE privileges
|
||||||
#
|
#
|
||||||
|
set sql_mode="";
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
|
set sql_mode=default;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -59,7 +61,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
|
@@ -171,6 +171,40 @@ line
|
|||||||
]
|
]
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
#
|
#
|
||||||
|
# Testing a pretty=0 file
|
||||||
|
#
|
||||||
|
CREATE TABLE t1
|
||||||
|
(
|
||||||
|
ISBN CHAR(15) NOT NULL,
|
||||||
|
Language CHAR(2) FIELD_FORMAT='LANG',
|
||||||
|
Subject CHAR(32) FIELD_FORMAT='SUBJECT',
|
||||||
|
AuthorFN CHAR(128) FIELD_FORMAT='AUTHOR:[X]:FIRSTNAME',
|
||||||
|
AuthorLN CHAR(128) FIELD_FORMAT='AUTHOR:[X]:LASTNAME',
|
||||||
|
Title CHAR(32) FIELD_FORMAT='TITLE',
|
||||||
|
Translation CHAR(32) FIELD_FORMAT='TRANSLATED:PREFIX',
|
||||||
|
TranslatorFN CHAR(80) FIELD_FORMAT='TRANSLATED:TRANSLATOR:FIRSTNAME',
|
||||||
|
TranslatorLN CHAR(80) FIELD_FORMAT='TRANSLATED:TRANSLATOR:LASTNAME',
|
||||||
|
Publisher CHAR(20) FIELD_FORMAT='PUBLISHER:NAME',
|
||||||
|
Location CHAR(16) FIELD_FORMAT='PUBLISHER:PLACE',
|
||||||
|
Year int(4) FIELD_FORMAT='DATEPUB',
|
||||||
|
INDEX IX(ISBN)
|
||||||
|
)
|
||||||
|
ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='bib0.json' LRECL=320 OPTION_LIST='Pretty=0';
|
||||||
|
SHOW INDEX FROM t1;
|
||||||
|
Table Non_unique Key_name Seq_in_index Column_name Collation Cardinality Sub_part Packed Null Index_type Comment Index_comment
|
||||||
|
t1 1 IX 1 ISBN A NULL NULL NULL XINDEX
|
||||||
|
SELECT * FROM t1;
|
||||||
|
ISBN Language Subject AuthorFN AuthorLN Title Translation TranslatorFN TranslatorLN Publisher Location Year
|
||||||
|
9782212090819 fr applications Jean-Michel Bernadac Construire une application XML NULL NULL NULL Eyrolles Paris 1999
|
||||||
|
9782212090819 fr applications Fran<61>ois Knab Construire une application XML NULL NULL NULL Eyrolles Paris 1999
|
||||||
|
9782840825685 fr applications William J. Pardi XML en Action adapt<70> de l'anglais par James Guerin Microsoft Press Paris 2001
|
||||||
|
DESCRIBE SELECT * FROM t1 WHERE ISBN = '9782212090819';
|
||||||
|
id select_type table type possible_keys key key_len ref rows Extra
|
||||||
|
1 SIMPLE t1 ref IX IX 15 const 1 Using where
|
||||||
|
UPDATE t1 SET AuthorFN = 'Philippe' WHERE ISBN = '9782212090819';
|
||||||
|
ERROR HY000: Got error 122 'Cannot write expanded column when Pretty is not 2' from CONNECT
|
||||||
|
DROP TABLE t1;
|
||||||
|
#
|
||||||
# A file with 2 arrays
|
# A file with 2 arrays
|
||||||
#
|
#
|
||||||
CREATE TABLE t1 (
|
CREATE TABLE t1 (
|
||||||
|
@@ -1,63 +1,177 @@
|
|||||||
|
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=VIR BLOCK_SIZE=5;
|
||||||
#
|
#
|
||||||
# Test UDF's with constant arguments
|
# Test UDF's with constant arguments
|
||||||
#
|
#
|
||||||
|
SELECT JsonValue(56, 3.1416, 'foo', NULL);
|
||||||
|
ERROR HY000: Can't initialize function 'jsonvalue'; Cannot accept more than 1 argument
|
||||||
|
SELECT JsonValue(3.1416);
|
||||||
|
JsonValue(3.1416)
|
||||||
|
3.141600
|
||||||
|
SELECT JsonValue(-80);
|
||||||
|
JsonValue(-80)
|
||||||
|
-80
|
||||||
|
SELECT JsonValue('foo');
|
||||||
|
JsonValue('foo')
|
||||||
|
"foo"
|
||||||
|
SELECT JsonValue(9223372036854775807);
|
||||||
|
JsonValue(9223372036854775807)
|
||||||
|
9223372036854775807
|
||||||
|
SELECT JsonValue(NULL);
|
||||||
|
JsonValue(NULL)
|
||||||
|
null
|
||||||
|
SELECT JsonValue(TRUE);
|
||||||
|
JsonValue(TRUE)
|
||||||
|
true
|
||||||
|
SELECT JsonValue(FALSE);
|
||||||
|
JsonValue(FALSE)
|
||||||
|
false
|
||||||
|
SELECT JsonValue();
|
||||||
|
JsonValue()
|
||||||
|
null
|
||||||
|
SELECT JsonValue('[11, 22, 33]' json_) FROM t1;
|
||||||
|
JsonValue('[11, 22, 33]' json_)
|
||||||
|
[11,22,33]
|
||||||
|
[11,22,33]
|
||||||
|
[11,22,33]
|
||||||
|
[11,22,33]
|
||||||
|
[11,22,33]
|
||||||
SELECT Json_Array();
|
SELECT Json_Array();
|
||||||
Json_Array()
|
Json_Array()
|
||||||
[]
|
[]
|
||||||
SELECT Json_Object(56,3.1416,'foo',NULL);
|
SELECT Json_Array(56, 3.1416, 'My name is "Foo"', NULL);
|
||||||
Json_Object(56,3.1416,'foo',NULL)
|
Json_Array(56, 3.1416, 'My name is "Foo"', NULL)
|
||||||
{"56":56,"3.1416":3.141600,"foo":"foo","NULL":null}
|
|
||||||
SELECT Json_Object(56 qty,3.1416 price,'foo' truc, NULL garanty);
|
|
||||||
Json_Object(56 qty,3.1416 price,'foo' truc, NULL garanty)
|
|
||||||
{"qty":56,"price":3.141600,"truc":"foo","garanty":null}
|
|
||||||
SELECT Json_Array(56,3.1416,'My name is "Foo"',NULL);
|
|
||||||
Json_Array(56,3.1416,'My name is "Foo"',NULL)
|
|
||||||
[56,3.141600,"My name is \"Foo\"",null]
|
[56,3.141600,"My name is \"Foo\"",null]
|
||||||
SELECT Json_Array_Add(Json_Array(56,3.1416,'foo',NULL)) Array;
|
SELECT Json_Array(Json_Array(56, 3.1416, 'foo'), TRUE);
|
||||||
ERROR HY000: Can't initialize function 'Json_Array_Add'; Json_Value_Add must have at least 2 arguments
|
Json_Array(Json_Array(56, 3.1416, 'foo'), TRUE)
|
||||||
SELECT Json_Array_Add(Json_Array(56,3.1416,'foo',NULL),'One more') Array;
|
[[56,3.141600,"foo"],true]
|
||||||
|
SELECT Json_Array_Add(Json_Array(56, 3.1416, 'foo', NULL)) Array;
|
||||||
|
ERROR HY000: Can't initialize function 'json_array_add'; This function must have at least 2 arguments
|
||||||
|
SELECT Json_Array_Add(Json_Array(56, 3.1416, 'foo', NULL), 'One more') Array;
|
||||||
Array
|
Array
|
||||||
[56,3.141600,"foo",null,"One more"]
|
[56,3.141600,"foo",null,"One more"]
|
||||||
SELECT Json_Array_Add(Json_Value('one value'),'One more');
|
SELECT Json_Array_Add(JsonValue('one value'), 'One more');
|
||||||
Json_Array_Add(Json_Value('one value'),'One more')
|
ERROR HY000: Can't initialize function 'json_array_add'; First argument must be a json item
|
||||||
["one value","One more"]
|
SELECT Json_Array_Add('one value', 'One more');
|
||||||
SELECT Json_Array_Add('one value','One more');
|
ERROR HY000: Can't initialize function 'json_array_add'; First argument must be a json item
|
||||||
ERROR HY000: Can't initialize function 'Json_Array_Add'; Json_Value_Add first argument must be a json item
|
SELECT Json_Array_Add('one value' json_, 'One more');
|
||||||
SELECT Json_Array_Add('one value' json_,'One more');
|
Json_Array_Add('one value' json_, 'One more')
|
||||||
Json_Array_Add('one value' json_,'One more')
|
one value
|
||||||
[null,"One more"]
|
|
||||||
Warnings:
|
Warnings:
|
||||||
Warning 1105 Bad 'o' character near one value
|
Warning 1105 Error 2 opening one value
|
||||||
SELECT Json_Value(56,3.1416,'foo',NULL);
|
Warning 1105 First argument target is not an array
|
||||||
ERROR HY000: Can't initialize function 'Json_Value'; Json_Value cannot accept more than 1 argument
|
SELECT Json_Array_Add(5 json_, 'One more');
|
||||||
SELECT Json_Value(3.1416);
|
ERROR HY000: Can't initialize function 'json_array_add'; First argument must be a json item
|
||||||
Json_Value(3.1416)
|
SELECT Json_Array_Add('[5,3,8,7,9]' json_, 4, 0);
|
||||||
3.141600
|
Json_Array_Add('[5,3,8,7,9]' json_, 4, 0)
|
||||||
SELECT Json_Value('foo');
|
[4,5,3,8,7,9]
|
||||||
Json_Value('foo')
|
SELECT Json_Array_Add('[5,3,8,7,9]' json_, 4, 2) Array;
|
||||||
"foo"
|
Array
|
||||||
SELECT Json_Value(NULL);
|
[5,3,4,8,7,9]
|
||||||
Json_Value(NULL)
|
SELECT Json_Array_Add('[5,3,8,7,9]' json_, 4, 9);
|
||||||
null
|
Json_Array_Add('[5,3,8,7,9]' json_, 4, 9)
|
||||||
SELECT Json_Value();
|
[5,3,8,7,9,4]
|
||||||
Json_Value()
|
SELECT Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), '[2]', 33, 1);
|
||||||
null
|
Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), '[2]', 33, 1)
|
||||||
|
[1,2,[11,22],"[2]"]
|
||||||
|
SELECT Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), 33, '[2]', 1);
|
||||||
|
Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), 33, '[2]', 1)
|
||||||
|
[1,2,[11,33,22]]
|
||||||
|
SELECT Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), 33, 1, '[2]');
|
||||||
|
Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), 33, 1, '[2]')
|
||||||
|
[1,2,[11,33,22]]
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(56, 3.1416, 'machin', NULL), 'One more', 'Two more') Array;
|
||||||
|
Array
|
||||||
|
[56,3.141600,"machin",null,"One more","Two more"]
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(56, 3.1416, 'machin'), 'One more', 'Two more') Array FROM t1;
|
||||||
|
Array
|
||||||
|
[56,3.141600,"machin","One more","Two more"]
|
||||||
|
[56,3.141600,"machin","One more","Two more"]
|
||||||
|
[56,3.141600,"machin","One more","Two more"]
|
||||||
|
[56,3.141600,"machin","One more","Two more"]
|
||||||
|
[56,3.141600,"machin","One more","Two more"]
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(56, 3.1416, 'machin'), n) Array FROM t1;
|
||||||
|
Array
|
||||||
|
[56,3.141600,"machin",1]
|
||||||
|
[56,3.141600,"machin",2]
|
||||||
|
[56,3.141600,"machin",3]
|
||||||
|
[56,3.141600,"machin",4]
|
||||||
|
[56,3.141600,"machin",5]
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(n, 3.1416, 'machin'), n) Array FROM t1;
|
||||||
|
Array
|
||||||
|
[1,3.141600,"machin",1]
|
||||||
|
[2,3.141600,"machin",2]
|
||||||
|
[3,3.141600,"machin",3]
|
||||||
|
[4,3.141600,"machin",4]
|
||||||
|
[5,3.141600,"machin",5]
|
||||||
|
SELECT Json_Array_Add_Values('[56]', 3.1416, 'machin') Array;
|
||||||
|
Array
|
||||||
|
[56,3.141600,"machin"]
|
||||||
|
SELECT Json_Array_Delete(Json_Array(56, 3.1416, 'My name is "Foo"', NULL), 0);
|
||||||
|
Json_Array_Delete(Json_Array(56, 3.1416, 'My name is "Foo"', NULL), 0)
|
||||||
|
[3.141600,"My name is \"Foo\"",null]
|
||||||
|
SELECT Json_Array_Delete(Json_Object(56, 3.1416, 'My name is Foo', NULL), 2);
|
||||||
|
Json_Array_Delete(Json_Object(56, 3.1416, 'My name is Foo', NULL), 2)
|
||||||
|
{"56":56,"3.1416":3.141600,"My name is Foo":"My name is Foo","NULL":null}
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 First argument target is not an array
|
||||||
|
SELECT Json_Array_Delete(Json_Array(56, 3.1416, 'My name is "Foo"', NULL), '2');
|
||||||
|
Json_Array_Delete(Json_Array(56, 3.1416, 'My name is "Foo"', NULL), '2')
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 Missing or null array index
|
||||||
|
SELECT Json_Array_Delete(json_array(56, 3.1416, 'My name is "Foo"', NULL), '2', 2);
|
||||||
|
Json_Array_Delete(json_array(56, 3.1416, 'My name is "Foo"', NULL), '2', 2)
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 No sub-item at '2'
|
||||||
|
SELECT Json_Object(56, 3.1416, 'foo', NULL);
|
||||||
|
Json_Object(56, 3.1416, 'foo', NULL)
|
||||||
|
{"56":56,"3.1416":3.141600,"foo":"foo","NULL":null}
|
||||||
|
SELECT Json_Object(56 qty, 3.1416 price, 'foo' truc, NULL garanty);
|
||||||
|
Json_Object(56 qty, 3.1416 price, 'foo' truc, NULL garanty)
|
||||||
|
{"qty":56,"price":3.141600,"truc":"foo","garanty":null}
|
||||||
SELECT Json_Object();
|
SELECT Json_Object();
|
||||||
Json_Object()
|
Json_Object()
|
||||||
{}
|
{}
|
||||||
SELECT Json_Object(Json_Array(56,3.1416,'foo'),NULL);
|
SELECT Json_Object(Json_Array(56, 3.1416, 'foo'), NULL);
|
||||||
Json_Object(Json_Array(56,3.1416,'foo'),NULL)
|
Json_Object(Json_Array(56, 3.1416, 'foo'), NULL)
|
||||||
{"Array(56,3.1416,'foo')":[56,3.141600,"foo"],"NULL":null}
|
{"Array(56, 3.1416, 'foo')":[56,3.141600,"foo"],"NULL":null}
|
||||||
SELECT Json_Array(Json_Array(56,3.1416,'foo'),NULL);
|
SELECT Json_Array(Json_Object(56 "qty", 3.1416 "price", 'foo') ,NULL);
|
||||||
Json_Array(Json_Array(56,3.1416,'foo'),NULL)
|
Json_Array(Json_Object(56 "qty", 3.1416 "price", 'foo') ,NULL)
|
||||||
[[56,3.141600,"foo"],null]
|
|
||||||
SELECT Json_Array(Json_Object(56 "qty",3.1416 "price",'foo'),NULL);
|
|
||||||
Json_Array(Json_Object(56 "qty",3.1416 "price",'foo'),NULL)
|
|
||||||
[{"qty":56,"price":3.141600,"foo":"foo"},null]
|
[{"qty":56,"price":3.141600,"foo":"foo"},null]
|
||||||
|
SELECT Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL);
|
||||||
|
Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL)
|
||||||
|
{"qty":56,"price":3.141600,"truc":"machin","garanty":null}
|
||||||
|
SELECT Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty');
|
||||||
|
ERROR HY000: Can't initialize function 'json_object_key'; This function must have an even number of arguments
|
||||||
|
SELECT Json_Object_Add(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color);
|
||||||
|
Json_Object_Add(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color)
|
||||||
|
{"qty":56,"price":3.141600,"truc":"machin","garanty":null,"color":"blue"}
|
||||||
|
SELECT Json_Object_Add(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price);
|
||||||
|
Json_Object_Add(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price)
|
||||||
|
{"qty":56,"price":45.990000,"truc":"machin","garanty":null}
|
||||||
|
SELECT Json_Object_Add(Json_File('notexist.json'), 'cheese' item, '[1]', 1);
|
||||||
|
Json_Object_Add(Json_File('notexist.json'), 'cheese' item, '[1]', 1)
|
||||||
|
NULL
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 Error 2 opening notexist.json
|
||||||
|
Warning 1105 First argument target is not an object
|
||||||
|
SELECT Json_Object_Delete(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'truc');
|
||||||
|
Json_Object_Delete(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'truc')
|
||||||
|
{"qty":56,"price":3.141600,"garanty":null}
|
||||||
|
SELECT Json_Object_Delete(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'chose');
|
||||||
|
Json_Object_Delete(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'chose')
|
||||||
|
{"qty":56,"price":3.141600,"truc":"machin","garanty":null}
|
||||||
|
SELECT Json_Object_List(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty)) "Key List";
|
||||||
|
Key List
|
||||||
|
["qty","price","truc","garanty"]
|
||||||
|
SELECT Json_Object_List('{"qty":56, "price":3.1416, "truc":"machin", "garanty":null}') "Key List";
|
||||||
|
Key List
|
||||||
|
["qty","price","truc","garanty"]
|
||||||
#
|
#
|
||||||
# Test UDF's with column arguments
|
# Test UDF's with column arguments
|
||||||
#
|
#
|
||||||
CREATE TABLE t1
|
CREATE TABLE t2
|
||||||
(
|
(
|
||||||
ISBN CHAR(15),
|
ISBN CHAR(15),
|
||||||
LANG CHAR(2),
|
LANG CHAR(2),
|
||||||
@@ -69,21 +183,20 @@ TRANSLATOR CHAR(80),
|
|||||||
PUBLISHER CHAR(32),
|
PUBLISHER CHAR(32),
|
||||||
DATEPUB int(4)
|
DATEPUB int(4)
|
||||||
) ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='biblio.json';
|
) ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='biblio.json';
|
||||||
SELECT Json_Array(AUTHOR, TITLE, DATEPUB) FROM t1;
|
SELECT Json_Array(AUTHOR, TITLE, DATEPUB) FROM t2;
|
||||||
Json_Array(AUTHOR, TITLE, DATEPUB)
|
Json_Array(AUTHOR, TITLE, DATEPUB)
|
||||||
["Jean-Christophe Bernadac","Construire une application XML",1999]
|
["Jean-Christophe Bernadac","Construire une application XML",1999]
|
||||||
["William J. Pardi","XML en Action",1999]
|
["William J. Pardi","XML en Action",1999]
|
||||||
SELECT Json_Object(AUTHOR, TITLE, DATEPUB) FROM t1;
|
SELECT Json_Object(AUTHOR, TITLE, DATEPUB) FROM t2;
|
||||||
Json_Object(AUTHOR, TITLE, DATEPUB)
|
Json_Object(AUTHOR, TITLE, DATEPUB)
|
||||||
{"AUTHOR":"Jean-Christophe Bernadac","TITLE":"Construire une application XML","DATEPUB":1999}
|
{"AUTHOR":"Jean-Christophe Bernadac","TITLE":"Construire une application XML","DATEPUB":1999}
|
||||||
{"AUTHOR":"William J. Pardi","TITLE":"XML en Action","DATEPUB":1999}
|
{"AUTHOR":"William J. Pardi","TITLE":"XML en Action","DATEPUB":1999}
|
||||||
SELECT Json_Array_Grp(TITLE, DATEPUB) FROM t1;
|
SELECT Json_Array_Grp(TITLE, DATEPUB) FROM t2;
|
||||||
ERROR HY000: Can't initialize function 'Json_Array_Grp'; Json_Array_Grp can only accept 1 argument
|
ERROR HY000: Can't initialize function 'json_array_grp'; This function can only accept 1 argument
|
||||||
SELECT Json_Array_Grp(TITLE) FROM t1;
|
SELECT Json_Array_Grp(TITLE) FROM t2;
|
||||||
Json_Array_Grp(TITLE)
|
Json_Array_Grp(TITLE)
|
||||||
["Construire une application XML","XML en Action"]
|
["Construire une application XML","XML en Action"]
|
||||||
DROP TABLE t1;
|
CREATE TABLE t3 (
|
||||||
CREATE TABLE t1 (
|
|
||||||
SERIALNO CHAR(5) NOT NULL,
|
SERIALNO CHAR(5) NOT NULL,
|
||||||
NAME VARCHAR(12) NOT NULL FLAG=6,
|
NAME VARCHAR(12) NOT NULL FLAG=6,
|
||||||
SEX SMALLINT(1) NOT NULL,
|
SEX SMALLINT(1) NOT NULL,
|
||||||
@@ -93,10 +206,10 @@ DEPARTMENT CHAr(4) NOT NULL FLAG=41,
|
|||||||
SECRETARY CHAR(5) DEFAULT NULL FLAG=46,
|
SECRETARY CHAR(5) DEFAULT NULL FLAG=46,
|
||||||
SALARY DOUBLE(8,2) NOT NULL FLAG=52
|
SALARY DOUBLE(8,2) NOT NULL FLAG=52
|
||||||
) ENGINE=CONNECT TABLE_TYPE=FIX BLOCK_SIZE=8 FILE_NAME='employee.dat' ENDING=1;
|
) ENGINE=CONNECT TABLE_TYPE=FIX BLOCK_SIZE=8 FILE_NAME='employee.dat' ENDING=1;
|
||||||
SELECT Json_Object(SERIALNO, NAME, TITLE, SALARY) FROM t1 WHERE NAME = 'MERCHANT';
|
SELECT Json_Object(SERIALNO, NAME, TITLE, SALARY) FROM t3 WHERE NAME = 'MERCHANT';
|
||||||
Json_Object(SERIALNO, NAME, TITLE, SALARY)
|
Json_Object(SERIALNO, NAME, TITLE, SALARY)
|
||||||
{"SERIALNO":"78943","NAME":"MERCHANT","TITLE":"SALESMAN","SALARY":8700.000000}
|
{"SERIALNO":"78943","NAME":"MERCHANT","TITLE":"SALESMAN","SALARY":8700.000000}
|
||||||
SELECT DEPARTMENT, Json_Array_Grp(NAME) FROM t1 GROUP BY DEPARTMENT;
|
SELECT DEPARTMENT, Json_Array_Grp(NAME) FROM t3 GROUP BY DEPARTMENT;
|
||||||
DEPARTMENT Json_Array_Grp(NAME)
|
DEPARTMENT Json_Array_Grp(NAME)
|
||||||
0021 ["STRONG","SHORTSIGHT"]
|
0021 ["STRONG","SHORTSIGHT"]
|
||||||
0318 ["BANCROFT","PLUMHEAD","HONEY","TONGHO","WALTER","SHRINKY","WERTHER","MERCHANT","WHEELFOR"]
|
0318 ["BANCROFT","PLUMHEAD","HONEY","TONGHO","WALTER","SHRINKY","WERTHER","MERCHANT","WHEELFOR"]
|
||||||
@@ -104,26 +217,36 @@ DEPARTMENT Json_Array_Grp(NAME)
|
|||||||
2452 ["BIGHEAD","ORELLY","BIGHORN","SMITH","CHERRY"]
|
2452 ["BIGHEAD","ORELLY","BIGHORN","SMITH","CHERRY"]
|
||||||
Warnings:
|
Warnings:
|
||||||
Warning 1105 Result truncated to json_grp_size values
|
Warning 1105 Result truncated to json_grp_size values
|
||||||
set connect_json_grp_size=30;
|
SET connect_json_grp_size=30;
|
||||||
SELECT Json_Array(DEPARTMENT, Json_Array_Grp(NAME)) FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Object(title, Json_Array_Grp(name) `json_names`) from t3 GROUP BY title;
|
||||||
|
Json_Object(title, Json_Array_Grp(name) `json_names`)
|
||||||
|
{"title":"ADMINISTRATOR","names":["GOOSEPEN","FUNNIGUY","SHRINKY"]}
|
||||||
|
{"title":"DIRECTOR","names":["QUINN","WERTHER","STRONG"]}
|
||||||
|
{"title":"ENGINEER","names":["BROWNY","ORELLY","MARTIN","TONGHO","WALTER","SMITH"]}
|
||||||
|
{"title":"PROGRAMMER","names":["BUGHAPPY"]}
|
||||||
|
{"title":"SALESMAN","names":["WHEELFOR","MERCHANT","BULLOZER","BANCROFT","FODDERMAN"]}
|
||||||
|
{"title":"SCIENTIST","names":["BIGHEAD","BIGHORN"]}
|
||||||
|
{"title":"SECRETARY","names":["MESSIFUL","HONEY","SHORTSIGHT","CHERRY","MONAPENNY"]}
|
||||||
|
{"title":"TYPIST","names":["KITTY","PLUMHEAD"]}
|
||||||
|
SELECT Json_Array(DEPARTMENT, Json_Array_Grp(NAME)) FROM t3 GROUP BY DEPARTMENT;
|
||||||
Json_Array(DEPARTMENT, Json_Array_Grp(NAME))
|
Json_Array(DEPARTMENT, Json_Array_Grp(NAME))
|
||||||
["0021",["STRONG","SHORTSIGHT"]]
|
["0021",["STRONG","SHORTSIGHT"]]
|
||||||
["0318",["BANCROFT","PLUMHEAD","HONEY","TONGHO","WALTER","SHRINKY","WERTHER","MERCHANT","WHEELFOR"]]
|
["0318",["BANCROFT","PLUMHEAD","HONEY","TONGHO","WALTER","SHRINKY","WERTHER","MERCHANT","WHEELFOR"]]
|
||||||
["0319",["BULLOZER","QUINN","BROWNY","KITTY","MONAPENNY","MARTIN","FUNNIGUY","BUGHAPPY","FODDERMAN","MESSIFUL","GOOSEPEN"]]
|
["0319",["BULLOZER","QUINN","BROWNY","KITTY","MONAPENNY","MARTIN","FUNNIGUY","BUGHAPPY","FODDERMAN","MESSIFUL","GOOSEPEN"]]
|
||||||
["2452",["BIGHEAD","ORELLY","BIGHORN","SMITH","CHERRY"]]
|
["2452",["BIGHEAD","ORELLY","BIGHORN","SMITH","CHERRY"]]
|
||||||
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(NAME) json_NAMES) FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(NAME) json_NAMES) FROM t3 GROUP BY DEPARTMENT;
|
||||||
Json_Object(DEPARTMENT, Json_Array_Grp(NAME) json_NAMES)
|
Json_Object(DEPARTMENT, Json_Array_Grp(NAME) json_NAMES)
|
||||||
{"DEPARTMENT":"0021","NAMES":["STRONG","SHORTSIGHT"]}
|
{"DEPARTMENT":"0021","NAMES":["STRONG","SHORTSIGHT"]}
|
||||||
{"DEPARTMENT":"0318","NAMES":["BANCROFT","PLUMHEAD","HONEY","TONGHO","WALTER","SHRINKY","WERTHER","MERCHANT","WHEELFOR"]}
|
{"DEPARTMENT":"0318","NAMES":["BANCROFT","PLUMHEAD","HONEY","TONGHO","WALTER","SHRINKY","WERTHER","MERCHANT","WHEELFOR"]}
|
||||||
{"DEPARTMENT":"0319","NAMES":["BULLOZER","QUINN","BROWNY","KITTY","MONAPENNY","MARTIN","FUNNIGUY","BUGHAPPY","FODDERMAN","MESSIFUL","GOOSEPEN"]}
|
{"DEPARTMENT":"0319","NAMES":["BULLOZER","QUINN","BROWNY","KITTY","MONAPENNY","MARTIN","FUNNIGUY","BUGHAPPY","FODDERMAN","MESSIFUL","GOOSEPEN"]}
|
||||||
{"DEPARTMENT":"2452","NAMES":["BIGHEAD","ORELLY","BIGHORN","SMITH","CHERRY"]}
|
{"DEPARTMENT":"2452","NAMES":["BIGHEAD","ORELLY","BIGHORN","SMITH","CHERRY"]}
|
||||||
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(Json_Object(SERIALNO, NAME, TITLE, SALARY)) json_EMPLOYES) FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(Json_Object(SERIALNO, NAME, TITLE, SALARY)) json_EMPLOYES) FROM t3 GROUP BY DEPARTMENT;
|
||||||
Json_Object(DEPARTMENT, Json_Array_Grp(Json_Object(SERIALNO, NAME, TITLE, SALARY)) json_EMPLOYES)
|
Json_Object(DEPARTMENT, Json_Array_Grp(Json_Object(SERIALNO, NAME, TITLE, SALARY)) json_EMPLOYES)
|
||||||
{"DEPARTMENT":"0021","EMPLOYES":[{"SERIALNO":"87777","NAME":"STRONG","TITLE":"DIRECTOR","SALARY":23000.000000},{"SERIALNO":"22222","NAME":"SHORTSIGHT","TITLE":"SECRETARY","SALARY":5500.000000}]}
|
{"DEPARTMENT":"0021","EMPLOYES":[{"SERIALNO":"87777","NAME":"STRONG","TITLE":"DIRECTOR","SALARY":23000.000000},{"SERIALNO":"22222","NAME":"SHORTSIGHT","TITLE":"SECRETARY","SALARY":5500.000000}]}
|
||||||
{"DEPARTMENT":"0318","EMPLOYES":[{"SERIALNO":"74200","NAME":"BANCROFT","TITLE":"SALESMAN","SALARY":9600.000000},{"SERIALNO":"24888","NAME":"PLUMHEAD","TITLE":"TYPIST","SALARY":2800.000000},{"SERIALNO":"27845","NAME":"HONEY","TITLE":"SECRETARY","SALARY":4900.000000},{"SERIALNO":"73452","NAME":"TONGHO","TITLE":"ENGINEER","SALARY":6800.000000},{"SERIALNO":"74234","NAME":"WALTER","TITLE":"ENGINEER","SALARY":7400.000000},{"SERIALNO":"77777","NAME":"SHRINKY","TITLE":"ADMINISTRATOR","SALARY":7500.000000},{"SERIALNO":"70012","NAME":"WERTHER","TITLE":"DIRECTOR","SALARY":14500.000000},{"SERIALNO":"78943","NAME":"MERCHANT","TITLE":"SALESMAN","SALARY":8700.000000},{"SERIALNO":"73111","NAME":"WHEELFOR","TITLE":"SALESMAN","SALARY":10030.000000}]}
|
{"DEPARTMENT":"0318","EMPLOYES":[{"SERIALNO":"74200","NAME":"BANCROFT","TITLE":"SALESMAN","SALARY":9600.000000},{"SERIALNO":"24888","NAME":"PLUMHEAD","TITLE":"TYPIST","SALARY":2800.000000},{"SERIALNO":"27845","NAME":"HONEY","TITLE":"SECRETARY","SALARY":4900.000000},{"SERIALNO":"73452","NAME":"TONGHO","TITLE":"ENGINEER","SALARY":6800.000000},{"SERIALNO":"74234","NAME":"WALTER","TITLE":"ENGINEER","SALARY":7400.000000},{"SERIALNO":"77777","NAME":"SHRINKY","TITLE":"ADMINISTRATOR","SALARY":7500.000000},{"SERIALNO":"70012","NAME":"WERTHER","TITLE":"DIRECTOR","SALARY":14500.000000},{"SERIALNO":"78943","NAME":"MERCHANT","TITLE":"SALESMAN","SALARY":8700.000000},{"SERIALNO":"73111","NAME":"WHEELFOR","TITLE":"SALESMAN","SALARY":10030.000000}]}
|
||||||
{"DEPARTMENT":"0319","EMPLOYES":[{"SERIALNO":"76543","NAME":"BULLOZER","TITLE":"SALESMAN","SALARY":14800.000000},{"SERIALNO":"40567","NAME":"QUINN","TITLE":"DIRECTOR","SALARY":14000.000000},{"SERIALNO":"00137","NAME":"BROWNY","TITLE":"ENGINEER","SALARY":10500.000000},{"SERIALNO":"12345","NAME":"KITTY","TITLE":"TYPIST","SALARY":3000.450000},{"SERIALNO":"33333","NAME":"MONAPENNY","TITLE":"SECRETARY","SALARY":3800.000000},{"SERIALNO":"00023","NAME":"MARTIN","TITLE":"ENGINEER","SALARY":10000.000000},{"SERIALNO":"07654","NAME":"FUNNIGUY","TITLE":"ADMINISTRATOR","SALARY":8500.000000},{"SERIALNO":"45678","NAME":"BUGHAPPY","TITLE":"PROGRAMMER","SALARY":8500.000000},{"SERIALNO":"56789","NAME":"FODDERMAN","TITLE":"SALESMAN","SALARY":7000.000000},{"SERIALNO":"55555","NAME":"MESSIFUL","TITLE":"SECRETARY","SALARY":5000.500000},{"SERIALNO":"98765","NAME":"GOOSEPEN","TITLE":"ADMINISTRATOR","SALARY":4700.000000}]}
|
{"DEPARTMENT":"0319","EMPLOYES":[{"SERIALNO":"76543","NAME":"BULLOZER","TITLE":"SALESMAN","SALARY":14800.000000},{"SERIALNO":"40567","NAME":"QUINN","TITLE":"DIRECTOR","SALARY":14000.000000},{"SERIALNO":"00137","NAME":"BROWNY","TITLE":"ENGINEER","SALARY":10500.000000},{"SERIALNO":"12345","NAME":"KITTY","TITLE":"TYPIST","SALARY":3000.450000},{"SERIALNO":"33333","NAME":"MONAPENNY","TITLE":"SECRETARY","SALARY":3800.000000},{"SERIALNO":"00023","NAME":"MARTIN","TITLE":"ENGINEER","SALARY":10000.000000},{"SERIALNO":"07654","NAME":"FUNNIGUY","TITLE":"ADMINISTRATOR","SALARY":8500.000000},{"SERIALNO":"45678","NAME":"BUGHAPPY","TITLE":"PROGRAMMER","SALARY":8500.000000},{"SERIALNO":"56789","NAME":"FODDERMAN","TITLE":"SALESMAN","SALARY":7000.000000},{"SERIALNO":"55555","NAME":"MESSIFUL","TITLE":"SECRETARY","SALARY":5000.500000},{"SERIALNO":"98765","NAME":"GOOSEPEN","TITLE":"ADMINISTRATOR","SALARY":4700.000000}]}
|
||||||
{"DEPARTMENT":"2452","EMPLOYES":[{"SERIALNO":"34567","NAME":"BIGHEAD","TITLE":"SCIENTIST","SALARY":8000.000000},{"SERIALNO":"31416","NAME":"ORELLY","TITLE":"ENGINEER","SALARY":13400.000000},{"SERIALNO":"36666","NAME":"BIGHORN","TITLE":"SCIENTIST","SALARY":11000.000000},{"SERIALNO":"02345","NAME":"SMITH","TITLE":"ENGINEER","SALARY":9000.000000},{"SERIALNO":"11111","NAME":"CHERRY","TITLE":"SECRETARY","SALARY":4500.000000}]}
|
{"DEPARTMENT":"2452","EMPLOYES":[{"SERIALNO":"34567","NAME":"BIGHEAD","TITLE":"SCIENTIST","SALARY":8000.000000},{"SERIALNO":"31416","NAME":"ORELLY","TITLE":"ENGINEER","SALARY":13400.000000},{"SERIALNO":"36666","NAME":"BIGHORN","TITLE":"SCIENTIST","SALARY":11000.000000},{"SERIALNO":"02345","NAME":"SMITH","TITLE":"ENGINEER","SALARY":9000.000000},{"SERIALNO":"11111","NAME":"CHERRY","TITLE":"SECRETARY","SALARY":4500.000000}]}
|
||||||
SELECT Json_Object(DEPARTMENT, TITLE, Json_Array_Grp(Json_Object(SERIALNO, NAME, SALARY)) json_EMPLOYES) FROM t1 GROUP BY DEPARTMENT, TITLE;
|
SELECT Json_Object(DEPARTMENT, TITLE, Json_Array_Grp(Json_Object(SERIALNO, NAME, SALARY)) json_EMPLOYES) FROM t3 GROUP BY DEPARTMENT, TITLE;
|
||||||
Json_Object(DEPARTMENT, TITLE, Json_Array_Grp(Json_Object(SERIALNO, NAME, SALARY)) json_EMPLOYES)
|
Json_Object(DEPARTMENT, TITLE, Json_Array_Grp(Json_Object(SERIALNO, NAME, SALARY)) json_EMPLOYES)
|
||||||
{"DEPARTMENT":"0021","TITLE":"DIRECTOR","EMPLOYES":[{"SERIALNO":"87777","NAME":"STRONG","SALARY":23000.000000}]}
|
{"DEPARTMENT":"0021","TITLE":"DIRECTOR","EMPLOYES":[{"SERIALNO":"87777","NAME":"STRONG","SALARY":23000.000000}]}
|
||||||
{"DEPARTMENT":"0021","TITLE":"SECRETARY","EMPLOYES":[{"SERIALNO":"22222","NAME":"SHORTSIGHT","SALARY":5500.000000}]}
|
{"DEPARTMENT":"0021","TITLE":"SECRETARY","EMPLOYES":[{"SERIALNO":"22222","NAME":"SHORTSIGHT","SALARY":5500.000000}]}
|
||||||
@@ -143,25 +266,382 @@ Json_Object(DEPARTMENT, TITLE, Json_Array_Grp(Json_Object(SERIALNO, NAME, SALARY
|
|||||||
{"DEPARTMENT":"2452","TITLE":"ENGINEER","EMPLOYES":[{"SERIALNO":"31416","NAME":"ORELLY","SALARY":13400.000000},{"SERIALNO":"02345","NAME":"SMITH","SALARY":9000.000000}]}
|
{"DEPARTMENT":"2452","TITLE":"ENGINEER","EMPLOYES":[{"SERIALNO":"31416","NAME":"ORELLY","SALARY":13400.000000},{"SERIALNO":"02345","NAME":"SMITH","SALARY":9000.000000}]}
|
||||||
{"DEPARTMENT":"2452","TITLE":"SCIENTIST","EMPLOYES":[{"SERIALNO":"34567","NAME":"BIGHEAD","SALARY":8000.000000},{"SERIALNO":"36666","NAME":"BIGHORN","SALARY":11000.000000}]}
|
{"DEPARTMENT":"2452","TITLE":"SCIENTIST","EMPLOYES":[{"SERIALNO":"34567","NAME":"BIGHEAD","SALARY":8000.000000},{"SERIALNO":"36666","NAME":"BIGHORN","SALARY":11000.000000}]}
|
||||||
{"DEPARTMENT":"2452","TITLE":"SECRETARY","EMPLOYES":[{"SERIALNO":"11111","NAME":"CHERRY","SALARY":4500.000000}]}
|
{"DEPARTMENT":"2452","TITLE":"SECRETARY","EMPLOYES":[{"SERIALNO":"11111","NAME":"CHERRY","SALARY":4500.000000}]}
|
||||||
SELECT Json_Object_Grp(SALARY) FROM t1;
|
SELECT Json_Object_Grp(SALARY) FROM t3;
|
||||||
ERROR HY000: Can't initialize function 'Json_Object_Grp'; Json_Array_Grp can only accept 2 arguments
|
ERROR HY000: Can't initialize function 'json_object_grp'; This function requires 2 arguments (key, value)
|
||||||
SELECT Json_Object_Grp(SALARY, NAME) FROM t1;
|
SELECT Json_Object_Grp(NAME, SALARY) FROM t3;
|
||||||
Json_Object_Grp(SALARY, NAME)
|
Json_Object_Grp(NAME, SALARY)
|
||||||
{"BANCROFT":9600.000000,"SMITH":9000.000000,"MERCHANT":8700.000000,"FUNNIGUY":8500.000000,"BUGHAPPY":8500.000000,"BIGHEAD":8000.000000,"SHRINKY":7500.000000,"WALTER":7400.000000,"FODDERMAN":7000.000000,"TONGHO":6800.000000,"SHORTSIGHT":5500.000000,"MESSIFUL":5000.500000,"HONEY":4900.000000,"GOOSEPEN":4700.000000,"CHERRY":4500.000000,"MONAPENNY":3800.000000,"KITTY":3000.450000,"PLUMHEAD":2800.000000,"STRONG":23000.000000,"BULLOZER":14800.000000,"WERTHER":14500.000000,"QUINN":14000.000000,"ORELLY":13400.000000,"BIGHORN":11000.000000,"BROWNY":10500.000000,"WHEELFOR":10030.000000,"MARTIN":10000.000000}
|
{"BANCROFT":9600.000000,"SMITH":9000.000000,"MERCHANT":8700.000000,"FUNNIGUY":8500.000000,"BUGHAPPY":8500.000000,"BIGHEAD":8000.000000,"SHRINKY":7500.000000,"WALTER":7400.000000,"FODDERMAN":7000.000000,"TONGHO":6800.000000,"SHORTSIGHT":5500.000000,"MESSIFUL":5000.500000,"HONEY":4900.000000,"GOOSEPEN":4700.000000,"CHERRY":4500.000000,"MONAPENNY":3800.000000,"KITTY":3000.450000,"PLUMHEAD":2800.000000,"STRONG":23000.000000,"BULLOZER":14800.000000,"WERTHER":14500.000000,"QUINN":14000.000000,"ORELLY":13400.000000,"BIGHORN":11000.000000,"BROWNY":10500.000000,"WHEELFOR":10030.000000,"MARTIN":10000.000000}
|
||||||
SELECT Json_Object(DEPARTMENT, Json_Object_Grp(SALARY, NAME) "Json_SALARIES") FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Object(DEPARTMENT, Json_Object_Grp(NAME, SALARY) "Json_SALARIES") FROM t3 GROUP BY DEPARTMENT;
|
||||||
Json_Object(DEPARTMENT, Json_Object_Grp(SALARY, NAME) "Json_SALARIES")
|
Json_Object(DEPARTMENT, Json_Object_Grp(NAME, SALARY) "Json_SALARIES")
|
||||||
{"DEPARTMENT":"0021","SALARIES":{"STRONG":23000.000000,"SHORTSIGHT":5500.000000}}
|
{"DEPARTMENT":"0021","SALARIES":{"STRONG":23000.000000,"SHORTSIGHT":5500.000000}}
|
||||||
{"DEPARTMENT":"0318","SALARIES":{"BANCROFT":9600.000000,"PLUMHEAD":2800.000000,"HONEY":4900.000000,"TONGHO":6800.000000,"WALTER":7400.000000,"SHRINKY":7500.000000,"WERTHER":14500.000000,"MERCHANT":8700.000000,"WHEELFOR":10030.000000}}
|
{"DEPARTMENT":"0318","SALARIES":{"BANCROFT":9600.000000,"PLUMHEAD":2800.000000,"HONEY":4900.000000,"TONGHO":6800.000000,"WALTER":7400.000000,"SHRINKY":7500.000000,"WERTHER":14500.000000,"MERCHANT":8700.000000,"WHEELFOR":10030.000000}}
|
||||||
{"DEPARTMENT":"0319","SALARIES":{"BULLOZER":14800.000000,"QUINN":14000.000000,"BROWNY":10500.000000,"KITTY":3000.450000,"MONAPENNY":3800.000000,"MARTIN":10000.000000,"FUNNIGUY":8500.000000,"BUGHAPPY":8500.000000,"FODDERMAN":7000.000000,"MESSIFUL":5000.500000,"GOOSEPEN":4700.000000}}
|
{"DEPARTMENT":"0319","SALARIES":{"BULLOZER":14800.000000,"QUINN":14000.000000,"BROWNY":10500.000000,"KITTY":3000.450000,"MONAPENNY":3800.000000,"MARTIN":10000.000000,"FUNNIGUY":8500.000000,"BUGHAPPY":8500.000000,"FODDERMAN":7000.000000,"MESSIFUL":5000.500000,"GOOSEPEN":4700.000000}}
|
||||||
{"DEPARTMENT":"2452","SALARIES":{"BIGHEAD":8000.000000,"ORELLY":13400.000000,"BIGHORN":11000.000000,"SMITH":9000.000000,"CHERRY":4500.000000}}
|
{"DEPARTMENT":"2452","SALARIES":{"BIGHEAD":8000.000000,"ORELLY":13400.000000,"BIGHORN":11000.000000,"SMITH":9000.000000,"CHERRY":4500.000000}}
|
||||||
SELECT Json_Array_Grp(NAME) from t1;
|
SELECT Json_Array_Grp(NAME) FROM t3;
|
||||||
Json_Array_Grp(NAME)
|
Json_Array_Grp(NAME)
|
||||||
["BANCROFT","SMITH","MERCHANT","FUNNIGUY","BUGHAPPY","BIGHEAD","SHRINKY","WALTER","FODDERMAN","TONGHO","SHORTSIGHT","MESSIFUL","HONEY","GOOSEPEN","CHERRY","MONAPENNY","KITTY","PLUMHEAD","STRONG","BULLOZER","WERTHER","QUINN","ORELLY","BIGHORN","BROWNY","WHEELFOR","MARTIN"]
|
["BANCROFT","SMITH","MERCHANT","FUNNIGUY","BUGHAPPY","BIGHEAD","SHRINKY","WALTER","FODDERMAN","TONGHO","SHORTSIGHT","MESSIFUL","HONEY","GOOSEPEN","CHERRY","MONAPENNY","KITTY","PLUMHEAD","STRONG","BULLOZER","WERTHER","QUINN","ORELLY","BIGHORN","BROWNY","WHEELFOR","MARTIN"]
|
||||||
|
SELECT Json_Object_Key(name, title) FROM t3 WHERE DEPARTMENT = 318;
|
||||||
|
Json_Object_Key(name, title)
|
||||||
|
{"BANCROFT":"SALESMAN"}
|
||||||
|
{"MERCHANT":"SALESMAN"}
|
||||||
|
{"SHRINKY":"ADMINISTRATOR"}
|
||||||
|
{"WALTER":"ENGINEER"}
|
||||||
|
{"TONGHO":"ENGINEER"}
|
||||||
|
{"HONEY":"SECRETARY"}
|
||||||
|
{"PLUMHEAD":"TYPIST"}
|
||||||
|
{"WERTHER":"DIRECTOR"}
|
||||||
|
{"WHEELFOR":"SALESMAN"}
|
||||||
|
SELECT Json_Object_Grp(name, title) FROM t3 WHERE DEPARTMENT = 318;
|
||||||
|
Json_Object_Grp(name, title)
|
||||||
|
{"BANCROFT":"SALESMAN","MERCHANT":"SALESMAN","SHRINKY":"ADMINISTRATOR","WALTER":"ENGINEER","TONGHO":"ENGINEER","HONEY":"SECRETARY","PLUMHEAD":"TYPIST","WERTHER":"DIRECTOR","WHEELFOR":"SALESMAN"}
|
||||||
|
#
|
||||||
|
# Test value getting UDF's
|
||||||
|
#
|
||||||
|
SELECT JsonGet_String(Json_Array_Grp(name),'[#]') FROM t3;
|
||||||
|
JsonGet_String(Json_Array_Grp(name),'[#]')
|
||||||
|
27
|
||||||
|
SELECT JsonGet_String(Json_Array_Grp(name),'[","]') FROM t3;
|
||||||
|
JsonGet_String(Json_Array_Grp(name),'[","]')
|
||||||
|
BANCROFT,SMITH,MERCHANT,FUNNIGUY,BUGHAPPY,BIGHEAD,SHRINKY,WALTER,FODDERMAN,TONGHO,SHORTSIGHT,MESSIFUL,HONEY,GOOSEPEN,CHERRY,MONAPENNY,KITTY,PLUMHEAD,STRONG,BULLOZER,WERTHER,QUINN,ORELLY,BIGHORN,BROWNY,WHEELFOR,MARTIN
|
||||||
|
SELECT JsonGet_String(Json_Array_Grp(name),'[>]') FROM t3;
|
||||||
|
JsonGet_String(Json_Array_Grp(name),'[>]')
|
||||||
|
WHEELFOR
|
||||||
|
SET @j1 = '[45,28,36,45,89]';
|
||||||
|
SELECT JsonGet_String(@j1,'[1]');
|
||||||
|
JsonGet_String(@j1,'[1]')
|
||||||
|
28
|
||||||
|
SELECT JsonGet_String(@j1 json_,'[3]');
|
||||||
|
JsonGet_String(@j1 json_,'[3]')
|
||||||
|
45
|
||||||
|
SELECT JsonGet_String(Json_Array(45,28,36,45,89),'[3]');
|
||||||
|
JsonGet_String(Json_Array(45,28,36,45,89),'[3]')
|
||||||
|
45
|
||||||
|
SELECT JsonGet_String(Json_Array(45,28,36,45,89),'["+"]') "list",'=' as "egal",JsonGet_String(Json_Array(45,28,36,45,89),'[+]') "sum";
|
||||||
|
list egal sum
|
||||||
|
45+28+36+45+89 = 243.00
|
||||||
|
SELECT JsonGet_String(Json_Array(json_array(45,28),json_array(36,45,89)),'[1]:[0]');
|
||||||
|
JsonGet_String(Json_Array(json_array(45,28),json_array(36,45,89)),'[1]:[0]')
|
||||||
|
36
|
||||||
|
SELECT JsonGet_String(Json_Array(json_array(45,28),json_array(36,45,89)),'[1]:*');
|
||||||
|
JsonGet_String(Json_Array(json_array(45,28),json_array(36,45,89)),'[1]:*')
|
||||||
|
[36,45,89]
|
||||||
|
SELECT JsonGet_String(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'truc');
|
||||||
|
JsonGet_String(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'truc')
|
||||||
|
machin
|
||||||
|
SET @j2 = '{"qty":56,"price":3.141600,"truc":"machin","garanty":null}';
|
||||||
|
SELECT JsonGet_String(@j2 json_,'truc');
|
||||||
|
JsonGet_String(@j2 json_,'truc')
|
||||||
|
machin
|
||||||
|
SELECT JsonGet_String(@j2,'truc');
|
||||||
|
JsonGet_String(@j2,'truc')
|
||||||
|
machin
|
||||||
|
SELECT JsonGet_String(@j2,'chose');
|
||||||
|
JsonGet_String(@j2,'chose')
|
||||||
|
NULL
|
||||||
|
SELECT JsonGet_String(NULL json_, NULL);
|
||||||
|
JsonGet_String(NULL json_, NULL)
|
||||||
|
NULL
|
||||||
|
Warnings:
|
||||||
|
Warning 1105
|
||||||
|
SELECT department, JsonGet_String(Json_Object(department, Json_Array_Grp(salary) "Json_salaries"),'salaries:[+]') Sumsal FROM t3 GROUP BY department;
|
||||||
|
department Sumsal
|
||||||
|
0021 28500.00
|
||||||
|
0318 72230.00
|
||||||
|
0319 89800.95
|
||||||
|
2452 45900.00
|
||||||
|
SELECT JsonGet_Int(@j1, '[4]');
|
||||||
|
JsonGet_Int(@j1, '[4]')
|
||||||
|
89
|
||||||
|
SELECT JsonGet_Int(@j1, '[#]');
|
||||||
|
JsonGet_Int(@j1, '[#]')
|
||||||
|
5
|
||||||
|
SELECT JsonGet_Int(@j1, '[+]');
|
||||||
|
JsonGet_Int(@j1, '[+]')
|
||||||
|
243
|
||||||
|
SELECT JsonGet_Int(@j1 json_, '[3]');
|
||||||
|
JsonGet_Int(@j1 json_, '[3]')
|
||||||
|
45
|
||||||
|
SELECT JsonGet_Int(Json_Array(45,28,36,45,89), '[3]');
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[3]')
|
||||||
|
45
|
||||||
|
SELECT JsonGet_Int(Json_Array(45,28,36,45,89), '["+"]');
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '["+"]')
|
||||||
|
45
|
||||||
|
SELECT JsonGet_Int(Json_Array(45,28,36,45,89), '[+]');
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[+]')
|
||||||
|
243
|
||||||
|
SELECT JsonGet_Int(Json_Array(json_array(45,28), json_array(36,45,89)), '[1]:[0]');
|
||||||
|
JsonGet_Int(Json_Array(json_array(45,28), json_array(36,45,89)), '[1]:[0]')
|
||||||
|
36
|
||||||
|
SELECT JsonGet_Int(Json_Array(json_array(45,28), json_array(36,45,89)), '[0]:[1]');
|
||||||
|
JsonGet_Int(Json_Array(json_array(45,28), json_array(36,45,89)), '[0]:[1]')
|
||||||
|
28
|
||||||
|
SELECT JsonGet_Int(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'qty');
|
||||||
|
JsonGet_Int(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'qty')
|
||||||
|
56
|
||||||
|
SELECT JsonGet_Int(@j2 json_, 'price');
|
||||||
|
JsonGet_Int(@j2 json_, 'price')
|
||||||
|
3
|
||||||
|
SELECT JsonGet_Int(@j2, 'qty');
|
||||||
|
JsonGet_Int(@j2, 'qty')
|
||||||
|
56
|
||||||
|
SELECT JsonGet_Int('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'chose');
|
||||||
|
JsonGet_Int('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'chose')
|
||||||
|
NULL
|
||||||
|
SELECT JsonGet_Int(JsonGet_String(Json_Array(Json_Array(45,28),Json_Array(36,45,89)), '[1]:*'), '[+]') sum;
|
||||||
|
sum
|
||||||
|
170
|
||||||
|
SELECT department, JsonGet_Int(Json_Object(department, Json_Array_Grp(salary) "Json_salaries"), 'salaries:[+]') Sumsal FROM t3 GROUP BY department;
|
||||||
|
department Sumsal
|
||||||
|
0021 28500
|
||||||
|
0318 72230
|
||||||
|
0319 89800
|
||||||
|
2452 45900
|
||||||
|
SELECT JsonGet_Real(@j1, '[2]');
|
||||||
|
JsonGet_Real(@j1, '[2]')
|
||||||
|
36.000000000000000
|
||||||
|
SELECT JsonGet_Real(@j1 json_, '[3]', 2);
|
||||||
|
JsonGet_Real(@j1 json_, '[3]', 2)
|
||||||
|
45.00
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '[3]');
|
||||||
|
JsonGet_Real(Json_Array(45,28,36,45,89), '[3]')
|
||||||
|
45.000000000000000
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '["+"]');
|
||||||
|
JsonGet_Real(Json_Array(45,28,36,45,89), '["+"]')
|
||||||
|
45.000000000000000
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '[+]');
|
||||||
|
JsonGet_Real(Json_Array(45,28,36,45,89), '[+]')
|
||||||
|
243.000000000000000
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '[!]');
|
||||||
|
JsonGet_Real(Json_Array(45,28,36,45,89), '[!]')
|
||||||
|
48.600000000000000
|
||||||
|
SELECT JsonGet_Real(Json_Array(json_array(45,28), json_array(36,45,89)), '[1]:[0]');
|
||||||
|
JsonGet_Real(Json_Array(json_array(45,28), json_array(36,45,89)), '[1]:[0]')
|
||||||
|
36.000000000000000
|
||||||
|
SELECT JsonGet_Real(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'price');
|
||||||
|
JsonGet_Real(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'price')
|
||||||
|
3.141600000000000
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}' json_, 'qty');
|
||||||
|
JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}' json_, 'qty')
|
||||||
|
56.000000000000000
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'price');
|
||||||
|
JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'price')
|
||||||
|
3.141600000000000
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'price', 4);
|
||||||
|
JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'price', 4)
|
||||||
|
3.1416
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'chose');
|
||||||
|
JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'chose')
|
||||||
|
NULL
|
||||||
|
SELECT department, JsonGet_Real(Json_Object(department, Json_Array_Grp(salary) "Json_salaries"),'salaries:[+]') Sumsal FROM t3 GROUP BY department;
|
||||||
|
department Sumsal
|
||||||
|
0021 28500.000000000000000
|
||||||
|
0318 72230.000000000000000
|
||||||
|
0319 89800.950000000000000
|
||||||
|
2452 45900.000000000000000
|
||||||
|
#
|
||||||
|
# Documentation examples
|
||||||
|
#
|
||||||
|
SELECT
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[4]') "Rank",
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[#]') "Number",
|
||||||
|
JsonGet_String(Json_Array(45,28,36,45,89), '[","]') "Concat",
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[+]') "Sum",
|
||||||
|
JsonGet_Real(Json_Array(45,28,36,45,89), '[!]', 2) "Avg";
|
||||||
|
Rank Number Concat Sum Avg
|
||||||
|
89 5 45,28,36,45,89 243 48.60
|
||||||
|
SELECT
|
||||||
|
JsonGet_String('{"qty":7,"price":29.50,"garanty":null}', 'price') "String",
|
||||||
|
JsonGet_Int('{"qty":7,"price":29.50,"garanty":null}', 'price') "Int",
|
||||||
|
JsonGet_Real('{"qty":7,"price":29.50,"garanty":null}', 'price') "Real";
|
||||||
|
String Int Real
|
||||||
|
29.50 29 29.500000000000000
|
||||||
|
SELECT JsonGet_Real('{"qty":7,"price":29.50,"garanty":null}', 'price', 3) "Real";
|
||||||
|
Real
|
||||||
|
29.500
|
||||||
|
#
|
||||||
|
# Testing Locate
|
||||||
|
#
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'machin');
|
||||||
|
JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'machin')
|
||||||
|
truc
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),56);
|
||||||
|
JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),56)
|
||||||
|
qty
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),3.1416);
|
||||||
|
JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),3.1416)
|
||||||
|
price
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'chose');
|
||||||
|
JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'chose')
|
||||||
|
NULL
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, 'Jack') Path;
|
||||||
|
Path
|
||||||
|
AUTHORS:[1]:FN
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, 'jack' ci) Path;
|
||||||
|
Path
|
||||||
|
AUTHORS:[1]:FN
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, '{"FN":"Jack", "LN":"London"}' json_) Path;
|
||||||
|
Path
|
||||||
|
AUTHORS:[1]
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, '{"FN":"jack", "LN":"London"}' json_) Path;
|
||||||
|
Path
|
||||||
|
NULL
|
||||||
|
SELECT JsonLocate('[45,28,36,45,89]',36);
|
||||||
|
JsonLocate('[45,28,36,45,89]',36)
|
||||||
|
[2]
|
||||||
|
SELECT JsonLocate('[45,28,36,45,89]' json_,28.0);
|
||||||
|
JsonLocate('[45,28,36,45,89]' json_,28.0)
|
||||||
|
NULL
|
||||||
|
SELECT Json_Locate_All('[45,28,36,45,89]',10);
|
||||||
|
Json_Locate_All('[45,28,36,45,89]',10)
|
||||||
|
[]
|
||||||
|
SELECT Json_Locate_All('[45,28,36,45,89]',45);
|
||||||
|
Json_Locate_All('[45,28,36,45,89]',45)
|
||||||
|
["[0]","[3]"]
|
||||||
|
SELECT Json_Locate_All('[[45,28],36,45,89]',45);
|
||||||
|
Json_Locate_All('[[45,28],36,45,89]',45)
|
||||||
|
["[0]:[0]","[2]"]
|
||||||
|
SELECT Json_Locate_All('[[45,28,45],36,45,89]',45);
|
||||||
|
Json_Locate_All('[[45,28,45],36,45,89]',45)
|
||||||
|
["[0]:[0]","[0]:[2]","[2]"]
|
||||||
|
SELECT Json_Locate_All('[[45,28,45],36,45,89]',JsonGet_Int('[3,45]','[1]'));
|
||||||
|
Json_Locate_All('[[45,28,45],36,45,89]',JsonGet_Int('[3,45]','[1]'))
|
||||||
|
["[0]:[0]","[0]:[2]","[2]"]
|
||||||
|
SELECT JsonLocate('[[45,28,45],36,45,89]',45,n) from t1;
|
||||||
|
JsonLocate('[[45,28,45],36,45,89]',45,n)
|
||||||
|
[0]:[0]
|
||||||
|
[0]:[2]
|
||||||
|
[2]
|
||||||
|
NULL
|
||||||
|
NULL
|
||||||
|
SELECT JsonGet_String(Json_Locate_All('[[45,28,45],36,45,89]',45),concat('[',n-1,']')) FROM t1;
|
||||||
|
JsonGet_String(Json_Locate_All('[[45,28,45],36,45,89]',45),concat('[',n-1,']'))
|
||||||
|
[0]:[0]
|
||||||
|
[0]:[2]
|
||||||
|
[2]
|
||||||
|
NULL
|
||||||
|
NULL
|
||||||
|
SELECT JsonGet_String(Json_Locate_All('[[45,28,45],36,45,89]',45),concat('[',n-1,']')) AS `Path` FROM t1 GROUP BY n HAVING `Path` IS NOT NULL;
|
||||||
|
Path
|
||||||
|
[0]:[0]
|
||||||
|
[0]:[2]
|
||||||
|
[2]
|
||||||
|
SELECT Json_Locate_All('[45,28,[36,45,89]]',45);
|
||||||
|
Json_Locate_All('[45,28,[36,45,89]]',45)
|
||||||
|
["[0]","[2]:[1]"]
|
||||||
|
SELECT Json_Locate_All('[[45,28],[36,45.0,89]]',JsonValue(45.0));
|
||||||
|
Json_Locate_All('[[45,28],[36,45.0,89]]',JsonValue(45.0))
|
||||||
|
[]
|
||||||
|
SELECT Json_Locate_All('[[45,28],[36,45.0,89]]',45.0);
|
||||||
|
Json_Locate_All('[[45,28],[36,45.0,89]]',45.0)
|
||||||
|
["[1]:[1]"]
|
||||||
|
SELECT JsonLocate('[[45,28],[36,45,89]]','[36,45,89]' json_);
|
||||||
|
JsonLocate('[[45,28],[36,45,89]]','[36,45,89]' json_)
|
||||||
|
[1]
|
||||||
|
SELECT JsonLocate('[[45,28],[36,45,89]]','[45,28]' json_);
|
||||||
|
JsonLocate('[[45,28],[36,45,89]]','[45,28]' json_)
|
||||||
|
[0]
|
||||||
|
SELECT Json_Locate_All('[[45,28],[[36,45],89]]','45') "All paths";
|
||||||
|
All paths
|
||||||
|
[]
|
||||||
|
SELECT Json_Locate_All('[[45,28],[[36,45],89]]','[36,45]' json_);
|
||||||
|
Json_Locate_All('[[45,28],[[36,45],89]]','[36,45]' json_)
|
||||||
|
["[1]:[0]"]
|
||||||
|
SELECT JsonGet_Int(Json_Locate_All('[[45,28],[[36,45],89]]',45), '[#]') "Nb of occurs";
|
||||||
|
Nb of occurs
|
||||||
|
2
|
||||||
|
SELECT Json_Locate_All('[[45,28],[[36,45],89]]',45,2);
|
||||||
|
Json_Locate_All('[[45,28],[[36,45],89]]',45,2)
|
||||||
|
["[0]:[0]"]
|
||||||
|
SELECT JsonGet_String(Json_Locate_All('[45,28,36,45,89]',45),'[0]');
|
||||||
|
JsonGet_String(Json_Locate_All('[45,28,36,45,89]',45),'[0]')
|
||||||
|
[0]
|
||||||
|
SELECT JsonLocate(Json_File('test/biblio.json'), 'Knab');
|
||||||
|
JsonLocate(Json_File('test/biblio.json'), 'Knab')
|
||||||
|
[0]:AUTHOR:[1]:LASTNAME
|
||||||
|
SELECT Json_Locate_All('test/biblio.json' jfile_, 'Knab');
|
||||||
|
Json_Locate_All('test/biblio.json' jfile_, 'Knab')
|
||||||
|
["[0]:AUTHOR:[1]:LASTNAME"]
|
||||||
|
#
|
||||||
|
# Testing json files
|
||||||
|
#
|
||||||
|
SELECT Jfile_Make('[{"_id":5,"type":"food","item":"beer","taste":"light","price":5.65,"ratings":[5,8,9]},
|
||||||
|
{"_id":6,"type":"car","item":"roadster","mileage":56000,"ratings":[6,9]},
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,4]},
|
||||||
|
{"_id":8,"type":"furniture","item":"table","size":{"W":60,"L":80,"H":40},"ratings":[5,8,7]}]', 'test/fx.json', 0) AS NewFile;
|
||||||
|
NewFile
|
||||||
|
test/fx.json
|
||||||
|
SELECT Jfile_Make('test/fx.json', 1);
|
||||||
|
Jfile_Make('test/fx.json', 1)
|
||||||
|
test/fx.json
|
||||||
|
SELECT Jfile_Make('test/fx.json' jfile_);
|
||||||
|
Jfile_Make('test/fx.json' jfile_)
|
||||||
|
test/fx.json
|
||||||
|
SELECT Jfile_Make(Jbin_File('test/fx.json'), 0);
|
||||||
|
Jfile_Make(Jbin_File('test/fx.json'), 0)
|
||||||
|
test/fx.json
|
||||||
|
SELECT Json_File('test/fx.json', 1);
|
||||||
|
Json_File('test/fx.json', 1)
|
||||||
|
[{"_id":5,"type":"food","item":"beer","taste":"light","price":5.65,"ratings":[5,8,9]},{"_id":6,"type":"car","item":"roadster","mileage":56000,"ratings":[6,9]},{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,4]},{"_id":8,"type":"furniture","item":"table","size":{"W":60,"L":80,"H":40},"ratings":[5,8,7]}]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 File pretty format doesn't match the specified pretty value
|
||||||
|
SELECT Json_File('test/fx.json', 2);
|
||||||
|
Json_File('test/fx.json', 2)
|
||||||
|
[{"_id":5,"type":"food","item":"beer","taste":"light","price":5.65,"ratings":[5,8,9]},{"_id":6,"type":"car","item":"roadster","mileage":56000,"ratings":[6,9]},{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,4]},{"_id":8,"type":"furniture","item":"table","size":{"W":60,"L":80,"H":40},"ratings":[5,8,7]}]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 File pretty format doesn't match the specified pretty value
|
||||||
|
SELECT Json_File('test/fx.json', 0);
|
||||||
|
Json_File('test/fx.json', 0)
|
||||||
|
[{"_id":5,"type":"food","item":"beer","taste":"light","price":5.65,"ratings":[5,8,9]},{"_id":6,"type":"car","item":"roadster","mileage":56000,"ratings":[6,9]},{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,4]},{"_id":8,"type":"furniture","item":"table","size":{"W":60,"L":80,"H":40},"ratings":[5,8,7]}]
|
||||||
|
SELECT Json_File('test/fx.json', '[0]');
|
||||||
|
Json_File('test/fx.json', '[0]')
|
||||||
|
{"_id":5,"type":"food","item":"beer","taste":"light","price":5.65,"ratings":[5,8,9]}
|
||||||
|
SELECT Json_File('test/fx.json', '[?]');
|
||||||
|
Json_File('test/fx.json', '[?]')
|
||||||
|
NULL
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 Invalid function specification ?
|
||||||
|
SELECT JsonGet_String(Json_File('test/fx.json'), '[1]:*');
|
||||||
|
JsonGet_String(Json_File('test/fx.json'), '[1]:*')
|
||||||
|
{"_id":6,"type":"car","item":"roadster","mileage":56000,"ratings":[6,9]}
|
||||||
|
SELECT JsonGet_String(Json_File('test/fx.json'), '[1]');
|
||||||
|
JsonGet_String(Json_File('test/fx.json'), '[1]')
|
||||||
|
6 car roadster 56000 ???
|
||||||
|
SELECT JsonGet_Int(Json_File('test/fx.json'), '[1]:mileage') AS Mileage;
|
||||||
|
Mileage
|
||||||
|
56000
|
||||||
|
SELECT JsonGet_Real(Json_File('test/fx.json'), '[0]:price', 2) AS Price;
|
||||||
|
Price
|
||||||
|
5.65
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 'ratings');
|
||||||
|
Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 'ratings')
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,4,6]}
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 1, 'ratings');
|
||||||
|
Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 1, 'ratings')
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,6,4]}
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 'ratings', 1);
|
||||||
|
Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 'ratings', 1)
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,6,4]}
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]:ratings'), 6, 0);
|
||||||
|
Json_Array_Add(Json_File('test/fx.json', '[2]:ratings'), 6, 0)
|
||||||
|
[6,2,4]
|
||||||
|
SELECT Json_Array_Delete(Json_File('test/fx.json', '[2]'), 'ratings', 1);
|
||||||
|
Json_Array_Delete(Json_File('test/fx.json', '[2]'), 'ratings', 1)
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2]}
|
||||||
|
SELECT Json_Object_Add(Json_File('test/fx.json', '[2]'), 'france' origin);
|
||||||
|
Json_Object_Add(Json_File('test/fx.json', '[2]'), 'france' origin)
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"france","ratings":[2,4]}
|
||||||
|
SELECT Json_Object_Add(Json_File('test/fx.json', '[2]'), 70 H, 'size');
|
||||||
|
Json_Object_Add(Json_File('test/fx.json', '[2]'), 70 H, 'size')
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,4]}
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 No sub-item at 'size'
|
||||||
|
SELECT Json_Object_Add(Json_File('test/fx.json', '[3]'), 70 H, 'size');
|
||||||
|
Json_Object_Add(Json_File('test/fx.json', '[3]'), 70 H, 'size')
|
||||||
|
{"_id":8,"type":"furniture","item":"table","size":{"W":60,"L":80,"H":70},"ratings":[5,8,7]}
|
||||||
|
SELECT Json_Object_List(Json_File('test/fx.json', '[3]:size'));
|
||||||
|
Json_Object_List(Json_File('test/fx.json', '[3]:size'))
|
||||||
|
["W","L","H"]
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
DROP FUNCTION Json_Array;
|
DROP TABLE t2;
|
||||||
DROP FUNCTION Json_Array_Add;
|
DROP TABLE t3;
|
||||||
DROP FUNCTION Json_Object;
|
|
||||||
DROP FUNCTION Json_Object_Nonull;
|
|
||||||
DROP FUNCTION Json_Value;
|
|
||||||
DROP FUNCTION Json_Array_Grp;
|
|
||||||
DROP FUNCTION Json_Object_Grp;
|
|
||||||
|
588
storage/connect/mysql-test/connect/r/json_udf_bin.result
Normal file
588
storage/connect/mysql-test/connect/r/json_udf_bin.result
Normal file
@@ -0,0 +1,588 @@
|
|||||||
|
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=VIR BLOCK_SIZE=3;
|
||||||
|
#
|
||||||
|
# Test Jbin UDF's
|
||||||
|
#
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), n) from t1;
|
||||||
|
Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), n)
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,1]
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,2]
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,3]
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(n, 3.1416, 'My name is "Foo"', NULL), n) from t1;
|
||||||
|
Json_Array_Add(Jbin_Array(n, 3.1416, 'My name is "Foo"', NULL), n)
|
||||||
|
[1,3.141600,"My name is \"Foo\"",null,1]
|
||||||
|
[2,3.141600,"My name is \"Foo\"",null,2]
|
||||||
|
[3,3.141600,"My name is \"Foo\"",null,3]
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), Jbin_Array('a','b',n)) from t1;
|
||||||
|
Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), Jbin_Array('a','b',n))
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,["a","b",1]]
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,["a","b",2]]
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,["a","b",3]]
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), JsonGet_String(Jbin_Array('a','b','c'), '[1]'));
|
||||||
|
Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), JsonGet_String(Jbin_Array('a','b','c'), '[1]'))
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,"b"]
|
||||||
|
SELECT Json_Array_Delete(Jbin_Array_Add_Values(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), "One more", 2), 4);
|
||||||
|
Json_Array_Delete(Jbin_Array_Add_Values(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), "One more", 2), 4)
|
||||||
|
[56,3.141600,"My name is \"Foo\"",null,2]
|
||||||
|
SELECT Json_Array_Delete(Jbin_Array(56, Jbin_Array(3.1416, 'My name is "Foo"'), NULL), '[1]', 1);
|
||||||
|
Json_Array_Delete(Jbin_Array(56, Jbin_Array(3.1416, 'My name is "Foo"'), NULL), '[1]', 1)
|
||||||
|
[56,[3.141600],null]
|
||||||
|
SELECT Json_Array_Delete(Jbin_Array(56, Jbin_Array(3.1416, 'My name is "Foo"'), TRUE), 1, '[1]');
|
||||||
|
Json_Array_Delete(Jbin_Array(56, Jbin_Array(3.1416, 'My name is "Foo"'), TRUE), 1, '[1]')
|
||||||
|
[56,[3.141600],true]
|
||||||
|
SELECT Json_Array(1, TRUE, 0, FALSE);
|
||||||
|
Json_Array(1, TRUE, 0, FALSE)
|
||||||
|
[1,true,0,false]
|
||||||
|
SELECT Json_Serialize(Jbin_Array(TRUE, FALSE));
|
||||||
|
Json_Serialize(Jbin_Array(TRUE, FALSE))
|
||||||
|
[true,false]
|
||||||
|
SELECT Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL);
|
||||||
|
Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL)
|
||||||
|
{"qty":56,"price":3.141600,"truc":"machin","garanty":null}
|
||||||
|
SELECT Json_Serialize(Jbin_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL));
|
||||||
|
Json_Serialize(Jbin_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL))
|
||||||
|
{"qty":56,"price":3.141600,"truc":"machin","garanty":null}
|
||||||
|
SELECT Jbin_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty');
|
||||||
|
ERROR HY000: Can't initialize function 'jbin_object_key'; This function must have an even number of arguments
|
||||||
|
SELECT Json_Object_Add(Jbin_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color);
|
||||||
|
Json_Object_Add(Jbin_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color)
|
||||||
|
{"qty":56,"price":3.141600,"truc":"machin","garanty":null,"color":"blue"}
|
||||||
|
SELECT Json_Object_Add(Jbin_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price);
|
||||||
|
Json_Object_Add(Jbin_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price)
|
||||||
|
{"qty":56,"price":45.990000,"truc":"machin","garanty":null}
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Nonull(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color);
|
||||||
|
Json_Object_Add(Jbin_Object_Nonull(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color)
|
||||||
|
{"qty":56,"price":3.141600,"truc":"machin","color":"blue"}
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Nonull(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price);
|
||||||
|
Json_Object_Add(Jbin_Object_Nonull(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price)
|
||||||
|
{"qty":56,"price":45.990000,"truc":"machin"}
|
||||||
|
#
|
||||||
|
# Test Jbin file UDF's
|
||||||
|
#
|
||||||
|
SELECT Json_Serialize(Jbin_File('gloss.json'));
|
||||||
|
Json_Serialize(Jbin_File('gloss.json'))
|
||||||
|
{"glossary":{"title":"example glossary","GlossDiv":{"title":"S","GlossList":{"GlossEntry":{"ID":"SGML","SortAs":"SGML","GlossTerm":"Standard Generalized Markup Language","Acronym":"SGML","Abbrev":"ISO 8879:1986","GlossDef":{"para":"A meta-markup language, used to create markup languages such as DocBook.","GlossSeeAlso":["GML","XML"]},"GlossSee":"markup"}}}}}
|
||||||
|
SELECT JsonLocate(Jbin_File('gloss.json'),'XML');
|
||||||
|
JsonLocate(Jbin_File('gloss.json'),'XML')
|
||||||
|
glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso:[1]
|
||||||
|
SELECT Json_Object_Key('first', 'foo', 'second', Jbin_Array('a', 33));
|
||||||
|
Json_Object_Key('first', 'foo', 'second', Jbin_Array('a', 33))
|
||||||
|
{"first":"foo","second":["a",33]}
|
||||||
|
SELECT Json_Get_Item(Json_Array('a','b','c'), '[1]');
|
||||||
|
Json_Get_Item(Json_Array('a','b','c'), '[1]')
|
||||||
|
NULL
|
||||||
|
SELECT Json_Get_Item(Json_Object('foo' AS "first", Json_Array('a', 33) AS "json_second"), 'second') AS "item";
|
||||||
|
item
|
||||||
|
["a",33]
|
||||||
|
SELECT Json_Get_Item(Jbin_Object('foo' first, Jbin_Array('a', 33) jbin_second), 'second:*') item;
|
||||||
|
item
|
||||||
|
["a",33]
|
||||||
|
SELECT Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv');
|
||||||
|
Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv')
|
||||||
|
{"title":"S","GlossList":{"GlossEntry":{"ID":"SGML","SortAs":"SGML","GlossTerm":"Standard Generalized Markup Language","Acronym":"SGML","Abbrev":"ISO 8879:1986","GlossDef":{"para":"A meta-markup language, used to create markup languages such as DocBook.","GlossSeeAlso":["GML","XML"]},"GlossSee":"markup"}}}
|
||||||
|
SELECT Json_Serialize(Jbin_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv'));
|
||||||
|
Json_Serialize(Jbin_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv'))
|
||||||
|
{"title":"S","GlossList":{"GlossEntry":{"ID":"SGML","SortAs":"SGML","GlossTerm":"Standard Generalized Markup Language","Acronym":"SGML","Abbrev":"ISO 8879:1986","GlossDef":{"para":"A meta-markup language, used to create markup languages such as DocBook.","GlossSeeAlso":["GML","XML"]},"GlossSee":"markup"}}}
|
||||||
|
SELECT Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv:*');
|
||||||
|
Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv:*')
|
||||||
|
{"title":"S","GlossList":{"GlossEntry":{"ID":"SGML","SortAs":"SGML","GlossTerm":"Standard Generalized Markup Language","Acronym":"SGML","Abbrev":"ISO 8879:1986","GlossDef":{"para":"A meta-markup language, used to create markup languages such as DocBook.","GlossSeeAlso":["GML","XML"]},"GlossSee":"markup"}}}
|
||||||
|
SELECT JsonGet_String(Json_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso') lang;
|
||||||
|
lang
|
||||||
|
GML
|
||||||
|
SELECT Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso') "See also";
|
||||||
|
See also
|
||||||
|
["GML","XML"]
|
||||||
|
SELECT Json_Serialize(Jbin_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso')) "See also";
|
||||||
|
See also
|
||||||
|
["GML","XML"]
|
||||||
|
SELECT JsonGet_String(Json_Get_Item(Json_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso'),'[0]') lang;
|
||||||
|
lang
|
||||||
|
GML
|
||||||
|
#
|
||||||
|
# Test Item Get/Set/Insert/Update UDF's
|
||||||
|
#
|
||||||
|
SELECT Json_Get_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), '[]');
|
||||||
|
Json_Get_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), '[]')
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Get_Item(Jbin_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), '[1]');
|
||||||
|
Json_Get_Item(Jbin_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), '[1]')
|
||||||
|
NULL
|
||||||
|
SELECT Json_Get_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), '[1]');
|
||||||
|
Json_Get_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), '[1]')
|
||||||
|
NULL
|
||||||
|
SELECT Json_Set_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)));
|
||||||
|
Json_Set_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)))
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 'foo');
|
||||||
|
ERROR HY000: Can't initialize function 'json_set_item'; This function must have an odd number of arguments
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq')
|
||||||
|
[1,2,{"trois":3,"quatre":4,"cinq":5}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 7, '[1]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 7, '[1]')
|
||||||
|
[1,7,{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 7, '[1]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 7, '[1]')
|
||||||
|
[1,7,{"trois":3,"quatre":4,"cinq":5}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Json_Array(7, 8, 9), '[1]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Json_Array(7, 8, 9), '[1]')
|
||||||
|
[1,[7,8,9],{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[2]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[2]')
|
||||||
|
[1,2,[7,8,9]]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[2]:*');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[2]:*')
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 Invalid specification * in a write path
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 3.1416, 'foo');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 3.1416, 'foo')
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 'toto', '[1]:[2]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 'toto', '[1]:[2]')
|
||||||
|
[1,[7,8,"toto"],{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 300, '[2]:nxt:total:[]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 300, '[2]:nxt:total:[]')
|
||||||
|
[1,[7,8,9],{"trois":3,"quatre":4,"nxt":{"total":[300]}}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 300, '[2]:nxt:total:[]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 300, '[2]:nxt:total:[]')
|
||||||
|
[1,[7,8,9,10],{"trois":3,"quatre":4,"cinq":5,"nxt":{"total":[300]}}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[1]', 5, '[2]:cinq', 10, '[1]:[]');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[1]', 5, '[2]:cinq', 10, '[1]:[]')
|
||||||
|
[1,[7,8,9,10],{"trois":3,"quatre":4,"cinq":5}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 44, '[2]:quatre');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 44, '[2]:quatre')
|
||||||
|
[1,2,{"trois":3,"quatre":44}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, 'truc');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, 'truc')
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '')
|
||||||
|
[1,2,{"trois":3,"quatre":4},5]
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '*');
|
||||||
|
Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '*')
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 Invalid specification * in a write path
|
||||||
|
SELECT Json_Serialize(Jbin_Set_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq'));
|
||||||
|
Json_Serialize(Jbin_Set_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq'))
|
||||||
|
[1,2,{"trois":3,"quatre":4,"cinq":5}]
|
||||||
|
SELECT Json_Insert_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq');
|
||||||
|
Json_Insert_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq')
|
||||||
|
[1,2,{"trois":3,"quatre":4,"cinq":5}]
|
||||||
|
SELECT Json_Update_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq');
|
||||||
|
Json_Update_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq')
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Insert_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 44, '[2]:quatre');
|
||||||
|
Json_Insert_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 44, '[2]:quatre')
|
||||||
|
[1,[7,8,9,10],{"trois":3,"quatre":4,"cinq":5}]
|
||||||
|
SELECT Json_Update_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 44, '[2]:quatre');
|
||||||
|
Json_Update_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 44, '[2]:quatre')
|
||||||
|
[1,[7,8,9],{"trois":3,"quatre":44}]
|
||||||
|
SELECT Json_Insert_Item(Json_Array(1, Json_Array(7, 8, 9), Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[1]', 300, '[2]:nxt:total:[]');
|
||||||
|
Json_Insert_Item(Json_Array(1, Json_Array(7, 8, 9), Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[1]', 300, '[2]:nxt:total:[]')
|
||||||
|
[1,[7,8,9],{"trois":3,"quatre":4,"cinq":5,"nxt":{"total":[300]}}]
|
||||||
|
SELECT Json_Update_Item(Json_Array(1, Json_Array(7, 8, 9), Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[1]', 300, '[2]:nxt:total:[]');
|
||||||
|
Json_Update_Item(Json_Array(1, Json_Array(7, 8, 9), Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[1]', 300, '[2]:nxt:total:[]')
|
||||||
|
[1,[7,10,9],{"trois":3,"quatre":4}]
|
||||||
|
SELECT Json_Insert_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[]');
|
||||||
|
Json_Insert_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[]')
|
||||||
|
[1,2,{"trois":3,"quatre":4},5]
|
||||||
|
SELECT Json_Update_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[]');
|
||||||
|
Json_Update_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[]')
|
||||||
|
[1,2,{"trois":3,"quatre":4}]
|
||||||
|
#
|
||||||
|
# Test merging items UDF's
|
||||||
|
#
|
||||||
|
SELECT Json_Item_Merge(Jbin_Array('a','b','c'), Jbin_Array('d','e','f'));
|
||||||
|
Json_Item_Merge(Jbin_Array('a','b','c'), Jbin_Array('d','e','f'))
|
||||||
|
["a","b","c","d","e","f"]
|
||||||
|
SELECT Json_Item_Merge(Json_Array('a','b','c'), Json_Array('d','e','f')) AS "Result";
|
||||||
|
Result
|
||||||
|
["a","b","c","d","e","f"]
|
||||||
|
SELECT Json_Array_Add(Jbin_Item_Merge(Jbin_Array('a','b','c'), Jbin_Array('d','e','f')), 'and', 3);
|
||||||
|
Json_Array_Add(Jbin_Item_Merge(Jbin_Array('a','b','c'), Jbin_Array('d','e','f')), 'and', 3)
|
||||||
|
["a","b","c","and","d","e","f"]
|
||||||
|
SELECT Json_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "d",5 "e",6 "f"));
|
||||||
|
Json_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "d",5 "e",6 "f"))
|
||||||
|
{"a":1,"b":2,"c":3,"d":4,"e":5,"f":6}
|
||||||
|
SELECT Json_Item_Merge(Jbin_Object(1 "a",2 "b",2 "c"), Jbin_Array('d','e','f'));
|
||||||
|
Json_Item_Merge(Jbin_Object(1 "a",2 "b",2 "c"), Jbin_Array('d','e','f'))
|
||||||
|
Binary Json object
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 Second argument is not an object
|
||||||
|
SELECT Json_Object_Add(Jbin_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "d",5 "e",6 "f")), 'x' AS "and");
|
||||||
|
Json_Object_Add(Jbin_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "d",5 "e",6 "f")), 'x' AS "and")
|
||||||
|
{"a":1,"b":2,"c":3,"d":4,"e":5,"f":6,"and":"x"}
|
||||||
|
SELECT Json_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "a",5 "e",6 "f"));
|
||||||
|
Json_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "a",5 "e",6 "f"))
|
||||||
|
{"a":4,"b":2,"c":3,"e":5,"f":6}
|
||||||
|
SELECT Json_Item_Merge('foo', Json_Array('d','e','f'));
|
||||||
|
ERROR HY000: Can't initialize function 'json_item_merge'; First argument must be a json item
|
||||||
|
#
|
||||||
|
# Test making file UDF's
|
||||||
|
#
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json')
|
||||||
|
bt1.json
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
Json_File('bt1.json')
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Json_File(Jfile_Make(Jbin_File('bt1.json'), 0));
|
||||||
|
Json_File(Jfile_Make(Jbin_File('bt1.json'), 0))
|
||||||
|
"a"
|
||||||
|
"b"
|
||||||
|
"c"
|
||||||
|
|
||||||
|
SELECT Json_File(Jfile_Make(Jbin_File('bt1.json'), 1));
|
||||||
|
Json_File(Jfile_Make(Jbin_File('bt1.json'), 1))
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Json_File(Jfile_Make(Jbin_File('bt1.json'), 2));
|
||||||
|
Json_File(Jfile_Make(Jbin_File('bt1.json'), 2))
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Json_File('bt1.json', 0);
|
||||||
|
Json_File('bt1.json', 0)
|
||||||
|
["a","b","c"]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 File pretty format doesn't match the specified pretty value
|
||||||
|
SELECT Json_File('bt1.json', 1);
|
||||||
|
Json_File('bt1.json', 1)
|
||||||
|
["a","b","c"]
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 File pretty format doesn't match the specified pretty value
|
||||||
|
SELECT Json_File('bt1.json', 2);
|
||||||
|
Json_File('bt1.json', 2)
|
||||||
|
["a","b","c"]
|
||||||
|
SELECT Json_Serialize(Jbin_Array('a','b','c'));
|
||||||
|
Json_Serialize(Jbin_Array('a','b','c'))
|
||||||
|
["a","b","c"]
|
||||||
|
SELECT Json_Serialize(Jbin_Array_Add(Jbin_File('not_exist.json'), 'd'));
|
||||||
|
Json_Serialize(Jbin_Array_Add(Jbin_File('not_exist.json'), 'd'))
|
||||||
|
Null json tree
|
||||||
|
Warnings:
|
||||||
|
Warning 1105 Open(map) error 2 on not_exist.json
|
||||||
|
Warning 1105 First argument is not an array
|
||||||
|
# This does not modify the file
|
||||||
|
SELECT Json_Serialize(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'));
|
||||||
|
Json_Serialize(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'))
|
||||||
|
["a","b","c","d"]
|
||||||
|
SELECT Json_File('bt1.json', 2);
|
||||||
|
Json_File('bt1.json', 2)
|
||||||
|
["a","b","c"]
|
||||||
|
# This does modify the file
|
||||||
|
SELECT Json_Array_Add(Jbin_File('bt1.json'), 'd');
|
||||||
|
Json_Array_Add(Jbin_File('bt1.json'), 'd')
|
||||||
|
bt1.json
|
||||||
|
SELECT Json_File('bt1.json', 2);
|
||||||
|
Json_File('bt1.json', 2)
|
||||||
|
["a","b","c","d"]
|
||||||
|
# Back to the original file
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json')
|
||||||
|
bt1.json
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_Array('a','b','c'), 'd') "Jbin_foo") AS "Result";
|
||||||
|
Result
|
||||||
|
{"foo":["a","b","c","d"]}
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_File('bt1.json'), 'd')) AS "Result";
|
||||||
|
Result
|
||||||
|
{"Array_Add(Jbin_File('bt1.json'), 'd')":["a","b","c","d"]}
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_File('bt1.json'), 'd') "Jbin_bt1") AS "Result";
|
||||||
|
Result
|
||||||
|
{"bt1":["a","b","c","d"]}
|
||||||
|
# This does modify the file
|
||||||
|
SELECT Json_Object(Json_Array_Add(Jbin_File('bt1.json'), 'd') "Jfile_bt1") AS "Result";
|
||||||
|
Result
|
||||||
|
{"bt1":["a","b","c","d"]}
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
Json_File('bt1.json')
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
"d"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Json_File(Json_Array_Delete(Jbin_File('bt1.json'), 3), 2);
|
||||||
|
Json_File(Json_Array_Delete(Jbin_File('bt1.json'), 3), 2)
|
||||||
|
["a","b","c"]
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_File('bt1.json'), 'd') "Jbin_bt1", n "t1") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
{"bt1":["a","b","c","d"],"t1":1}
|
||||||
|
{"bt1":["a","b","c","d"],"t1":2}
|
||||||
|
{"bt1":["a","b","c","d"],"t1":3}
|
||||||
|
SELECT Json_File(Json_Array_Add(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'), 'e')) AS "Result";
|
||||||
|
Result
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
"d",
|
||||||
|
"e"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json')
|
||||||
|
bt1.json
|
||||||
|
SELECT Json_File(Json_Array_Add(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'), 'e')) AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
"d",
|
||||||
|
"e"
|
||||||
|
]
|
||||||
|
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
"d",
|
||||||
|
"e"
|
||||||
|
]
|
||||||
|
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
"d",
|
||||||
|
"e"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json')
|
||||||
|
bt1.json
|
||||||
|
SELECT Json_Array_Add(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'), n) AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
bt1.json
|
||||||
|
bt1.json
|
||||||
|
bt1.json
|
||||||
|
# Show modified file
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
Json_File('bt1.json')
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
"d",
|
||||||
|
1,
|
||||||
|
"d",
|
||||||
|
2,
|
||||||
|
"d",
|
||||||
|
3
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json')
|
||||||
|
bt1.json
|
||||||
|
SELECT Json_Array_Add(Jbin_File('bt1.json'), n) AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
bt1.json
|
||||||
|
bt1.json
|
||||||
|
bt1.json
|
||||||
|
# Show modified file
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
Json_File('bt1.json')
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
1,
|
||||||
|
2,
|
||||||
|
3
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json')
|
||||||
|
bt1.json
|
||||||
|
SELECT Json_File(Jbin_Item_Merge(Jbin_File('bt1.json'), Jbin_Array('d','e','f')));
|
||||||
|
Json_File(Jbin_Item_Merge(Jbin_File('bt1.json'), Jbin_Array('d','e','f')))
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Json_File(Json_Item_Merge(Jbin_File('bt1.json'), Jbin_Array('d','e','f')));
|
||||||
|
Json_File(Json_Item_Merge(Jbin_File('bt1.json'), Jbin_Array('d','e','f')))
|
||||||
|
[
|
||||||
|
"a",
|
||||||
|
"b",
|
||||||
|
"c",
|
||||||
|
"d",
|
||||||
|
"e",
|
||||||
|
"f"
|
||||||
|
]
|
||||||
|
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json')
|
||||||
|
bt1.json
|
||||||
|
# Test DELETE from file
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 1)) AS "Result";
|
||||||
|
Result
|
||||||
|
{"Array_Delete(Jbin_File('bt1.json'), 1)":["a","c"]}
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 2) "Jbin_bt1") AS "Result";
|
||||||
|
Result
|
||||||
|
{"bt1":["a","b"]}
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 0) "Jbin_bt1", n "t1") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
{"bt1":["b","c"],"t1":1}
|
||||||
|
{"bt1":["b","c"],"t1":2}
|
||||||
|
{"bt1":["b","c"],"t1":3}
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 3 - n) "Jbin_bt1") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
{"bt1":["a","b"]}
|
||||||
|
{"bt1":["a"]}
|
||||||
|
{"bt1":[]}
|
||||||
|
SELECT Json_Object(Json_Array_Delete(Jbin_File('bt1.json'), 3 - n) "Jbin_bt1") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
{"bt1":["a","b"]}
|
||||||
|
{"bt1":["a"]}
|
||||||
|
{"bt1":[]}
|
||||||
|
# Show modified file
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
Json_File('bt1.json')
|
||||||
|
[
|
||||||
|
|
||||||
|
]
|
||||||
|
|
||||||
|
# Object file
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0)
|
||||||
|
bt2.json
|
||||||
|
SELECT Json_File('bt2.json', 0);
|
||||||
|
Json_File('bt2.json', 0)
|
||||||
|
{"a":1,"b":2,"c":3}
|
||||||
|
SELECT Json_File('bt2.json');
|
||||||
|
Json_File('bt2.json')
|
||||||
|
{"a":1,"b":2,"c":3}
|
||||||
|
|
||||||
|
SELECT Json_Serialize(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"));
|
||||||
|
Json_Serialize(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"))
|
||||||
|
{"a":1,"b":2,"c":3,"d":4}
|
||||||
|
# First query (file not modified)
|
||||||
|
SELECT Json_Object(Jbin_Object_Add(Jbin_File('bt2.json'), 4 AS "d") AS "Jbin_new") AS "Result";
|
||||||
|
Result
|
||||||
|
{"new":{"a":1,"b":2,"c":3,"d":4}}
|
||||||
|
# First query (file modified)
|
||||||
|
SELECT Json_Object(Json_Object_Add(Jbin_File('bt2.json'), 4 AS "d") AS "Jfile_new") AS "Result";
|
||||||
|
Result
|
||||||
|
{"new":{"a":1,"b":2,"c":3,"d":4}}
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0)
|
||||||
|
bt2.json
|
||||||
|
SELECT Json_Object(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d") "Jbin_new", n "t1") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
{"new":{"a":1,"b":2,"c":3,"d":4},"t1":1}
|
||||||
|
{"new":{"a":1,"b":2,"c":3,"d":4},"t1":2}
|
||||||
|
{"new":{"a":1,"b":2,"c":3,"d":4},"t1":3}
|
||||||
|
SELECT Json_File(Json_Object_Add(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"), 5 "e")) AS "Result";
|
||||||
|
Result
|
||||||
|
{"a":1,"b":2,"c":3,"d":4,"e":5}
|
||||||
|
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"), 5 "e") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
bt2.json
|
||||||
|
bt2.json
|
||||||
|
bt2.json
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"), n "n") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
bt2.json
|
||||||
|
bt2.json
|
||||||
|
bt2.json
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0)
|
||||||
|
bt2.json
|
||||||
|
SELECT Json_Object_Add(Jbin_File('bt2.json'), n) AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
bt2.json
|
||||||
|
bt2.json
|
||||||
|
bt2.json
|
||||||
|
SELECT Json_File('bt2.json');
|
||||||
|
Json_File('bt2.json')
|
||||||
|
{"a":1,"b":2,"c":3,"n":3}
|
||||||
|
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0)
|
||||||
|
bt2.json
|
||||||
|
SELECT Json_Serialize(Jbin_Item_Merge(Jbin_File('bt2.json'), Jbin_Object(4 "d",5 "e",6 "f"))) AS "Result";
|
||||||
|
Result
|
||||||
|
{"a":1,"b":2,"c":3,"d":4,"e":5,"f":6}
|
||||||
|
SELECT Json_File(Json_Item_Merge(Jbin_File('bt2.json'), Jbin_Object(4 "d",5 "e",6 "f"))) AS "Result";
|
||||||
|
Result
|
||||||
|
{"a":1,"b":2,"c":3,"d":4,"e":5,"f":6}
|
||||||
|
|
||||||
|
SELECT Json_Item_Merge(Json_Object(1 "a", 2 "b", 3 "c"), Json_Object(4 "d",5 "b",6 "f")) AS "Result";
|
||||||
|
Result
|
||||||
|
{"a":1,"b":5,"c":3,"d":4,"f":6}
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'b')) AS "Result";
|
||||||
|
Result
|
||||||
|
{"Object_Delete(Jbin_File('bt2.json'), 'b')":{"a":1,"c":3,"d":4,"e":5,"f":6}}
|
||||||
|
SELECT Json_Object(Jbin_Object_Delete(Jbin_File('bt2.json'), 'c') "Jbin_bt1") AS "Result";
|
||||||
|
Result
|
||||||
|
{"bt1":{"a":1,"d":4,"e":5,"f":6}}
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'c') "Jbin_bt1") AS "Result";
|
||||||
|
Result
|
||||||
|
{"bt1":{"a":1,"d":4,"e":5,"f":6}}
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'c') "Jfile_bt1") AS "Result";
|
||||||
|
Result
|
||||||
|
{"bt1":{"a":1,"d":4,"e":5,"f":6}}
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'a') "Jbin_bt1", n "t1") AS "Result" from t1;
|
||||||
|
Result
|
||||||
|
{"bt1":{"d":4,"e":5,"f":6},"t1":1}
|
||||||
|
{"bt1":{"d":4,"e":5,"f":6},"t1":2}
|
||||||
|
{"bt1":{"d":4,"e":5,"f":6},"t1":3}
|
||||||
|
SELECT Json_Serialize(Jbin_Object_List(Jbin_File('bt2.json'))) "Key list";
|
||||||
|
Key list
|
||||||
|
["d","e","f"]
|
||||||
|
SELECT Jfile_Make('{"a":1, "b":[44, 55]}' json_, 'bt3.json', 0);
|
||||||
|
Jfile_Make('{"a":1, "b":[44, 55]}' json_, 'bt3.json', 0)
|
||||||
|
bt3.json
|
||||||
|
SELECT Json_Array_Add(Json_File('bt3.json', 'b'), 66);
|
||||||
|
Json_Array_Add(Json_File('bt3.json', 'b'), 66)
|
||||||
|
[44,55,66]
|
||||||
|
SELECT Json_Array_Add(Json_File('bt3.json'), 66, 'b');
|
||||||
|
Json_Array_Add(Json_File('bt3.json'), 66, 'b')
|
||||||
|
{"a":1,"b":[44,55,66]}
|
||||||
|
SELECT Json_Array_Add(Jbin_File('bt3.json', 'b'), 66);
|
||||||
|
Json_Array_Add(Jbin_File('bt3.json', 'b'), 66)
|
||||||
|
bt3.json
|
||||||
|
SELECT Json_File('bt3.json', 3);
|
||||||
|
Json_File('bt3.json', 3)
|
||||||
|
{"a":1,"b":[44,55,66]}
|
||||||
|
SELECT Jfile_Make('{"a":1, "b":[44, 55]}' json_, 'bt3.json', 0);
|
||||||
|
Jfile_Make('{"a":1, "b":[44, 55]}' json_, 'bt3.json', 0)
|
||||||
|
bt3.json
|
||||||
|
CREATE TABLE t2 (
|
||||||
|
n INT KEY,
|
||||||
|
jfile_cols CHAR(12) NOT NULL)
|
||||||
|
ENGINE= MYISAM;
|
||||||
|
INSERT INTO t2 VALUES(1,'bt3.json');
|
||||||
|
# In this table, the jfile_cols column just contains a file name
|
||||||
|
UPDATE t2 SET jfile_cols = Json_Array_Add(Jbin_File('bt3.json', 'b'), 66) WHERE n = 1;
|
||||||
|
SELECT JsonGet_String(jfile_cols, '*') FROM t2;
|
||||||
|
JsonGet_String(jfile_cols, '*')
|
||||||
|
{"a":1,"b":[44,55,66]}
|
||||||
|
UPDATE t2 SET jfile_cols = Json_Insert_Item(jfile_cols, 77, 'b:[]') WHERE n = 1;
|
||||||
|
SELECT JsonGet_String(jfile_cols, 'b:*') FROM t2;
|
||||||
|
JsonGet_String(jfile_cols, 'b:*')
|
||||||
|
[44,55,66,77]
|
||||||
|
UPDATE t2 SET jfile_cols = Json_Insert_Item(Jbin_Insert_Item(jfile_cols, 88, 'b:') , 99, 'b:') WHERE n = 1;
|
||||||
|
SELECT JsonGet_String(jfile_cols, '*') FROM t2;
|
||||||
|
JsonGet_String(jfile_cols, '*')
|
||||||
|
{"a":1,"b":[44,55,66,77,88,99]}
|
||||||
|
DROP TABLE t1, t2;
|
@@ -1,8 +1,10 @@
|
|||||||
#
|
#
|
||||||
# Testing FILE privilege
|
# Testing FILE privilege
|
||||||
#
|
#
|
||||||
|
set sql_mode="";
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
|
set sql_mode=default;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -40,7 +42,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
|
@@ -49,10 +49,11 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE VIEW v1 AS SELECT * FROM t1;
|
||||||
ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
||||||
# Testing a VIEW created with FILE privileges but accessed with no FILE
|
# Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
|
# using SQL SECIRITY INVOKER
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
@@ -64,6 +65,19 @@ UPDATE v1 SET a=123;
|
|||||||
ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
||||||
DELETE FROM v1;
|
DELETE FROM v1;
|
||||||
ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
||||||
|
# Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
|
# using SQL SECIRITY DEFINER
|
||||||
|
DROP VIEW v1;
|
||||||
|
SELECT user();
|
||||||
|
user()
|
||||||
|
root@localhost
|
||||||
|
CREATE SQL SECURITY DEFINER VIEW v1 AS SELECT * FROM t1;
|
||||||
|
SELECT user();
|
||||||
|
user()
|
||||||
|
user@localhost
|
||||||
|
SELECT * FROM v1 WHERE a='test1';
|
||||||
|
a
|
||||||
|
test1
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
|
@@ -3,6 +3,7 @@ Warning 1105 No file name. Table will use t1.xml
|
|||||||
#
|
#
|
||||||
# Beginning of grant.inc
|
# Beginning of grant.inc
|
||||||
#
|
#
|
||||||
|
CREATE USER user@localhost;
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -63,7 +64,7 @@ ERROR 28000: Access denied for user 'user'@'localhost' (using password: NO)
|
|||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
root@localhost
|
root@localhost
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
SELECT user();
|
SELECT user();
|
||||||
user()
|
user()
|
||||||
user@localhost
|
user@localhost
|
||||||
|
2
storage/connect/mysql-test/connect/std_data/bib0.json
Normal file
2
storage/connect/mysql-test/connect/std_data/bib0.json
Normal file
@@ -0,0 +1,2 @@
|
|||||||
|
{"ISBN":"9782212090819","LANG":"fr","SUBJECT":"applications","AUTHOR":[{"FIRSTNAME":"Jean-Michel","LASTNAME":"Bernadac"},{"FIRSTNAME":"Fran<61>ois","LASTNAME":"Knab"}],"TITLE":"Construire une application XML","PUBLISHER":{"NAME":"Eyrolles","PLACE":"Paris"},"DATEPUB":1999}
|
||||||
|
{"ISBN":"9782840825685","LANG":"fr","SUBJECT":"applications","AUTHOR":[{"FIRSTNAME":"William J.","LASTNAME":"Pardi"}],"TITLE":"XML en Action","TRANSLATED":{"PREFIX":"adapt<70> de l'anglais par","TRANSLATOR":{"FIRSTNAME":"James","LASTNAME":"Guerin"}},"PUBLISHER":{"NAME":"Microsoft Press","PLACE":"Paris"},"DATEPUB":2001}
|
@@ -24,12 +24,10 @@
|
|||||||
"ISBN": "9782840825685",
|
"ISBN": "9782840825685",
|
||||||
"LANG": "fr",
|
"LANG": "fr",
|
||||||
"SUBJECT": "applications",
|
"SUBJECT": "applications",
|
||||||
"AUTHOR": [
|
"AUTHOR": {
|
||||||
{
|
"FIRSTNAME": "William J.",
|
||||||
"FIRSTNAME": "William J.",
|
"LASTNAME": "Pardi"
|
||||||
"LASTNAME": "Pardi"
|
},
|
||||||
}
|
|
||||||
],
|
|
||||||
"TITLE": "XML en Action",
|
"TITLE": "XML en Action",
|
||||||
"TRANSLATION": "adapt<70> de l'anglais par",
|
"TRANSLATION": "adapt<70> de l'anglais par",
|
||||||
"TRANSLATOR": {
|
"TRANSLATOR": {
|
||||||
|
22
storage/connect/mysql-test/connect/std_data/gloss.json
Normal file
22
storage/connect/mysql-test/connect/std_data/gloss.json
Normal file
@@ -0,0 +1,22 @@
|
|||||||
|
{
|
||||||
|
"glossary": {
|
||||||
|
"title": "example glossary",
|
||||||
|
"GlossDiv": {
|
||||||
|
"title": "S",
|
||||||
|
"GlossList": {
|
||||||
|
"GlossEntry": {
|
||||||
|
"ID": "SGML",
|
||||||
|
"SortAs": "SGML",
|
||||||
|
"GlossTerm": "Standard Generalized Markup Language",
|
||||||
|
"Acronym": "SGML",
|
||||||
|
"Abbrev": "ISO 8879:1986",
|
||||||
|
"GlossDef": {
|
||||||
|
"para": "A meta-markup language, used to create markup languages such as DocBook.",
|
||||||
|
"GlossSeeAlso": ["GML", "XML"]
|
||||||
|
},
|
||||||
|
"GlossSee": "markup"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@@ -14,3 +14,15 @@ SELECT id, DAYNAME(dat) FROM t1;
|
|||||||
SELECT id, DAYNAME(datim) FROM t1 LIMIT 1;
|
SELECT id, DAYNAME(datim) FROM t1 LIMIT 1;
|
||||||
SELECT id, TIME(tim) FROM t1 LIMIT 1;
|
SELECT id, TIME(tim) FROM t1 LIMIT 1;
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Testing use of dates in where clause (MDEV-8926)
|
||||||
|
--echo #
|
||||||
|
CREATE TABLE t1 (col1 DATE) ENGINE=CONNECT TABLE_TYPE=CSV;
|
||||||
|
INSERT INTO t1 VALUES('2015-01-01'),('2015-02-01'),('2015-03-01'),('2015-04-01');
|
||||||
|
SELECT * FROM t1 WHERE col1 = '2015-02-01';
|
||||||
|
SELECT * FROM t1 WHERE col1 > '2015-02-01';
|
||||||
|
SELECT * FROM t1 WHERE col1 >= '2015-02-01';
|
||||||
|
SELECT * FROM t1 WHERE col1 < '2015-02-01';
|
||||||
|
SELECT * FROM t1 WHERE col1 <= '2015-02-01';
|
||||||
|
DROP TABLE t1;
|
||||||
|
@@ -1,6 +1,7 @@
|
|||||||
--echo #
|
--echo #
|
||||||
--echo # Beginning of grant.inc
|
--echo # Beginning of grant.inc
|
||||||
--echo #
|
--echo #
|
||||||
|
CREATE USER user@localhost;
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
--connect(user,localhost,user,,)
|
--connect(user,localhost,user,,)
|
||||||
@@ -53,7 +54,7 @@ CREATE VIEW v1 AS SELECT * FROM t1;
|
|||||||
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
--connection default
|
--connection default
|
||||||
SELECT user();
|
SELECT user();
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
--connection user
|
--connection user
|
||||||
SELECT user();
|
SELECT user();
|
||||||
--error ER_ACCESS_DENIED_ERROR
|
--error ER_ACCESS_DENIED_ERROR
|
||||||
|
@@ -1,4 +1,5 @@
|
|||||||
-- source include/not_embedded.inc
|
-- source include/not_embedded.inc
|
||||||
|
set sql_mode="";
|
||||||
|
|
||||||
let $MYSQLD_DATADIR= `select @@datadir`;
|
let $MYSQLD_DATADIR= `select @@datadir`;
|
||||||
|
|
||||||
@@ -49,7 +50,7 @@ CREATE VIEW v1 AS SELECT * FROM t1;
|
|||||||
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
--connection default
|
--connection default
|
||||||
SELECT user();
|
SELECT user();
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
--connection user
|
--connection user
|
||||||
SELECT user();
|
SELECT user();
|
||||||
--error ER_ACCESS_DENIED_ERROR
|
--error ER_ACCESS_DENIED_ERROR
|
||||||
@@ -92,4 +93,4 @@ let $TABLE_OPTIONS=TABLE_TYPE=VEC MAX_ROWS=100;
|
|||||||
let $FILE_EXT=VEC;
|
let $FILE_EXT=VEC;
|
||||||
--source grant.inc
|
--source grant.inc
|
||||||
|
|
||||||
|
set sql_mode=default;
|
||||||
|
@@ -5,8 +5,10 @@ let $MYSQLD_DATADIR= `select @@datadir`;
|
|||||||
--echo #
|
--echo #
|
||||||
--echo # Checking FILE privileges
|
--echo # Checking FILE privileges
|
||||||
--echo #
|
--echo #
|
||||||
|
set sql_mode="";
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
|
set sql_mode=default;
|
||||||
--connect(user,localhost,user,,)
|
--connect(user,localhost,user,,)
|
||||||
--connection user
|
--connection user
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -54,7 +56,7 @@ CREATE VIEW v1 AS SELECT * FROM t1;
|
|||||||
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
--connection default
|
--connection default
|
||||||
SELECT user();
|
SELECT user();
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
--connection user
|
--connection user
|
||||||
SELECT user();
|
SELECT user();
|
||||||
--error ER_ACCESS_DENIED_ERROR
|
--error ER_ACCESS_DENIED_ERROR
|
||||||
|
@@ -4,6 +4,7 @@
|
|||||||
let $MYSQLD_DATADIR= `select @@datadir`;
|
let $MYSQLD_DATADIR= `select @@datadir`;
|
||||||
|
|
||||||
--copy_file $MTR_SUITE_DIR/std_data/biblio.json $MYSQLD_DATADIR/test/biblio.json
|
--copy_file $MTR_SUITE_DIR/std_data/biblio.json $MYSQLD_DATADIR/test/biblio.json
|
||||||
|
--copy_file $MTR_SUITE_DIR/std_data/bib0.json $MYSQLD_DATADIR/test/bib0.json
|
||||||
--copy_file $MTR_SUITE_DIR/std_data/expense.json $MYSQLD_DATADIR/test/expense.json
|
--copy_file $MTR_SUITE_DIR/std_data/expense.json $MYSQLD_DATADIR/test/expense.json
|
||||||
--copy_file $MTR_SUITE_DIR/std_data/mulexp3.json $MYSQLD_DATADIR/test/mulexp3.json
|
--copy_file $MTR_SUITE_DIR/std_data/mulexp3.json $MYSQLD_DATADIR/test/mulexp3.json
|
||||||
--copy_file $MTR_SUITE_DIR/std_data/mulexp4.json $MYSQLD_DATADIR/test/mulexp4.json
|
--copy_file $MTR_SUITE_DIR/std_data/mulexp4.json $MYSQLD_DATADIR/test/mulexp4.json
|
||||||
@@ -115,6 +116,33 @@ ENGINE=CONNECT TABLE_TYPE=DOS FILE_NAME='biblio.json';
|
|||||||
SELECT * FROM t1;
|
SELECT * FROM t1;
|
||||||
DROP TABLE t1;
|
DROP TABLE t1;
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Testing a pretty=0 file
|
||||||
|
--echo #
|
||||||
|
CREATE TABLE t1
|
||||||
|
(
|
||||||
|
ISBN CHAR(15) NOT NULL,
|
||||||
|
Language CHAR(2) FIELD_FORMAT='LANG',
|
||||||
|
Subject CHAR(32) FIELD_FORMAT='SUBJECT',
|
||||||
|
AuthorFN CHAR(128) FIELD_FORMAT='AUTHOR:[X]:FIRSTNAME',
|
||||||
|
AuthorLN CHAR(128) FIELD_FORMAT='AUTHOR:[X]:LASTNAME',
|
||||||
|
Title CHAR(32) FIELD_FORMAT='TITLE',
|
||||||
|
Translation CHAR(32) FIELD_FORMAT='TRANSLATED:PREFIX',
|
||||||
|
TranslatorFN CHAR(80) FIELD_FORMAT='TRANSLATED:TRANSLATOR:FIRSTNAME',
|
||||||
|
TranslatorLN CHAR(80) FIELD_FORMAT='TRANSLATED:TRANSLATOR:LASTNAME',
|
||||||
|
Publisher CHAR(20) FIELD_FORMAT='PUBLISHER:NAME',
|
||||||
|
Location CHAR(16) FIELD_FORMAT='PUBLISHER:PLACE',
|
||||||
|
Year int(4) FIELD_FORMAT='DATEPUB',
|
||||||
|
INDEX IX(ISBN)
|
||||||
|
)
|
||||||
|
ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='bib0.json' LRECL=320 OPTION_LIST='Pretty=0';
|
||||||
|
SHOW INDEX FROM t1;
|
||||||
|
SELECT * FROM t1;
|
||||||
|
DESCRIBE SELECT * FROM t1 WHERE ISBN = '9782212090819';
|
||||||
|
--error ER_GET_ERRMSG
|
||||||
|
UPDATE t1 SET AuthorFN = 'Philippe' WHERE ISBN = '9782212090819';
|
||||||
|
DROP TABLE t1;
|
||||||
|
|
||||||
--echo #
|
--echo #
|
||||||
--echo # A file with 2 arrays
|
--echo # A file with 2 arrays
|
||||||
--echo #
|
--echo #
|
||||||
@@ -258,6 +286,8 @@ DROP TABLE t1, t2, t3, t4;
|
|||||||
# Clean up
|
# Clean up
|
||||||
#
|
#
|
||||||
--remove_file $MYSQLD_DATADIR/test/biblio.json
|
--remove_file $MYSQLD_DATADIR/test/biblio.json
|
||||||
|
--remove_file $MYSQLD_DATADIR/test/bib0.dnx
|
||||||
|
--remove_file $MYSQLD_DATADIR/test/bib0.json
|
||||||
--remove_file $MYSQLD_DATADIR/test/expense.json
|
--remove_file $MYSQLD_DATADIR/test/expense.json
|
||||||
--remove_file $MYSQLD_DATADIR/test/mulexp3.json
|
--remove_file $MYSQLD_DATADIR/test/mulexp3.json
|
||||||
--remove_file $MYSQLD_DATADIR/test/mulexp4.json
|
--remove_file $MYSQLD_DATADIR/test/mulexp4.json
|
||||||
|
@@ -9,28 +9,50 @@ if (!$HA_CONNECT_SO) {
|
|||||||
--skip Needs a dynamically built ha_connect.so
|
--skip Needs a dynamically built ha_connect.so
|
||||||
}
|
}
|
||||||
|
|
||||||
let $is_win = `select convert(@@version_compile_os using latin1) IN ("Win32","Win64","Windows")`;
|
--eval CREATE FUNCTION json_array RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_array_add RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_array_add_values RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_array_delete RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_object RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_object_nonull RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_object_key RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_object_add RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_object_delete RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_object_list RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jsonvalue RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE AGGREGATE FUNCTION json_array_grp RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE AGGREGATE FUNCTION json_object_grp RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jsonget_string RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jsonget_int RETURNS INTEGER SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jsonget_real RETURNS REAL SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jsonlocate RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_locate_all RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_file RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jfile_make RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jsoncontains RETURNS INTEGER SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jsoncontains_path RETURNS INTEGER SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_get_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_set_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_insert_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_update_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_item_merge RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION json_serialize RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_array RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_array_add_values RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_array_add RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_array_delete RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_object RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_object_nonull RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_object_key RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_object_add RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_object_delete RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_object_list RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_get_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_item_merge RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_set_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_insert_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_update_item RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
--eval CREATE FUNCTION jbin_file RETURNS STRING SONAME '$HA_CONNECT_SO';
|
||||||
|
|
||||||
if ($is_win)
|
|
||||||
{
|
|
||||||
--eval CREATE FUNCTION Json_Array RETURNS STRING SONAME 'ha_connect.dll';
|
|
||||||
--eval CREATE FUNCTION Json_Array_Add RETURNS STRING SONAME 'ha_connect.dll';
|
|
||||||
--eval CREATE FUNCTION Json_Object RETURNS STRING SONAME 'ha_connect.dll';
|
|
||||||
--eval CREATE FUNCTION Json_Object_Nonull RETURNS STRING SONAME 'ha_connect.dll';
|
|
||||||
--eval CREATE FUNCTION Json_Value returns STRING SONAME 'ha_connect.dll';
|
|
||||||
--eval CREATE AGGREGATE FUNCTION Json_Array_Grp RETURNS STRING SONAME 'ha_connect.dll';
|
|
||||||
--eval CREATE AGGREGATE FUNCTION Json_Object_Grp RETURNS STRING SONAME 'ha_connect.dll';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!$is_win)
|
|
||||||
{
|
|
||||||
--eval CREATE FUNCTION Json_Array RETURNS STRING SONAME 'ha_connect.so';
|
|
||||||
--eval CREATE FUNCTION Json_Array_Add RETURNS STRING SONAME 'ha_connect.so';
|
|
||||||
--eval CREATE FUNCTION Json_Object RETURNS STRING SONAME 'ha_connect.so';
|
|
||||||
--eval CREATE FUNCTION Json_Object_Nonull RETURNS STRING SONAME 'ha_connect.so';
|
|
||||||
--eval CREATE FUNCTION Json_Value returns STRING SONAME 'ha_connect.so';
|
|
||||||
--eval CREATE AGGREGATE FUNCTION Json_Array_Grp RETURNS STRING SONAME 'ha_connect.so';
|
|
||||||
--eval CREATE AGGREGATE FUNCTION Json_Object_Grp RETURNS STRING SONAME 'ha_connect.so';
|
|
||||||
}
|
|
||||||
--enable_query_log
|
--enable_query_log
|
||||||
|
|
||||||
|
@@ -5,35 +5,78 @@ let $MYSQLD_DATADIR= `select @@datadir`;
|
|||||||
--copy_file $MTR_SUITE_DIR/std_data/biblio.json $MYSQLD_DATADIR/test/biblio.json
|
--copy_file $MTR_SUITE_DIR/std_data/biblio.json $MYSQLD_DATADIR/test/biblio.json
|
||||||
--copy_file $MTR_SUITE_DIR/std_data/employee.dat $MYSQLD_DATADIR/test/employee.dat
|
--copy_file $MTR_SUITE_DIR/std_data/employee.dat $MYSQLD_DATADIR/test/employee.dat
|
||||||
|
|
||||||
|
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=VIR BLOCK_SIZE=5;
|
||||||
|
|
||||||
--echo #
|
--echo #
|
||||||
--echo # Test UDF's with constant arguments
|
--echo # Test UDF's with constant arguments
|
||||||
--echo #
|
--echo #
|
||||||
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
|
SELECT JsonValue(56, 3.1416, 'foo', NULL);
|
||||||
|
SELECT JsonValue(3.1416);
|
||||||
|
SELECT JsonValue(-80);
|
||||||
|
SELECT JsonValue('foo');
|
||||||
|
SELECT JsonValue(9223372036854775807);
|
||||||
|
SELECT JsonValue(NULL);
|
||||||
|
SELECT JsonValue(TRUE);
|
||||||
|
SELECT JsonValue(FALSE);
|
||||||
|
SELECT JsonValue();
|
||||||
|
SELECT JsonValue('[11, 22, 33]' json_) FROM t1;
|
||||||
|
#
|
||||||
SELECT Json_Array();
|
SELECT Json_Array();
|
||||||
SELECT Json_Object(56,3.1416,'foo',NULL);
|
SELECT Json_Array(56, 3.1416, 'My name is "Foo"', NULL);
|
||||||
SELECT Json_Object(56 qty,3.1416 price,'foo' truc, NULL garanty);
|
SELECT Json_Array(Json_Array(56, 3.1416, 'foo'), TRUE);
|
||||||
SELECT Json_Array(56,3.1416,'My name is "Foo"',NULL);
|
#
|
||||||
--error ER_CANT_INITIALIZE_UDF
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
SELECT Json_Array_Add(Json_Array(56,3.1416,'foo',NULL)) Array;
|
SELECT Json_Array_Add(Json_Array(56, 3.1416, 'foo', NULL)) Array;
|
||||||
SELECT Json_Array_Add(Json_Array(56,3.1416,'foo',NULL),'One more') Array;
|
SELECT Json_Array_Add(Json_Array(56, 3.1416, 'foo', NULL), 'One more') Array;
|
||||||
SELECT Json_Array_Add(Json_Value('one value'),'One more');
|
|
||||||
--error ER_CANT_INITIALIZE_UDF
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
SELECT Json_Array_Add('one value','One more');
|
SELECT Json_Array_Add(JsonValue('one value'), 'One more');
|
||||||
SELECT Json_Array_Add('one value' json_,'One more');
|
|
||||||
--error ER_CANT_INITIALIZE_UDF
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
SELECT Json_Value(56,3.1416,'foo',NULL);
|
SELECT Json_Array_Add('one value', 'One more');
|
||||||
SELECT Json_Value(3.1416);
|
SELECT Json_Array_Add('one value' json_, 'One more');
|
||||||
SELECT Json_Value('foo');
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
SELECT Json_Value(NULL);
|
SELECT Json_Array_Add(5 json_, 'One more');
|
||||||
SELECT Json_Value();
|
SELECT Json_Array_Add('[5,3,8,7,9]' json_, 4, 0);
|
||||||
|
SELECT Json_Array_Add('[5,3,8,7,9]' json_, 4, 2) Array;
|
||||||
|
SELECT Json_Array_Add('[5,3,8,7,9]' json_, 4, 9);
|
||||||
|
SELECT Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), '[2]', 33, 1);
|
||||||
|
SELECT Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), 33, '[2]', 1);
|
||||||
|
SELECT Json_Array_Add(Json_Array(1, 2, Json_Array(11, 22)), 33, 1, '[2]');
|
||||||
|
#
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(56, 3.1416, 'machin', NULL), 'One more', 'Two more') Array;
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(56, 3.1416, 'machin'), 'One more', 'Two more') Array FROM t1;
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(56, 3.1416, 'machin'), n) Array FROM t1;
|
||||||
|
SELECT Json_Array_Add_Values(Json_Array(n, 3.1416, 'machin'), n) Array FROM t1;
|
||||||
|
SELECT Json_Array_Add_Values('[56]', 3.1416, 'machin') Array;
|
||||||
|
#
|
||||||
|
SELECT Json_Array_Delete(Json_Array(56, 3.1416, 'My name is "Foo"', NULL), 0);
|
||||||
|
SELECT Json_Array_Delete(Json_Object(56, 3.1416, 'My name is Foo', NULL), 2);
|
||||||
|
SELECT Json_Array_Delete(Json_Array(56, 3.1416, 'My name is "Foo"', NULL), '2');
|
||||||
|
SELECT Json_Array_Delete(json_array(56, 3.1416, 'My name is "Foo"', NULL), '2', 2);
|
||||||
|
#
|
||||||
|
SELECT Json_Object(56, 3.1416, 'foo', NULL);
|
||||||
|
SELECT Json_Object(56 qty, 3.1416 price, 'foo' truc, NULL garanty);
|
||||||
SELECT Json_Object();
|
SELECT Json_Object();
|
||||||
SELECT Json_Object(Json_Array(56,3.1416,'foo'),NULL);
|
SELECT Json_Object(Json_Array(56, 3.1416, 'foo'), NULL);
|
||||||
SELECT Json_Array(Json_Array(56,3.1416,'foo'),NULL);
|
SELECT Json_Array(Json_Object(56 "qty", 3.1416 "price", 'foo') ,NULL);
|
||||||
SELECT Json_Array(Json_Object(56 "qty",3.1416 "price",'foo'),NULL);
|
SELECT Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL);
|
||||||
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
|
SELECT Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty');
|
||||||
|
#
|
||||||
|
SELECT Json_Object_Add(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color);
|
||||||
|
SELECT Json_Object_Add(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price);
|
||||||
|
SELECT Json_Object_Add(Json_File('notexist.json'), 'cheese' item, '[1]', 1);
|
||||||
|
#
|
||||||
|
SELECT Json_Object_Delete(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'truc');
|
||||||
|
SELECT Json_Object_Delete(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'chose');
|
||||||
|
#
|
||||||
|
SELECT Json_Object_List(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty)) "Key List";
|
||||||
|
SELECT Json_Object_List('{"qty":56, "price":3.1416, "truc":"machin", "garanty":null}') "Key List";
|
||||||
|
|
||||||
--echo #
|
--echo #
|
||||||
--echo # Test UDF's with column arguments
|
--echo # Test UDF's with column arguments
|
||||||
--echo #
|
--echo #
|
||||||
CREATE TABLE t1
|
CREATE TABLE t2
|
||||||
(
|
(
|
||||||
ISBN CHAR(15),
|
ISBN CHAR(15),
|
||||||
LANG CHAR(2),
|
LANG CHAR(2),
|
||||||
@@ -46,14 +89,13 @@ CREATE TABLE t1
|
|||||||
DATEPUB int(4)
|
DATEPUB int(4)
|
||||||
) ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='biblio.json';
|
) ENGINE=CONNECT TABLE_TYPE=JSON FILE_NAME='biblio.json';
|
||||||
|
|
||||||
SELECT Json_Array(AUTHOR, TITLE, DATEPUB) FROM t1;
|
SELECT Json_Array(AUTHOR, TITLE, DATEPUB) FROM t2;
|
||||||
SELECT Json_Object(AUTHOR, TITLE, DATEPUB) FROM t1;
|
SELECT Json_Object(AUTHOR, TITLE, DATEPUB) FROM t2;
|
||||||
--error ER_CANT_INITIALIZE_UDF
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
SELECT Json_Array_Grp(TITLE, DATEPUB) FROM t1;
|
SELECT Json_Array_Grp(TITLE, DATEPUB) FROM t2;
|
||||||
SELECT Json_Array_Grp(TITLE) FROM t1;
|
SELECT Json_Array_Grp(TITLE) FROM t2;
|
||||||
DROP TABLE t1;
|
|
||||||
|
|
||||||
CREATE TABLE t1 (
|
CREATE TABLE t3 (
|
||||||
SERIALNO CHAR(5) NOT NULL,
|
SERIALNO CHAR(5) NOT NULL,
|
||||||
NAME VARCHAR(12) NOT NULL FLAG=6,
|
NAME VARCHAR(12) NOT NULL FLAG=6,
|
||||||
SEX SMALLINT(1) NOT NULL,
|
SEX SMALLINT(1) NOT NULL,
|
||||||
@@ -64,30 +106,160 @@ CREATE TABLE t1 (
|
|||||||
SALARY DOUBLE(8,2) NOT NULL FLAG=52
|
SALARY DOUBLE(8,2) NOT NULL FLAG=52
|
||||||
) ENGINE=CONNECT TABLE_TYPE=FIX BLOCK_SIZE=8 FILE_NAME='employee.dat' ENDING=1;
|
) ENGINE=CONNECT TABLE_TYPE=FIX BLOCK_SIZE=8 FILE_NAME='employee.dat' ENDING=1;
|
||||||
|
|
||||||
SELECT Json_Object(SERIALNO, NAME, TITLE, SALARY) FROM t1 WHERE NAME = 'MERCHANT';
|
SELECT Json_Object(SERIALNO, NAME, TITLE, SALARY) FROM t3 WHERE NAME = 'MERCHANT';
|
||||||
SELECT DEPARTMENT, Json_Array_Grp(NAME) FROM t1 GROUP BY DEPARTMENT;
|
SELECT DEPARTMENT, Json_Array_Grp(NAME) FROM t3 GROUP BY DEPARTMENT;
|
||||||
set connect_json_grp_size=30;
|
SET connect_json_grp_size=30;
|
||||||
SELECT Json_Array(DEPARTMENT, Json_Array_Grp(NAME)) FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Object(title, Json_Array_Grp(name) `json_names`) from t3 GROUP BY title;
|
||||||
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(NAME) json_NAMES) FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Array(DEPARTMENT, Json_Array_Grp(NAME)) FROM t3 GROUP BY DEPARTMENT;
|
||||||
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(Json_Object(SERIALNO, NAME, TITLE, SALARY)) json_EMPLOYES) FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(NAME) json_NAMES) FROM t3 GROUP BY DEPARTMENT;
|
||||||
SELECT Json_Object(DEPARTMENT, TITLE, Json_Array_Grp(Json_Object(SERIALNO, NAME, SALARY)) json_EMPLOYES) FROM t1 GROUP BY DEPARTMENT, TITLE;
|
SELECT Json_Object(DEPARTMENT, Json_Array_Grp(Json_Object(SERIALNO, NAME, TITLE, SALARY)) json_EMPLOYES) FROM t3 GROUP BY DEPARTMENT;
|
||||||
|
SELECT Json_Object(DEPARTMENT, TITLE, Json_Array_Grp(Json_Object(SERIALNO, NAME, SALARY)) json_EMPLOYES) FROM t3 GROUP BY DEPARTMENT, TITLE;
|
||||||
--error ER_CANT_INITIALIZE_UDF
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
SELECT Json_Object_Grp(SALARY) FROM t1;
|
SELECT Json_Object_Grp(SALARY) FROM t3;
|
||||||
SELECT Json_Object_Grp(SALARY, NAME) FROM t1;
|
SELECT Json_Object_Grp(NAME, SALARY) FROM t3;
|
||||||
SELECT Json_Object(DEPARTMENT, Json_Object_Grp(SALARY, NAME) "Json_SALARIES") FROM t1 GROUP BY DEPARTMENT;
|
SELECT Json_Object(DEPARTMENT, Json_Object_Grp(NAME, SALARY) "Json_SALARIES") FROM t3 GROUP BY DEPARTMENT;
|
||||||
SELECT Json_Array_Grp(NAME) from t1;
|
SELECT Json_Array_Grp(NAME) FROM t3;
|
||||||
DROP TABLE t1;
|
#
|
||||||
|
SELECT Json_Object_Key(name, title) FROM t3 WHERE DEPARTMENT = 318;
|
||||||
|
SELECT Json_Object_Grp(name, title) FROM t3 WHERE DEPARTMENT = 318;
|
||||||
|
|
||||||
DROP FUNCTION Json_Array;
|
--echo #
|
||||||
DROP FUNCTION Json_Array_Add;
|
--echo # Test value getting UDF's
|
||||||
DROP FUNCTION Json_Object;
|
--echo #
|
||||||
DROP FUNCTION Json_Object_Nonull;
|
SELECT JsonGet_String(Json_Array_Grp(name),'[#]') FROM t3;
|
||||||
DROP FUNCTION Json_Value;
|
SELECT JsonGet_String(Json_Array_Grp(name),'[","]') FROM t3;
|
||||||
DROP FUNCTION Json_Array_Grp;
|
SELECT JsonGet_String(Json_Array_Grp(name),'[>]') FROM t3;
|
||||||
DROP FUNCTION Json_Object_Grp;
|
SET @j1 = '[45,28,36,45,89]';
|
||||||
|
SELECT JsonGet_String(@j1,'[1]');
|
||||||
|
SELECT JsonGet_String(@j1 json_,'[3]');
|
||||||
|
SELECT JsonGet_String(Json_Array(45,28,36,45,89),'[3]');
|
||||||
|
SELECT JsonGet_String(Json_Array(45,28,36,45,89),'["+"]') "list",'=' as "egal",JsonGet_String(Json_Array(45,28,36,45,89),'[+]') "sum";
|
||||||
|
SELECT JsonGet_String(Json_Array(json_array(45,28),json_array(36,45,89)),'[1]:[0]');
|
||||||
|
SELECT JsonGet_String(Json_Array(json_array(45,28),json_array(36,45,89)),'[1]:*');
|
||||||
|
SELECT JsonGet_String(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'truc');
|
||||||
|
SET @j2 = '{"qty":56,"price":3.141600,"truc":"machin","garanty":null}';
|
||||||
|
SELECT JsonGet_String(@j2 json_,'truc');
|
||||||
|
SELECT JsonGet_String(@j2,'truc');
|
||||||
|
SELECT JsonGet_String(@j2,'chose');
|
||||||
|
SELECT JsonGet_String(NULL json_, NULL);
|
||||||
|
SELECT department, JsonGet_String(Json_Object(department, Json_Array_Grp(salary) "Json_salaries"),'salaries:[+]') Sumsal FROM t3 GROUP BY department;
|
||||||
|
#
|
||||||
|
SELECT JsonGet_Int(@j1, '[4]');
|
||||||
|
SELECT JsonGet_Int(@j1, '[#]');
|
||||||
|
SELECT JsonGet_Int(@j1, '[+]');
|
||||||
|
SELECT JsonGet_Int(@j1 json_, '[3]');
|
||||||
|
SELECT JsonGet_Int(Json_Array(45,28,36,45,89), '[3]');
|
||||||
|
SELECT JsonGet_Int(Json_Array(45,28,36,45,89), '["+"]');
|
||||||
|
SELECT JsonGet_Int(Json_Array(45,28,36,45,89), '[+]');
|
||||||
|
SELECT JsonGet_Int(Json_Array(json_array(45,28), json_array(36,45,89)), '[1]:[0]');
|
||||||
|
SELECT JsonGet_Int(Json_Array(json_array(45,28), json_array(36,45,89)), '[0]:[1]');
|
||||||
|
SELECT JsonGet_Int(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'qty');
|
||||||
|
SELECT JsonGet_Int(@j2 json_, 'price');
|
||||||
|
SELECT JsonGet_Int(@j2, 'qty');
|
||||||
|
SELECT JsonGet_Int('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'chose');
|
||||||
|
SELECT JsonGet_Int(JsonGet_String(Json_Array(Json_Array(45,28),Json_Array(36,45,89)), '[1]:*'), '[+]') sum;
|
||||||
|
SELECT department, JsonGet_Int(Json_Object(department, Json_Array_Grp(salary) "Json_salaries"), 'salaries:[+]') Sumsal FROM t3 GROUP BY department;
|
||||||
|
#
|
||||||
|
SELECT JsonGet_Real(@j1, '[2]');
|
||||||
|
SELECT JsonGet_Real(@j1 json_, '[3]', 2);
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '[3]');
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '["+"]');
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '[+]');
|
||||||
|
SELECT JsonGet_Real(Json_Array(45,28,36,45,89), '[!]');
|
||||||
|
SELECT JsonGet_Real(Json_Array(json_array(45,28), json_array(36,45,89)), '[1]:[0]');
|
||||||
|
SELECT JsonGet_Real(Json_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'price');
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}' json_, 'qty');
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'price');
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'price', 4);
|
||||||
|
SELECT JsonGet_Real('{"qty":56,"price":3.141600,"truc":"machin","garanty":null}', 'chose');
|
||||||
|
SELECT department, JsonGet_Real(Json_Object(department, Json_Array_Grp(salary) "Json_salaries"),'salaries:[+]') Sumsal FROM t3 GROUP BY department;
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Documentation examples
|
||||||
|
--echo #
|
||||||
|
SELECT
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[4]') "Rank",
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[#]') "Number",
|
||||||
|
JsonGet_String(Json_Array(45,28,36,45,89), '[","]') "Concat",
|
||||||
|
JsonGet_Int(Json_Array(45,28,36,45,89), '[+]') "Sum",
|
||||||
|
JsonGet_Real(Json_Array(45,28,36,45,89), '[!]', 2) "Avg";
|
||||||
|
SELECT
|
||||||
|
JsonGet_String('{"qty":7,"price":29.50,"garanty":null}', 'price') "String",
|
||||||
|
JsonGet_Int('{"qty":7,"price":29.50,"garanty":null}', 'price') "Int",
|
||||||
|
JsonGet_Real('{"qty":7,"price":29.50,"garanty":null}', 'price') "Real";
|
||||||
|
SELECT JsonGet_Real('{"qty":7,"price":29.50,"garanty":null}', 'price', 3) "Real";
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Testing Locate
|
||||||
|
--echo #
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'machin');
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),56);
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),3.1416);
|
||||||
|
SELECT JsonLocate(Json_Object(56 qty,3.1416 price,'machin' truc, NULL garanty),'chose');
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, 'Jack') Path;
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, 'jack' ci) Path;
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, '{"FN":"Jack", "LN":"London"}' json_) Path;
|
||||||
|
SELECT JsonLocate('{"AUTHORS":[{"FN":"Jules", "LN":"Verne"}, {"FN":"Jack", "LN":"London"}]}' json_, '{"FN":"jack", "LN":"London"}' json_) Path;
|
||||||
|
SELECT JsonLocate('[45,28,36,45,89]',36);
|
||||||
|
SELECT JsonLocate('[45,28,36,45,89]' json_,28.0);
|
||||||
|
SELECT Json_Locate_All('[45,28,36,45,89]',10);
|
||||||
|
SELECT Json_Locate_All('[45,28,36,45,89]',45);
|
||||||
|
SELECT Json_Locate_All('[[45,28],36,45,89]',45);
|
||||||
|
SELECT Json_Locate_All('[[45,28,45],36,45,89]',45);
|
||||||
|
SELECT Json_Locate_All('[[45,28,45],36,45,89]',JsonGet_Int('[3,45]','[1]'));
|
||||||
|
SELECT JsonLocate('[[45,28,45],36,45,89]',45,n) from t1;
|
||||||
|
SELECT JsonGet_String(Json_Locate_All('[[45,28,45],36,45,89]',45),concat('[',n-1,']')) FROM t1;
|
||||||
|
SELECT JsonGet_String(Json_Locate_All('[[45,28,45],36,45,89]',45),concat('[',n-1,']')) AS `Path` FROM t1 GROUP BY n HAVING `Path` IS NOT NULL;
|
||||||
|
SELECT Json_Locate_All('[45,28,[36,45,89]]',45);
|
||||||
|
SELECT Json_Locate_All('[[45,28],[36,45.0,89]]',JsonValue(45.0));
|
||||||
|
SELECT Json_Locate_All('[[45,28],[36,45.0,89]]',45.0);
|
||||||
|
SELECT JsonLocate('[[45,28],[36,45,89]]','[36,45,89]' json_);
|
||||||
|
SELECT JsonLocate('[[45,28],[36,45,89]]','[45,28]' json_);
|
||||||
|
SELECT Json_Locate_All('[[45,28],[[36,45],89]]','45') "All paths";
|
||||||
|
SELECT Json_Locate_All('[[45,28],[[36,45],89]]','[36,45]' json_);
|
||||||
|
SELECT JsonGet_Int(Json_Locate_All('[[45,28],[[36,45],89]]',45), '[#]') "Nb of occurs";
|
||||||
|
SELECT Json_Locate_All('[[45,28],[[36,45],89]]',45,2);
|
||||||
|
SELECT JsonGet_String(Json_Locate_All('[45,28,36,45,89]',45),'[0]');
|
||||||
|
SELECT JsonLocate(Json_File('test/biblio.json'), 'Knab');
|
||||||
|
SELECT Json_Locate_All('test/biblio.json' jfile_, 'Knab');
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Testing json files
|
||||||
|
--echo #
|
||||||
|
SELECT Jfile_Make('[{"_id":5,"type":"food","item":"beer","taste":"light","price":5.65,"ratings":[5,8,9]},
|
||||||
|
{"_id":6,"type":"car","item":"roadster","mileage":56000,"ratings":[6,9]},
|
||||||
|
{"_id":7,"type":"food","item":"meat","origin":"argentina","ratings":[2,4]},
|
||||||
|
{"_id":8,"type":"furniture","item":"table","size":{"W":60,"L":80,"H":40},"ratings":[5,8,7]}]', 'test/fx.json', 0) AS NewFile;
|
||||||
|
SELECT Jfile_Make('test/fx.json', 1);
|
||||||
|
SELECT Jfile_Make('test/fx.json' jfile_);
|
||||||
|
SELECT Jfile_Make(Jbin_File('test/fx.json'), 0);
|
||||||
|
SELECT Json_File('test/fx.json', 1);
|
||||||
|
SELECT Json_File('test/fx.json', 2);
|
||||||
|
SELECT Json_File('test/fx.json', 0);
|
||||||
|
SELECT Json_File('test/fx.json', '[0]');
|
||||||
|
SELECT Json_File('test/fx.json', '[?]');
|
||||||
|
SELECT JsonGet_String(Json_File('test/fx.json'), '[1]:*');
|
||||||
|
SELECT JsonGet_String(Json_File('test/fx.json'), '[1]');
|
||||||
|
SELECT JsonGet_Int(Json_File('test/fx.json'), '[1]:mileage') AS Mileage;
|
||||||
|
SELECT JsonGet_Real(Json_File('test/fx.json'), '[0]:price', 2) AS Price;
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 'ratings');
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 1, 'ratings');
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]'), 6, 'ratings', 1);
|
||||||
|
SELECT Json_Array_Add(Json_File('test/fx.json', '[2]:ratings'), 6, 0);
|
||||||
|
SELECT Json_Array_Delete(Json_File('test/fx.json', '[2]'), 'ratings', 1);
|
||||||
|
SELECT Json_Object_Add(Json_File('test/fx.json', '[2]'), 'france' origin);
|
||||||
|
SELECT Json_Object_Add(Json_File('test/fx.json', '[2]'), 70 H, 'size');
|
||||||
|
SELECT Json_Object_Add(Json_File('test/fx.json', '[3]'), 70 H, 'size');
|
||||||
|
SELECT Json_Object_List(Json_File('test/fx.json', '[3]:size'));
|
||||||
|
|
||||||
|
DROP TABLE t1;
|
||||||
|
DROP TABLE t2;
|
||||||
|
DROP TABLE t3;
|
||||||
|
|
||||||
#
|
#
|
||||||
# Clean up
|
# Clean up
|
||||||
#
|
#
|
||||||
|
--source json_udf2.inc
|
||||||
--remove_file $MYSQLD_DATADIR/test/biblio.json
|
--remove_file $MYSQLD_DATADIR/test/biblio.json
|
||||||
--remove_file $MYSQLD_DATADIR/test/employee.dat
|
--remove_file $MYSQLD_DATADIR/test/employee.dat
|
||||||
|
--remove_file $MYSQLD_DATADIR/test/fx.json
|
||||||
|
49
storage/connect/mysql-test/connect/t/json_udf2.inc
Normal file
49
storage/connect/mysql-test/connect/t/json_udf2.inc
Normal file
@@ -0,0 +1,49 @@
|
|||||||
|
--disable_query_log
|
||||||
|
|
||||||
|
DROP FUNCTION json_array;
|
||||||
|
DROP FUNCTION json_array_add;
|
||||||
|
DROP FUNCTION json_array_add_values;
|
||||||
|
DROP FUNCTION json_array_delete;
|
||||||
|
DROP FUNCTION json_object;
|
||||||
|
DROP FUNCTION json_object_nonull;
|
||||||
|
DROP FUNCTION json_object_key;
|
||||||
|
DROP FUNCTION json_object_add;
|
||||||
|
DROP FUNCTION json_object_delete;
|
||||||
|
DROP FUNCTION json_object_list;
|
||||||
|
DROP FUNCTION jsonvalue;
|
||||||
|
DROP FUNCTION json_array_grp;
|
||||||
|
DROP FUNCTION json_object_grp;
|
||||||
|
DROP FUNCTION jsonget_string;
|
||||||
|
DROP FUNCTION jsonget_int;
|
||||||
|
DROP FUNCTION jsonget_real;
|
||||||
|
DROP FUNCTION jsonlocate;
|
||||||
|
DROP FUNCTION json_locate_all;
|
||||||
|
DROP FUNCTION json_file;
|
||||||
|
DROP FUNCTION jfile_make;
|
||||||
|
DROP FUNCTION json_get_item;
|
||||||
|
DROP FUNCTION json_item_merge;
|
||||||
|
DROP FUNCTION jsoncontains;
|
||||||
|
DROP FUNCTION jsoncontains_path;
|
||||||
|
DROP FUNCTION json_set_item;
|
||||||
|
DROP FUNCTION json_insert_item;
|
||||||
|
DROP FUNCTION json_update_item;
|
||||||
|
DROP FUNCTION json_serialize;
|
||||||
|
DROP FUNCTION jbin_array;
|
||||||
|
DROP FUNCTION jbin_array_add_values;
|
||||||
|
DROP FUNCTION jbin_array_add;
|
||||||
|
DROP FUNCTION jbin_array_delete;
|
||||||
|
DROP FUNCTION jbin_object;
|
||||||
|
DROP FUNCTION jbin_object_nonull;
|
||||||
|
DROP FUNCTION jbin_object_key;
|
||||||
|
DROP FUNCTION jbin_object_add;
|
||||||
|
DROP FUNCTION jbin_object_delete;
|
||||||
|
DROP FUNCTION jbin_object_list;
|
||||||
|
DROP FUNCTION jbin_get_item;
|
||||||
|
DROP FUNCTION jbin_item_merge;
|
||||||
|
DROP FUNCTION jbin_set_item;
|
||||||
|
DROP FUNCTION jbin_insert_item;
|
||||||
|
DROP FUNCTION jbin_update_item;
|
||||||
|
DROP FUNCTION jbin_file;
|
||||||
|
|
||||||
|
--enable_query_log
|
||||||
|
|
212
storage/connect/mysql-test/connect/t/json_udf_bin.test
Normal file
212
storage/connect/mysql-test/connect/t/json_udf_bin.test
Normal file
@@ -0,0 +1,212 @@
|
|||||||
|
--source json_udf.inc
|
||||||
|
|
||||||
|
let $MYSQLD_DATADIR= `select @@datadir`;
|
||||||
|
|
||||||
|
--copy_file $MTR_SUITE_DIR/std_data/gloss.json $MYSQLD_DATADIR/gloss.json
|
||||||
|
|
||||||
|
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=VIR BLOCK_SIZE=3;
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Test Jbin UDF's
|
||||||
|
--echo #
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), n) from t1;
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(n, 3.1416, 'My name is "Foo"', NULL), n) from t1;
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), Jbin_Array('a','b',n)) from t1;
|
||||||
|
SELECT Json_Array_Add(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), JsonGet_String(Jbin_Array('a','b','c'), '[1]'));
|
||||||
|
SELECT Json_Array_Delete(Jbin_Array_Add_Values(Jbin_Array(56, 3.1416, 'My name is "Foo"', NULL), "One more", 2), 4);
|
||||||
|
SELECT Json_Array_Delete(Jbin_Array(56, Jbin_Array(3.1416, 'My name is "Foo"'), NULL), '[1]', 1);
|
||||||
|
SELECT Json_Array_Delete(Jbin_Array(56, Jbin_Array(3.1416, 'My name is "Foo"'), TRUE), 1, '[1]');
|
||||||
|
SELECT Json_Array(1, TRUE, 0, FALSE);
|
||||||
|
SELECT Json_Serialize(Jbin_Array(TRUE, FALSE));
|
||||||
|
#
|
||||||
|
SELECT Json_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL);
|
||||||
|
SELECT Json_Serialize(Jbin_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty', NULL));
|
||||||
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
|
SELECT Jbin_Object_Key('qty', 56, 'price', 3.1416, 'truc', 'machin', 'garanty');
|
||||||
|
SELECT Json_Object_Add(Jbin_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color);
|
||||||
|
SELECT Json_Object_Add(Jbin_Object(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price);
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Nonull(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 'blue' color);
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Nonull(56 qty, 3.1416 price, 'machin' truc, NULL garanty), 45.99 price);
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Test Jbin file UDF's
|
||||||
|
--echo #
|
||||||
|
SELECT Json_Serialize(Jbin_File('gloss.json'));
|
||||||
|
SELECT JsonLocate(Jbin_File('gloss.json'),'XML');
|
||||||
|
#
|
||||||
|
SELECT Json_Object_Key('first', 'foo', 'second', Jbin_Array('a', 33));
|
||||||
|
SELECT Json_Get_Item(Json_Array('a','b','c'), '[1]');
|
||||||
|
SELECT Json_Get_Item(Json_Object('foo' AS "first", Json_Array('a', 33) AS "json_second"), 'second') AS "item";
|
||||||
|
SELECT Json_Get_Item(Jbin_Object('foo' first, Jbin_Array('a', 33) jbin_second), 'second:*') item;
|
||||||
|
SELECT Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv');
|
||||||
|
SELECT Json_Serialize(Jbin_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv'));
|
||||||
|
SELECT Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv:*');
|
||||||
|
SELECT JsonGet_String(Json_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso') lang;
|
||||||
|
SELECT Json_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso') "See also";
|
||||||
|
SELECT Json_Serialize(Jbin_Get_Item(Jbin_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso')) "See also";
|
||||||
|
SELECT JsonGet_String(Json_Get_Item(Json_File('gloss.json'),'glossary:GlossDiv:GlossList:GlossEntry:GlossDef:GlossSeeAlso'),'[0]') lang;
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Test Item Get/Set/Insert/Update UDF's
|
||||||
|
--echo #
|
||||||
|
SELECT Json_Get_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), '[]');
|
||||||
|
SELECT Json_Get_Item(Jbin_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), '[1]');
|
||||||
|
SELECT Json_Get_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), '[1]');
|
||||||
|
#
|
||||||
|
SELECT Json_Set_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)));
|
||||||
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 'foo');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 7, '[1]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 7, '[1]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Json_Array(7, 8, 9), '[1]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[2]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[2]:*');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 3.1416, 'foo');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 'toto', '[1]:[2]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 300, '[2]:nxt:total:[]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 300, '[2]:nxt:total:[]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), Jbin_Array(7, 8, 9), '[1]', 5, '[2]:cinq', 10, '[1]:[]');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 44, '[2]:quatre');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, 'truc');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '');
|
||||||
|
SELECT Json_Set_Item(Jbin_Array(1, 2, Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '*');
|
||||||
|
SELECT Json_Serialize(Jbin_Set_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq'));
|
||||||
|
#
|
||||||
|
SELECT Json_Insert_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq');
|
||||||
|
SELECT Json_Update_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq');
|
||||||
|
SELECT Json_Insert_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 44, '[2]:quatre');
|
||||||
|
SELECT Json_Update_Item(Jbin_Array(1, Jbin_Array(7, 8, 9), Jbin_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[]', 44, '[2]:quatre');
|
||||||
|
SELECT Json_Insert_Item(Json_Array(1, Json_Array(7, 8, 9), Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[1]', 300, '[2]:nxt:total:[]');
|
||||||
|
SELECT Json_Update_Item(Json_Array(1, Json_Array(7, 8, 9), Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[2]:cinq', 10, '[1]:[1]', 300, '[2]:nxt:total:[]');
|
||||||
|
SELECT Json_Insert_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[]');
|
||||||
|
SELECT Json_Update_Item(Json_Array(1, 2, Json_Object_Key('trois', 3, 'quatre', 4)), 5, '[]');
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Test merging items UDF's
|
||||||
|
--echo #
|
||||||
|
SELECT Json_Item_Merge(Jbin_Array('a','b','c'), Jbin_Array('d','e','f'));
|
||||||
|
SELECT Json_Item_Merge(Json_Array('a','b','c'), Json_Array('d','e','f')) AS "Result";
|
||||||
|
SELECT Json_Array_Add(Jbin_Item_Merge(Jbin_Array('a','b','c'), Jbin_Array('d','e','f')), 'and', 3);
|
||||||
|
SELECT Json_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "d",5 "e",6 "f"));
|
||||||
|
SELECT Json_Item_Merge(Jbin_Object(1 "a",2 "b",2 "c"), Jbin_Array('d','e','f'));
|
||||||
|
SELECT Json_Object_Add(Jbin_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "d",5 "e",6 "f")), 'x' AS "and");
|
||||||
|
SELECT Json_Item_Merge(Jbin_Object(1 "a",2 "b",3 "c"), Jbin_Object(4 "a",5 "e",6 "f"));
|
||||||
|
--error ER_CANT_INITIALIZE_UDF
|
||||||
|
SELECT Json_Item_Merge('foo', Json_Array('d','e','f'));
|
||||||
|
|
||||||
|
--echo #
|
||||||
|
--echo # Test making file UDF's
|
||||||
|
--echo #
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
SELECT Json_File(Jfile_Make(Jbin_File('bt1.json'), 0));
|
||||||
|
SELECT Json_File(Jfile_Make(Jbin_File('bt1.json'), 1));
|
||||||
|
SELECT Json_File(Jfile_Make(Jbin_File('bt1.json'), 2));
|
||||||
|
SELECT Json_File('bt1.json', 0);
|
||||||
|
SELECT Json_File('bt1.json', 1);
|
||||||
|
SELECT Json_File('bt1.json', 2);
|
||||||
|
SELECT Json_Serialize(Jbin_Array('a','b','c'));
|
||||||
|
SELECT Json_Serialize(Jbin_Array_Add(Jbin_File('not_exist.json'), 'd'));
|
||||||
|
--echo # This does not modify the file
|
||||||
|
SELECT Json_Serialize(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'));
|
||||||
|
SELECT Json_File('bt1.json', 2);
|
||||||
|
--echo # This does modify the file
|
||||||
|
SELECT Json_Array_Add(Jbin_File('bt1.json'), 'd');
|
||||||
|
SELECT Json_File('bt1.json', 2);
|
||||||
|
--echo # Back to the original file
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_Array('a','b','c'), 'd') "Jbin_foo") AS "Result";
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_File('bt1.json'), 'd')) AS "Result";
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_File('bt1.json'), 'd') "Jbin_bt1") AS "Result";
|
||||||
|
--echo # This does modify the file
|
||||||
|
SELECT Json_Object(Json_Array_Add(Jbin_File('bt1.json'), 'd') "Jfile_bt1") AS "Result";
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
SELECT Json_File(Json_Array_Delete(Jbin_File('bt1.json'), 3), 2);
|
||||||
|
SELECT Json_Object(Jbin_Array_Add(Jbin_File('bt1.json'), 'd') "Jbin_bt1", n "t1") AS "Result" from t1;
|
||||||
|
SELECT Json_File(Json_Array_Add(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'), 'e')) AS "Result";
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
SELECT Json_File(Json_Array_Add(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'), 'e')) AS "Result" from t1;
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
SELECT Json_Array_Add(Jbin_Array_Add(Jbin_File('bt1.json'), 'd'), n) AS "Result" from t1;
|
||||||
|
--echo # Show modified file
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
SELECT Json_Array_Add(Jbin_File('bt1.json'), n) AS "Result" from t1;
|
||||||
|
--echo # Show modified file
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
SELECT Json_File(Jbin_Item_Merge(Jbin_File('bt1.json'), Jbin_Array('d','e','f')));
|
||||||
|
SELECT Json_File(Json_Item_Merge(Jbin_File('bt1.json'), Jbin_Array('d','e','f')));
|
||||||
|
SELECT Jfile_Make(Jbin_Array('a','b','c'), 'bt1.json');
|
||||||
|
--echo # Test DELETE from file
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 1)) AS "Result";
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 2) "Jbin_bt1") AS "Result";
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 0) "Jbin_bt1", n "t1") AS "Result" from t1;
|
||||||
|
SELECT Json_Object(Jbin_Array_Delete(Jbin_File('bt1.json'), 3 - n) "Jbin_bt1") AS "Result" from t1;
|
||||||
|
SELECT Json_Object(Json_Array_Delete(Jbin_File('bt1.json'), 3 - n) "Jbin_bt1") AS "Result" from t1;
|
||||||
|
--echo # Show modified file
|
||||||
|
SELECT Json_File('bt1.json');
|
||||||
|
--echo # Object file
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
SELECT Json_File('bt2.json', 0);
|
||||||
|
SELECT Json_File('bt2.json');
|
||||||
|
SELECT Json_Serialize(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"));
|
||||||
|
--echo # First query (file not modified)
|
||||||
|
SELECT Json_Object(Jbin_Object_Add(Jbin_File('bt2.json'), 4 AS "d") AS "Jbin_new") AS "Result";
|
||||||
|
--echo # First query (file modified)
|
||||||
|
SELECT Json_Object(Json_Object_Add(Jbin_File('bt2.json'), 4 AS "d") AS "Jfile_new") AS "Result";
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
SELECT Json_Object(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d") "Jbin_new", n "t1") AS "Result" from t1;
|
||||||
|
SELECT Json_File(Json_Object_Add(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"), 5 "e")) AS "Result";
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"), 5 "e") AS "Result" from t1;
|
||||||
|
SELECT Json_Object_Add(Jbin_Object_Add(Jbin_File('bt2.json'), 4 "d"), n "n") AS "Result" from t1;
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
SELECT Json_Object_Add(Jbin_File('bt2.json'), n) AS "Result" from t1;
|
||||||
|
SELECT Json_File('bt2.json');
|
||||||
|
SELECT Jfile_Make(Jbin_Object(1 "a", 2 "b", 3 "c"), 'bt2.json', 0);
|
||||||
|
SELECT Json_Serialize(Jbin_Item_Merge(Jbin_File('bt2.json'), Jbin_Object(4 "d",5 "e",6 "f"))) AS "Result";
|
||||||
|
SELECT Json_File(Json_Item_Merge(Jbin_File('bt2.json'), Jbin_Object(4 "d",5 "e",6 "f"))) AS "Result";
|
||||||
|
SELECT Json_Item_Merge(Json_Object(1 "a", 2 "b", 3 "c"), Json_Object(4 "d",5 "b",6 "f")) AS "Result";
|
||||||
|
#
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'b')) AS "Result";
|
||||||
|
SELECT Json_Object(Jbin_Object_Delete(Jbin_File('bt2.json'), 'c') "Jbin_bt1") AS "Result";
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'c') "Jbin_bt1") AS "Result";
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'c') "Jfile_bt1") AS "Result";
|
||||||
|
SELECT Json_Object(Json_Object_Delete(Jbin_File('bt2.json'), 'a') "Jbin_bt1", n "t1") AS "Result" from t1;
|
||||||
|
#
|
||||||
|
SELECT Json_Serialize(Jbin_Object_List(Jbin_File('bt2.json'))) "Key list";
|
||||||
|
|
||||||
|
#
|
||||||
|
# Test documentation examples
|
||||||
|
#
|
||||||
|
SELECT Jfile_Make('{"a":1, "b":[44, 55]}' json_, 'bt3.json', 0);
|
||||||
|
SELECT Json_Array_Add(Json_File('bt3.json', 'b'), 66);
|
||||||
|
SELECT Json_Array_Add(Json_File('bt3.json'), 66, 'b');
|
||||||
|
SELECT Json_Array_Add(Jbin_File('bt3.json', 'b'), 66);
|
||||||
|
SELECT Json_File('bt3.json', 3);
|
||||||
|
SELECT Jfile_Make('{"a":1, "b":[44, 55]}' json_, 'bt3.json', 0);
|
||||||
|
#
|
||||||
|
CREATE TABLE t2 (
|
||||||
|
n INT KEY,
|
||||||
|
jfile_cols CHAR(12) NOT NULL)
|
||||||
|
ENGINE= MYISAM;
|
||||||
|
INSERT INTO t2 VALUES(1,'bt3.json');
|
||||||
|
--echo # In this table, the jfile_cols column just contains a file name
|
||||||
|
UPDATE t2 SET jfile_cols = Json_Array_Add(Jbin_File('bt3.json', 'b'), 66) WHERE n = 1;
|
||||||
|
SELECT JsonGet_String(jfile_cols, '*') FROM t2;
|
||||||
|
UPDATE t2 SET jfile_cols = Json_Insert_Item(jfile_cols, 77, 'b:[]') WHERE n = 1;
|
||||||
|
SELECT JsonGet_String(jfile_cols, 'b:*') FROM t2;
|
||||||
|
UPDATE t2 SET jfile_cols = Json_Insert_Item(Jbin_Insert_Item(jfile_cols, 88, 'b:') , 99, 'b:') WHERE n = 1;
|
||||||
|
SELECT JsonGet_String(jfile_cols, '*') FROM t2;
|
||||||
|
|
||||||
|
DROP TABLE t1, t2;
|
||||||
|
|
||||||
|
#
|
||||||
|
# Clean up
|
||||||
|
#
|
||||||
|
--source json_udf2.inc
|
||||||
|
--remove_file $MYSQLD_DATADIR/gloss.json
|
||||||
|
--remove_file $MYSQLD_DATADIR/bt1.json
|
||||||
|
--remove_file $MYSQLD_DATADIR/bt2.json
|
||||||
|
--remove_file $MYSQLD_DATADIR/bt3.json
|
@@ -19,8 +19,10 @@ DROP TABLE t1;
|
|||||||
--echo #
|
--echo #
|
||||||
--echo # Testing FILE privilege
|
--echo # Testing FILE privilege
|
||||||
--echo #
|
--echo #
|
||||||
|
set sql_mode="";
|
||||||
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
GRANT ALL PRIVILEGES ON *.* TO user@localhost;
|
||||||
REVOKE FILE ON *.* FROM user@localhost;
|
REVOKE FILE ON *.* FROM user@localhost;
|
||||||
|
set sql_mode=default;
|
||||||
--connect(user,localhost,user,,)
|
--connect(user,localhost,user,,)
|
||||||
--connection user
|
--connection user
|
||||||
SELECT user();
|
SELECT user();
|
||||||
@@ -54,7 +56,7 @@ CREATE VIEW v1 AS SELECT * FROM t1;
|
|||||||
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
--connection default
|
--connection default
|
||||||
SELECT user();
|
SELECT user();
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
--connection user
|
--connection user
|
||||||
SELECT user();
|
SELECT user();
|
||||||
--error ER_ACCESS_DENIED_ERROR
|
--error ER_ACCESS_DENIED_ERROR
|
||||||
|
@@ -27,6 +27,15 @@
|
|||||||
#Servername=localhost
|
#Servername=localhost
|
||||||
#Port=5432
|
#Port=5432
|
||||||
#
|
#
|
||||||
|
# 5. Allow user "mtr" to connect to the database "mtr"
|
||||||
|
# Add this line into the begginning of pg_hba.conf
|
||||||
|
# (usually /var/lib/pgsql/data/pg_hba.conf on Linux):
|
||||||
|
#host mtr mtr 127.0.0.1/32 password
|
||||||
|
#
|
||||||
|
# 6. Restart the server:
|
||||||
|
# sudo service postgresql restart
|
||||||
|
#
|
||||||
|
#
|
||||||
|
|
||||||
SET NAMES utf8;
|
SET NAMES utf8;
|
||||||
|
|
||||||
|
@@ -56,9 +56,10 @@ ALTER TABLE t1 READONLY=1;
|
|||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE VIEW v1 AS SELECT * FROM t1;
|
||||||
|
|
||||||
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
|
--echo # using SQL SECIRITY INVOKER
|
||||||
--connection default
|
--connection default
|
||||||
SELECT user();
|
SELECT user();
|
||||||
CREATE VIEW v1 AS SELECT * FROM t1;
|
CREATE SQL SECURITY INVOKER VIEW v1 AS SELECT * FROM t1;
|
||||||
--connection user
|
--connection user
|
||||||
SELECT user();
|
SELECT user();
|
||||||
--error ER_ACCESS_DENIED_ERROR
|
--error ER_ACCESS_DENIED_ERROR
|
||||||
@@ -70,6 +71,17 @@ UPDATE v1 SET a=123;
|
|||||||
--error ER_ACCESS_DENIED_ERROR
|
--error ER_ACCESS_DENIED_ERROR
|
||||||
DELETE FROM v1;
|
DELETE FROM v1;
|
||||||
|
|
||||||
|
--echo # Testing a VIEW created with FILE privileges but accessed with no FILE
|
||||||
|
--echo # using SQL SECIRITY DEFINER
|
||||||
|
--connection default
|
||||||
|
DROP VIEW v1;
|
||||||
|
SELECT user();
|
||||||
|
CREATE SQL SECURITY DEFINER VIEW v1 AS SELECT * FROM t1;
|
||||||
|
--connection user
|
||||||
|
SELECT user();
|
||||||
|
SELECT * FROM v1 WHERE a='test1';
|
||||||
|
|
||||||
|
|
||||||
--disconnect user
|
--disconnect user
|
||||||
--connection default
|
--connection default
|
||||||
SELECT user();
|
SELECT user();
|
||||||
|
@@ -143,7 +143,7 @@ PGLOBAL PlugInit(LPCSTR Language, uint worksize)
|
|||||||
fprintf(stderr, MSG(GLOBAL_ERROR), (int)sizeof(GLOBAL));
|
fprintf(stderr, MSG(GLOBAL_ERROR), (int)sizeof(GLOBAL));
|
||||||
return NULL;
|
return NULL;
|
||||||
} else {
|
} else {
|
||||||
g->Sarea_Size = worksize;
|
g->Sarea = NULL;
|
||||||
g->Createas = 0;
|
g->Createas = 0;
|
||||||
g->Alchecked = 0;
|
g->Alchecked = 0;
|
||||||
g->Mrr = 0;
|
g->Mrr = 0;
|
||||||
@@ -155,7 +155,7 @@ PGLOBAL PlugInit(LPCSTR Language, uint worksize)
|
|||||||
/*******************************************************************/
|
/*******************************************************************/
|
||||||
/* Allocate the main work segment. */
|
/* Allocate the main work segment. */
|
||||||
/*******************************************************************/
|
/*******************************************************************/
|
||||||
if (!(g->Sarea = PlugAllocMem(g, worksize))) {
|
if (worksize && !(g->Sarea = PlugAllocMem(g, worksize))) {
|
||||||
char errmsg[256];
|
char errmsg[256];
|
||||||
sprintf(errmsg, MSG(WORK_AREA), g->Message);
|
sprintf(errmsg, MSG(WORK_AREA), g->Message);
|
||||||
strcpy(g->Message, errmsg);
|
strcpy(g->Message, errmsg);
|
||||||
@@ -163,7 +163,7 @@ PGLOBAL PlugInit(LPCSTR Language, uint worksize)
|
|||||||
} else
|
} else
|
||||||
g->Sarea_Size = worksize;
|
g->Sarea_Size = worksize;
|
||||||
|
|
||||||
} /* endif g */
|
} /* endif g */
|
||||||
|
|
||||||
g->jump_level = -1; /* New setting to allow recursive call of Plug */
|
g->jump_level = -1; /* New setting to allow recursive call of Plug */
|
||||||
return(g);
|
return(g);
|
||||||
|
@@ -47,6 +47,7 @@
|
|||||||
#include "valblk.h"
|
#include "valblk.h"
|
||||||
#include "tabmul.h"
|
#include "tabmul.h"
|
||||||
#include "ha_connect.h"
|
#include "ha_connect.h"
|
||||||
|
#include "mycat.h"
|
||||||
|
|
||||||
#if !defined(__WIN__)
|
#if !defined(__WIN__)
|
||||||
extern handlerton *connect_hton;
|
extern handlerton *connect_hton;
|
||||||
|
@@ -2019,7 +2019,7 @@ int TDBDOS::EstimatedLength(void)
|
|||||||
dep = 1 + cdp->GetLong() / 20; // Why 20 ?????
|
dep = 1 + cdp->GetLong() / 20; // Why 20 ?????
|
||||||
} else for (; cdp; cdp = cdp->GetNext())
|
} else for (; cdp; cdp = cdp->GetNext())
|
||||||
if (!(cdp->Flags & (U_VIRTUAL|U_SPECIAL)))
|
if (!(cdp->Flags & (U_VIRTUAL|U_SPECIAL)))
|
||||||
dep = MY_MAX(dep, cdp->GetOffset());
|
dep = MY_MAX(dep, cdp->GetOffset());
|
||||||
|
|
||||||
return (int)dep;
|
return (int)dep;
|
||||||
} // end of Estimated Length
|
} // end of Estimated Length
|
||||||
@@ -2204,7 +2204,7 @@ bool TDBDOS::PrepareWriting(PGLOBAL)
|
|||||||
} // endif Mode
|
} // endif Mode
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
} // end of WriteDB
|
} // end of PrepareWriting
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* WriteDB: Data Base write routine for DOS access method. */
|
/* WriteDB: Data Base write routine for DOS access method. */
|
||||||
@@ -2216,7 +2216,7 @@ int TDBDOS::WriteDB(PGLOBAL g)
|
|||||||
|
|
||||||
// Make the line to write
|
// Make the line to write
|
||||||
if (PrepareWriting(g))
|
if (PrepareWriting(g))
|
||||||
return true;
|
return RC_FX;
|
||||||
|
|
||||||
if (trace > 1)
|
if (trace > 1)
|
||||||
htrc("Write: line is='%s'\n", To_Line);
|
htrc("Write: line is='%s'\n", To_Line);
|
||||||
|
@@ -659,7 +659,7 @@ int TDBJSN::ReadDB(PGLOBAL g)
|
|||||||
if (!IsRead() && ((rc = ReadBuffer(g)) != RC_OK)) {
|
if (!IsRead() && ((rc = ReadBuffer(g)) != RC_OK)) {
|
||||||
// Deferred reading failed
|
// Deferred reading failed
|
||||||
} else if (!(Row = ParseJson(g, To_Line,
|
} else if (!(Row = ParseJson(g, To_Line,
|
||||||
strlen(To_Line), Pretty, &Comma))) {
|
strlen(To_Line), &Pretty, &Comma))) {
|
||||||
rc = (Pretty == 1 && !strcmp(To_Line, "]")) ? RC_EF : RC_FX;
|
rc = (Pretty == 1 && !strcmp(To_Line, "]")) ? RC_EF : RC_FX;
|
||||||
} else {
|
} else {
|
||||||
Row = FindRow(g);
|
Row = FindRow(g);
|
||||||
@@ -755,7 +755,6 @@ int TDBJSN::MakeTopTree(PGLOBAL g, PJSON jsp)
|
|||||||
} else
|
} else
|
||||||
strcpy(To_Line, s);
|
strcpy(To_Line, s);
|
||||||
|
|
||||||
// Row->Clear();
|
|
||||||
return false;
|
return false;
|
||||||
} else
|
} else
|
||||||
return true;
|
return true;
|
||||||
@@ -980,7 +979,7 @@ bool JSONCOL::ParseJpath(PGLOBAL g)
|
|||||||
Nod = colp->Nod;
|
Nod = colp->Nod;
|
||||||
Nodes = colp->Nodes;
|
Nodes = colp->Nodes;
|
||||||
Xpd = colp->Xpd;
|
Xpd = colp->Xpd;
|
||||||
goto fin;
|
goto fin;
|
||||||
} // endif Name
|
} // endif Name
|
||||||
|
|
||||||
sprintf(g->Message, "Cannot parse updated column %s", Name);
|
sprintf(g->Message, "Cannot parse updated column %s", Name);
|
||||||
@@ -1046,7 +1045,8 @@ void JSONCOL::SetJsonValue(PGLOBAL g, PVAL vp, PJVAL val, int n)
|
|||||||
switch (val->GetValType()) {
|
switch (val->GetValType()) {
|
||||||
case TYPE_STRG:
|
case TYPE_STRG:
|
||||||
case TYPE_INTG:
|
case TYPE_INTG:
|
||||||
case TYPE_DBL:
|
case TYPE_BINT:
|
||||||
|
case TYPE_DBL:
|
||||||
vp->SetValue_pval(val->GetValue());
|
vp->SetValue_pval(val->GetValue());
|
||||||
break;
|
break;
|
||||||
case TYPE_BOOL:
|
case TYPE_BOOL:
|
||||||
@@ -1107,7 +1107,7 @@ PVAL JSONCOL::GetColumnValue(PGLOBAL g, PJSON row, int i)
|
|||||||
} else switch (row->GetType()) {
|
} else switch (row->GetType()) {
|
||||||
case TYPE_JOB:
|
case TYPE_JOB:
|
||||||
if (!Nodes[i].Key) {
|
if (!Nodes[i].Key) {
|
||||||
// Expected Array was not there
|
// Expected Array was not there, wrap the value
|
||||||
if (i < Nod-1)
|
if (i < Nod-1)
|
||||||
continue;
|
continue;
|
||||||
else
|
else
|
||||||
@@ -1128,11 +1128,11 @@ PVAL JSONCOL::GetColumnValue(PGLOBAL g, PJSON row, int i)
|
|||||||
else
|
else
|
||||||
return CalculateArray(g, arp, i);
|
return CalculateArray(g, arp, i);
|
||||||
|
|
||||||
} else if (i < Nod-1) {
|
} else {
|
||||||
strcpy(g->Message, "Unexpected array");
|
// Unexpected array, unwrap it as [0]
|
||||||
val = NULL; // Not an expected array
|
val = arp->GetValue(0);
|
||||||
} else
|
i--;
|
||||||
val = arp->GetValue(0);
|
} // endif's
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case TYPE_JVAL:
|
case TYPE_JVAL:
|
||||||
@@ -1275,30 +1275,31 @@ PJSON JSONCOL::GetRow(PGLOBAL g)
|
|||||||
PJAR arp;
|
PJAR arp;
|
||||||
PJSON nwr, row = Tjp->Row;
|
PJSON nwr, row = Tjp->Row;
|
||||||
|
|
||||||
for (int i = 0; i < Nod-1 && row; i++) {
|
for (int i = 0; i < Nod && row; i++) {
|
||||||
if (Nodes[i+1].Op == OP_XX)
|
if (Nodes[i+1].Op == OP_XX)
|
||||||
break;
|
break;
|
||||||
else switch (row->GetType()) {
|
else switch (row->GetType()) {
|
||||||
case TYPE_JOB:
|
case TYPE_JOB:
|
||||||
if (!Nodes[i].Key)
|
if (!Nodes[i].Key)
|
||||||
// Expected Array was not there
|
// Expected Array was not there, wrap the value
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
val = ((PJOB)row)->GetValue(Nodes[i].Key);
|
val = ((PJOB)row)->GetValue(Nodes[i].Key);
|
||||||
break;
|
break;
|
||||||
case TYPE_JAR:
|
case TYPE_JAR:
|
||||||
if (!Nodes[i].Key) {
|
arp = (PJAR)row;
|
||||||
arp = (PJAR)row;
|
|
||||||
|
|
||||||
|
if (!Nodes[i].Key) {
|
||||||
if (Nodes[i].Op == OP_EQ)
|
if (Nodes[i].Op == OP_EQ)
|
||||||
val = arp->GetValue(Nodes[i].Rank);
|
val = arp->GetValue(Nodes[i].Rank);
|
||||||
else
|
else
|
||||||
val = arp->GetValue(Nodes[i].Rx);
|
val = arp->GetValue(Nodes[i].Rx);
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
strcpy(g->Message, "Unexpected array");
|
// Unexpected array, unwrap it as [0]
|
||||||
val = NULL; // Not an expected array
|
val = arp->GetValue(0);
|
||||||
} // endif Nodes
|
i--;
|
||||||
|
} // endif Nodes
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case TYPE_JVAL:
|
case TYPE_JVAL:
|
||||||
@@ -1353,7 +1354,7 @@ void JSONCOL::WriteColumn(PGLOBAL g)
|
|||||||
longjmp(g->jumper[g->jump_level], 666);
|
longjmp(g->jumper[g->jump_level], 666);
|
||||||
} // endif Xpd
|
} // endif Xpd
|
||||||
|
|
||||||
/*********************************************************************/
|
/*********************************************************************/
|
||||||
/* Check whether this node must be written. */
|
/* Check whether this node must be written. */
|
||||||
/*********************************************************************/
|
/*********************************************************************/
|
||||||
if (Value != To_Val)
|
if (Value != To_Val)
|
||||||
@@ -1370,7 +1371,6 @@ void JSONCOL::WriteColumn(PGLOBAL g)
|
|||||||
PJAR arp = NULL;
|
PJAR arp = NULL;
|
||||||
PJVAL jvp = NULL;
|
PJVAL jvp = NULL;
|
||||||
PJSON jsp, row = GetRow(g);
|
PJSON jsp, row = GetRow(g);
|
||||||
JTYP type = row->GetType();
|
|
||||||
|
|
||||||
switch (row->GetType()) {
|
switch (row->GetType()) {
|
||||||
case TYPE_JOB: objp = (PJOB)row; break;
|
case TYPE_JOB: objp = (PJOB)row; break;
|
||||||
@@ -1384,7 +1384,7 @@ void JSONCOL::WriteColumn(PGLOBAL g)
|
|||||||
if (Nodes[Nod-1].Op == OP_XX) {
|
if (Nodes[Nod-1].Op == OP_XX) {
|
||||||
s = Value->GetCharValue();
|
s = Value->GetCharValue();
|
||||||
|
|
||||||
if (!(jsp = ParseJson(g, s, (int)strlen(s), 0))) {
|
if (!(jsp = ParseJson(g, s, (int)strlen(s)))) {
|
||||||
strcpy(g->Message, s);
|
strcpy(g->Message, s);
|
||||||
longjmp(g->jumper[g->jump_level], 666);
|
longjmp(g->jumper[g->jump_level], 666);
|
||||||
} // endif jsp
|
} // endif jsp
|
||||||
@@ -1522,7 +1522,7 @@ int TDBJSON::MakeDocument(PGLOBAL g)
|
|||||||
/* Parse the json file and allocate its tree structure. */
|
/* Parse the json file and allocate its tree structure. */
|
||||||
/*********************************************************************/
|
/*********************************************************************/
|
||||||
g->Message[0] = 0;
|
g->Message[0] = 0;
|
||||||
jsp = Top = ParseJson(g, memory, len, Pretty);
|
jsp = Top = ParseJson(g, memory, len, &Pretty);
|
||||||
Txfp->CloseTableFile(g, false);
|
Txfp->CloseTableFile(g, false);
|
||||||
Mode = mode; // Restore saved Mode
|
Mode = mode; // Restore saved Mode
|
||||||
|
|
||||||
@@ -1540,7 +1540,7 @@ int TDBJSON::MakeDocument(PGLOBAL g)
|
|||||||
|
|
||||||
if (*objpath != '[') { // objpass is a key
|
if (*objpath != '[') { // objpass is a key
|
||||||
if (jsp->GetType() != TYPE_JOB) {
|
if (jsp->GetType() != TYPE_JOB) {
|
||||||
strcpy(g->Message, "Table path does no match json file");
|
strcpy(g->Message, "Table path does not match the json file");
|
||||||
return RC_FX;
|
return RC_FX;
|
||||||
} // endif Type
|
} // endif Type
|
||||||
|
|
||||||
@@ -1556,7 +1556,7 @@ int TDBJSON::MakeDocument(PGLOBAL g)
|
|||||||
|
|
||||||
} else if (objpath[strlen(objpath)-1] == ']') {
|
} else if (objpath[strlen(objpath)-1] == ']') {
|
||||||
if (jsp->GetType() != TYPE_JAR) {
|
if (jsp->GetType() != TYPE_JAR) {
|
||||||
strcpy(g->Message, "Table path does no match json file");
|
strcpy(g->Message, "Table path does not match the json file");
|
||||||
return RC_FX;
|
return RC_FX;
|
||||||
} // endif Type
|
} // endif Type
|
||||||
|
|
||||||
@@ -1837,7 +1837,6 @@ void TDBJSON::CloseDB(PGLOBAL g)
|
|||||||
// Save the modified document
|
// Save the modified document
|
||||||
char filename[_MAX_PATH];
|
char filename[_MAX_PATH];
|
||||||
PSZ msg;
|
PSZ msg;
|
||||||
FILE *fop;
|
|
||||||
|
|
||||||
Doc->InitArray(g);
|
Doc->InitArray(g);
|
||||||
|
|
||||||
@@ -1845,11 +1844,7 @@ void TDBJSON::CloseDB(PGLOBAL g)
|
|||||||
PlugSetPath(filename, ((PJDEF)To_Def)->Fn, GetPath());
|
PlugSetPath(filename, ((PJDEF)To_Def)->Fn, GetPath());
|
||||||
|
|
||||||
// Serialize the modified table
|
// Serialize the modified table
|
||||||
if (!(fop = fopen(filename, "wb"))) {
|
if ((msg = Serialize(g, Top, filename, Pretty)))
|
||||||
sprintf(g->Message, MSG(OPEN_MODE_ERROR),
|
|
||||||
"w", (int)errno, filename);
|
|
||||||
strcat(strcat(g->Message, ": "), strerror(errno));
|
|
||||||
} else if ((msg = Serialize(g, Top, fop, Pretty)))
|
|
||||||
puts(msg);
|
puts(msg);
|
||||||
|
|
||||||
} // end of CloseDB
|
} // end of CloseDB
|
||||||
|
@@ -1054,32 +1054,14 @@ int TDBMYSQL::SendCommand(PGLOBAL g)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Data Base indexed read routine for MYSQL access method. */
|
/* Data Base indexed read routine for MYSQL access method. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
bool TDBMYSQL::ReadKey(PGLOBAL g, OPVAL op, const void *key, int len)
|
bool TDBMYSQL::ReadKey(PGLOBAL g, OPVAL op, const key_range *kr)
|
||||||
{
|
{
|
||||||
bool oom;
|
|
||||||
int oldlen = Query->GetLength();
|
int oldlen = Query->GetLength();
|
||||||
PHC hc = To_Def->GetHandler();
|
PHC hc = To_Def->GetHandler();
|
||||||
|
|
||||||
if (op == OP_FIRST && hc->end_range) {
|
if (!(kr || hc->end_range) || op == OP_NEXT ||
|
||||||
#ifdef _DEBUG
|
Mode == MODE_UPDATE || Mode == MODE_DELETE) {
|
||||||
assert(!key);
|
if (!kr && Mode == MODE_READX) {
|
||||||
#endif
|
|
||||||
key_range *end_key = &hc->save_end_range;
|
|
||||||
|
|
||||||
key = end_key->key;
|
|
||||||
len = end_key->length;
|
|
||||||
|
|
||||||
switch (end_key->flag) {
|
|
||||||
case HA_READ_BEFORE_KEY: op = OP_LT; break;
|
|
||||||
case HA_READ_AFTER_KEY: op = OP_LE; break;
|
|
||||||
default: key = NULL;
|
|
||||||
} // endswitch flag
|
|
||||||
|
|
||||||
} // endif OP_FIRST
|
|
||||||
|
|
||||||
if (!key || op == OP_NEXT ||
|
|
||||||
Mode == MODE_UPDATE || Mode == MODE_DELETE) {
|
|
||||||
if (!key && Mode == MODE_READX) {
|
|
||||||
// This is a false indexed read
|
// This is a false indexed read
|
||||||
m_Rc = Myc.ExecSQL(g, Query->GetStr());
|
m_Rc = Myc.ExecSQL(g, Query->GetStr());
|
||||||
Mode = MODE_READ;
|
Mode = MODE_READ;
|
||||||
@@ -1091,23 +1073,35 @@ bool TDBMYSQL::ReadKey(PGLOBAL g, OPVAL op, const void *key, int len)
|
|||||||
if (Myc.m_Res)
|
if (Myc.m_Res)
|
||||||
Myc.FreeResult();
|
Myc.FreeResult();
|
||||||
|
|
||||||
if (hc->MakeKeyWhere(g, Query, op, '`', key, len))
|
if (hc->MakeKeyWhere(g, Query, op, '`', kr))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
if (To_CondFil) {
|
if (To_CondFil) {
|
||||||
oom = Query->Append(" AND (");
|
if (To_CondFil->Idx != hc->active_index) {
|
||||||
oom |= Query->Append(To_CondFil->Body);
|
To_CondFil->Idx = hc->active_index;
|
||||||
|
To_CondFil->Body= (char*)PlugSubAlloc(g, NULL, 0);
|
||||||
|
*To_CondFil->Body= 0;
|
||||||
|
|
||||||
if ((oom |= Query->Append(')'))) {
|
if ((To_CondFil = hc->CheckCond(g, To_CondFil, To_CondFil->Cond)))
|
||||||
strcpy(g->Message, "Readkey: Out of memory");
|
PlugSubAlloc(g, NULL, strlen(To_CondFil->Body) + 1);
|
||||||
return true;
|
|
||||||
} // endif oom
|
|
||||||
|
|
||||||
} // endif To_Condfil
|
} // endif active_index
|
||||||
|
|
||||||
} // endif's op
|
if (To_CondFil)
|
||||||
|
if (Query->Append(" AND ") || Query->Append(To_CondFil->Body)) {
|
||||||
|
strcpy(g->Message, "Readkey: Out of memory");
|
||||||
|
return true;
|
||||||
|
} // endif Append
|
||||||
|
|
||||||
m_Rc = Myc.ExecSQL(g, Query->GetStr());
|
} // endif To_Condfil
|
||||||
|
|
||||||
|
Mode = MODE_READ;
|
||||||
|
} // endif's op
|
||||||
|
|
||||||
|
if (trace)
|
||||||
|
htrc("MYSQL ReadKey: Query=%s\n", Query->GetStr());
|
||||||
|
|
||||||
|
m_Rc = Myc.ExecSQL(g, Query->GetStr());
|
||||||
Query->Truncate(oldlen);
|
Query->Truncate(oldlen);
|
||||||
return (m_Rc == RC_FX) ? true : false;
|
return (m_Rc == RC_FX) ? true : false;
|
||||||
} // end of ReadKey
|
} // end of ReadKey
|
||||||
|
@@ -99,7 +99,7 @@ class TDBMYSQL : public TDBASE {
|
|||||||
virtual int WriteDB(PGLOBAL g);
|
virtual int WriteDB(PGLOBAL g);
|
||||||
virtual int DeleteDB(PGLOBAL g, int irc);
|
virtual int DeleteDB(PGLOBAL g, int irc);
|
||||||
virtual void CloseDB(PGLOBAL g);
|
virtual void CloseDB(PGLOBAL g);
|
||||||
virtual bool ReadKey(PGLOBAL g, OPVAL op, const void *key, int len);
|
virtual bool ReadKey(PGLOBAL g, OPVAL op, const key_range *kr);
|
||||||
|
|
||||||
// Specific routines
|
// Specific routines
|
||||||
bool SetColumnRanks(PGLOBAL g);
|
bool SetColumnRanks(PGLOBAL g);
|
||||||
|
@@ -1,7 +1,7 @@
|
|||||||
/************* Tabodbc C++ Program Source Code File (.CPP) *************/
|
/************* Tabodbc C++ Program Source Code File (.CPP) *************/
|
||||||
/* PROGRAM NAME: TABODBC */
|
/* PROGRAM NAME: TABODBC */
|
||||||
/* ------------- */
|
/* ------------- */
|
||||||
/* Version 2.9 */
|
/* Version 3.0 */
|
||||||
/* */
|
/* */
|
||||||
/* COPYRIGHT: */
|
/* COPYRIGHT: */
|
||||||
/* ---------- */
|
/* ---------- */
|
||||||
@@ -35,6 +35,7 @@
|
|||||||
/* Include relevant MariaDB header file. */
|
/* Include relevant MariaDB header file. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
#include "my_global.h"
|
#include "my_global.h"
|
||||||
|
#include "sql_class.h"
|
||||||
#if defined(__WIN__)
|
#if defined(__WIN__)
|
||||||
#include <io.h>
|
#include <io.h>
|
||||||
#include <fcntl.h>
|
#include <fcntl.h>
|
||||||
@@ -72,6 +73,7 @@
|
|||||||
#include "reldef.h"
|
#include "reldef.h"
|
||||||
#include "tabcol.h"
|
#include "tabcol.h"
|
||||||
#include "valblk.h"
|
#include "valblk.h"
|
||||||
|
#include "ha_connect.h"
|
||||||
|
|
||||||
#include "sql_string.h"
|
#include "sql_string.h"
|
||||||
|
|
||||||
@@ -322,7 +324,7 @@ PSZ TDBODBC::GetFile(PGLOBAL g)
|
|||||||
if (Connect) {
|
if (Connect) {
|
||||||
char *p1, *p2;
|
char *p1, *p2;
|
||||||
int i;
|
int i;
|
||||||
size_t n;
|
size_t n;
|
||||||
|
|
||||||
if (!(p1 = strstr(Connect, "DBQ="))) {
|
if (!(p1 = strstr(Connect, "DBQ="))) {
|
||||||
char *p, *lc = strlwr(PlugDup(g, Connect));
|
char *p, *lc = strlwr(PlugDup(g, Connect));
|
||||||
@@ -334,8 +336,8 @@ PSZ TDBODBC::GetFile(PGLOBAL g)
|
|||||||
} else
|
} else
|
||||||
i = 4;
|
i = 4;
|
||||||
|
|
||||||
if (p1) {
|
if (p1) {
|
||||||
p1 += i; // Beginning of file name
|
p1 += i; // Beginning of file name
|
||||||
p2 = strchr(p1, ';'); // End of file path/name
|
p2 = strchr(p1, ';'); // End of file path/name
|
||||||
|
|
||||||
// Make the File path/name from the connect string
|
// Make the File path/name from the connect string
|
||||||
@@ -397,176 +399,209 @@ int TDBODBC::Decode(char *txt, char *buf, size_t n)
|
|||||||
/* Note: when implementing EOM filtering, column only used in local */
|
/* Note: when implementing EOM filtering, column only used in local */
|
||||||
/* filter should be removed from column list. */
|
/* filter should be removed from column list. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
char *TDBODBC::MakeSQL(PGLOBAL g, bool cnt)
|
bool TDBODBC::MakeSQL(PGLOBAL g, bool cnt)
|
||||||
{
|
{
|
||||||
char *colist, *tabname, *sql, buf[NAM_LEN * 3];
|
char *schmp = NULL, *catp = NULL, buf[NAM_LEN * 3];
|
||||||
LPCSTR schmp = NULL, catp = NULL;
|
int len;
|
||||||
int len, ncol = 0;
|
bool oom = false, first = true;
|
||||||
bool first = true;
|
PTABLE tablep = To_Table;
|
||||||
PTABLE tablep = To_Table;
|
PCOL colp;
|
||||||
PCOL colp;
|
|
||||||
|
|
||||||
if (Srcdef)
|
if (Srcdef) {
|
||||||
return Srcdef;
|
Query = new(g)STRING(g, 0, Srcdef);
|
||||||
|
return false;
|
||||||
|
} // endif Srcdef
|
||||||
|
|
||||||
if (!cnt) {
|
// Allocate the string used to contain the Query
|
||||||
// Normal SQL statement to retrieve results
|
Query = new(g)STRING(g, 1023, "SELECT ");
|
||||||
for (colp = Columns; colp; colp = colp->GetNext())
|
|
||||||
if (!colp->IsSpecial())
|
|
||||||
ncol++;
|
|
||||||
|
|
||||||
if (ncol) {
|
if (!cnt) {
|
||||||
colist = (char*)PlugSubAlloc(g, NULL, (NAM_LEN + 4) * ncol);
|
if (Columns) {
|
||||||
|
// Normal SQL statement to retrieve results
|
||||||
|
for (colp = Columns; colp; colp = colp->GetNext())
|
||||||
|
if (!colp->IsSpecial()) {
|
||||||
|
if (!first)
|
||||||
|
oom |= Query->Append(", ");
|
||||||
|
else
|
||||||
|
first = false;
|
||||||
|
|
||||||
for (colp = Columns; colp; colp = colp->GetNext())
|
// Column name can be encoded in UTF-8
|
||||||
if (!colp->IsSpecial()) {
|
Decode(colp->GetName(), buf, sizeof(buf));
|
||||||
// Column name can be in UTF-8 encoding
|
|
||||||
/*rc=*/ Decode(colp->GetName(), buf, sizeof(buf));
|
|
||||||
|
|
||||||
if (Quote) {
|
if (Quote) {
|
||||||
if (first) {
|
// Put column name between identifier quotes in case in contains blanks
|
||||||
strcat(strcat(strcpy(colist, Quote), buf), Quote);
|
oom |= Query->Append(Quote);
|
||||||
first = false;
|
oom |= Query->Append(buf);
|
||||||
} else
|
oom |= Query->Append(Quote);
|
||||||
strcat(strcat(strcat(strcat(colist, ", "),
|
} else
|
||||||
Quote), buf), Quote);
|
oom |= Query->Append(buf);
|
||||||
|
|
||||||
} else {
|
} // endif colp
|
||||||
if (first) {
|
|
||||||
strcpy(colist, buf);
|
|
||||||
first = false;
|
|
||||||
} else
|
|
||||||
strcat(strcat(colist, ", "), buf);
|
|
||||||
|
|
||||||
} // endif Quote
|
} else
|
||||||
|
// !Columns can occur for queries such that sql count(*) from...
|
||||||
} // endif !Special
|
|
||||||
|
|
||||||
} else {
|
|
||||||
// ncol == 0 can occur for queries such that sql count(*) from...
|
|
||||||
// for which we will count the rows from sql * from...
|
// for which we will count the rows from sql * from...
|
||||||
colist = (char*)PlugSubAlloc(g, NULL, 2);
|
oom |= Query->Append('*');
|
||||||
strcpy(colist, "*");
|
|
||||||
} // endif ncol
|
|
||||||
|
|
||||||
} else {
|
} else
|
||||||
// SQL statement used to retrieve the size of the result
|
// SQL statement used to retrieve the size of the result
|
||||||
colist = (char*)PlugSubAlloc(g, NULL, 9);
|
oom |= Query->Append("count(*)");
|
||||||
strcpy(colist, "count(*)");
|
|
||||||
} // endif cnt
|
|
||||||
|
|
||||||
// Table name can be encoded in UTF-8
|
oom |= Query->Append(" FROM ");
|
||||||
/*rc = */Decode(TableName, buf, sizeof(buf));
|
|
||||||
|
|
||||||
// Put table name between identifier quotes in case in contains blanks
|
|
||||||
tabname = (char*)PlugSubAlloc(g, NULL, strlen(buf) + 3);
|
|
||||||
|
|
||||||
if (Quote)
|
|
||||||
strcat(strcat(strcpy(tabname, Quote), buf), Quote);
|
|
||||||
else
|
|
||||||
strcpy(tabname, buf);
|
|
||||||
|
|
||||||
// Below 14 is length of 'select ' + length of ' from ' + 1
|
|
||||||
len = (strlen(colist) + strlen(buf) + 14);
|
|
||||||
len += (To_CondFil ? strlen(To_CondFil->Body) + 7 : 0);
|
|
||||||
|
|
||||||
if (Catalog && *Catalog)
|
if (Catalog && *Catalog)
|
||||||
catp = Catalog;
|
catp = Catalog;
|
||||||
|
|
||||||
if (catp)
|
|
||||||
len += (strlen(catp) + 2);
|
|
||||||
|
|
||||||
if (tablep->GetSchema())
|
if (tablep->GetSchema())
|
||||||
schmp = tablep->GetSchema();
|
schmp = (char*)tablep->GetSchema();
|
||||||
else if (Schema && *Schema)
|
else if (Schema && *Schema)
|
||||||
schmp = Schema;
|
schmp = Schema;
|
||||||
|
|
||||||
if (schmp)
|
|
||||||
len += (strlen(schmp) + 1);
|
|
||||||
|
|
||||||
sql = (char*)PlugSubAlloc(g, NULL, len);
|
|
||||||
strcat(strcat(strcpy(sql, "SELECT "), colist), " FROM ");
|
|
||||||
|
|
||||||
if (catp) {
|
if (catp) {
|
||||||
strcat(sql, catp);
|
oom |= Query->Append(catp);
|
||||||
|
|
||||||
if (schmp)
|
if (schmp) {
|
||||||
strcat(strcat(sql, "."), schmp);
|
oom |= Query->Append('.');
|
||||||
else
|
oom |= Query->Append(schmp);
|
||||||
strcat(sql, ".");
|
} // endif schmp
|
||||||
|
|
||||||
strcat(sql, ".");
|
oom |= Query->Append('.');
|
||||||
} else if (schmp)
|
} else if (schmp) {
|
||||||
strcat(strcat(sql, schmp), ".");
|
oom |= Query->Append(schmp);
|
||||||
|
oom |= Query->Append('.');
|
||||||
|
} // endif schmp
|
||||||
|
|
||||||
strcat(sql, tabname);
|
// Table name can be encoded in UTF-8
|
||||||
|
Decode(TableName, buf, sizeof(buf));
|
||||||
|
|
||||||
if (To_CondFil)
|
if (Quote) {
|
||||||
strcat(strcat(sql, " WHERE "), To_CondFil->Body);
|
// Put table name between identifier quotes in case in contains blanks
|
||||||
|
oom |= Query->Append(Quote);
|
||||||
|
oom |= Query->Append(buf);
|
||||||
|
oom |= Query->Append(Quote);
|
||||||
|
} else
|
||||||
|
oom |= Query->Append(buf);
|
||||||
|
|
||||||
if (trace)
|
len = Query->GetLength();
|
||||||
htrc("sql: '%s'\n", sql);
|
|
||||||
|
|
||||||
return sql;
|
if (To_CondFil) {
|
||||||
|
if (Mode == MODE_READ) {
|
||||||
|
oom |= Query->Append(" WHERE ");
|
||||||
|
oom |= Query->Append(To_CondFil->Body);
|
||||||
|
len = Query->GetLength() + 1;
|
||||||
|
} else
|
||||||
|
len += (strlen(To_CondFil->Body) + 256);
|
||||||
|
|
||||||
|
} else
|
||||||
|
len += ((Mode == MODE_READX) ? 256 : 1);
|
||||||
|
|
||||||
|
if (oom || Query->Resize(len)) {
|
||||||
|
strcpy(g->Message, "MakeSQL: Out of memory");
|
||||||
|
return true;
|
||||||
|
} // endif oom
|
||||||
|
|
||||||
|
if (trace)
|
||||||
|
htrc("Query=%s\n", Query->GetStr());
|
||||||
|
|
||||||
|
return false;
|
||||||
} // end of MakeSQL
|
} // end of MakeSQL
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* MakeInsert: make the Insert statement used with ODBC connection. */
|
/* MakeInsert: make the Insert statement used with ODBC connection. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
char *TDBODBC::MakeInsert(PGLOBAL g)
|
bool TDBODBC::MakeInsert(PGLOBAL g)
|
||||||
{
|
{
|
||||||
char *stmt, *colist, *valist, buf[NAM_LEN * 3];
|
char *schmp = NULL, *catp = NULL, buf[NAM_LEN * 3];
|
||||||
// char *tk = "`";
|
int len = 0;
|
||||||
int len = 0;
|
bool b = false, oom = false;
|
||||||
bool b = FALSE;
|
PTABLE tablep = To_Table;
|
||||||
PCOL colp;
|
PCOL colp;
|
||||||
|
|
||||||
for (colp = Columns; colp; colp = colp->GetNext())
|
for (colp = Columns; colp; colp = colp->GetNext())
|
||||||
if (colp->IsSpecial()) {
|
if (colp->IsSpecial()) {
|
||||||
strcpy(g->Message, MSG(NO_ODBC_SPECOL));
|
strcpy(g->Message, MSG(NO_ODBC_SPECOL));
|
||||||
return NULL;
|
return true;
|
||||||
} else {
|
} else {
|
||||||
len += (strlen(colp->GetName()) + 4);
|
// Column name can be encoded in UTF-8
|
||||||
|
Decode(colp->GetName(), buf, sizeof(buf));
|
||||||
|
len += (strlen(buf) + 6); // comma + quotes + valist
|
||||||
((PODBCCOL)colp)->Rank = ++Nparm;
|
((PODBCCOL)colp)->Rank = ++Nparm;
|
||||||
} // endif colp
|
} // endif colp
|
||||||
|
|
||||||
colist = (char*)PlugSubAlloc(g, NULL, len);
|
// Below 32 is enough to contain the fixed part of the query
|
||||||
*colist = '\0';
|
if (Catalog && *Catalog)
|
||||||
valist = (char*)PlugSubAlloc(g, NULL, 2 * Nparm);
|
catp = Catalog;
|
||||||
*valist = '\0';
|
|
||||||
|
|
||||||
for (colp = Columns; colp; colp = colp->GetNext()) {
|
if (catp)
|
||||||
if (b) {
|
len += strlen(catp) + 1;
|
||||||
strcat(colist, ", ");
|
|
||||||
strcat(valist, ",");
|
|
||||||
} else
|
|
||||||
b = true;
|
|
||||||
|
|
||||||
// Column name can be in UTF-8 encoding
|
if (tablep->GetSchema())
|
||||||
Decode(colp->GetName(), buf, sizeof(buf));
|
schmp = (char*)tablep->GetSchema();
|
||||||
|
else if (Schema && *Schema)
|
||||||
|
schmp = Schema;
|
||||||
|
|
||||||
if (Quote)
|
if (schmp)
|
||||||
strcat(strcat(strcat(colist, Quote), buf), Quote);
|
len += strlen(schmp) + 1;
|
||||||
else
|
|
||||||
strcat(colist, buf);
|
|
||||||
|
|
||||||
strcat(valist, "?"); // Parameter marker
|
// Column name can be encoded in UTF-8
|
||||||
} // endfor colp
|
Decode(TableName, buf, sizeof(buf));
|
||||||
|
len += (strlen(buf) + 32);
|
||||||
|
Query = new(g) STRING(g, len, "INSERT INTO ");
|
||||||
|
|
||||||
// Below 32 is enough to contain the fixed part of the query
|
if (catp) {
|
||||||
len = (strlen(TableName) + strlen(colist) + strlen(valist) + 32);
|
oom |= Query->Append(catp);
|
||||||
stmt = (char*)PlugSubAlloc(g, NULL, len);
|
|
||||||
strcpy(stmt, "INSERT INTO ");
|
|
||||||
|
|
||||||
if (Quote)
|
if (schmp) {
|
||||||
strcat(strcat(strcat(stmt, Quote), TableName), Quote);
|
oom |= Query->Append('.');
|
||||||
else
|
oom |= Query->Append(schmp);
|
||||||
strcat(stmt, TableName);
|
} // endif schmp
|
||||||
|
|
||||||
strcat(strcat(strcat(stmt, " ("), colist), ") VALUES (");
|
oom |= Query->Append('.');
|
||||||
strcat(strcat(stmt, valist), ")");
|
} else if (schmp) {
|
||||||
|
oom |= Query->Append(schmp);
|
||||||
|
oom |= Query->Append('.');
|
||||||
|
} // endif schmp
|
||||||
|
|
||||||
return stmt;
|
if (Quote) {
|
||||||
|
// Put table name between identifier quotes in case in contains blanks
|
||||||
|
oom |= Query->Append(Quote);
|
||||||
|
oom |= Query->Append(buf);
|
||||||
|
oom |= Query->Append(Quote);
|
||||||
|
} else
|
||||||
|
oom |= Query->Append(buf);
|
||||||
|
|
||||||
|
oom |= Query->Append('(');
|
||||||
|
|
||||||
|
for (colp = Columns; colp; colp = colp->GetNext()) {
|
||||||
|
if (b)
|
||||||
|
oom |= Query->Append(", ");
|
||||||
|
else
|
||||||
|
b = true;
|
||||||
|
|
||||||
|
// Column name can be in UTF-8 encoding
|
||||||
|
Decode(colp->GetName(), buf, sizeof(buf));
|
||||||
|
|
||||||
|
if (Quote) {
|
||||||
|
// Put column name between identifier quotes in case in contains blanks
|
||||||
|
oom |= Query->Append(Quote);
|
||||||
|
oom |= Query->Append(buf);
|
||||||
|
oom |= Query->Append(Quote);
|
||||||
|
} else
|
||||||
|
oom |= Query->Append(buf);
|
||||||
|
|
||||||
|
} // endfor colp
|
||||||
|
|
||||||
|
oom |= Query->Append(") VALUES (");
|
||||||
|
|
||||||
|
for (int i = 0; i < Nparm; i++)
|
||||||
|
oom |= Query->Append("?,");
|
||||||
|
|
||||||
|
if (oom)
|
||||||
|
strcpy(g->Message, "MakeInsert: Out of memory");
|
||||||
|
else
|
||||||
|
Query->RepLast(')');
|
||||||
|
|
||||||
|
return oom;
|
||||||
} // end of MakeInsert
|
} // end of MakeInsert
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -591,7 +626,7 @@ bool TDBODBC::BindParameters(PGLOBAL g)
|
|||||||
/* MakeCommand: make the Update or Delete statement to send to the */
|
/* MakeCommand: make the Update or Delete statement to send to the */
|
||||||
/* MySQL server. Limited to remote values and filtering. */
|
/* MySQL server. Limited to remote values and filtering. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
char *TDBODBC::MakeCommand(PGLOBAL g)
|
bool TDBODBC::MakeCommand(PGLOBAL g)
|
||||||
{
|
{
|
||||||
char *p, *stmt, name[68], *body = NULL, *qc = Ocp->GetQuoteChar();
|
char *p, *stmt, name[68], *body = NULL, *qc = Ocp->GetQuoteChar();
|
||||||
char *qrystr = (char*)PlugSubAlloc(g, NULL, strlen(Qrystr) + 1);
|
char *qrystr = (char*)PlugSubAlloc(g, NULL, strlen(Qrystr) + 1);
|
||||||
@@ -649,7 +684,8 @@ char *TDBODBC::MakeCommand(PGLOBAL g)
|
|||||||
return NULL;
|
return NULL;
|
||||||
} // endif p
|
} // endif p
|
||||||
|
|
||||||
return stmt;
|
Query = new(g) STRING(g, 0, stmt);
|
||||||
|
return (!Query->GetSize());
|
||||||
} // end of MakeCommand
|
} // end of MakeCommand
|
||||||
|
|
||||||
#if 0
|
#if 0
|
||||||
@@ -826,10 +862,12 @@ bool TDBODBC::OpenDB(PGLOBAL g)
|
|||||||
|
|
||||||
if (Memory < 3) {
|
if (Memory < 3) {
|
||||||
// Method will depend on cursor type
|
// Method will depend on cursor type
|
||||||
if ((Rbuf = Ocp->Rewind(Query, (PODBCCOL)Columns)) < 0) {
|
if ((Rbuf = Ocp->Rewind(Query->GetStr(), (PODBCCOL)Columns)) < 0)
|
||||||
Ocp->Close();
|
if (Mode != MODE_READX) {
|
||||||
return true;
|
Ocp->Close();
|
||||||
} // endif Rewind
|
return true;
|
||||||
|
} else
|
||||||
|
Rbuf = 0;
|
||||||
|
|
||||||
} else
|
} else
|
||||||
Rbuf = Qrp->Nblin;
|
Rbuf = Qrp->Nblin;
|
||||||
@@ -864,15 +902,14 @@ bool TDBODBC::OpenDB(PGLOBAL g)
|
|||||||
/*********************************************************************/
|
/*********************************************************************/
|
||||||
if (Mode == MODE_READ || Mode == MODE_READX) {
|
if (Mode == MODE_READ || Mode == MODE_READX) {
|
||||||
if (Memory > 1 && !Srcdef) {
|
if (Memory > 1 && !Srcdef) {
|
||||||
char *Sql;
|
int n;
|
||||||
int n;
|
|
||||||
|
|
||||||
if ((Sql = MakeSQL(g, true))) {
|
if (!MakeSQL(g, true)) {
|
||||||
// Allocate a Count(*) column
|
// Allocate a Count(*) column
|
||||||
Cnp = new(g) ODBCCOL;
|
Cnp = new(g) ODBCCOL;
|
||||||
Cnp->InitValue(g);
|
Cnp->InitValue(g);
|
||||||
|
|
||||||
if ((n = Ocp->GetResultSize(Sql, Cnp)) < 0) {
|
if ((n = Ocp->GetResultSize(Query->GetStr(), Cnp)) < 0) {
|
||||||
strcpy(g->Message, "Cannot get result size");
|
strcpy(g->Message, "Cannot get result size");
|
||||||
return true;
|
return true;
|
||||||
} // endif n
|
} // endif n
|
||||||
@@ -882,36 +919,36 @@ bool TDBODBC::OpenDB(PGLOBAL g)
|
|||||||
if ((Qrp = Ocp->AllocateResult(g)))
|
if ((Qrp = Ocp->AllocateResult(g)))
|
||||||
Memory = 2; // Must be filled
|
Memory = 2; // Must be filled
|
||||||
else {
|
else {
|
||||||
strcpy(g->Message, "Memory allocation failed");
|
strcpy(g->Message, "Result set memory allocation failed");
|
||||||
return true;
|
return true;
|
||||||
} // endif n
|
} // endif n
|
||||||
|
|
||||||
Ocp->m_Rows = 0;
|
Ocp->m_Rows = 0;
|
||||||
} else {
|
} else
|
||||||
strcpy(g->Message, "MakeSQL failed");
|
|
||||||
return true;
|
return true;
|
||||||
} // endif Sql
|
|
||||||
|
|
||||||
} // endif Memory
|
} // endif Memory
|
||||||
|
|
||||||
if ((Query = MakeSQL(g, false))) {
|
if (!(rc = MakeSQL(g, false))) {
|
||||||
for (PODBCCOL colp = (PODBCCOL)Columns; colp;
|
for (PODBCCOL colp = (PODBCCOL)Columns; colp;
|
||||||
colp = (PODBCCOL)colp->GetNext())
|
colp = (PODBCCOL)colp->GetNext())
|
||||||
if (!colp->IsSpecial())
|
if (!colp->IsSpecial())
|
||||||
colp->AllocateBuffers(g, Rows);
|
colp->AllocateBuffers(g, Rows);
|
||||||
|
|
||||||
rc = ((Rows = Ocp->ExecDirectSQL(Query, (PODBCCOL)Columns)) < 0);
|
rc = (Mode == MODE_READ)
|
||||||
} // endif Query
|
? ((Rows = Ocp->ExecDirectSQL(Query->GetStr(), (PODBCCOL)Columns)) < 0)
|
||||||
|
: false;
|
||||||
|
} // endif rc
|
||||||
|
|
||||||
} else if (Mode == MODE_INSERT) {
|
} else if (Mode == MODE_INSERT) {
|
||||||
if ((Query = MakeInsert(g))) {
|
if (!(rc = MakeInsert(g))) {
|
||||||
if (Nparm != Ocp->PrepareSQL(Query)) {
|
if (Nparm != Ocp->PrepareSQL(Query->GetStr())) {
|
||||||
strcpy(g->Message, MSG(PARM_CNT_MISS));
|
strcpy(g->Message, MSG(PARM_CNT_MISS));
|
||||||
rc = true;
|
rc = true;
|
||||||
} else
|
} else
|
||||||
rc = BindParameters(g);
|
rc = BindParameters(g);
|
||||||
|
|
||||||
} // endif Query
|
} // endif rc
|
||||||
|
|
||||||
} else if (Mode == MODE_UPDATE || Mode == MODE_DELETE) {
|
} else if (Mode == MODE_UPDATE || Mode == MODE_DELETE) {
|
||||||
rc = false; // wait for CheckCond before calling MakeCommand(g);
|
rc = false; // wait for CheckCond before calling MakeCommand(g);
|
||||||
@@ -969,6 +1006,59 @@ bool TDBODBC::SetRecpos(PGLOBAL g, int recpos)
|
|||||||
return false;
|
return false;
|
||||||
} // end of SetRecpos
|
} // end of SetRecpos
|
||||||
|
|
||||||
|
/***********************************************************************/
|
||||||
|
/* Data Base indexed read routine for MYSQL access method. */
|
||||||
|
/***********************************************************************/
|
||||||
|
bool TDBODBC::ReadKey(PGLOBAL g, OPVAL op, const key_range *kr)
|
||||||
|
{
|
||||||
|
char c = Quote ? *Quote : 0;
|
||||||
|
int oldlen = Query->GetLength();
|
||||||
|
PHC hc = To_Def->GetHandler();
|
||||||
|
|
||||||
|
if (!(kr || hc->end_range) || op == OP_NEXT ||
|
||||||
|
Mode == MODE_UPDATE || Mode == MODE_DELETE) {
|
||||||
|
if (!kr && Mode == MODE_READX) {
|
||||||
|
// This is a false indexed read
|
||||||
|
Rows = Ocp->ExecDirectSQL((char*)Query->GetStr(), (PODBCCOL)Columns);
|
||||||
|
Mode = MODE_READ;
|
||||||
|
return (Rows < 0);
|
||||||
|
} // endif key
|
||||||
|
|
||||||
|
return false;
|
||||||
|
} else {
|
||||||
|
if (To_Def->GetHandler()->MakeKeyWhere(g, Query, op, c, kr))
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (To_CondFil) {
|
||||||
|
if (To_CondFil->Idx != hc->active_index) {
|
||||||
|
To_CondFil->Idx = hc->active_index;
|
||||||
|
To_CondFil->Body= (char*)PlugSubAlloc(g, NULL, 0);
|
||||||
|
*To_CondFil->Body= 0;
|
||||||
|
|
||||||
|
if ((To_CondFil = hc->CheckCond(g, To_CondFil, To_CondFil->Cond)))
|
||||||
|
PlugSubAlloc(g, NULL, strlen(To_CondFil->Body) + 1);
|
||||||
|
|
||||||
|
} // endif active_index
|
||||||
|
|
||||||
|
if (To_CondFil)
|
||||||
|
if (Query->Append(" AND ") || Query->Append(To_CondFil->Body)) {
|
||||||
|
strcpy(g->Message, "Readkey: Out of memory");
|
||||||
|
return true;
|
||||||
|
} // endif Append
|
||||||
|
|
||||||
|
} // endif To_Condfil
|
||||||
|
|
||||||
|
Mode = MODE_READ;
|
||||||
|
} // endif's op
|
||||||
|
|
||||||
|
if (trace)
|
||||||
|
htrc("ODBC ReadKey: Query=%s\n", Query->GetStr());
|
||||||
|
|
||||||
|
Rows = Ocp->ExecDirectSQL((char*)Query->GetStr(), (PODBCCOL)Columns);
|
||||||
|
Query->Truncate(oldlen);
|
||||||
|
return (Rows < 0);
|
||||||
|
} // end of ReadKey
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* VRDNDOS: Data Base read routine for odbc access method. */
|
/* VRDNDOS: Data Base read routine for odbc access method. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
@@ -981,11 +1071,11 @@ int TDBODBC::ReadDB(PGLOBAL g)
|
|||||||
GetTdb_No(), Mode, To_Key_Col, To_Link, To_Kindex);
|
GetTdb_No(), Mode, To_Key_Col, To_Link, To_Kindex);
|
||||||
|
|
||||||
if (Mode == MODE_UPDATE || Mode == MODE_DELETE) {
|
if (Mode == MODE_UPDATE || Mode == MODE_DELETE) {
|
||||||
if (!Query && !(Query = MakeCommand(g)))
|
if (!Query && MakeCommand(g))
|
||||||
return RC_FX;
|
return RC_FX;
|
||||||
|
|
||||||
// Send the UPDATE/DELETE command to the remote table
|
// Send the UPDATE/DELETE command to the remote table
|
||||||
if (!Ocp->ExecSQLcommand(Query)) {
|
if (!Ocp->ExecSQLcommand(Query->GetStr())) {
|
||||||
sprintf(g->Message, "%s: %d affected rows", TableName, AftRows);
|
sprintf(g->Message, "%s: %d affected rows", TableName, AftRows);
|
||||||
|
|
||||||
if (trace)
|
if (trace)
|
||||||
@@ -1063,11 +1153,11 @@ int TDBODBC::WriteDB(PGLOBAL g)
|
|||||||
int TDBODBC::DeleteDB(PGLOBAL g, int irc)
|
int TDBODBC::DeleteDB(PGLOBAL g, int irc)
|
||||||
{
|
{
|
||||||
if (irc == RC_FX) {
|
if (irc == RC_FX) {
|
||||||
if (!Query && !(Query = MakeCommand(g)))
|
if (!Query && MakeCommand(g))
|
||||||
return RC_FX;
|
return RC_FX;
|
||||||
|
|
||||||
// Send the DELETE (all) command to the remote table
|
// Send the DELETE (all) command to the remote table
|
||||||
if (!Ocp->ExecSQLcommand(Query)) {
|
if (!Ocp->ExecSQLcommand(Query->GetStr())) {
|
||||||
sprintf(g->Message, "%s: %d affected rows", TableName, AftRows);
|
sprintf(g->Message, "%s: %d affected rows", TableName, AftRows);
|
||||||
|
|
||||||
if (trace)
|
if (trace)
|
||||||
@@ -1279,12 +1369,7 @@ void ODBCCOL::ReadColumn(PGLOBAL g)
|
|||||||
|
|
||||||
} // endif Buf_Type
|
} // endif Buf_Type
|
||||||
|
|
||||||
// Nulls are handled by StrLen[n] == SQL_NULL_DATA
|
if (trace > 1) {
|
||||||
// MDEV-8561
|
|
||||||
//if (Value->IsZero())
|
|
||||||
// Value->SetNull(Nullable);
|
|
||||||
|
|
||||||
if (trace) {
|
|
||||||
char buf[64];
|
char buf[64];
|
||||||
|
|
||||||
htrc("ODBC Column %s: rows=%d buf=%p type=%d value=%s\n",
|
htrc("ODBC Column %s: rows=%d buf=%p type=%d value=%s\n",
|
||||||
@@ -1572,9 +1657,12 @@ bool TDBXDBC::OpenDB(PGLOBAL g)
|
|||||||
int TDBXDBC::ReadDB(PGLOBAL g)
|
int TDBXDBC::ReadDB(PGLOBAL g)
|
||||||
{
|
{
|
||||||
if (Cmdlist) {
|
if (Cmdlist) {
|
||||||
Query = Cmdlist->Cmd;
|
if (!Query)
|
||||||
|
Query = new(g)STRING(g, 0, Cmdlist->Cmd);
|
||||||
|
else
|
||||||
|
Query->Set(Cmdlist->Cmd);
|
||||||
|
|
||||||
if (Ocp->ExecSQLcommand(Query))
|
if (Ocp->ExecSQLcommand(Query->GetStr()))
|
||||||
Nerr++;
|
Nerr++;
|
||||||
|
|
||||||
Fpos++; // Used for progress info
|
Fpos++; // Used for progress info
|
||||||
@@ -1632,10 +1720,10 @@ void XSRCCOL::ReadColumn(PGLOBAL g)
|
|||||||
PTDBXDBC tdbp = (PTDBXDBC)To_Tdb;
|
PTDBXDBC tdbp = (PTDBXDBC)To_Tdb;
|
||||||
|
|
||||||
switch (Flag) {
|
switch (Flag) {
|
||||||
case 0: Value->SetValue_psz(tdbp->Query); break;
|
case 0: Value->SetValue_psz(tdbp->Query->GetStr()); break;
|
||||||
case 1: Value->SetValue(tdbp->AftRows); break;
|
case 1: Value->SetValue(tdbp->AftRows); break;
|
||||||
case 2: Value->SetValue_psz(g->Message); break;
|
case 2: Value->SetValue_psz(g->Message); break;
|
||||||
default: Value->SetValue_psz("Invalid Flag"); break;
|
default: Value->SetValue_psz("Invalid Flag"); break;
|
||||||
} // endswitch Flag
|
} // endswitch Flag
|
||||||
|
|
||||||
} // end of ReadColumn
|
} // end of ReadColumn
|
||||||
|
@@ -42,7 +42,8 @@ class DllExport ODBCDEF : public TABDEF { /* Logical table description */
|
|||||||
int GetOptions(void) {return Options;}
|
int GetOptions(void) {return Options;}
|
||||||
|
|
||||||
// Methods
|
// Methods
|
||||||
virtual bool DefineAM(PGLOBAL g, LPCSTR am, int poff);
|
virtual int Indexable(void) {return 2;}
|
||||||
|
virtual bool DefineAM(PGLOBAL g, LPCSTR am, int poff);
|
||||||
virtual PTDB GetTable(PGLOBAL g, MODE m);
|
virtual PTDB GetTable(PGLOBAL g, MODE m);
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
@@ -111,15 +112,14 @@ class TDBODBC : public TDBASE {
|
|||||||
virtual int WriteDB(PGLOBAL g);
|
virtual int WriteDB(PGLOBAL g);
|
||||||
virtual int DeleteDB(PGLOBAL g, int irc);
|
virtual int DeleteDB(PGLOBAL g, int irc);
|
||||||
virtual void CloseDB(PGLOBAL g);
|
virtual void CloseDB(PGLOBAL g);
|
||||||
virtual bool ReadKey(PGLOBAL g, OPVAL op, const void *key, int len)
|
virtual bool ReadKey(PGLOBAL g, OPVAL op, const key_range *kr);
|
||||||
{return true;}
|
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// Internal functions
|
// Internal functions
|
||||||
int Decode(char *utf, char *buf, size_t n);
|
int Decode(char *utf, char *buf, size_t n);
|
||||||
char *MakeSQL(PGLOBAL g, bool cnt);
|
bool MakeSQL(PGLOBAL g, bool cnt);
|
||||||
char *MakeInsert(PGLOBAL g);
|
bool MakeInsert(PGLOBAL g);
|
||||||
char *MakeCommand(PGLOBAL g);
|
bool MakeCommand(PGLOBAL g);
|
||||||
//bool MakeFilter(PGLOBAL g, bool c);
|
//bool MakeFilter(PGLOBAL g, bool c);
|
||||||
bool BindParameters(PGLOBAL g);
|
bool BindParameters(PGLOBAL g);
|
||||||
//char *MakeUpdate(PGLOBAL g);
|
//char *MakeUpdate(PGLOBAL g);
|
||||||
@@ -129,14 +129,14 @@ class TDBODBC : public TDBASE {
|
|||||||
ODBConn *Ocp; // Points to an ODBC connection class
|
ODBConn *Ocp; // Points to an ODBC connection class
|
||||||
ODBCCOL *Cnp; // Points to count(*) column
|
ODBCCOL *Cnp; // Points to count(*) column
|
||||||
ODBCPARM Ops; // Additional parameters
|
ODBCPARM Ops; // Additional parameters
|
||||||
char *Connect; // Points to connection string
|
PSTRG Query; // Constructed SQL query
|
||||||
|
char *Connect; // Points to connection string
|
||||||
char *TableName; // Points to ODBC table name
|
char *TableName; // Points to ODBC table name
|
||||||
char *Schema; // Points to ODBC table Schema
|
char *Schema; // Points to ODBC table Schema
|
||||||
char *User; // User connect info
|
char *User; // User connect info
|
||||||
char *Pwd; // Password connect info
|
char *Pwd; // Password connect info
|
||||||
char *Catalog; // Points to ODBC table Catalog
|
char *Catalog; // Points to ODBC table Catalog
|
||||||
char *Srcdef; // The source table SQL definition
|
char *Srcdef; // The source table SQL definition
|
||||||
char *Query; // Points to SQL statement
|
|
||||||
char *Count; // Points to count(*) SQL statement
|
char *Count; // Points to count(*) SQL statement
|
||||||
//char *Where; // Points to local where clause
|
//char *Where; // Points to local where clause
|
||||||
char *Quote; // The identifier quoting character
|
char *Quote; // The identifier quoting character
|
||||||
|
@@ -60,7 +60,7 @@ extern "C" char version[];
|
|||||||
#endif // !__WIN__
|
#endif // !__WIN__
|
||||||
|
|
||||||
#define TYPE_UNKNOWN 12 /* Must be greater than other types */
|
#define TYPE_UNKNOWN 12 /* Must be greater than other types */
|
||||||
#define XSTR(M) sizeof(M) - strlen(M) - 1 /* To avoid overflow*/
|
#define XLEN(M) sizeof(M) - strlen(M) - 1 /* To avoid overflow*/
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Class and structure used by XMLColumns. */
|
/* Class and structure used by XMLColumns. */
|
||||||
@@ -226,30 +226,30 @@ PQRYRES XMLColumns(PGLOBAL g, char *db, char *tab, PTOS topt, bool info)
|
|||||||
more:
|
more:
|
||||||
if (vp->atp) {
|
if (vp->atp) {
|
||||||
strncpy(colname, vp->atp->GetName(g), sizeof(colname));
|
strncpy(colname, vp->atp->GetName(g), sizeof(colname));
|
||||||
strncat(xcol->Name, colname, XSTR(xcol->Name));
|
strncat(xcol->Name, colname, XLEN(xcol->Name));
|
||||||
|
|
||||||
switch (vp->atp->GetText(g, buf, sizeof(buf))) {
|
switch (vp->atp->GetText(g, buf, sizeof(buf))) {
|
||||||
case RC_INFO:
|
case RC_INFO:
|
||||||
PushWarning(g, txmp);
|
PushWarning(g, txmp);
|
||||||
case RC_OK:
|
case RC_OK:
|
||||||
strncat(fmt, "@", XSTR(fmt));
|
strncat(fmt, "@", XLEN(fmt));
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
goto err;
|
goto err;
|
||||||
} // enswitch rc
|
} // enswitch rc
|
||||||
|
|
||||||
if (j)
|
if (j)
|
||||||
strncat(fmt, colname, XSTR(fmt));
|
strncat(fmt, colname, XLEN(fmt));
|
||||||
|
|
||||||
} else {
|
} else {
|
||||||
if (tdp->Usedom && node->GetType() != 1)
|
if (tdp->Usedom && node->GetType() != 1)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
strncpy(colname, node->GetName(g), sizeof(colname));
|
strncpy(colname, node->GetName(g), sizeof(colname));
|
||||||
strncat(xcol->Name, colname, XSTR(xcol->Name));
|
strncat(xcol->Name, colname, XLEN(xcol->Name));
|
||||||
|
|
||||||
if (j)
|
if (j)
|
||||||
strncat(fmt, colname, XSTR(fmt));
|
strncat(fmt, colname, XLEN(fmt));
|
||||||
|
|
||||||
if (j < lvl && ok) {
|
if (j < lvl && ok) {
|
||||||
vp = lvlp[j+1];
|
vp = lvlp[j+1];
|
||||||
@@ -267,10 +267,10 @@ PQRYRES XMLColumns(PGLOBAL g, char *db, char *tab, PTOS topt, bool info)
|
|||||||
if (!vp->atp)
|
if (!vp->atp)
|
||||||
node = vp->nl->GetItem(g, vp->k++, node);
|
node = vp->nl->GetItem(g, vp->k++, node);
|
||||||
|
|
||||||
strncat(fmt, colname, XSTR(fmt));
|
strncat(fmt, colname, XLEN(fmt));
|
||||||
strncat(fmt, "/", XSTR(fmt));
|
strncat(fmt, "/", XLEN(fmt));
|
||||||
strncat(xcol->Name, "_", XSTR(xcol->Name));
|
strncat(xcol->Name, "_", XLEN(xcol->Name));
|
||||||
j++;
|
j++;
|
||||||
vp->n = (int)strlen(xcol->Name);
|
vp->n = (int)strlen(xcol->Name);
|
||||||
vp->m = (int)strlen(fmt);
|
vp->m = (int)strlen(fmt);
|
||||||
goto more;
|
goto more;
|
||||||
|
@@ -340,7 +340,7 @@ PVAL AllocateValue(PGLOBAL g, void *value, short type, short prec)
|
|||||||
|
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case TYPE_STRING:
|
case TYPE_STRING:
|
||||||
valp = new(g) TYPVAL<PSZ>((PSZ)value);
|
valp = new(g) TYPVAL<PSZ>((PSZ)value, prec);
|
||||||
break;
|
break;
|
||||||
case TYPE_SHORT:
|
case TYPE_SHORT:
|
||||||
valp = new(g) TYPVAL<short>(*(short*)value, TYPE_SHORT);
|
valp = new(g) TYPVAL<short>(*(short*)value, TYPE_SHORT);
|
||||||
@@ -1209,12 +1209,12 @@ void TYPVAL<TYPE>::Print(PGLOBAL g, char *ps, uint z)
|
|||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* STRING public constructor from a constant string. */
|
/* STRING public constructor from a constant string. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
TYPVAL<PSZ>::TYPVAL(PSZ s) : VALUE(TYPE_STRING)
|
TYPVAL<PSZ>::TYPVAL(PSZ s, short c) : VALUE(TYPE_STRING)
|
||||||
{
|
{
|
||||||
Strp = s;
|
Strp = s;
|
||||||
Len = strlen(s);
|
Len = strlen(s);
|
||||||
Clen = Len;
|
Clen = Len;
|
||||||
Ci = false;
|
Ci = (c == 1);
|
||||||
} // end of STRING constructor
|
} // end of STRING constructor
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
|
@@ -216,7 +216,7 @@ template <>
|
|||||||
class DllExport TYPVAL<PSZ>: public VALUE {
|
class DllExport TYPVAL<PSZ>: public VALUE {
|
||||||
public:
|
public:
|
||||||
// Constructors
|
// Constructors
|
||||||
TYPVAL(PSZ s);
|
TYPVAL(PSZ s, short c = 0);
|
||||||
TYPVAL(PGLOBAL g, PSZ s, int n, int c);
|
TYPVAL(PGLOBAL g, PSZ s, int n, int c);
|
||||||
|
|
||||||
// Implementation
|
// Implementation
|
||||||
|
@@ -11,6 +11,7 @@
|
|||||||
/* Include mariaDB header file. */
|
/* Include mariaDB header file. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
#include "my_global.h"
|
#include "my_global.h"
|
||||||
|
#include "m_string.h"
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Include required application header files */
|
/* Include required application header files */
|
||||||
@@ -290,14 +291,14 @@ bool STRING::Set(char *s, uint n)
|
|||||||
} // end of Set
|
} // end of Set
|
||||||
|
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
/* Append a char* to a STRING. */
|
/* Append a char* to a STRING. */
|
||||||
/***********************************************************************/
|
/***********************************************************************/
|
||||||
bool STRING::Append(const char *s, uint ln)
|
bool STRING::Append(const char *s, uint ln, bool nq)
|
||||||
{
|
{
|
||||||
if (!s)
|
if (!s)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
uint len = Length + ln + 1;
|
uint i, len = Length + ln + 1;
|
||||||
|
|
||||||
if (len > Size) {
|
if (len > Size) {
|
||||||
char *p = Realloc(len);
|
char *p = Realloc(len);
|
||||||
@@ -311,8 +312,22 @@ bool STRING::Append(const char *s, uint ln)
|
|||||||
|
|
||||||
} // endif n
|
} // endif n
|
||||||
|
|
||||||
strncpy(Strp + Length, s, ln);
|
if (nq) {
|
||||||
Length = len - 1;
|
for (i = 0; i < ln; i++)
|
||||||
|
switch (s[i]) {
|
||||||
|
case '\\': Strp[Length++] = '\\'; Strp[Length++] = '\\'; break;
|
||||||
|
case '\0': Strp[Length++] = '\\'; Strp[Length++] = '0'; break;
|
||||||
|
case '\'': Strp[Length++] = '\\'; Strp[Length++] = '\''; break;
|
||||||
|
case '\n': Strp[Length++] = '\\'; Strp[Length++] = 'n'; break;
|
||||||
|
case '\r': Strp[Length++] = '\\'; Strp[Length++] = 'r'; break;
|
||||||
|
case '\032': Strp[Length++] = '\\'; Strp[Length++] = 'Z'; break;
|
||||||
|
default: Strp[Length++] = s[i];
|
||||||
|
} // endswitch s[i]
|
||||||
|
|
||||||
|
} else
|
||||||
|
for (i = 0; i < ln && s[i]; i++)
|
||||||
|
Strp[Length++] = s[i];
|
||||||
|
|
||||||
Strp[Length] = 0;
|
Strp[Length] = 0;
|
||||||
return false;
|
return false;
|
||||||
} // end of Append
|
} // end of Append
|
||||||
|
@@ -134,7 +134,7 @@ class DllExport STRING : public BLOCK {
|
|||||||
inline void Reset(void) {*Strp = 0;}
|
inline void Reset(void) {*Strp = 0;}
|
||||||
bool Set(PSZ s);
|
bool Set(PSZ s);
|
||||||
bool Set(char *s, uint n);
|
bool Set(char *s, uint n);
|
||||||
bool Append(const char *s, uint ln);
|
bool Append(const char *s, uint ln, bool nq = false);
|
||||||
bool Append(PSZ s);
|
bool Append(PSZ s);
|
||||||
bool Append(STRING &str);
|
bool Append(STRING &str);
|
||||||
bool Append(char c);
|
bool Append(char c);
|
||||||
|
@@ -19,6 +19,7 @@
|
|||||||
#include "m_ctype.h"
|
#include "m_ctype.h"
|
||||||
|
|
||||||
typedef class CMD *PCMD;
|
typedef class CMD *PCMD;
|
||||||
|
typedef struct st_key_range key_range;
|
||||||
|
|
||||||
// Commands executed by XDBC and MYX tables
|
// Commands executed by XDBC and MYX tables
|
||||||
class CMD : public BLOCK {
|
class CMD : public BLOCK {
|
||||||
@@ -32,12 +33,24 @@ class CMD : public BLOCK {
|
|||||||
}; // end of class CMD
|
}; // end of class CMD
|
||||||
|
|
||||||
// Condition filter structure
|
// Condition filter structure
|
||||||
typedef struct _cond_filter {
|
class CONDFIL : public BLOCK {
|
||||||
char *Body;
|
public:
|
||||||
OPVAL Op;
|
// Constructor
|
||||||
PCMD Cmds;
|
CONDFIL(const Item *cond, uint idx, AMT type)
|
||||||
} CONDFIL, *PCFIL;
|
{
|
||||||
|
Cond = cond; Idx = idx; Type = type; Body = NULL; Op = OP_XX; Cmds = NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Members
|
||||||
|
const Item *Cond;
|
||||||
|
AMT Type;
|
||||||
|
uint Idx;
|
||||||
|
char *Body;
|
||||||
|
OPVAL Op;
|
||||||
|
PCMD Cmds;
|
||||||
|
}; // end of class CONDFIL
|
||||||
|
|
||||||
|
typedef class CONDFIL *PCFIL;
|
||||||
typedef class TDBCAT *PTDBCAT;
|
typedef class TDBCAT *PTDBCAT;
|
||||||
typedef class CATCOL *PCATCOL;
|
typedef class CATCOL *PCATCOL;
|
||||||
|
|
||||||
@@ -109,7 +122,7 @@ class DllExport TDB: public BLOCK { // Table Descriptor Block.
|
|||||||
virtual int DeleteDB(PGLOBAL, int) = 0;
|
virtual int DeleteDB(PGLOBAL, int) = 0;
|
||||||
virtual void CloseDB(PGLOBAL) = 0;
|
virtual void CloseDB(PGLOBAL) = 0;
|
||||||
virtual int CheckWrite(PGLOBAL) {return 0;}
|
virtual int CheckWrite(PGLOBAL) {return 0;}
|
||||||
virtual bool ReadKey(PGLOBAL, OPVAL, const void *, int) = 0;
|
virtual bool ReadKey(PGLOBAL, OPVAL, const key_range *) = 0;
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
// Members
|
// Members
|
||||||
@@ -188,7 +201,7 @@ class DllExport TDBASE : public TDB {
|
|||||||
virtual void MarkDB(PGLOBAL g, PTDB tdb2);
|
virtual void MarkDB(PGLOBAL g, PTDB tdb2);
|
||||||
virtual int MakeIndex(PGLOBAL g, PIXDEF, bool)
|
virtual int MakeIndex(PGLOBAL g, PIXDEF, bool)
|
||||||
{strcpy(g->Message, "Remote index"); return RC_INFO;}
|
{strcpy(g->Message, "Remote index"); return RC_INFO;}
|
||||||
virtual bool ReadKey(PGLOBAL, OPVAL, const void *, int)
|
virtual bool ReadKey(PGLOBAL, OPVAL, const key_range *)
|
||||||
{assert(false); return true;}
|
{assert(false); return true;}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
|
Reference in New Issue
Block a user