Commit d8f99f16 authored by Olivier Bertrand's avatar Olivier Bertrand

- Add FBLOCK when opening ODBC, JSON and MONGO tables.

This to have automatic closing in case of thrown error.
  modified:   storage/connect/cmgoconn.cpp
  modified:   storage/connect/cmgoconn.h
  modified:   storage/connect/filamzip.cpp
  modified:   storage/connect/javaconn.cpp
  modified:   storage/connect/javaconn.h
  modified:   storage/connect/odbconn.cpp
  modified:   storage/connect/odbconn.h
  modified:   storage/connect/plgdbsem.h
  modified:   storage/connect/plgdbutl.cpp

- Fix INCOL bug when inserting several lines to MONGO tables
  modified:   storage/connect/cmgoconn.cpp
  modified:   storage/connect/tabcmg.cpp
  modified:   storage/connect/tabjmg.cpp

- MONGO_SUPPORT is set for both MongoDB drivers
  CMGO_SUPPORT  is set only when the C driver is available
  modified:   storage/connect/CMakeLists.txt
  modified:   storage/connect/filter.h
  modified:   storage/connect/filter.h
  modified:   storage/connect/ha_connect.cc
  modified:   storage/connect/mongo.cpp
  modified:   storage/connect/mycat.cc
  modified:   storage/connect/tabjson.cpp
  modified:   storage/connect/tabjson.h

- Separate enums JCATINFO and
  modified:   storage/connect/javaconn.h
  modified:   storage/connect/jdbconn.cpp

- Fix crash when executing JDBC catfunc=driver
  modified:   storage/connect/jdbconn.cpp

- Report an error when the Mongo driver if explicitly
specified and not supported.
  modified:   storage/connect/mongo.cpp

- Fix bug causing catalog JSON tables to fail
  modified:   storage/connect/tabjson.cpp

- Protect by mutex the Ready variable of the TBLTBM table type
  modified:   storage/connect/tabtbl.cpp

- Put testing of Thread TBL tables in a separate test
With added case and modified old case that could avoid the test to fail.
  modified:   storage/connect/mysql-test/connect/r/tbl.result
  modified:   storage/connect/mysql-test/connect/t/tbl.test
  new file:   storage/connect/mysql-test/connect/r/tbl_thread.result
  new file:   storage/connect/mysql-test/connect/t/tbl_thread.test

- jmongo3.test no more exists
  deleted:    storage/connect/mysql-test/connect/t/jmongo3.test

- Add new tests for the MONGO feature (disabled)
  modified:   storage/connect/mysql-test/connect/disabled.def
  new file:   storage/connect/mysql-test/connect/r/json_java_2.result
  new file:   storage/connect/mysql-test/connect/r/json_java_3.result
  new file:   storage/connect/mysql-test/connect/r/json_mongo_c.result
  new file:   storage/connect/mysql-test/connect/r/mongo_c.result
  new file:   storage/connect/mysql-test/connect/r/mongo_java_2.result
  new file:   storage/connect/mysql-test/connect/r/mongo_java_3.result
  new file:   storage/connect/mysql-test/connect/std_data/Mongo2.jar
  new file:   storage/connect/mysql-test/connect/std_data/cities.json
  new file:   storage/connect/mysql-test/connect/t/json_java_2.test
  new file:   storage/connect/mysql-test/connect/t/json_java_3.test
  new file:   storage/connect/mysql-test/connect/t/json_mongo_c.test
  new file:   storage/connect/mysql-test/connect/t/mongo.inc
  new file:   storage/connect/mysql-test/connect/t/mongo_c.test
  new file:   storage/connect/mysql-test/connect/t/mongo_java_2.test
  new file:   storage/connect/mysql-test/connect/t/mongo_java_3.test
  new file:   storage/connect/mysql-test/connect/t/mongo_test.inc
parent df3fd420
......@@ -247,11 +247,8 @@ ENDIF(CONNECT_WITH_ODBC)
#
# JDBC and MongoDB Java Driver
#
IF(APPLE)
OPTION(CONNECT_WITH_JDBC "Compile CONNECT storage engine without JDBC support" OFF)
ELSE()
OPTION(CONNECT_WITH_JDBC "Compile CONNECT storage engine with JDBC support" ON)
ENDIF()
OPTION(CONNECT_WITH_MONGO "Compile CONNECT storage engine with MONGO support" ON)
OPTION(CONNECT_WITH_JDBC "Compile CONNECT storage engine with JDBC support" ON)
IF(CONNECT_WITH_JDBC)
FIND_PACKAGE(Java 1.6)
......@@ -263,12 +260,9 @@ IF(CONNECT_WITH_JDBC)
# SET(JDBC_LIBRARY ${JAVA_JVM_LIBRARY}) will be dynamically linked
SET(CONNECT_SOURCES ${CONNECT_SOURCES}
javaconn.cpp jdbconn.cpp tabjdbc.cpp
jmgoconn.cpp jmgfam.cpp mongo.cpp tabjmg.cpp
jdbccat.h javaconn.h jdbconn.h tabjdbc.h
jmgoconn.h jmgfam.h mongo.h tabjmg.h
JdbcInterface.java ApacheInterface.java MariadbInterface.java
MysqlInterface.java OracleInterface.java PostgresqlInterface.java
Mongo2Interface.java Mongo3Interface.java
JavaWrappers.jar)
# TODO: Find how to compile and install the java wrapper classes
# Find required libraries and include directories
......@@ -278,6 +272,13 @@ IF(CONNECT_WITH_JDBC)
INSTALL(FILES ${CMAKE_CURRENT_SOURCE_DIR}/JavaWrappers.jar
DESTINATION ${INSTALL_PLUGINDIR} COMPONENT connect-engine)
add_definitions(-DJDBC_SUPPORT)
IF(CONNECT_WITH_MONGO)
SET(CONNECT_SOURCES ${CONNECT_SOURCES}
jmgfam.cpp jmgoconn.cpp mongo.cpp tabjmg.cpp
jmgfam.h jmgoconn.h mongo.h tabjmg.h
Mongo2Interface.java Mongo3Interface.java)
add_definitions(-DMONGO_SUPPORT)
ENDIF()
ELSE()
SET(JDBC_LIBRARY "")
ENDIF()
......@@ -299,8 +300,6 @@ ENDIF(CONNECT_WITH_ZIP)
# MONGO C Driver (CMAKE NOT YET WORKING)
#
#OPTION(CONNECT_WITH_MONGO "Compile CONNECT storage engine with MONGO support" ON)
#IF(CONNECT_WITH_MONGO)
# IF(WIN32)
# # Adding some typical places to search in
......@@ -311,17 +310,18 @@ ENDIF(CONNECT_WITH_ZIP)
# C:/mongo-c-driver/lib
# D:/mongo-c-driver/lib)
# ENDIF(WIN32)
# FIND_PACKAGE(libmongoc)
# FIND_PACKAGE(libmongoc 1.7)
# IF (MONGO_FOUND)
# INCLUDE_DIRECTORIES(${MONGO_INCLUDE_DIR})
# SET(MONGO_LIBRARY ${MONGO_LIBRARIES})
# SET(CONNECT_SOURCES ${CONNECT_SOURCES}
# cmgoconn.cpp cmgfam.cpp tabcmg.cpp
# cmgoconn.h cmgfam.h tabcmg.h)
# add_definitions(-DCMGO_SUPPORT)
# IF (NOT JAVA_FOUND AND JNI_FOUND)
# SET(CONNECT_SOURCES ${CONNECT_SOURCES} mongo.cpp mongo.h)
# add_definitions(-DMONGO_SUPPORT)
# ENDIF (NOT JAVA_FOUND AND JNI_FOUND)
# add_definitions(-DMONGO_SUPPORT)
# ENDIF(MONGO_FOUND)
#ENDIF(CONNECT_WITH_MONGO)
......
......@@ -92,6 +92,32 @@ void INCOL::AddCol(PGLOBAL g, PCOL colp, char *jp)
} // end of AddCol
/***********************************************************************/
/* Clear. */
/***********************************************************************/
void INCOL::Init(void)
{
bson_init(Child);
for (PKC kp = Klist; kp; kp = kp->Next)
if (kp->Incolp)
kp->Incolp->Init();
} // end of init
/***********************************************************************/
/* Destroy. */
/***********************************************************************/
void INCOL::Destroy(void)
{
bson_destroy(Child);
for (PKC kp = Klist; kp; kp = kp->Next)
if (kp->Incolp)
kp->Incolp->Destroy();
} // end of Destroy
/* -------------------------- Class CMgoConn ------------------------- */
/***********************************************************************/
......@@ -109,6 +135,7 @@ CMgoConn::CMgoConn(PGLOBAL g, PCPARM pcg)
Query = NULL;
Opts = NULL;
Fpc = NULL;
fp = NULL;
m_Connected = false;
} // end of CMgoConn standard constructor
......@@ -149,6 +176,24 @@ bool CMgoConn::Connect(PGLOBAL g)
return true;
} // endif Collection
/*********************************************************************/
/* Link a Fblock. This make possible to automatically close it */
/* in case of error (throw). */
/*********************************************************************/
PDBUSER dbuserp = (PDBUSER)g->Activityp->Aptr;
fp = (PFBLOCK)PlugSubAlloc(g, NULL, sizeof(FBLOCK));
fp->Type = TYPE_FB_MONGO;
fp->Fname = NULL;
fp->Next = dbuserp->Openlist;
dbuserp->Openlist = fp;
fp->Count = 1;
fp->Length = 0;
fp->Memory = NULL;
fp->Mode = MODE_ANY;
fp->File = this;
fp->Handle = 0;
m_Connected = true;
return false;
} // end of Connect
......@@ -493,19 +538,19 @@ bool CMgoConn::DocWrite(PGLOBAL g, PINCOL icp)
bool isdoc = !kp->Incolp->Array;
if (isdoc)
BSON_APPEND_DOCUMENT_BEGIN(&icp->Child, kp->Key, &kp->Incolp->Child);
BSON_APPEND_DOCUMENT_BEGIN(icp->Child, kp->Key, kp->Incolp->Child);
else
BSON_APPEND_ARRAY_BEGIN(&icp->Child, kp->Key, &kp->Incolp->Child);
BSON_APPEND_ARRAY_BEGIN(icp->Child, kp->Key, kp->Incolp->Child);
if (DocWrite(g, kp->Incolp))
return true;
if (isdoc)
bson_append_document_end(&icp->Child, &kp->Incolp->Child);
bson_append_document_end(icp->Child, kp->Incolp->Child);
else
bson_append_array_end(&icp->Child, &kp->Incolp->Child);
bson_append_array_end(icp->Child, kp->Incolp->Child);
} else if (AddValue(g, kp->Colp, &icp->Child, kp->Key, false))
} else if (AddValue(g, kp->Colp, icp->Child, kp->Key, false))
return true;
return false;
......@@ -520,19 +565,19 @@ int CMgoConn::Write(PGLOBAL g)
PTDB tp = Pcg->Tdbp;
if (tp->GetMode() == MODE_INSERT) {
bson_init(&Fpc->Child);
Fpc->Init();
if (DocWrite(g, Fpc))
return RC_FX;
if (trace) {
char *str = bson_as_json(&Fpc->Child, NULL);
char *str = bson_as_json(Fpc->Child, NULL);
htrc("Inserting: %s\n", str);
bson_free(str);
} // endif trace
if (!mongoc_collection_insert(Collection, MONGOC_INSERT_NONE,
&Fpc->Child, NULL, &Error)) {
Fpc->Child, NULL, &Error)) {
sprintf(g->Message, "Mongo insert: %s", Error.message);
rc = RC_FX;
} // endif insert
......@@ -641,6 +686,8 @@ void CMgoConn::Close(void)
if (Client) mongoc_client_pool_push(Pool, Client);
if (Pool) mongoc_client_pool_destroy(Pool);
if (Uri) mongoc_uri_destroy(Uri);
if (Fpc) Fpc->Destroy();
if (fp) fp->Count = 0;
} // end of Close
/***********************************************************************/
......
......@@ -48,19 +48,21 @@ typedef struct KEYCOL {
class INCOL : public BLOCK {
public:
// Constructor
INCOL(bool ar) { Klist = NULL; Array = ar; }
INCOL(bool ar) { Child = bson_new(); Klist = NULL; Array = ar; }
// Methods
void AddCol(PGLOBAL g, PCOL colp, char *jp);
void Init(void);
void Destroy(void);
//Members
bson_t Child;
PKC Klist;
bool Array;
bson_t *Child;
PKC Klist;
bool Array;
}; // end of INCOL;
/***********************************************************************/
/* CMgoConn class. */
/* CMgoConn class. */
/***********************************************************************/
class CMgoConn : public BLOCK {
friend class TDBCMG;
......@@ -108,5 +110,6 @@ class CMgoConn : public BLOCK {
bson_iter_t Iter; // Used to retrieve column value
bson_iter_t Desc; // Descendant iter
PINCOL Fpc; // To insert INCOL classes
PFBLOCK fp;
bool m_Connected;
}; // end of class CMgoConn
......@@ -290,6 +290,9 @@ void ZIPUTIL::close()
zipfile = NULL;
} // endif zipfile
if (fp)
fp->Count = 0;
} // end of close
/***********************************************************************/
......@@ -493,6 +496,9 @@ void UNZIPUTL::close()
zipfile = NULL;
} // endif zipfile
if (fp)
fp->Count = 0;
} // end of close
/***********************************************************************/
......
......@@ -1405,7 +1405,7 @@ PFIL FILTER::Copy(PTABS t)
} // end of Copy
#endif // 0
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
/***********************************************************************/
/* Make selector json representation for Mongo tables. */
/***********************************************************************/
......@@ -1483,7 +1483,7 @@ bool FILTER::MakeSelector(PGLOBAL g, PSTRG s)
s->Append('}');
return false;
} // end of MakeSelector
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
/*********************************************************************/
/* Make file output of FILTER contents. */
......
......@@ -61,9 +61,9 @@ class DllExport FILTER : public XOBJECT { /* Filter description block */
//virtual PXOB CheckSubQuery(PGLOBAL, PSQL);
//virtual bool CheckLocal(PTDB);
//virtual int CheckSpcCol(PTDB tdbp, int n);
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
bool MakeSelector(PGLOBAL g, PSTRG s);
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
virtual void Printf(PGLOBAL g, FILE *f, uint n);
virtual void Prints(PGLOBAL g, char *ps, uint z);
// PFIL Linearize(bool nosep);
......
......@@ -208,16 +208,18 @@ PQRYRES OEMColumns(PGLOBAL g, PTOS topt, char *tab, char *db, bool info);
PQRYRES VirColumns(PGLOBAL g, bool info);
PQRYRES JSONColumns(PGLOBAL g, PCSZ db, PCSZ dsn, PTOS topt, bool info);
PQRYRES XMLColumns(PGLOBAL g, char *db, char *tab, PTOS topt, bool info);
#if defined(JDBC_SUPPORT) || defined(MONGO_SUPPORT)
#if defined(MONGO_SUPPORT)
PQRYRES MGOColumns(PGLOBAL g, PCSZ db, PCSZ url, PTOS topt, bool info);
#endif // JDBC_SUPPORT || MONGO_SUPPORT
#endif // MONGO_SUPPORT
int TranslateJDBCType(int stp, char *tn, int prec, int& len, char& v);
void PushWarning(PGLOBAL g, THD *thd, int level);
bool CheckSelf(PGLOBAL g, TABLE_SHARE *s, PCSZ host, PCSZ db,
PCSZ tab, PCSZ src, int port);
bool ZipLoadFile(PGLOBAL, PCSZ, PCSZ, PCSZ, bool, bool);
bool ExactInfo(void);
#if defined(CMGO_SUPPORT)
void mongo_init(bool);
#endif // CMGO_SUPPORT
USETEMP UseTemp(void);
int GetConvSize(void);
TYPCONV GetTypeConv(void);
......@@ -688,9 +690,9 @@ static int connect_init_func(void *p)
XmlInitParserLib();
#endif // LIBXML2_SUPPORT
#if defined(MONGO_SUPPORT)
#if defined(CMGO_SUPPORT)
mongo_init(true);
#endif // MONGO_SUPPORT
#endif // CMGO_SUPPORT
init_connect_psi_keys();
......@@ -730,9 +732,9 @@ static int connect_done_func(void *)
XmlCleanupParserLib();
#endif // LIBXML2_SUPPORT
#if defined(MONGO_SUPPORT)
#if defined(CMGO_SUPPORT)
mongo_init(false);
#endif // MONGO_SUPPORT
#endif // CMGO_SUPPORT
#ifdef JDBC_SUPPORT
JAVAConn::ResetJVM();
......@@ -5360,11 +5362,11 @@ static int connect_assisted_discovery(handlerton *, THD* thd,
#if defined(JDBC_SUPPORT)
PJPARM sjp= NULL;
#endif // JDBC_SUPPORT
#if defined(JDBC_SUPPORT) || defined(MONGO_SUPPORT)
#if defined(MONGO_SUPPORT)
PCSZ driver= NULL;
char *url= NULL;
//char *prop= NULL;
#endif // JDBC_SUPPORT || MONGO_SUPPORT
#endif // MONGO_SUPPORT
uint tm, fnc= FNC_NO, supfnc= (FNC_NO | FNC_COL);
bool bif, ok= false, dbf= false;
TABTYPE ttp= TAB_UNDEF;
......@@ -5639,14 +5641,14 @@ static int connect_assisted_discovery(handlerton *, THD* thd,
ok = true;
break;
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
case TAB_MONGO:
if (!topt->tabname)
topt->tabname = tab;
ok = true;
break;
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
case TAB_VIR:
ok = true;
break;
......@@ -5789,22 +5791,14 @@ static int connect_assisted_discovery(handlerton *, THD* thd,
case TAB_JSON:
qrp = JSONColumns(g, db, dsn, topt, fnc == FNC_COL);
break;
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
case TAB_MONGO:
if (!(url = strz(g, create_info->connect_string)) || !*url)
url = "mongodb://localhost:27017";
#if !defined(MONGO_SUPPORT)
driver = "JAVA";
#elif !defined(JDBC_SUPPORT)
driver = "C";
#else // MONGO_SUPPORT && JDBC_SUPPORT
if (!driver)
driver = "C";
#endif // MONGO_SUPPORT && JDBC_SUPPORT
qrp = MGOColumns(g, db, url, topt, fnc == FNC_COL);
break;
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
#if defined(LIBXML2_SUPPORT) || defined(DOMDOC_SUPPORT)
case TAB_XML:
qrp = XMLColumns(g, (char*)db, tab, topt, fnc == FNC_COL);
......
......@@ -124,6 +124,7 @@ JAVAConn::JAVAConn(PGLOBAL g, PCSZ wrapper)
m_Wrap = strcat(strcpy(wn, "wrappers/"), m_Wrap);
} // endif m_Wrap
fp = NULL;
m_Opened = false;
m_Connected = false;
m_Rows = 0;
......@@ -567,6 +568,24 @@ bool JAVAConn::Open(PGLOBAL g)
return true;
} // endif Check
/*********************************************************************/
/* Link a Fblock. This make possible to automatically close it */
/* in case of error (throw). */
/*********************************************************************/
PDBUSER dbuserp = (PDBUSER)g->Activityp->Aptr;
fp = (PFBLOCK)PlugSubAlloc(g, NULL, sizeof(FBLOCK));
fp->Type = TYPE_FB_JAVA;
fp->Fname = NULL;
fp->Next = dbuserp->Openlist;
dbuserp->Openlist = fp;
fp->Count = 1;
fp->Length = 0;
fp->Memory = NULL;
fp->Mode = MODE_ANY;
fp->File = this;
fp->Handle = 0;
m_Opened = true;
return false;
} // end of Open
......@@ -595,5 +614,8 @@ void JAVAConn::Close()
if ((rc = jvm->DetachCurrentThread()) != JNI_OK)
printf("DetachCurrentThread: rc=%d\n", (int)rc);
if (fp)
fp->Count = 0;
m_Opened = false;
} // end of Close
......@@ -25,18 +25,16 @@
//efine MAX_DNAME_LEN 256 // Max size of Recordset names
//efine MAX_CONNECT_LEN 512 // Max size of Connect string
//efine MAX_CURSOR_NAME 18 // Max size of a cursor name
#define DEFAULT_FIELD_TYPE 0 // TYPE_NULL
//efine DEFAULT_FIELD_TYPE 0 // TYPE_NULL
#if !defined(__WIN__)
typedef unsigned char *PUCHAR;
#endif // !__WIN__
enum JCATINFO {
CAT_TAB = 1, // JDBC Tables
CAT_COL = 2, // JDBC Columns
CAT_KEY = 3, // JDBC PrimaryKeys
//CAT_STAT = 4, // SQLStatistics
//CAT_SPC = 5 // SQLSpecialColumns
JCAT_TAB = 1, // JDBC Tables
JCAT_COL = 2, // JDBC Columns
JCAT_KEY = 3, // JDBC PrimaryKeys
};
/***********************************************************************/
......@@ -121,6 +119,7 @@ class JAVAConn : public BLOCK {
jclass jdi; // Pointer to the java wrapper class
jobject job; // The java wrapper class object
jmethodID errid; // The GetErrmsg method ID
PFBLOCK fp;
bool m_Opened;
bool m_Connected;
PCSZ DiscFunc;
......
......@@ -289,7 +289,7 @@ PQRYRES JDBCColumns(PGLOBAL g, PCSZ db, PCSZ table, PCSZ colpat,
if (trace)
htrc("Getting col results ncol=%d\n", qrp->Nbcol);
if (!(cap = AllocCatInfo(g, CAT_COL, db, table, qrp)))
if (!(cap = AllocCatInfo(g, JCAT_COL, db, table, qrp)))
return NULL;
// Colpat cannot be null or empty for some drivers
......@@ -410,7 +410,7 @@ PQRYRES JDBCTables(PGLOBAL g, PCSZ db, PCSZ tabpat, PCSZ tabtyp,
return qrp;
// Tabpat cannot be null or empty for some drivers
if (!(cap = AllocCatInfo(g, CAT_TAB, db,
if (!(cap = AllocCatInfo(g, JCAT_TAB, db,
(tabpat && *tabpat) ? tabpat : PlugDup(g, "%"), qrp)))
return NULL;
......@@ -465,7 +465,7 @@ PQRYRES JDBCDrivers(PGLOBAL g, int maxres, bool info)
if (!info) {
jcp = new(g) JDBConn(g, NULL);
if (jcp->Open(NULL) != RC_OK)
if (jcp->Open(g) != RC_OK)
return NULL;
if (!maxres)
......@@ -1407,28 +1407,19 @@ bool JDBConn::SetParam(JDBCCOL *colp)
// Now do call the proper JDBC API
switch (cap->Id) {
case CAT_COL:
case JCAT_COL:
fnc = "GetColumns";
break;
case CAT_TAB:
case JCAT_TAB:
fnc = "GetTables";
break;
#if 0
case CAT_KEY:
case JCAT_KEY:
fnc = "SQLPrimaryKeys";
rc = SQLPrimaryKeys(hstmt, name.ptr(2), name.length(2),
name.ptr(1), name.length(1),
name.ptr(0), name.length(0));
break;
case CAT_STAT:
fnc = "SQLStatistics";
rc = SQLStatistics(hstmt, name.ptr(2), name.length(2),
name.ptr(1), name.length(1),
name.ptr(0), name.length(0),
cap->Unique, cap->Accuracy);
break;
case CAT_SPC:
ThrowDJX("SQLSpecialColumns not available yet");
#endif // 0
default:
sprintf(g->Message, "Invalid SQL function id");
......
......@@ -18,7 +18,7 @@
#include "plgdbsem.h"
#include "xtable.h"
#include "tabext.h"
#if defined(MONGO_SUPPORT)
#if defined(CMGO_SUPPORT)
#include "tabcmg.h"
#endif // MONGO_SUPPORT
#if defined(JDBC_SUPPORT)
......@@ -61,18 +61,29 @@ PQRYRES MGOColumns(PGLOBAL g, PCSZ db, PCSZ uri, PTOS topt, bool info)
/*********************************************************************/
/* Open MongoDB. */
/*********************************************************************/
# if !defined(JDBC_SUPPORT)
cmgd = new(g) CMGDISC(g, (int*)length);
#elif !defined(MONGO_SUPPORT)
cmgd = new(g) JMGDISC(g, (int*)length);
#else
PCSZ drv = GetStringTableOption(g, topt, "Driver", "C");
PCSZ drv = GetStringTableOption(g, topt, "Driver", NULL);
if (toupper(*drv) == 'C')
if (drv && toupper(*drv) == 'C') {
#if defined(CMGO_SUPPORT)
cmgd = new(g) CMGDISC(g, (int*)length);
else
#else
sprintf(g->Message, "Mongo %s Driver not available", "C");
goto err;
#endif
} else if (drv && toupper(*drv) == 'J') {
#if defined(JDBC_SUPPORT)
cmgd = new(g) JMGDISC(g, (int*)length);
#else
sprintf(g->Message, "Mongo %s Driver not available", "Java");
goto err;
#endif
} else { // Driver not specified
#if defined(CMGO_SUPPORT)
cmgd = new(g) CMGDISC(g, (int*)length);
#else
cmgd = new(g) JMGDISC(g, (int*)length);
#endif
} // endif drv
if ((n = cmgd->GetColumns(g, db, uri, topt)) < 0)
goto err;
......@@ -302,13 +313,7 @@ bool MGODEF::DefineAM(PGLOBAL g, LPCSTR, int poff)
else if (!Tabschema)
Tabschema = GetStringCatInfo(g, "Dbname", "*");
# if !defined(JDBC_SUPPORT)
Driver = "C";
#elif !defined(MONGO_SUPPORT)
Driver = "JAVA";
#else
Driver = GetStringCatInfo(g, "Driver", "C");
#endif
Driver = GetStringCatInfo(g, "Driver", NULL);
Uri = GetStringCatInfo(g, "Connect", "mongodb://localhost:27017");
Colist = GetStringCatInfo(g, "Colist", NULL);
Filter = GetStringCatInfo(g, "Filter", NULL);
......@@ -329,27 +334,38 @@ bool MGODEF::DefineAM(PGLOBAL g, LPCSTR, int poff)
/***********************************************************************/
PTDB MGODEF::GetTable(PGLOBAL g, MODE m)
{
if (Catfunc == FNC_COL) {
#if defined(MONGO_SUPPORT)
if (Driver && toupper(*Driver) == 'C')
return new(g)TDBGOL(this);
#endif // MONGO_SUPPORT
if (Driver && toupper(*Driver) == 'C') {
#if defined(CMGO_SUPPORT)
if (Catfunc == FNC_COL)
return new(g) TDBGOL(this);
else
return new(g) TDBCMG(this);
#else
sprintf(g->Message, "Mongo %s Driver not available", "C");
return NULL;
#endif
} else if (Driver && toupper(*Driver) == 'J') {
#if defined(JDBC_SUPPORT)
return new(g)TDBJGL(this);
#else // !JDBC_SUPPORT
strcpy(g->Message, "No column find, no MONGO nor Java support");
if (Catfunc == FNC_COL)
return new(g) TDBJGL(this);
else
return new(g) TDBJMG(this);
#else
sprintf(g->Message, "Mongo %s Driver not available", "Java");
return NULL;
#endif // !JDBC_SUPPORT
} // endif Catfunc
#endif
} else { // Driver not specified
#if defined(CMGO_SUPPORT)
if (Catfunc == FNC_COL)
return new(g) TDBGOL(this);
else
return new(g) TDBCMG(this);
#else
if (Catfunc == FNC_COL)
return new(g) TDBJGL(this);
else
return new(g) TDBJMG(this);
#endif
} // endif Driver
#if defined(MONGO_SUPPORT)
if (Driver && toupper(*Driver) == 'C')
return new(g) TDBCMG(this);
#endif // MONGO_SUPPORT
#if defined(JDBC_SUPPORT)
return new(g) TDBJMG(this);
#else // !JDBC_SUPPORT
strcpy(g->Message, "No MONGO nor Java support");
return NULL;
#endif // !JDBC_SUPPORT
} // end of GetTable
......@@ -96,9 +96,9 @@
#if defined(XML_SUPPORT)
#include "tabxml.h"
#endif // XML_SUPPORT
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
#include "mongo.h"
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
#if defined(ZIP_SUPPORT)
#include "tabzip.h"
#endif // ZIP_SUPPORT
......@@ -164,7 +164,7 @@ TABTYPE GetTypeID(const char *type)
#if defined(ZIP_SUPPORT)
: (!stricmp(type, "ZIP")) ? TAB_ZIP
#endif
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
: (!stricmp(type, "MONGO")) ? TAB_MONGO
#endif
: (!stricmp(type, "OEM")) ? TAB_OEM : TAB_NIY;
......@@ -557,9 +557,9 @@ PRELDEF MYCAT::MakeTableDesc(PGLOBAL g, PTABLE tablep, LPCSTR am)
#endif // PIVOT_SUPPORT
case TAB_VIR: tdp= new(g) VIRDEF; break;
case TAB_JSON: tdp= new(g) JSONDEF; break;
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
case TAB_MONGO: tdp = new(g) MGODEF; break;
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
#if defined(ZIP_SUPPORT)
case TAB_ZIP: tdp= new(g) ZIPDEF; break;
#endif // ZIP_SUPPORT
......
......@@ -13,6 +13,9 @@ jdbc : Variable settings depend on machine configuration
jdbc_new : Variable settings depend on machine configuration
jdbc_oracle : Variable settings depend on machine configuration
jdbc_postgresql : Variable settings depend on machine configuration
json_mgo : Need MongoDB running and its C Driver installed
mongo : Need MongoDB running and its C Driver installed
jmongo3 : Need MongoDB running and its Java Driver installed
json_mongo_c : Need MongoDB running and its C Driver installed
json_java_2 : Need MongoDB running and its Java Driver installed
json_java_3 : Need MongoDB running and its Java Driver installed
mongo_c : Need MongoDB running and its C Driver installed
mongo_java_2 : Need MongoDB running and its Java Driver installed
mongo_java_3 : Need MongoDB running and its Java Driver installed
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
......@@ -141,22 +141,3 @@ DROP TABLE t1;
DROP TABLE t2;
DROP TABLE t3;
DROP TABLE t4;
#
# Checking thread TBL tables
#
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 11 as v';
SELECT * FROM t1;
v
11
CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 22 as v';
SELECT * FROM t2;
v
22
CREATE TABLE total (v BIGINT(20) UNSIGNED NOT NULL) ENGINE=CONNECT TABLE_TYPE=TBL TABLE_LIST='t1,t2' OPTION_LIST='thread=yes,port=PORT';;
SELECT * FROM total order by v desc;
v
22
11
DROP TABLE total;
DROP TABLE t1;
DROP TABLE t2;
connect master,127.0.0.1,root,,test,$MASTER_MYPORT,;
connect slave,127.0.0.1,root,,test,$SLAVE_MYPORT,;
connection master;
CREATE DATABASE connect;
connection slave;
CREATE DATABASE connect;
connection default;
#
# Checking thread TBL tables
#
CREATE TABLE t1 (a int, b char(10));
INSERT INTO t1 VALUES (0,'test00'),(1,'test01'),(2,'test02'),(3,'test03');
SELECT * FROM t1;
a b
0 test00
1 test01
2 test02
3 test03
connection master;
CREATE TABLE rt2 (a int, b char(10));
INSERT INTO rt2 VALUES (4,'test04'),(5,'test05'),(6,'test06'),(7,'test07');
SELECT * FROM rt2;
a b
4 test04
5 test05
6 test06
7 test07
connection slave;
CREATE TABLE rt3 (a int, b char(10));
INSERT INTO rt3 VALUES (8,'test08'),(9,'test09'),(10,'test10'),(11,'test11');
SELECT * FROM rt3;
a b
8 test08
9 test09
10 test10
11 test11
connection default;
CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=MYSQL
CONNECTION='mysql://root@localhost:MASTER_PORT/test/rt2';
SELECT * FROM t2;
a b
4 test04
5 test05
6 test06
7 test07
CREATE TABLE t3 ENGINE=CONNECT TABLE_TYPE=MYSQL
CONNECTION='mysql://root@localhost:SLAVE_PORT/test/rt3';
SELECT * FROM t3;
a b
8 test08
9 test09
10 test10
11 test11
CREATE TABLE total (a int, b char(10))
ENGINE=CONNECT TABLE_TYPE=TBL TABLE_LIST='t1,t2,t3'
OPTION_LIST='thread=yes,port=PORT';
SELECT * FROM total order by a desc;
a b
11 test11
10 test10
9 test09
8 test08
7 test07
6 test06
5 test05
4 test04
3 test03
2 test02
1 test01
0 test00
connection master;
DROP TABLE rt2;
connection slave;
DROP TABLE rt3;
connection default;
DROP TABLE t1,t2,t3,total;
#
# Old thread TBL tables test
#
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 11 as v' OPTION_LIST='port=MASTER_PORT';
SELECT * FROM t1;
v
11
CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 22 as v' OPTION_LIST='port=SLAVE_PORT';
SELECT * FROM t2;
v
22
CREATE TABLE total (v BIGINT(20) UNSIGNED NOT NULL) ENGINE=CONNECT TABLE_TYPE=TBL TABLE_LIST='t1,t2' OPTION_LIST='thread=yes,port=PORT';;
SELECT * FROM total order by v desc;
v
22
11
DROP TABLE total;
DROP TABLE t1;
DROP TABLE t2;
connection master;
DROP TABLE IF EXISTS connect.t1;
DROP DATABASE IF EXISTS connect;
connection slave;
DROP TABLE IF EXISTS connect.t1;
DROP DATABASE IF EXISTS connect;
This diff was suppressed by a .gitattributes entry.
This diff is collapsed.
-- source jdbconn.inc
eval SET GLOBAL connect_class_path='$MTR_SUITE_DIR/std_data/Mongo3.jar';
CREATE TABLE t1 (Document varchar(1024) field_format='*')
ENGINE=CONNECT TABLE_TYPE=MONGO TABNAME=restaurants OPTION_LIST='Version=3' DATA_CHARSET=utf8;
SELECT * from t1 limit 3;
DROP TABLE t1;
#
# Test catfunc
#
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=MONGO TABNAME=restaurants CATFUNC=columns OPTION_LIST='Level=1,Version=3' DATA_CHARSET=utf8;
SELECT * from t1;
DROP TABLE t1;
#
# Explicit columns
#
CREATE TABLE t1 (
_id VARCHAR(24) NOT NULL,
name VARCHAR(255) NOT NULL,
cuisine VARCHAR(255) NOT NULL,
borough VARCHAR(255) NOT NULL,
restaurant_id VARCHAR(255) NOT NULL)
ENGINE=CONNECT TABLE_TYPE=MONGO TABNAME=restaurants
CONNECTION='mongodb://localhost:27017' DATA_CHARSET=utf8;
SELECT * FROM t1 LIMIT 10;
DROP TABLE t1;
#
# Test discovery
#
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=MONGO TABNAME=restaurants OPTION_LIST='Level=1,Version=3' DATA_CHARSET=utf8;
SHOW CREATE TABLE t1;
SELECT * FROM t1 LIMIT 5;
DROP TABLE t1;
#
# Dropping a column
#
CREATE TABLE t1
ENGINE=CONNECT TABLE_TYPE=MONGO TABNAME=restaurants DATA_CHARSET=utf8
COLIST='{"grades":0}' OPTION_LIST='Driver=java,level=0';
SELECT * FROM t1 LIMIT 10;
DROP TABLE t1;
#
# Specifying Jpath
#
CREATE TABLE t1 (
_id VARCHAR(24) NOT NULL,
name VARCHAR(64) NOT NULL,
cuisine CHAR(200) NOT NULL,
borough CHAR(16) NOT NULL,
street VARCHAR(65) FIELD_FORMAT='address.street',
building CHAR(16) FIELD_FORMAT='address.building',
zipcode CHAR(5) FIELD_FORMAT='address.zipcode',
grade CHAR(1) FIELD_FORMAT='grades.0.grade',
score INT(4) NOT NULL FIELD_FORMAT='grades.0.score',
`date` DATE FIELD_FORMAT='grades.0.date',
restaurant_id VARCHAR(255) NOT NULL)
ENGINE=CONNECT TABLE_TYPE=MONGO TABNAME='restaurants' DATA_CHARSET=utf8;
--vertical_results
SELECT * FROM t1 LIMIT 1;
--horizontal_results
SELECT name, street, score, date FROM t1 LIMIT 5;
SELECT name, cuisine, borough FROM t1 WHERE grade = 'A' LIMIT 10;
SELECT COUNT(*) FROM t1 WHERE grade = 'A';
SELECT * FROM t1 WHERE cuisine = 'English';
SELECT * FROM t1 WHERE score = building;
DROP TABLE t1;
-- source jdbconn_cleanup.inc
-- source jdbconn.inc
-- source mongo.inc
eval SET GLOBAL connect_class_path='$MTR_SUITE_DIR/std_data/Mongo2.jar';
let $DRV= Java;
let $VERS= 2;
let $TYPE= JSON;
let $CONN= CONNECTION='mongodb://localhost:27017' LRECL=4096;
-- source mongo_test.inc
-- source jdbconn_cleanup.inc
-- source jdbconn.inc
-- source mongo.inc
eval SET GLOBAL connect_class_path='$MTR_SUITE_DIR/std_data/Mongo3.jar';
let $DRV= Java;
let $VERS= 3;
let $TYPE= JSON;
let $CONN= CONNECTION='mongodb://localhost:27017' LRECL=4096;
-- source mongo_test.inc
-- source jdbconn_cleanup.inc
-- source mongo.inc
let $DRV= C;
let $VERS= 0;
let $PROJ= {"projection":;
let $ENDP= };
let $TYPE= JSON;
let $CONN= CONNECTION='mongodb://localhost:27017' LRECL=1024;
-- source mongo_test.inc
let $MONGO= C:/PROGRA~1/MongoDB/Server/3.4/bin/mongo;
let $MONGOIMPORT= C:/PROGRA~1/MongoDB/Server/3.4/bin/mongoimport;
-- source mongo.inc
let $DRV= C;
let $VERS= 0;
let $PROJ= {"projection":;
let $ENDP= };
let $TYPE= MONGO;
-- source mongo_test.inc
-- source jdbconn.inc
-- source mongo.inc
eval SET GLOBAL connect_class_path='$MTR_SUITE_DIR/std_data/Mongo2.jar';
let $DRV= Java;
let $VERS= 2;
let $TYPE= MONGO;
-- source mongo_test.inc
-- source jdbconn_cleanup.inc
-- source jdbconn.inc
-- source mongo.inc
eval SET GLOBAL connect_class_path='$MTR_SUITE_DIR/std_data/Mongo3.jar';
let $DRV= Java;
let $VERS= 3;
let $TYPE= MONGO;
-- source mongo_test.inc
-- source jdbconn_cleanup.inc
--echo #
--echo # Test the MONGO table type
--echo #
eval CREATE TABLE t1 (Document varchar(1024) field_format='*')
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME=restaurants $CONN
OPTION_LIST='Driver=$DRV,Version=$VERS' DATA_CHARSET=utf8;
SELECT * from t1 limit 3;
DROP TABLE t1;
--echo #
--echo # Test catfunc
--echo #
eval CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME=restaurants CATFUNC=columns
OPTION_LIST='Level=1,Driver=$DRV,Version=$VERS' DATA_CHARSET=utf8 $CONN;
SELECT * from t1;
DROP TABLE t1;
--echo #
--echo # Explicit columns
--echo #
eval CREATE TABLE t1 (
_id VARCHAR(24) NOT NULL,
name VARCHAR(255) NOT NULL,
cuisine VARCHAR(255) NOT NULL,
borough VARCHAR(255) NOT NULL,
restaurant_id VARCHAR(255) NOT NULL)
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME=restaurants
CONNECTION='mongodb://localhost:27017' LRECL=1024 DATA_CHARSET=utf8
OPTION_LIST='Driver=$DRV,Version=$VERS';
SELECT * FROM t1 LIMIT 10;
DROP TABLE t1;
--echo #
--echo # Test discovery
--echo #
eval CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME=restaurants
OPTION_LIST='Level=1,Driver=$DRV,Version=$VERS' $CONN DATA_CHARSET=utf8;
SHOW CREATE TABLE t1;
SELECT * FROM t1 LIMIT 5;
DROP TABLE t1;
--echo #
--echo # Dropping a column
--echo #
let $COLIST= $PROJ{"grades":0}$ENDP;
eval CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME=restaurants DATA_CHARSET=utf8
COLIST='$COLIST' OPTION_LIST='Driver=$DRV,Version=$VERS,level=0' $CONN;
SELECT * FROM t1 LIMIT 10;
DROP TABLE t1;
--echo #
--echo # Specifying Jpath
--echo #
eval CREATE TABLE t1 (
_id VARCHAR(24) NOT NULL,
name VARCHAR(64) NOT NULL,
cuisine CHAR(200) NOT NULL,
borough CHAR(16) NOT NULL,
street VARCHAR(65) FIELD_FORMAT='address.street',
building CHAR(16) FIELD_FORMAT='address.building',
zipcode CHAR(5) FIELD_FORMAT='address.zipcode',
grade CHAR(1) FIELD_FORMAT='grades.0.grade',
score INT(4) NOT NULL FIELD_FORMAT='grades.0.score',
`date` DATE FIELD_FORMAT='grades.0.date',
restaurant_id VARCHAR(255) NOT NULL)
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME='restaurants' DATA_CHARSET=utf8
OPTION_LIST='Driver=$DRV,Version=$VERS' $CONN;
--vertical_results
SELECT * FROM t1 LIMIT 1;
--horizontal_results
SELECT name, street, score, date FROM t1 LIMIT 5;
SELECT name, cuisine, borough FROM t1 WHERE grade = 'A' LIMIT 10;
SELECT COUNT(*) FROM t1 WHERE grade = 'A';
SELECT * FROM t1 WHERE cuisine = 'English';
SELECT * FROM t1 WHERE score = building;
DROP TABLE t1;
--echo #
--echo # Specifying Filter
--echo #
eval CREATE TABLE t1 (
_id CHAR(24) NOT NULL,
name CHAR(64) NOT NULL,
borough CHAR(16) NOT NULL,
restaurant_id CHAR(8) NOT NULL)
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME=restaurants DATA_CHARSET=utf8
FILTER='{"cuisine":"French","borough":{"\$ne":"Manhattan"}}'
OPTION_LIST='Driver=$DRV,Version=$VERS' $CONN;
SELECT name FROM t1 WHERE borough = 'Queens';
DROP TABLE t1;
--echo #
--echo # Testing pipeline
--echo #
eval CREATE TABLE t1 (
name VARCHAR(64) NOT NULL,
borough CHAR(16) NOT NULL,
date DATETIME NOT NULL,
grade CHAR(1) NOT NULL,
score INT(4) NOT NULL)
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME='restaurants' DATA_CHARSET=utf8
COLIST='{"pipeline":[{"\$match":{"cuisine":"French"}},{"\$unwind":"\$grades"},{"\$project":{"_id":0,"name":1,"borough":1,"date":"\$grades.date","grade":"\$grades.grade","score":"\$grades.score"}}]}'
OPTION_LIST='Driver=$DRV,Version=$VERS,Pipeline=1' $CONN;
SELECT * FROM t1 LIMIT 10;
SELECT name, grade, score, date FROM t1 WHERE borough = 'Bronx';
DROP TABLE t1;
--echo #
--echo # try level 2 discovery
--echo #
let $COLIST= $PROJ{"cuisine":0}$ENDP;
eval CREATE TABLE t1
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME=restaurants
FILTER='{"cuisine":"French","borough":{"\$ne":"Manhattan"}}'
COLIST='$COLIST' $CONN
OPTION_LIST='Driver=$DRV,level=2,version=$VERS';
SHOW CREATE TABLE t1;
IF ($TYPE == MONGO)
{
SELECT name, borough, address_street, grades_0_score AS score FROM t1 WHERE grades_0_grade = 'B';
}
IF ($TYPE == JSON)
{
SELECT name, borough, address_street, grades_score AS score FROM t1 WHERE grades_grade = 'B';
}
DROP TABLE t1;
--echo #
--echo # try CRUD operations
--echo #
--exec $MONGO --eval "db.testcoll.drop()" --quiet
eval CREATE TABLE t1 (_id INT(4) NOT NULL, msg CHAR(64))
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME='testcoll'
OPTION_LIST='Driver=$DRV,Version=$VERS' $CONN;
DELETE FROM t1;
INSERT INTO t1 VALUES(0,NULL),(1,'One'),(2,'Two'),(3,'Three');
SELECT * FROM t1;
UPDATE t1 SET msg = 'Deux' WHERE _id = 2;
DELETE FROM t1 WHERE msg IS NULL;
SELECT * FROM t1;
DELETE FROM t1;
DROP TABLE t1;
--exec $MONGO --eval "db.testcoll.drop()" --quiet
--echo #
--echo # List states whose population is equal or more than 10 millions
--echo #
--exec $MONGO --eval "db.cities.drop()" --quiet
--exec $MONGOIMPORT --quiet $MTR_SUITE_DIR/std_data/cities.json
eval CREATE TABLE t1 (
_id char(5) NOT NULL,
city char(16) NOT NULL,
loc_0 double(12,6) NOT NULL `FIELD_FORMAT`='loc.0',
loc_1 char(12) NOT NULL `FIELD_FORMAT`='loc.1',
pop int(11) NOT NULL,
state char(2) NOT NULL)
ENGINE=CONNECT CONNECTION='mongodb://localhost:27017' TABLE_TYPE='MONGO' TABNAME='cities'
OPTION_LIST='Driver=$DRV,Version=$VERS' $CONN DATA_CHARSET='utf8';
--echo # Using SQL for grouping
SELECT state, sum(pop) AS totalPop FROM t1 GROUP BY state HAVING totalPop >= 10000000 ORDER BY totalPop DESC;
DROP TABLE t1;
--echo # Using a pipeline for grouping
eval CREATE TABLE t1 (_id CHAR(2) NOT NULL, totalPop INT(11) NOT NULL)
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME='cities' DATA_CHARSET=utf8
COLIST='{"pipeline":[{"\$group":{"_id":"\$state","totalPop":{"\$sum":"\$pop"}}},{"\$match":{"totalPop":{"\$gte":10000000}}},{"\$sort":{"totalPop":-1}}]}'
OPTION_LIST='Driver=$DRV,Version=$VERS,Pipeline=1' $CONN;
SELECT * FROM t1;
DROP TABLE t1;
--exec $MONGO --eval "db.cities.drop()" --quiet
--echo #
--echo # Test making array
--echo #
eval CREATE TABLE t1 (
_id int(4) NOT NULL,
item CHAR(8) NOT NULL,
prices_0 INT(6) FIELD_FORMAT='prices.0',
prices_1 INT(6) FIELD_FORMAT='prices.1',
prices_2 INT(6) FIELD_FORMAT='prices.2',
prices_3 INT(6) FIELD_FORMAT='prices.3',
prices_4 INT(6) FIELD_FORMAT='prices.4')
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME='testcoll' DATA_CHARSET=utf8
OPTION_LIST='Driver=$DRV,Version=$VERS' $CONN;
INSERT INTO t1 VALUES
(1,'journal',87,45,63,12,78),
(2,'notebook',123,456,789,NULL,NULL),
(3,'paper',5,7,3,8,NULL),
(4,'planner',25,71,NULL,44,27),
(5,'postcard',5,7,3,8,NULL);
SELECT * FROM t1;
DROP TABLE t1;
--echo #
--echo # Test array aggregation
--echo #
eval CREATE TABLE t1
ENGINE=CONNECT TABLE_TYPE=$TYPE TABNAME='testcoll'
COLIST='{"pipeline":[{"\$project":{"_id":0,"item":1,"total":{"\$sum":"\$prices"},"average":{"\$avg":"\$prices"}}}]}'
OPTION_LIST='Driver=$DRV,Version=$VERS,Pipeline=YES' $CONN;
SELECT * FROM t1;
DROP TABLE t1;
--exec $MONGO --eval "db.testcoll.drop()" --quiet
-- source include/not_embedded.inc
--source include/not_embedded.inc
let $MYSQLD_DATADIR= `select @@datadir`;
let $PORT= `select @@port`;
......@@ -51,20 +51,3 @@ DROP TABLE t1;
DROP TABLE t2;
DROP TABLE t3;
DROP TABLE t4;
--echo #
--echo # Checking thread TBL tables
--echo #
CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 11 as v';
SELECT * FROM t1;
CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 22 as v';
SELECT * FROM t2;
--replace_result $PORT PORT
--eval CREATE TABLE total (v BIGINT(20) UNSIGNED NOT NULL) ENGINE=CONNECT TABLE_TYPE=TBL TABLE_LIST='t1,t2' OPTION_LIST='thread=yes,port=$PORT';
SELECT * FROM total order by v desc;
DROP TABLE total;
DROP TABLE t1;
DROP TABLE t2;
-- source myconn.inc
connection default;
let $PORT= `select @@port`;
--echo #
--echo # Checking thread TBL tables
--echo #
CREATE TABLE t1 (a int, b char(10));
INSERT INTO t1 VALUES (0,'test00'),(1,'test01'),(2,'test02'),(3,'test03');
SELECT * FROM t1;
connection master;
CREATE TABLE rt2 (a int, b char(10));
INSERT INTO rt2 VALUES (4,'test04'),(5,'test05'),(6,'test06'),(7,'test07');
SELECT * FROM rt2;
connection slave;
CREATE TABLE rt3 (a int, b char(10));
INSERT INTO rt3 VALUES (8,'test08'),(9,'test09'),(10,'test10'),(11,'test11');
SELECT * FROM rt3;
connection default;
--replace_result $MASTER_MYPORT MASTER_PORT
eval CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=MYSQL
CONNECTION='mysql://root@localhost:$MASTER_MYPORT/test/rt2';
SELECT * FROM t2;
--replace_result $SLAVE_MYPORT SLAVE_PORT
eval CREATE TABLE t3 ENGINE=CONNECT TABLE_TYPE=MYSQL
CONNECTION='mysql://root@localhost:$SLAVE_MYPORT/test/rt3';
SELECT * FROM t3;
--replace_result $PORT PORT
eval CREATE TABLE total (a int, b char(10))
ENGINE=CONNECT TABLE_TYPE=TBL TABLE_LIST='t1,t2,t3'
OPTION_LIST='thread=yes,port=$PORT';
SELECT * FROM total order by a desc;
connection master;
DROP TABLE rt2;
connection slave;
DROP TABLE rt3;
connection default;
DROP TABLE t1,t2,t3,total;
--echo #
--echo # Old thread TBL tables test
--echo #
--replace_result $MASTER_MYPORT MASTER_PORT
--eval CREATE TABLE t1 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 11 as v' OPTION_LIST='port=$MASTER_MYPORT'
SELECT * FROM t1;
--replace_result $SLAVE_MYPORT SLAVE_PORT
--eval CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=MYSQL SRCDEF='select 22 as v' OPTION_LIST='port=$SLAVE_MYPORT'
SELECT * FROM t2;
--replace_result $PORT PORT
--eval CREATE TABLE total (v BIGINT(20) UNSIGNED NOT NULL) ENGINE=CONNECT TABLE_TYPE=TBL TABLE_LIST='t1,t2' OPTION_LIST='thread=yes,port=$PORT';
SELECT * FROM total order by v desc;
DROP TABLE total;
DROP TABLE t1;
DROP TABLE t2;
-- source myconn_cleanup.inc
......@@ -968,6 +968,7 @@ ODBConn::ODBConn(PGLOBAL g, TDBODBC *tdbp)
m_Catver = (tdbp) ? tdbp->Catver : 0;
m_Rows = 0;
m_Fetch = 0;
m_Fp = NULL;
m_Connect = NULL;
m_User = NULL;
m_Pwd = NULL;
......@@ -1137,7 +1138,25 @@ int ODBConn::Open(PCSZ ConnectString, POPARM sop, DWORD options)
} else // Connect using SQLConnect
Connect();
/*ver = GetStringInfo(SQL_DRIVER_ODBC_VER);*/
/*********************************************************************/
/* Link a Fblock. This make possible to automatically close it */
/* in case of error (throw). */
/*********************************************************************/
PDBUSER dbuserp = (PDBUSER)g->Activityp->Aptr;
m_Fp = (PFBLOCK)PlugSubAlloc(g, NULL, sizeof(FBLOCK));
m_Fp->Type = TYPE_FB_ODBC;
m_Fp->Fname = NULL;
m_Fp->Next = dbuserp->Openlist;
dbuserp->Openlist = m_Fp;
m_Fp->Count = 1;
m_Fp->Length = 0;
m_Fp->Memory = NULL;
m_Fp->Mode = MODE_ANY;
m_Fp->File = this;
m_Fp->Handle = 0;
/*ver = GetStringInfo(SQL_DRIVER_ODBC_VER);*/
// Verify support for required functionality and cache info
// VerifyConnect(); Deprecated
GetConnectInfo();
......@@ -2598,4 +2617,7 @@ void ODBConn::Close()
m_henv = SQL_NULL_HENV;
} // endif m_henv
if (m_Fp)
m_Fp->Count = 0;
} // end of Close
......@@ -27,7 +27,7 @@
//efine MAX_DNAME_LEN 256 // Max size of Recordset names
#define MAX_CONNECT_LEN 1024 // Max size of Connect string
//efine MAX_CURSOR_NAME 18 // Max size of a cursor name
#define DEFAULT_FIELD_TYPE SQL_TYPE_NULL // pick "C" data type to match SQL data type
//efine DEFAULT_FIELD_TYPE SQL_TYPE_NULL // pick "C" data type to match SQL data type
#if !defined(__WIN__)
typedef unsigned char *PUCHAR;
......@@ -169,7 +169,7 @@ class ODBConn : public BLOCK {
bool DriverConnect(DWORD Options);
void VerifyConnect(void);
void GetConnectInfo(void);
void Free(void);
//void Free(void);
protected:
// Static members
......@@ -187,7 +187,8 @@ class ODBConn : public BLOCK {
DWORD m_UpdateOptions;
DWORD m_RowsetSize;
char m_IDQuoteChar[2];
PCSZ m_Connect;
PFBLOCK m_Fp;
PCSZ m_Connect;
PCSZ m_User;
PCSZ m_Pwd;
int m_Catver;
......
......@@ -48,7 +48,10 @@ enum BLKTYP {TYPE_TABLE = 50, /* Table Name/Srcdef/... Block */
TYPE_FB_HANDLE = 24, /* File block (handle) */
TYPE_FB_XML = 21, /* DOM XML file block */
TYPE_FB_XML2 = 27, /* libxml2 XML file block */
TYPE_FB_ZIP = 28}; /* ZIP file block */
TYPE_FB_ODBC = 25, /* ODBC file block */
TYPE_FB_ZIP = 28, /* ZIP file block */
TYPE_FB_JAVA = 29, /* JAVA file block */
TYPE_FB_MONGO = 30}; /* MONGO file block */
enum TABTYPE {TAB_UNDEF = 0, /* Table of undefined type */
TAB_DOS = 1, /* Fixed column offset, variable LRECL */
......
......@@ -68,9 +68,20 @@
#include "tabcol.h" // header of XTAB and COLUMN classes
#include "valblk.h"
#include "rcmsg.h"
#if defined(ODBC_SUPPORT)
#include "tabext.h"
#include "odbccat.h"
#include "tabodbc.h"
#endif // ODBC_SUPPORT
#ifdef ZIP_SUPPORT
#include "filamzip.h"
#endif // ZIP_SUPPORT
#endif // ZIP_SUPPORT
#ifdef JDBC_SUPPORT
#include "javaconn.h"
#endif // JDBC_SUPPORT
#ifdef CMGO_SUPPORT
#include "cmgoconn.h"
#endif // MONGO_SUPPORT
/***********************************************************************/
/* DB static variables. */
......@@ -923,6 +934,13 @@ int PlugCloseFile(PGLOBAL g __attribute__((unused)), PFBLOCK fp, bool all)
CloseXML2File(g, fp, all);
break;
#endif // LIBXML2_SUPPORT
#ifdef ODBC_SUPPORT
case TYPE_FB_ODBC:
((ODBConn*)fp->File)->Close();
fp->Count = 0;
fp->File = NULL;
break;
#endif // ODBC_SUPPORT
#ifdef ZIP_SUPPORT
case TYPE_FB_ZIP:
if (fp->Mode == MODE_INSERT)
......@@ -936,6 +954,20 @@ int PlugCloseFile(PGLOBAL g __attribute__((unused)), PFBLOCK fp, bool all)
fp->File = NULL;
break;
#endif // ZIP_SUPPORT
#ifdef JDBC_SUPPORT
case TYPE_FB_JAVA:
((JAVAConn*)fp->File)->Close();
fp->Count = 0;
fp->File = NULL;
break;
#endif // JDBC_SUPPORT
#ifdef CMGO_SUPPORT
case TYPE_FB_MONGO:
((CMgoConn*)fp->File)->Close();
fp->Count = 0;
fp->File = NULL;
break;
#endif // MONGO_SUPPORT
default:
rc = RC_FX;
} // endswitch Type
......
......@@ -309,6 +309,8 @@ bool TDBCMG::OpenDB(PGLOBAL g)
return true;
} // endif Pipe
Use = USE_OPEN; // Do it now in case we are recursively called
if (Init(g))
return true;
......
......@@ -312,6 +312,8 @@ bool TDBJMG::OpenDB(PGLOBAL g)
return true;
} // endif Pipe
Use = USE_OPEN; // Do it now in case we are recursively called
if (Init(g))
return true;
......
......@@ -34,7 +34,7 @@
#if defined(JDBC_SUPPORT)
#include "jmgfam.h"
#endif // JDBC_SUPPORT
#if defined(MONGO_SUPPORT)
#if defined(CMGO_SUPPORT)
#include "cmgfam.h"
#endif // MONGO_SUPPORT
#include "tabmul.h"
......@@ -129,8 +129,8 @@ PQRYRES JSONColumns(PGLOBAL g, PCSZ db, PCSZ dsn, PTOS topt, bool info)
#endif // ZIP_SUPPORT
tdp->Fn = GetStringTableOption(g, topt, "Filename", NULL);
if (!(tdp->Database = SetPath(g, db)))
return NULL;
//if (!(tdp->Database = SetPath(g, db)))
// return NULL;
tdp->Objname = GetStringTableOption(g, topt, "Object", NULL);
tdp->Base = GetIntegerTableOption(g, topt, "Base", 0) ? 1 : 0;
......@@ -148,22 +148,23 @@ PQRYRES JSONColumns(PGLOBAL g, PCSZ db, PCSZ dsn, PTOS topt, bool info)
tdp->Fn, tdp->Objname, tdp->Pretty, lvl);
if (tdp->Uri) {
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
tdp->Collname = GetStringTableOption(g, topt, "Name", NULL);
tdp->Collname = GetStringTableOption(g, topt, "Tabname", tdp->Collname);
tdp->Schema = GetStringTableOption(g, topt, "Dbname", "test");
tdp->Options = (PSZ)GetStringTableOption(g, topt, "Colist", "all");
tdp->Pipe = GetBooleanTableOption(g, topt, "Pipeline", false);
tdp->Driver = (PSZ)GetStringTableOption(g, topt, "Driver", NULL);
tdp->Version = GetIntegerTableOption(g, topt, "Version", 3);
#if defined(JDBC_SUPPORT)
tdp->Wrapname = (PSZ)GetStringTableOption(g, topt, "Wrapper",
(tdp->Version == 2) ? "Mongo2Interface" : "Mongo3Interface");
#endif // JDBC_SUPPORT
tdp->Pretty = 0;
#else // !MONGO_SUPPORT || JDBC_SUPPORT
#else // !MONGO_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "MONGO");
return NULL;
#endif // !MONGO_SUPPORT || JDBC_SUPPORT
#endif // !MONGO_SUPPORT
} // endif Uri
if (tdp->Pretty == 2) {
......@@ -199,21 +200,32 @@ PQRYRES JSONColumns(PGLOBAL g, PCSZ db, PCSZ dsn, PTOS topt, bool info)
return NULL;
#endif // !ZIP_SUPPORT
} else if (tdp->Uri) {
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if !defined(JDBC_SUPPORT)
tjnp = new(g) TDBJSN(tdp, new(g) CMGFAM(tdp));
#elif !defined(MONGO_SUPPORT)
tjnp = new(g) TDBJSN(tdp, new(g) JMGFAM(tdp));
#if defined(MONGO_SUPPORT)
if (tdp->Driver && toupper(*tdp->Driver) == 'C') {
#if defined(CMGO_SUPPORT)
tjnp = new(g) TDBJSN(tdp, new(g) CMGFAM(tdp));
#else
sprintf(g->Message, "Mongo %s Driver not available", "C");
return NULL;
#endif
} else if (tdp->Driver && toupper(*tdp->Driver) == 'J') {
#if defined(JDBC_SUPPORT)
tjnp = new(g) TDBJSN(tdp, new(g) JMGFAM(tdp));
#else
if (tdp->Driver && toupper(*tdp->Driver) == 'C')
sprintf(g->Message, "Mongo %s Driver not available", "Java");
return NULL;
#endif
} else { // Driver not specified
#if defined(CMGO_SUPPORT)
tjnp = new(g) TDBJSN(tdp, new(g) CMGFAM(tdp));
else
#else
tjnp = new(g) TDBJSN(tdp, new(g) JMGFAM(tdp));
#endif
#else // !MONGO_SUPPORT && !JDBC_SUPPORT
sprintf(g->Message, "No MongoDB support");
} // endif Driver
#else
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "MONGO");
return NULL;
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
} else
tjnp = new(g) TDBJSN(tdp, new(g) DOSFAM(tdp));
......@@ -484,16 +496,16 @@ JSONDEF::JSONDEF(void)
Base = 0;
Strict = false;
Sep = '.';
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
Uri = NULL;
Collname = Schema = Options = Filter = NULL;
Pipe = false;
Driver = NULL;
Version = 0;
#endif // MONGO_SUPPORT
#if defined(JDBC_SUPPORT)
Wrapname = NULL;
#endif // JDBC_SUPPORT
#endif // !MONGO_SUPPORT && !JDBC_SUPPORT
} // end of JSONDEF constructor
/***********************************************************************/
......@@ -510,7 +522,7 @@ bool JSONDEF::DefineAM(PGLOBAL g, LPCSTR, int poff)
Sep = *GetStringCatInfo(g, "Separator", ".");
if (Uri = GetStringCatInfo(g, "Connect", NULL)) {
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
Collname = GetStringCatInfo(g, "Name",
(Catfunc & (FNC_TABLE | FNC_COL)) ? NULL : Name);
Collname = GetStringCatInfo(g, "Tabname", Collname);
......@@ -527,10 +539,10 @@ bool JSONDEF::DefineAM(PGLOBAL g, LPCSTR, int poff)
else
Wrapname = GetStringCatInfo(g, "Wrapper", "Mongo3Interface");
#endif // JDBC_SUPPORT
#else // !MONGO_SUPPORT && !JDBC_SUPPORT
#else // !MONGO_SUPPORT
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "MONGO");
return true;
#endif // !MONGO_SUPPORT && !JDBC_SUPPORT
#endif // !MONGO_SUPPORT
} // endif Uri
return DOSDEF::DefineAM(g, (Uri ? "XMGO" : "DOS"), poff);
......@@ -556,18 +568,32 @@ PTDB JSONDEF::GetTable(PGLOBAL g, MODE m)
(m == MODE_UPDATE || m == MODE_DELETE));
if (Uri) {
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if !defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
if (Driver && toupper(*Driver) == 'C') {
#if defined(CMGO_SUPPORT)
txfp = new(g) CMGFAM(this);
#elif !defined(MONGO_SUPPORT)
txfp = new(g) JMGFAM(this);
#else
if (Driver && toupper(*Driver) == 'C')
sprintf(g->Message, "Mongo %s Driver not available", "C");
return NULL;
#endif
} else if (Driver && toupper(*Driver) == 'J') {
#if defined(JDBC_SUPPORT)
txfp = new(g) JMGFAM(this);
#else
sprintf(g->Message, "Mongo %s Driver not available", "Java");
return NULL;
#endif
} else { // Driver not specified
#if defined(CMGO_SUPPORT)
txfp = new(g) CMGFAM(this);
else
#else
txfp = new(g) JMGFAM(this);
#endif
#endif // MONGO_SUPPORT || JDBC_SUPPORT
} // endif Driver
#else
sprintf(g->Message, MSG(NO_FEAT_SUPPORT), "MONGO");
return NULL;
#endif // MONGO_SUPPORT
} else if (Zipped) {
#if defined(ZIP_SUPPORT)
if (m == MODE_READ || m == MODE_ANY || m == MODE_ALTER) {
......@@ -2250,7 +2276,11 @@ void TDBJSON::CloseDB(PGLOBAL g)
TDBJCL::TDBJCL(PJDEF tdp) : TDBCAT(tdp)
{
Topt = tdp->GetTopt();
Db = tdp->GetDB();
#if defined(MONGO_SUPPORT)
Db = tdp->Schema;
#else
Db = NULL;
#endif
Dsn = tdp->Uri;
} // end of TDBJCL constructor
......
......@@ -36,11 +36,11 @@ class DllExport JSONDEF : public DOSDEF { /* Table description */
friend class TDBJSON;
friend class TDBJSN;
friend class TDBJCL;
#if defined(MONGO_SUPPORT)
friend class CMGFAM;
#if defined(JDBC_SUPPORT)
friend class JMGFAM;
#endif // JDBC_SUPPORT
#if defined(MONGO_SUPPORT)
friend class CMGFAM;
#endif // MONGO_SUPPORT
friend PQRYRES JSONColumns(PGLOBAL, PCSZ, PCSZ, PTOS, bool);
public:
......@@ -66,7 +66,7 @@ class DllExport JSONDEF : public DOSDEF { /* Table description */
bool Strict; /* Strict syntax checking */
char Sep; /* The Jpath separator */
const char *Uri; /* MongoDB connection URI */
#if defined(MONGO_SUPPORT) || defined(JDBC_SUPPORT)
#if defined(MONGO_SUPPORT)
PCSZ Collname; /* External collection name */
PCSZ Schema; /* External schema (DB) name */
PSZ Options; /* Colist ; Pipe */
......@@ -77,7 +77,7 @@ class DllExport JSONDEF : public DOSDEF { /* Table description */
#if defined(JDBC_SUPPORT)
PSZ Wrapname; /* MongoDB java wrapper name */
#endif // JDBC_SUPPORT
#endif // MONGO_SUPPORT || JDBC_SUPPORT
#endif // MONGO_SUPPORT
}; // end of JSONDEF
/* -------------------------- TDBJSN class --------------------------- */
......@@ -89,11 +89,11 @@ class DllExport JSONDEF : public DOSDEF { /* Table description */
class DllExport TDBJSN : public TDBDOS {
friend class JSONCOL;
friend class JSONDEF;
#if defined(MONGO_SUPPORT)
friend class CMGFAM;
#if defined(JDBC_SUPPORT)
friend class JMGFAM;
#endif // JDBC_SUPPORT
#if defined(MONGO_SUPPORT)
friend class CMGFAM;
#endif // MONGO_SUPPORT
public:
// Constructor
......
......@@ -84,6 +84,8 @@
#define SYSEXIT void *
#endif // !__WIN__
extern pthread_mutex_t tblmut;
/* ---------------------------- Class TBLDEF ---------------------------- */
/**************************************************************************/
......@@ -575,8 +577,10 @@ pthread_handler_t ThreadOpen(void *p)
// Try to open the connection
if (!cmp->Tap->GetTo_Tdb()->OpenDB(cmp->G)) {
cmp->Ready = true;
} else
pthread_mutex_lock(&tblmut);
cmp->Ready = true;
pthread_mutex_unlock(&tblmut);
} else
cmp->Rc = RC_FX;
my_thread_end();
......@@ -792,14 +796,19 @@ int TDBTBM::ReadNextRemote(PGLOBAL g)
retry:
// Search for a remote table having its result set
for (PTBMT tp = Tmp; tp; tp = tp->Next)
pthread_mutex_lock(&tblmut);
for (PTBMT tp = Tmp; tp; tp = tp->Next)
if (tp->Ready) {
if (!tp->Complete)
Cmp = tp;
if (!tp->Complete) {
Cmp = tp;
break;
} // endif Complete
} else
b = true;
pthread_mutex_unlock(&tblmut);
if (!Cmp) {
if (b) { // more result to come
// sleep(20);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment