diff --git a/storage/connect/colblk.h b/storage/connect/colblk.h index 93d39524362..d004b96b5b3 100644 --- a/storage/connect/colblk.h +++ b/storage/connect/colblk.h @@ -1,205 +1,206 @@ -/*************** Colblk H Declares Source Code File (.H) ***************/ -/* Name: COLBLK.H Version 1.7 */ -/* */ -/* (C) Copyright to the author Olivier BERTRAND 2005-2014 */ -/* */ -/* This file contains the COLBLK and derived classes declares. */ -/***********************************************************************/ -#ifndef __COLBLK__H -#define __COLBLK__H - -/***********************************************************************/ -/* Include required application header files */ -/***********************************************************************/ -#include "xobject.h" -#include "reldef.h" - -/***********************************************************************/ -/* Class COLBLK: Base class for table column descriptors. */ -/***********************************************************************/ -class DllExport COLBLK : public XOBJECT { - friend class TDBPIVOT; - protected: - // Default constructors used by derived classes - COLBLK(PCOLDEF cdp = NULL, PTDB tdbp = NULL, int i = 0); - COLBLK(PCOL colp, PTDB tdbp = NULL); // Used in copy process - COLBLK(int n) {} // Used when changing a column class in TDBXML - - public: - // Implementation - virtual int GetType(void) {return TYPE_COLBLK;} - virtual int GetResultType(void) {return Buf_Type;} - virtual int GetScale(void) {return Format.Prec;} - virtual int GetPrecision(void) {return Precision;} - virtual int GetLength(void) {return Long;} - virtual int GetLengthEx(void); - virtual int GetAmType() {return TYPE_AM_ERROR;} - virtual void SetOk(void) {Status |= BUF_EMPTY;} - virtual PTDB GetTo_Tdb(void) {return To_Tdb;} - virtual int GetClustered(void) {return 0;} - virtual int IsClustered(void) {return FALSE;} - PCOL GetNext(void) {return Next;} - PSZ GetName(void) {return Name;} - int GetIndex(void) {return Index;} - ushort GetColUse(void) {return ColUse;} - int GetOpt(void) {return Opt;} - ushort GetColUse(ushort u) {return (ColUse & u);} - ushort GetStatus(void) {return Status;} - ushort GetStatus(ushort u) {return (Status & u);} - void SetColUse(ushort u) {ColUse = u;} - void SetStatus(ushort u) {Status = u;} - void AddColUse(ushort u) {ColUse |= u;} - void AddStatus(ushort u) {Status |= u;} - void SetNext(PCOL cp) {Next = cp;} - PXCOL GetKcol(void) {return To_Kcol;} - void SetKcol(PXCOL kcp) {To_Kcol = kcp;} - PCOLDEF GetCdp(void) {return Cdp;} - PSZ GetDomain(void) {return (Cdp) ? Cdp->Decode : NULL;} - PSZ GetDesc(void) {return (Cdp) ? Cdp->Desc : NULL;} - PSZ GetFmt(void) {return (Cdp) ? Cdp->Fmt : NULL;} - bool IsUnsigned(void) {return Unsigned;} - bool IsNullable(void) {return Nullable;} - void SetNullable(bool b) {Nullable = b;} - - // Methods - virtual void Reset(void); - virtual bool Compare(PXOB xp); - virtual bool SetFormat(PGLOBAL, FORMAT&); - virtual bool IsSpecial(void) {return false;} - virtual bool Eval(PGLOBAL g); - virtual bool SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check); - virtual void SetTo_Val(PVAL valp) {} - virtual void ReadColumn(PGLOBAL g); - virtual void WriteColumn(PGLOBAL g); - virtual void Print(PGLOBAL g, FILE *, uint); - virtual void Print(PGLOBAL g, char *, uint); - virtual bool VarSize(void) {return false;} - bool InitValue(PGLOBAL g); - - protected: - // Members - PCOL Next; // Next column in table - PSZ Name; // Column name - PCOLDEF Cdp; // To column definition block - PTDB To_Tdb; // Points to Table Descriptor Block - PXCOL To_Kcol; // Points to Xindex matching column - bool Nullable; // True if nullable - bool Unsigned; // True if unsigned - int Index; // Column number in table - int Opt; // Cluster/sort information - int Buf_Type; // Data type - int Long; // Internal length in table - int Precision; // Column length (as for ODBC) - int Freq; // Evaluated ceiling of distinct values - FORMAT Format; // Output format - ushort ColUse; // Column usage - ushort Status; // Column read status - }; // end of class COLBLK - -/***********************************************************************/ -/* Class SPCBLK: Base class for special column descriptors. */ -/***********************************************************************/ -class DllExport SPCBLK : public COLBLK { - public: - // Constructor - SPCBLK(PCOLUMN cp); - - // Implementation - virtual int GetAmType(void) = 0; - virtual bool GetRnm(void) {return false;} - - // Methods - virtual bool IsSpecial(void) {return true;} - virtual void ReadColumn(PGLOBAL g) = 0; - virtual void WriteColumn(PGLOBAL g); - - protected: - // Default constructor not to be used - SPCBLK(void) : COLBLK(1) {} - }; // end of class SPCBLK - -/***********************************************************************/ -/* Class RIDBLK: ROWID special column descriptor. */ -/***********************************************************************/ -class DllExport RIDBLK : public SPCBLK { - public: - // Constructor - RIDBLK(PCOLUMN cp, bool rnm); - - // Implementation - virtual int GetAmType(void) {return TYPE_AM_ROWID;} - virtual bool GetRnm(void) {return Rnm;} - - // Methods - virtual void ReadColumn(PGLOBAL g); - - protected: - bool Rnm; // False for RowID, True for RowNum - }; // end of class RIDBLK - -/***********************************************************************/ -/* Class FIDBLK: FILEID special column descriptor. */ -/***********************************************************************/ -class DllExport FIDBLK : public SPCBLK { - public: - // Constructor - FIDBLK(PCOLUMN cp); - - // Implementation - virtual int GetAmType(void) {return TYPE_AM_FILID;} - - // Methods - virtual void Reset(void) {} // This is a pseudo constant column - virtual void ReadColumn(PGLOBAL g); - - protected: - PSZ Fn; // The current To_File of the table - }; // end of class FIDBLK - -/***********************************************************************/ -/* Class TIDBLK: TABID special column descriptor. */ -/***********************************************************************/ -class DllExport TIDBLK : public SPCBLK { - public: - // Constructor - TIDBLK(PCOLUMN cp); - - // Implementation - virtual int GetAmType(void) {return TYPE_AM_TABID;} - - // Methods - virtual void Reset(void) {} // This is a pseudo constant column - virtual void ReadColumn(PGLOBAL g); - - protected: - // Default constructor not to be used - TIDBLK(void) {} - - // Members - PSZ Tname; // The current table name - }; // end of class TIDBLK - -/***********************************************************************/ -/* Class SIDBLK: SERVID special column descriptor. */ -/***********************************************************************/ -class DllExport SIDBLK : public SPCBLK { - public: - // Constructor - SIDBLK(PCOLUMN cp); - - // Implementation - virtual int GetAmType(void) {return TYPE_AM_SRVID;} - - // Methods - virtual void Reset(void) {} // This is a pseudo constant column - virtual void ReadColumn(PGLOBAL g); - - protected: - // Default constructor not to be used - SIDBLK(void) {} - - // Members - PSZ Sname; // The current server name - }; // end of class SIDBLK - -#endif // __COLBLK__H +/*************** Colblk H Declares Source Code File (.H) ***************/ +/* Name: COLBLK.H Version 1.7 */ +/* */ +/* (C) Copyright to the author Olivier BERTRAND 2005-2014 */ +/* */ +/* This file contains the COLBLK and derived classes declares. */ +/***********************************************************************/ +#ifndef __COLBLK__H +#define __COLBLK__H + +/***********************************************************************/ +/* Include required application header files */ +/***********************************************************************/ +#include "xobject.h" +#include "reldef.h" + +/***********************************************************************/ +/* Class COLBLK: Base class for table column descriptors. */ +/***********************************************************************/ +class DllExport COLBLK : public XOBJECT { + friend class TDBPIVOT; + protected: + // Default constructors used by derived classes + COLBLK(PCOLDEF cdp = NULL, PTDB tdbp = NULL, int i = 0); + COLBLK(PCOL colp, PTDB tdbp = NULL); // Used in copy process + COLBLK(int n) {} // Used when changing a column class in TDBXML + + public: + // Implementation + virtual int GetType(void) {return TYPE_COLBLK;} + virtual int GetResultType(void) {return Buf_Type;} + virtual int GetScale(void) {return Format.Prec;} + virtual int GetPrecision(void) {return Precision;} + virtual int GetLength(void) {return Long;} + virtual int GetLengthEx(void); + virtual int GetAmType() {return TYPE_AM_ERROR;} + virtual void SetOk(void) {Status |= BUF_EMPTY;} + virtual PTDB GetTo_Tdb(void) {return To_Tdb;} + virtual int GetClustered(void) {return 0;} + virtual int IsClustered(void) {return FALSE;} + PCOL GetNext(void) {return Next;} + PSZ GetName(void) {return Name;} + int GetIndex(void) {return Index;} + ushort GetColUse(void) {return ColUse;} + int GetOpt(void) {return Opt;} + ushort GetColUse(ushort u) {return (ColUse & u);} + ushort GetStatus(void) {return Status;} + ushort GetStatus(ushort u) {return (Status & u);} + void SetColUse(ushort u) {ColUse = u;} + void SetStatus(ushort u) {Status = u;} + void AddColUse(ushort u) {ColUse |= u;} + void AddStatus(ushort u) {Status |= u;} + void SetNext(PCOL cp) {Next = cp;} + PXCOL GetKcol(void) {return To_Kcol;} + void SetKcol(PXCOL kcp) {To_Kcol = kcp;} + PCOLDEF GetCdp(void) {return Cdp;} + PSZ GetDomain(void) {return (Cdp) ? Cdp->Decode : NULL;} + PSZ GetDesc(void) {return (Cdp) ? Cdp->Desc : NULL;} + PSZ GetFmt(void) {return (Cdp) ? Cdp->Fmt : NULL;} + bool IsUnsigned(void) {return Unsigned;} + bool IsVirtual(void) {return Cdp->IsVirtual();} + bool IsNullable(void) {return Nullable;} + void SetNullable(bool b) {Nullable = b;} + + // Methods + virtual void Reset(void); + virtual bool Compare(PXOB xp); + virtual bool SetFormat(PGLOBAL, FORMAT&); + virtual bool IsSpecial(void) {return false;} + virtual bool Eval(PGLOBAL g); + virtual bool SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check); + virtual void SetTo_Val(PVAL valp) {} + virtual void ReadColumn(PGLOBAL g); + virtual void WriteColumn(PGLOBAL g); + virtual void Print(PGLOBAL g, FILE *, uint); + virtual void Print(PGLOBAL g, char *, uint); + virtual bool VarSize(void) {return false;} + bool InitValue(PGLOBAL g); + + protected: + // Members + PCOL Next; // Next column in table + PSZ Name; // Column name + PCOLDEF Cdp; // To column definition block + PTDB To_Tdb; // Points to Table Descriptor Block + PXCOL To_Kcol; // Points to Xindex matching column + bool Nullable; // True if nullable + bool Unsigned; // True if unsigned + int Index; // Column number in table + int Opt; // Cluster/sort information + int Buf_Type; // Data type + int Long; // Internal length in table + int Precision; // Column length (as for ODBC) + int Freq; // Evaluated ceiling of distinct values + FORMAT Format; // Output format + ushort ColUse; // Column usage + ushort Status; // Column read status + }; // end of class COLBLK + +/***********************************************************************/ +/* Class SPCBLK: Base class for special column descriptors. */ +/***********************************************************************/ +class DllExport SPCBLK : public COLBLK { + public: + // Constructor + SPCBLK(PCOLUMN cp); + + // Implementation + virtual int GetAmType(void) = 0; + virtual bool GetRnm(void) {return false;} + + // Methods + virtual bool IsSpecial(void) {return true;} + virtual void ReadColumn(PGLOBAL g) = 0; + virtual void WriteColumn(PGLOBAL g); + + protected: + // Default constructor not to be used + SPCBLK(void) : COLBLK(1) {} + }; // end of class SPCBLK + +/***********************************************************************/ +/* Class RIDBLK: ROWID special column descriptor. */ +/***********************************************************************/ +class DllExport RIDBLK : public SPCBLK { + public: + // Constructor + RIDBLK(PCOLUMN cp, bool rnm); + + // Implementation + virtual int GetAmType(void) {return TYPE_AM_ROWID;} + virtual bool GetRnm(void) {return Rnm;} + + // Methods + virtual void ReadColumn(PGLOBAL g); + + protected: + bool Rnm; // False for RowID, True for RowNum + }; // end of class RIDBLK + +/***********************************************************************/ +/* Class FIDBLK: FILEID special column descriptor. */ +/***********************************************************************/ +class DllExport FIDBLK : public SPCBLK { + public: + // Constructor + FIDBLK(PCOLUMN cp); + + // Implementation + virtual int GetAmType(void) {return TYPE_AM_FILID;} + + // Methods + virtual void Reset(void) {} // This is a pseudo constant column + virtual void ReadColumn(PGLOBAL g); + + protected: + PSZ Fn; // The current To_File of the table + }; // end of class FIDBLK + +/***********************************************************************/ +/* Class TIDBLK: TABID special column descriptor. */ +/***********************************************************************/ +class DllExport TIDBLK : public SPCBLK { + public: + // Constructor + TIDBLK(PCOLUMN cp); + + // Implementation + virtual int GetAmType(void) {return TYPE_AM_TABID;} + + // Methods + virtual void Reset(void) {} // This is a pseudo constant column + virtual void ReadColumn(PGLOBAL g); + + protected: + // Default constructor not to be used + TIDBLK(void) {} + + // Members + PSZ Tname; // The current table name + }; // end of class TIDBLK + +/***********************************************************************/ +/* Class SIDBLK: SERVID special column descriptor. */ +/***********************************************************************/ +class DllExport SIDBLK : public SPCBLK { + public: + // Constructor + SIDBLK(PCOLUMN cp); + + // Implementation + virtual int GetAmType(void) {return TYPE_AM_SRVID;} + + // Methods + virtual void Reset(void) {} // This is a pseudo constant column + virtual void ReadColumn(PGLOBAL g); + + protected: + // Default constructor not to be used + SIDBLK(void) {} + + // Members + PSZ Sname; // The current server name + }; // end of class SIDBLK + +#endif // __COLBLK__H diff --git a/storage/connect/ha_connect.cc b/storage/connect/ha_connect.cc index 297af710ba8..e7aeddf38fb 100644 --- a/storage/connect/ha_connect.cc +++ b/storage/connect/ha_connect.cc @@ -1103,6 +1103,7 @@ void *ha_connect::GetColumnOption(PGLOBAL g, void *field, PCOLINFO pcf) break; case TYPE_DECIM: pcf->Precision= ((Field_new_decimal*)fp)->precision; + pcf->Length= pcf->Precision; pcf->Scale= fp->decimals(); break; case TYPE_DATE: @@ -4752,7 +4753,6 @@ static int connect_assisted_discovery(handlerton *hton, THD* thd, strncpy(dsn, create_info->connect_string.str, len); dsn[len]= 0; mydef->SetName(create_info->alias); - mydef->SetCat(cat); if (!mydef->ParseURL(g, dsn, false)) { if (mydef->GetHostname()) @@ -5231,21 +5231,18 @@ int ha_connect::create(const char *name, TABLE *table_arg, int port; host= GetListOption(g, "host", options->oplist, NULL); - db= GetListOption(g, "database", options->oplist, NULL); + db= GetStringOption("database", NULL); port= atoi(GetListOption(g, "port", options->oplist, "0")); if (create_info->connect_string.str) { char *dsn; int len= create_info->connect_string.length; PMYDEF mydef= new(g) MYSQLDEF(); - PDBUSER dup= PlgGetUser(g); - PCATLG cat= (dup) ? dup->Catalog : NULL; dsn= (char*)PlugSubAlloc(g, NULL, len + 1); strncpy(dsn, create_info->connect_string.str, len); dsn[len]= 0; mydef->SetName(create_info->alias); - mydef->SetCat(cat); if (!mydef->ParseURL(g, dsn, false)) { if (mydef->GetHostname()) diff --git a/storage/connect/mysql-test/connect/r/csv.result b/storage/connect/mysql-test/connect/r/csv.result index 3f424964881..be25a842bc4 100644 --- a/storage/connect/mysql-test/connect/r/csv.result +++ b/storage/connect/mysql-test/connect/r/csv.result @@ -52,9 +52,9 @@ children SMALLINT(2) NOT NULL INSERT INTO t1 VALUES ('BILL','1973-06-30',5); ERROR HY000: Table 't1' is read only UPDATE t1 SET children=6 WHERE name='BILL'; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT DELETE FROM t1 WHERE name='BILL'; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT TRUNCATE TABLE t1; ERROR HY000: Table 't1' is read only SELECT * FROM t1; diff --git a/storage/connect/mysql-test/connect/r/dbf.result b/storage/connect/mysql-test/connect/r/dbf.result index 30fac687119..d7b3fe0f114 100644 --- a/storage/connect/mysql-test/connect/r/dbf.result +++ b/storage/connect/mysql-test/connect/r/dbf.result @@ -77,9 +77,9 @@ t1 CREATE TABLE `t1` ( INSERT INTO t1 VALUES (30); ERROR HY000: Table 't1' is read only UPDATE t1 SET a=30 WHERE a=10; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT DELETE FROM t1 WHERE a=10; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT TRUNCATE TABLE t1; ERROR HY000: Table 't1' is read only ALTER TABLE t1 READONLY=NO; diff --git a/storage/connect/mysql-test/connect/r/fix.result b/storage/connect/mysql-test/connect/r/fix.result index a93948bb9c6..4d620c66a04 100644 --- a/storage/connect/mysql-test/connect/r/fix.result +++ b/storage/connect/mysql-test/connect/r/fix.result @@ -30,9 +30,9 @@ t1 CREATE TABLE `t1` ( INSERT INTO t1 VALUES (20); ERROR HY000: Table 't1' is read only UPDATE t1 SET id=20 WHERE id=10; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT DELETE FROM t1 WHERE id=10; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT TRUNCATE TABLE t1; ERROR HY000: Table 't1' is read only ALTER TABLE t1 READONLY=0; diff --git a/storage/connect/mysql-test/connect/r/ini.result b/storage/connect/mysql-test/connect/r/ini.result index 79996eb8525..a377cb3ee20 100644 --- a/storage/connect/mysql-test/connect/r/ini.result +++ b/storage/connect/mysql-test/connect/r/ini.result @@ -194,9 +194,9 @@ t1 CREATE TABLE `t1` ( INSERT INTO t1 VALUES ('US',40); ERROR HY000: Table 't1' is read only UPDATE t1 SET c2=20 WHERE c2=10; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT DELETE FROM t1 WHERE c2=10; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT TRUNCATE TABLE t1; ERROR HY000: Table 't1' is read only ALTER TABLE t1 READONLY=0; diff --git a/storage/connect/mysql-test/connect/r/vec.result b/storage/connect/mysql-test/connect/r/vec.result index e93305fb07a..51fb8aeee77 100644 --- a/storage/connect/mysql-test/connect/r/vec.result +++ b/storage/connect/mysql-test/connect/r/vec.result @@ -103,9 +103,9 @@ t1 CREATE TABLE `t1` ( INSERT INTO t1 VALUES (4,'test04'); ERROR HY000: Table 't1' is read only UPDATE t1 SET b='test04' WHERE a=3; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT DELETE FROM t1 WHERE a=3; -ERROR HY000: Table 't1' is read only +ERROR HY000: Got error 174 'Cannot modify this read/only protected table' from CONNECT TRUNCATE TABLE t1; ERROR HY000: Table 't1' is read only ALTER TABLE t1 READONLY=no; diff --git a/storage/connect/mysql-test/connect/t/csv.test b/storage/connect/mysql-test/connect/t/csv.test index a21686d8a08..5662fdb705b 100644 --- a/storage/connect/mysql-test/connect/t/csv.test +++ b/storage/connect/mysql-test/connect/t/csv.test @@ -1,185 +1,185 @@ -let $MYSQLD_DATADIR= `select @@datadir`; - ---copy_file $MTR_SUITE_DIR/std_data/people.csv $MYSQLD_DATADIR/test/people.csv - -SET NAMES utf8; - ---echo # ---echo # Testing errors ---echo # -CREATE TABLE t1 -( - ID INT NOT NULL -) Engine=CONNECT TABLE_TYPE=CSV FILE_NAME='nonexistent.txt'; ---replace_regex /on .*test.nonexistent.txt/on DATADIR\/test\/nonexistent.txt/ -# TODO: check why this is needed for Windows ---replace_result Open(rt) Open(rb) -SELECT * FROM t1; -DROP TABLE t1; - ---echo # ---echo # Testing examples from the manual ---echo # -CREATE TABLE t1 -( - name CHAR(12) NOT NULL, - birth DATE NOT NULL DATE_FORMAT='DD/MM/YY', - children SMALLINT(2) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='people.csv' - HEADER=1 SEP_CHAR=';' QUOTED=1; -SELECT * FROM t1; -INSERT INTO t1 VALUES ('RONALD','1980-02-26',4); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/people.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/people.csv'),'\r\n','\n'); - ---echo # ---echo # Testing READONLY tables ---echo # -CREATE TABLE t1 -( - name CHAR(12) NOT NULL, - birth DATE NOT NULL DATE_FORMAT='DD/MM/YY', - children SMALLINT(2) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='people.csv' - HEADER=1 SEP_CHAR=';' QUOTED=1 READONLY=yes; ---error ER_OPEN_AS_READONLY -INSERT INTO t1 VALUES ('BILL','1973-06-30',5); ---error ER_OPEN_AS_READONLY -UPDATE t1 SET children=6 WHERE name='BILL'; ---error ER_OPEN_AS_READONLY -DELETE FROM t1 WHERE name='BILL'; ---error ER_OPEN_AS_READONLY -TRUNCATE TABLE t1; -SELECT * FROM t1; -ALTER TABLE t1 READONLY=no; -SHOW CREATE TABLE t1; -INSERT INTO t1 VALUES ('BILL','1973-06-30',5); -SELECT * FROM t1; -ALTER TABLE t1 READONLY=1; -SHOW CREATE TABLE t1; ---error ER_OPEN_AS_READONLY -INSERT INTO t1 VALUES ('BILL','1973-06-30',5); -SELECT * FROM t1; -DROP TABLE t1; - - ---echo # ---echo # Testing that the underlying file is created ---echo # -CREATE TABLE t1 -( - c1 CHAR(12) NOT NULL, - c2 CHAR(12) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='tmp.csv' - HEADER=1 SEP_CHAR=',' QUOTED=1; -INSERT INTO t1 VALUES (10,10),(20,20),(300,300),(4000,4000), ('a b','c d'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/tmp.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/tmp.csv'),'\r\n','\n'); - ---echo # ---echo # Creating a CSV table from a MyISAM table ---echo # -CREATE TABLE t1 (a VARCHAR(10) NOT NULL, b INT NOT NULL) ENGINE=MyISAM; -INSERT INTO t1 VALUES ('test1',1), ('test2',2); -CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t2.csv' - AS SELECT * FROM t1; -SELECT * FROM t2; -DROP TABLE t2; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/t2.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t2.csv'),'\r\n','\n'); ---remove_file $MYSQLD_DATADIR/test/t2.csv - ---echo # ---echo # Testing international data ---echo # -CREATE TABLE t1 -( - c1 CHAR(12) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' - CHARSET=utf8; -INSERT INTO t1 VALUES ('á'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); ---remove_file $MYSQLD_DATADIR/test/t1.csv - -CREATE TABLE t1 -( - c1 CHAR(12) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' - CHARSET=utf8 DATA_CHARSET=latin1; -INSERT INTO t1 VALUES ('á'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); ---remove_file $MYSQLD_DATADIR/test/t1.csv - -CREATE TABLE t1 -( - c1 CHAR(12) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv'; -INSERT INTO t1 VALUES ('á'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); ---remove_file $MYSQLD_DATADIR/test/t1.csv - -CREATE TABLE t1 -( - c1 CHAR(12) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' - CHARSET=latin1; -INSERT INTO t1 VALUES ('á'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); ---remove_file $MYSQLD_DATADIR/test/t1.csv - -CREATE TABLE t1 -( - c1 CHAR(12) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' - CHARSET=latin1 DATA_CHARSET=utf8; -INSERT INTO t1 VALUES ('á'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); ---remove_file $MYSQLD_DATADIR/test/t1.csv - -CREATE TABLE t1 -( - c1 CHAR(12) CHARACTER SET latin1 NOT NULL, - c2 CHAR(12) CHARACTER SET utf8 NOT NULL -) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv'; -INSERT INTO t1 VALUES ('á','á'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.csv ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); ---remove_file $MYSQLD_DATADIR/test/t1.csv - - -# -# Clean up -# ---remove_file $MYSQLD_DATADIR/test/people.csv ---remove_file $MYSQLD_DATADIR/test/tmp.csv +let $MYSQLD_DATADIR= `select @@datadir`; + +--copy_file $MTR_SUITE_DIR/std_data/people.csv $MYSQLD_DATADIR/test/people.csv + +SET NAMES utf8; + +--echo # +--echo # Testing errors +--echo # +CREATE TABLE t1 +( + ID INT NOT NULL +) Engine=CONNECT TABLE_TYPE=CSV FILE_NAME='nonexistent.txt'; +--replace_regex /on .*test.nonexistent.txt/on DATADIR\/test\/nonexistent.txt/ +# TODO: check why this is needed for Windows +--replace_result Open(rt) Open(rb) +SELECT * FROM t1; +DROP TABLE t1; + +--echo # +--echo # Testing examples from the manual +--echo # +CREATE TABLE t1 +( + name CHAR(12) NOT NULL, + birth DATE NOT NULL DATE_FORMAT='DD/MM/YY', + children SMALLINT(2) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='people.csv' + HEADER=1 SEP_CHAR=';' QUOTED=1; +SELECT * FROM t1; +INSERT INTO t1 VALUES ('RONALD','1980-02-26',4); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/people.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/people.csv'),'\r\n','\n'); + +--echo # +--echo # Testing READONLY tables +--echo # +CREATE TABLE t1 +( + name CHAR(12) NOT NULL, + birth DATE NOT NULL DATE_FORMAT='DD/MM/YY', + children SMALLINT(2) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='people.csv' + HEADER=1 SEP_CHAR=';' QUOTED=1 READONLY=yes; +--error ER_OPEN_AS_READONLY +INSERT INTO t1 VALUES ('BILL','1973-06-30',5); +--error ER_GET_ERRMSG +UPDATE t1 SET children=6 WHERE name='BILL'; +--error ER_GET_ERRMSG +DELETE FROM t1 WHERE name='BILL'; +--error ER_OPEN_AS_READONLY +TRUNCATE TABLE t1; +SELECT * FROM t1; +ALTER TABLE t1 READONLY=no; +SHOW CREATE TABLE t1; +INSERT INTO t1 VALUES ('BILL','1973-06-30',5); +SELECT * FROM t1; +ALTER TABLE t1 READONLY=1; +SHOW CREATE TABLE t1; +--error ER_OPEN_AS_READONLY +INSERT INTO t1 VALUES ('BILL','1973-06-30',5); +SELECT * FROM t1; +DROP TABLE t1; + + +--echo # +--echo # Testing that the underlying file is created +--echo # +CREATE TABLE t1 +( + c1 CHAR(12) NOT NULL, + c2 CHAR(12) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='tmp.csv' + HEADER=1 SEP_CHAR=',' QUOTED=1; +INSERT INTO t1 VALUES (10,10),(20,20),(300,300),(4000,4000), ('a b','c d'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/tmp.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/tmp.csv'),'\r\n','\n'); + +--echo # +--echo # Creating a CSV table from a MyISAM table +--echo # +CREATE TABLE t1 (a VARCHAR(10) NOT NULL, b INT NOT NULL) ENGINE=MyISAM; +INSERT INTO t1 VALUES ('test1',1), ('test2',2); +CREATE TABLE t2 ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t2.csv' + AS SELECT * FROM t1; +SELECT * FROM t2; +DROP TABLE t2; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/t2.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t2.csv'),'\r\n','\n'); +--remove_file $MYSQLD_DATADIR/test/t2.csv + +--echo # +--echo # Testing international data +--echo # +CREATE TABLE t1 +( + c1 CHAR(12) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' + CHARSET=utf8; +INSERT INTO t1 VALUES ('á'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); +--remove_file $MYSQLD_DATADIR/test/t1.csv + +CREATE TABLE t1 +( + c1 CHAR(12) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' + CHARSET=utf8 DATA_CHARSET=latin1; +INSERT INTO t1 VALUES ('á'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); +--remove_file $MYSQLD_DATADIR/test/t1.csv + +CREATE TABLE t1 +( + c1 CHAR(12) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv'; +INSERT INTO t1 VALUES ('á'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); +--remove_file $MYSQLD_DATADIR/test/t1.csv + +CREATE TABLE t1 +( + c1 CHAR(12) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' + CHARSET=latin1; +INSERT INTO t1 VALUES ('á'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); +--remove_file $MYSQLD_DATADIR/test/t1.csv + +CREATE TABLE t1 +( + c1 CHAR(12) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv' + CHARSET=latin1 DATA_CHARSET=utf8; +INSERT INTO t1 VALUES ('á'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); +--remove_file $MYSQLD_DATADIR/test/t1.csv + +CREATE TABLE t1 +( + c1 CHAR(12) CHARACTER SET latin1 NOT NULL, + c2 CHAR(12) CHARACTER SET utf8 NOT NULL +) ENGINE=CONNECT TABLE_TYPE=CSV FILE_NAME='t1.csv'; +INSERT INTO t1 VALUES ('á','á'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.csv +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT HEX(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.csv'),'\r\n','\n')); +--remove_file $MYSQLD_DATADIR/test/t1.csv + + +# +# Clean up +# +--remove_file $MYSQLD_DATADIR/test/people.csv +--remove_file $MYSQLD_DATADIR/test/tmp.csv diff --git a/storage/connect/mysql-test/connect/t/dbf.test b/storage/connect/mysql-test/connect/t/dbf.test index 467c608fe38..b798b1a2bc5 100644 --- a/storage/connect/mysql-test/connect/t/dbf.test +++ b/storage/connect/mysql-test/connect/t/dbf.test @@ -68,9 +68,9 @@ ALTER TABLE t1 READONLY=Yes; SHOW CREATE TABLE t1; --error ER_OPEN_AS_READONLY INSERT INTO t1 VALUES (30); ---error ER_OPEN_AS_READONLY +--error ER_GET_ERRMSG UPDATE t1 SET a=30 WHERE a=10; ---error ER_OPEN_AS_READONLY +--error ER_GET_ERRMSG DELETE FROM t1 WHERE a=10; --error ER_OPEN_AS_READONLY TRUNCATE TABLE t1; diff --git a/storage/connect/mysql-test/connect/t/fix.test b/storage/connect/mysql-test/connect/t/fix.test index 72eb274f7d6..f05abbb9b92 100644 --- a/storage/connect/mysql-test/connect/t/fix.test +++ b/storage/connect/mysql-test/connect/t/fix.test @@ -30,9 +30,9 @@ ALTER TABLE t1 READONLY=1; SHOW CREATE TABLE t1; --error ER_OPEN_AS_READONLY INSERT INTO t1 VALUES (20); ---error ER_OPEN_AS_READONLY +--error ER_GET_ERRMSG UPDATE t1 SET id=20 WHERE id=10; ---error ER_OPEN_AS_READONLY +--error ER_GET_ERRMSG DELETE FROM t1 WHERE id=10; --error ER_OPEN_AS_READONLY TRUNCATE TABLE t1; diff --git a/storage/connect/mysql-test/connect/t/ini.test b/storage/connect/mysql-test/connect/t/ini.test index dd3b84e4699..449b97204a6 100644 --- a/storage/connect/mysql-test/connect/t/ini.test +++ b/storage/connect/mysql-test/connect/t/ini.test @@ -1,156 +1,156 @@ -let $MYSQLD_DATADIR= `select @@datadir`; - ---copy_file $MTR_SUITE_DIR/std_data/contact.ini $MYSQLD_DATADIR/test/contact.ini - ---echo # ---echo # Testing errors ---echo # -CREATE TABLE t1 -( - ID INT -) Engine=CONNECT TABLE_TYPE=INI FILE_NAME='nonexistent.txt'; ---replace_regex /on .*test.nonexistent.txt/on DATADIR\/test\/nonexistent.txt/ -# TODO: check why this is needed for Windows ---replace_result Open(rt) Open(rb) -SELECT * FROM t1; -DROP TABLE t1; - ---echo # ---echo # Testing examples from the manual ---echo # - -CREATE TABLE t1 -( - contact CHAR(16) flag=1, - name CHAR(20), - forename CHAR(32), - hired date date_format='DD/MM/YYYY', - address CHAR(64), - city CHAR(20), - zipcode CHAR(8), - tel CHAR(16) -) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='contact.ini'; -SELECT contact, name, hired, city, tel FROM t1; - -UPDATE t1 SET forename= 'Harry' where contact='UK1'; -SELECT * FROM t1 WHERE contact='UK1'; -INSERT INTO t1 (contact,forename) VALUES ('UK1','Harrison'); -SELECT * FROM t1 WHERE contact='UK1'; -INSERT INTO t1 (contact,forename) VALUES ('UK2','John'); -SELECT * FROM t1 WHERE contact='UK2'; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/contact.ini ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/contact.ini'),'\r\n','\n'),'\n\n','\n'); - -CREATE TABLE t1 -( - section CHAR(16) flag=1, - keyname CHAR(16) flag=2, - value CHAR(32) -) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='contact.ini' - OPTION_LIST='Layout=Row'; -UPDATE t1 SET value='Paul' WHERE section='UK2' AND keyname='forename'; -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/contact.ini ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/contact.ini'),'\r\n','\n'),'\n\n','\n'); - - ---echo # ---echo # Testing that the underlying file is created ---echo # -CREATE TABLE t1 -( - contact CHAR(12) NOT NULL flag=1, - c2 CHAR(12) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='tmp.ini'; -INSERT INTO t1 VALUES (10,10),(20,20),(300,300),(4000,4000), ('a b','c d'); -SELECT * FROM t1; -DROP TABLE t1; ---chmod 0777 $MYSQLD_DATADIR/test/tmp.ini ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/tmp.ini'),'\r\n','\n'),'\n\n','\n'); - - ---echo # ---echo # Testing bad table ---echo # -CREATE TABLE t1 -( - id INT -) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='t1.ini'; ---error ER_GET_ERRMSG -INSERT INTO t1 VALUES (10); -SELECT * FROM t1; -DROP TABLE t1; - - ---echo # ---echo # Testing READONLY tables ---echo # -CREATE TABLE t1 -( - contact CHAR(10) flag=1, - c2 CHAR(60) -) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='t1.ini'; -INSERT INTO t1 VALUES ('UK',10),('FR',20),('RU',30); -SELECT * FROM t1; -ALTER TABLE t1 READONLY=1; -SHOW CREATE TABLE t1; ---error ER_OPEN_AS_READONLY -INSERT INTO t1 VALUES ('US',40); ---error ER_OPEN_AS_READONLY -UPDATE t1 SET c2=20 WHERE c2=10; ---error ER_OPEN_AS_READONLY -DELETE FROM t1 WHERE c2=10; ---error ER_OPEN_AS_READONLY -TRUNCATE TABLE t1; -ALTER TABLE t1 READONLY=0; -SHOW CREATE TABLE t1; -INSERT INTO t1 VALUES ('US',40); -SELECT * FROM t1; -DROP TABLE t1; ---remove_file $MYSQLD_DATADIR/test/t1.ini - - -# -# Clean up -# ---remove_file $MYSQLD_DATADIR/test/contact.ini ---remove_file $MYSQLD_DATADIR/test/tmp.ini - - ---echo # ---echo # Bug: TABLE_TYPE=ini does not clear memory between CREATE TABLEs ---echo # -CREATE TABLE t1 (sec CHAR(10) NOT NULL FLAG=1, val CHAR(10) NOT NULL) -ENGINE=CONNECT TABLE_TYPE=INI; -INSERT INTO t1 VALUES ('sec1','val1'),('sec2','val2'); -SELECT sec AS s, val AS v FROM t1; -DROP TABLE t1; -CREATE TABLE t1 (sec2 CHAR(10) NOT NULL FLAG=1, val2 CHAR(10) NOT NULL) -ENGINE=CONNECT TABLE_TYPE=INI; -INSERT INTO t1 VALUES ('sec1','val11'),('sec2','val22'); -SELECT sec2 AS s, val2 AS v FROM t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.ini ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.ini'),'\r\n','\n'),'\n\n','\n'); -DROP TABLE t1; - -CREATE TABLE t1 (sec CHAR(10) NOT NULL FLAG=1, val CHAR(10) NOT NULL) -ENGINE=CONNECT TABLE_TYPE=INI; -CREATE TABLE t2 (sec CHAR(10) NOT NULL FLAG=1, val CHAR(10) NOT NULL) -ENGINE=CONNECT TABLE_TYPE=INI; -INSERT INTO t1 VALUES('1sec1','1val1'),('1sec2','1val2'); -INSERT INTO t2 VALUES('2sec1','2val1'),('2sec2','2val2'); -SELECT sec AS s, val AS v FROM t1; ---chmod 0777 $MYSQLD_DATADIR/test/t1.ini ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.ini'),'\r\n','\n'),'\n\n','\n'); -SELECT sec AS s, val AS v FROM t2; ---chmod 0777 $MYSQLD_DATADIR/test/t2.ini ---replace_result $MYSQLD_DATADIR DATADIR ---eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t2.ini'),'\r\n','\n'),'\n\n','\n'); -DROP TABLE t1, t2; +let $MYSQLD_DATADIR= `select @@datadir`; + +--copy_file $MTR_SUITE_DIR/std_data/contact.ini $MYSQLD_DATADIR/test/contact.ini + +--echo # +--echo # Testing errors +--echo # +CREATE TABLE t1 +( + ID INT +) Engine=CONNECT TABLE_TYPE=INI FILE_NAME='nonexistent.txt'; +--replace_regex /on .*test.nonexistent.txt/on DATADIR\/test\/nonexistent.txt/ +# TODO: check why this is needed for Windows +--replace_result Open(rt) Open(rb) +SELECT * FROM t1; +DROP TABLE t1; + +--echo # +--echo # Testing examples from the manual +--echo # + +CREATE TABLE t1 +( + contact CHAR(16) flag=1, + name CHAR(20), + forename CHAR(32), + hired date date_format='DD/MM/YYYY', + address CHAR(64), + city CHAR(20), + zipcode CHAR(8), + tel CHAR(16) +) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='contact.ini'; +SELECT contact, name, hired, city, tel FROM t1; + +UPDATE t1 SET forename= 'Harry' where contact='UK1'; +SELECT * FROM t1 WHERE contact='UK1'; +INSERT INTO t1 (contact,forename) VALUES ('UK1','Harrison'); +SELECT * FROM t1 WHERE contact='UK1'; +INSERT INTO t1 (contact,forename) VALUES ('UK2','John'); +SELECT * FROM t1 WHERE contact='UK2'; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/contact.ini +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/contact.ini'),'\r\n','\n'),'\n\n','\n'); + +CREATE TABLE t1 +( + section CHAR(16) flag=1, + keyname CHAR(16) flag=2, + value CHAR(32) +) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='contact.ini' + OPTION_LIST='Layout=Row'; +UPDATE t1 SET value='Paul' WHERE section='UK2' AND keyname='forename'; +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/contact.ini +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/contact.ini'),'\r\n','\n'),'\n\n','\n'); + + +--echo # +--echo # Testing that the underlying file is created +--echo # +CREATE TABLE t1 +( + contact CHAR(12) NOT NULL flag=1, + c2 CHAR(12) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='tmp.ini'; +INSERT INTO t1 VALUES (10,10),(20,20),(300,300),(4000,4000), ('a b','c d'); +SELECT * FROM t1; +DROP TABLE t1; +--chmod 0777 $MYSQLD_DATADIR/test/tmp.ini +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/tmp.ini'),'\r\n','\n'),'\n\n','\n'); + + +--echo # +--echo # Testing bad table +--echo # +CREATE TABLE t1 +( + id INT +) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='t1.ini'; +--error ER_GET_ERRMSG +INSERT INTO t1 VALUES (10); +SELECT * FROM t1; +DROP TABLE t1; + + +--echo # +--echo # Testing READONLY tables +--echo # +CREATE TABLE t1 +( + contact CHAR(10) flag=1, + c2 CHAR(60) +) ENGINE=CONNECT TABLE_TYPE=INI FILE_NAME='t1.ini'; +INSERT INTO t1 VALUES ('UK',10),('FR',20),('RU',30); +SELECT * FROM t1; +ALTER TABLE t1 READONLY=1; +SHOW CREATE TABLE t1; +--error ER_OPEN_AS_READONLY +INSERT INTO t1 VALUES ('US',40); +--error ER_GET_ERRMSG +UPDATE t1 SET c2=20 WHERE c2=10; +--error ER_GET_ERRMSG +DELETE FROM t1 WHERE c2=10; +--error ER_OPEN_AS_READONLY +TRUNCATE TABLE t1; +ALTER TABLE t1 READONLY=0; +SHOW CREATE TABLE t1; +INSERT INTO t1 VALUES ('US',40); +SELECT * FROM t1; +DROP TABLE t1; +--remove_file $MYSQLD_DATADIR/test/t1.ini + + +# +# Clean up +# +--remove_file $MYSQLD_DATADIR/test/contact.ini +--remove_file $MYSQLD_DATADIR/test/tmp.ini + + +--echo # +--echo # Bug: TABLE_TYPE=ini does not clear memory between CREATE TABLEs +--echo # +CREATE TABLE t1 (sec CHAR(10) NOT NULL FLAG=1, val CHAR(10) NOT NULL) +ENGINE=CONNECT TABLE_TYPE=INI; +INSERT INTO t1 VALUES ('sec1','val1'),('sec2','val2'); +SELECT sec AS s, val AS v FROM t1; +DROP TABLE t1; +CREATE TABLE t1 (sec2 CHAR(10) NOT NULL FLAG=1, val2 CHAR(10) NOT NULL) +ENGINE=CONNECT TABLE_TYPE=INI; +INSERT INTO t1 VALUES ('sec1','val11'),('sec2','val22'); +SELECT sec2 AS s, val2 AS v FROM t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.ini +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.ini'),'\r\n','\n'),'\n\n','\n'); +DROP TABLE t1; + +CREATE TABLE t1 (sec CHAR(10) NOT NULL FLAG=1, val CHAR(10) NOT NULL) +ENGINE=CONNECT TABLE_TYPE=INI; +CREATE TABLE t2 (sec CHAR(10) NOT NULL FLAG=1, val CHAR(10) NOT NULL) +ENGINE=CONNECT TABLE_TYPE=INI; +INSERT INTO t1 VALUES('1sec1','1val1'),('1sec2','1val2'); +INSERT INTO t2 VALUES('2sec1','2val1'),('2sec2','2val2'); +SELECT sec AS s, val AS v FROM t1; +--chmod 0777 $MYSQLD_DATADIR/test/t1.ini +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t1.ini'),'\r\n','\n'),'\n\n','\n'); +SELECT sec AS s, val AS v FROM t2; +--chmod 0777 $MYSQLD_DATADIR/test/t2.ini +--replace_result $MYSQLD_DATADIR DATADIR +--eval SELECT REPLACE(REPLACE(LOAD_FILE('$MYSQLD_DATADIR/test/t2.ini'),'\r\n','\n'),'\n\n','\n'); +DROP TABLE t1, t2; diff --git a/storage/connect/mysql-test/connect/t/vec.test b/storage/connect/mysql-test/connect/t/vec.test index aca78987a97..c88a857761d 100644 --- a/storage/connect/mysql-test/connect/t/vec.test +++ b/storage/connect/mysql-test/connect/t/vec.test @@ -1,80 +1,80 @@ -let $MYSQLD_DATADIR= `select @@datadir`; - -CREATE TABLE dir1 ( - spath VARCHAR(256) NOT NULL flag=1, - fname VARCHAR(256) NOT NULL, - ftype CHAR(4) NOT NULL, - size DOUBLE(12,0) NOT NULL flag=5 -) ENGINE=CONNECT TABLE_TYPE=DIR FILE_NAME='*vec*'; - - -CREATE TABLE t1 -( - a INT NOT NULL, - b CHAR(10) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=VEC FILE_NAME='t1vec'; -SHOW CREATE TABLE t1; -# Testing SELECT on empty file ---replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ -SELECT * FROM t1; -INSERT INTO t1 VALUES (0,'test01'), (1,'test01'), (2,'test02'), (3,'test03'); -SELECT * FROM t1; -SELECT a FROM t1; -SELECT b FROM t1; ---replace_result $MYSQLD_DATADIR DATADIR/ -SELECT fname, ftype, size FROM dir1 ORDER BY fname, ftype; -DROP TABLE t1; ---remove_file $MYSQLD_DATADIR/test/t1vec1 ---remove_file $MYSQLD_DATADIR/test/t1vec2 - - -CREATE TABLE t1 -( - a INT NOT NULL, - b CHAR(10) NOT NULL -) ENGINE=CONNECT TABLE_TYPE=VEC FILE_NAME='t1vec' MAX_ROWS=10; -SHOW CREATE TABLE t1; -# Testing SELECTs on empty file ---replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ -SELECT * FROM t1; ---replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ -SELECT a FROM t1; ---replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ -SELECT b FROM t1; -INSERT INTO t1 VALUES (0,'test01'), (1,'test01'), (2,'test02'), (3,'test03'); -SELECT * FROM t1; -SELECT a FROM t1; -SELECT b FROM t1; ---replace_result $MYSQLD_DATADIR DATADIR/ -SELECT fname, ftype, size FROM dir1 ORDER BY fname, ftype; ---echo # ---echo # Testing READONLY ---echo # -ALTER TABLE t1 READONLY=yes; -SHOW CREATE TABLE t1; ---error ER_OPEN_AS_READONLY -INSERT INTO t1 VALUES (4,'test04'); ---error ER_OPEN_AS_READONLY -UPDATE t1 SET b='test04' WHERE a=3; ---error ER_OPEN_AS_READONLY -DELETE FROM t1 WHERE a=3; ---error ER_OPEN_AS_READONLY -TRUNCATE TABLE t1; -ALTER TABLE t1 READONLY=no; -SHOW CREATE TABLE t1; -INSERT INTO t1 VALUES (4,'test04'); -UPDATE t1 SET b='test04a' WHERE a=4; -DELETE FROM t1 WHERE a=0; -SELECT * FROM t1; -TRUNCATE TABLE t1; -SELECT fname, ftype, size FROM dir1 ORDER BY fname, ftype; -SELECT * FROM t1; -DROP TABLE t1; ---remove_file $MYSQLD_DATADIR/test/t1vec ---remove_file $MYSQLD_DATADIR/test/t1vec.blk - - ---echo # ---echo # Clean up ---echo # -DROP TABLE dir1; +let $MYSQLD_DATADIR= `select @@datadir`; + +CREATE TABLE dir1 ( + spath VARCHAR(256) NOT NULL flag=1, + fname VARCHAR(256) NOT NULL, + ftype CHAR(4) NOT NULL, + size DOUBLE(12,0) NOT NULL flag=5 +) ENGINE=CONNECT TABLE_TYPE=DIR FILE_NAME='*vec*'; + + +CREATE TABLE t1 +( + a INT NOT NULL, + b CHAR(10) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=VEC FILE_NAME='t1vec'; +SHOW CREATE TABLE t1; +# Testing SELECT on empty file +--replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ +SELECT * FROM t1; +INSERT INTO t1 VALUES (0,'test01'), (1,'test01'), (2,'test02'), (3,'test03'); +SELECT * FROM t1; +SELECT a FROM t1; +SELECT b FROM t1; +--replace_result $MYSQLD_DATADIR DATADIR/ +SELECT fname, ftype, size FROM dir1 ORDER BY fname, ftype; +DROP TABLE t1; +--remove_file $MYSQLD_DATADIR/test/t1vec1 +--remove_file $MYSQLD_DATADIR/test/t1vec2 + + +CREATE TABLE t1 +( + a INT NOT NULL, + b CHAR(10) NOT NULL +) ENGINE=CONNECT TABLE_TYPE=VEC FILE_NAME='t1vec' MAX_ROWS=10; +SHOW CREATE TABLE t1; +# Testing SELECTs on empty file +--replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ +SELECT * FROM t1; +--replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ +SELECT a FROM t1; +--replace_regex /Open.rb. error 2 on .*\/test\/t1vec/Open(rb) error 2 on DATADIR\/test\/t1vec/ +SELECT b FROM t1; +INSERT INTO t1 VALUES (0,'test01'), (1,'test01'), (2,'test02'), (3,'test03'); +SELECT * FROM t1; +SELECT a FROM t1; +SELECT b FROM t1; +--replace_result $MYSQLD_DATADIR DATADIR/ +SELECT fname, ftype, size FROM dir1 ORDER BY fname, ftype; +--echo # +--echo # Testing READONLY +--echo # +ALTER TABLE t1 READONLY=yes; +SHOW CREATE TABLE t1; +--error ER_OPEN_AS_READONLY +INSERT INTO t1 VALUES (4,'test04'); +--error ER_GET_ERRMSG +UPDATE t1 SET b='test04' WHERE a=3; +--error ER_GET_ERRMSG +DELETE FROM t1 WHERE a=3; +--error ER_OPEN_AS_READONLY +TRUNCATE TABLE t1; +ALTER TABLE t1 READONLY=no; +SHOW CREATE TABLE t1; +INSERT INTO t1 VALUES (4,'test04'); +UPDATE t1 SET b='test04a' WHERE a=4; +DELETE FROM t1 WHERE a=0; +SELECT * FROM t1; +TRUNCATE TABLE t1; +SELECT fname, ftype, size FROM dir1 ORDER BY fname, ftype; +SELECT * FROM t1; +DROP TABLE t1; +--remove_file $MYSQLD_DATADIR/test/t1vec +--remove_file $MYSQLD_DATADIR/test/t1vec.blk + + +--echo # +--echo # Clean up +--echo # +DROP TABLE dir1; diff --git a/storage/connect/reldef.h b/storage/connect/reldef.h index fe6297f52e4..fbf66de373c 100644 --- a/storage/connect/reldef.h +++ b/storage/connect/reldef.h @@ -214,6 +214,7 @@ class DllExport COLDEF : public COLCRT { /* Column description block int Define(PGLOBAL g, void *memp, PCOLINFO cfp, int poff); void Define(PGLOBAL g, PCOL colp); bool IsSpecial(void) {return (Flags & U_SPECIAL) ? true : false;} + bool IsVirtual(void) {return (Flags & U_VIRTUAL) ? true : false;} protected: void *To_Min; /* Point to array of block min values */ diff --git a/storage/connect/tabdos.cpp b/storage/connect/tabdos.cpp index bb562defe17..81e7772e062 100644 --- a/storage/connect/tabdos.cpp +++ b/storage/connect/tabdos.cpp @@ -2168,10 +2168,12 @@ DOSCOL::DOSCOL(PGLOBAL g, PCOLDEF cdp, PTDB tp, PCOL cp, int i, PSZ am) } // endif Opt OldVal = NULL; // Currently used only in MinMax + Dsp = 0; Ldz = false; Nod = false; Dcm = -1; p = cdp->GetFmt(); + Buf = NULL; if (p && IsTypeNum(Buf_Type)) { // Formatted numeric value @@ -2183,6 +2185,9 @@ DOSCOL::DOSCOL(PGLOBAL g, PCOLDEF cdp, PTDB tp, PCOL cp, int i, PSZ am) case 'N': // Have no decimal point Nod = true; break; + case 'D': // Decimal separator + Dsp = *(++p); + break; } // endswitch p // Set number of decimal digits @@ -2204,6 +2209,7 @@ DOSCOL::DOSCOL(DOSCOL *col1, PTDB tdbp) : COLBLK(col1, tdbp) Long = col1->Long; To_Val = col1->To_Val; Ldz = col1->Ldz; + Dsp = col1->Dsp; Nod = col1->Nod; Dcm = col1->Dcm; OldVal = col1->OldVal; @@ -2277,7 +2283,7 @@ bool DOSCOL::SetBuffer(PGLOBAL g, PVAL value, bool ok, bool check) } // endif's Value, Buf_Type // Allocate the buffer used in WriteColumn for numeric columns - if (IsTypeNum(Buf_Type)) + if (!Buf && IsTypeNum(Buf_Type)) Buf = (char*)PlugSubAlloc(g, NULL, MY_MAX(32, Long + Dcm + 1)); // Because Colblk's have been made from a copy of the original TDB in @@ -2322,14 +2328,18 @@ void DOSCOL::ReadColumn(PGLOBAL g) p = tdbp->To_Line + Deplac; field = Long; + /*********************************************************************/ + /* For a variable length file, check if the field exists. */ + /*********************************************************************/ + if (tdbp->Ftype == RECFM_VAR && strlen(tdbp->To_Line) < (unsigned)Deplac) + field = 0; + else if (Dsp) + for(i = 0; i < field; i++) + if (p[i] == Dsp) + p[i] = '.'; + switch (tdbp->Ftype) { case RECFM_VAR: - /*****************************************************************/ - /* For a variable length file, check if the field exists. */ - /*****************************************************************/ - if (strlen(tdbp->To_Line) < (unsigned)Deplac) - field = 0; - case RECFM_FIX: // Fixed length text file case RECFM_DBF: // Fixed length DBase file if (Nod) switch (Buf_Type) { @@ -2458,6 +2468,7 @@ void DOSCOL::WriteColumn(PGLOBAL g) len = sprintf(Buf, fmt, field - i, Value->GetTinyValue()); break; case TYPE_DOUBLE: + case TYPE_DECIM: strcpy(fmt, (Ldz) ? "%0*.*lf" : "%*.*lf"); sprintf(Buf, fmt, field + ((Nod && Dcm) ? 1 : 0), Dcm, Value->GetFloatValue()); @@ -2466,7 +2477,7 @@ void DOSCOL::WriteColumn(PGLOBAL g) if (Nod && Dcm) for (i = k = 0; i < len; i++, k++) if (Buf[i] != ' ') { - if (Buf[i] == '.' || Buf[i] == ',') + if (Buf[i] == '.') k++; Buf[i] = Buf[k]; @@ -2474,10 +2485,13 @@ void DOSCOL::WriteColumn(PGLOBAL g) len = strlen(Buf); break; + default: + sprintf(g->Message, "Invalid field format for column %s", Name); + longjmp(g->jumper[g->jump_level], 31); } // endswitch BufType p2 = Buf; - } else // Standard PlugDB format + } else // Standard CONNECT format p2 = Value->ShowValue(Buf, field); if (trace) @@ -2486,7 +2500,10 @@ void DOSCOL::WriteColumn(PGLOBAL g) if ((len = strlen(p2)) > field) { sprintf(g->Message, MSG(VALUE_TOO_LONG), p2, Name, field); longjmp(g->jumper[g->jump_level], 31); - } // endif + } else if (Dsp) + for (i = 0; i < len; i++) + if (p2[i] == '.') + p2[i] = Dsp; if (trace > 1) htrc("buffer=%s\n", p2); diff --git a/storage/connect/tabdos.h b/storage/connect/tabdos.h index c6652c4d2d7..62639787325 100644 --- a/storage/connect/tabdos.h +++ b/storage/connect/tabdos.h @@ -241,7 +241,8 @@ class DllExport DOSCOL : public COLBLK { PVBLK Dval; // Array of column distinct values PVAL To_Val; // To value used for Update/Insert PVAL OldVal; // The previous value of the object. - char *Buf; // Buffer used in write operations + char *Buf; // Buffer used in read/write operations + char Dsp; // The decimal separator bool Ldz; // True if field contains leading zeros bool Nod; // True if no decimal point int Dcm; // Last Dcm digits are decimals diff --git a/storage/connect/tabfmt.cpp b/storage/connect/tabfmt.cpp index f0e565dcba7..e4a280fefd2 100644 --- a/storage/connect/tabfmt.cpp +++ b/storage/connect/tabfmt.cpp @@ -597,7 +597,7 @@ int TDBCSV::EstimatedLength(PGLOBAL g) PCSVCOL colp; for (colp = (PCSVCOL)Columns; colp; colp = (PCSVCOL)colp->Next) - if (!colp->IsSpecial()) // Not a pseudo column + if (!colp->IsSpecial() && !colp->IsVirtual()) // A true column Fields = MY_MAX(Fields, (int)colp->Fldnum); if (Columns) @@ -640,7 +640,7 @@ bool TDBCSV::OpenDB(PGLOBAL g) if (!Fields) // May have been set in TABFMT::OpenDB if (Mode != MODE_UPDATE && Mode != MODE_INSERT) { for (colp = (PCSVCOL)Columns; colp; colp = (PCSVCOL)colp->Next) - if (!colp->IsSpecial()) // Not a pseudo column + if (!colp->IsSpecial() && !colp->IsVirtual()) Fields = MY_MAX(Fields, (int)colp->Fldnum); if (Columns) @@ -648,7 +648,8 @@ bool TDBCSV::OpenDB(PGLOBAL g) } else for (cdp = tdp->GetCols(); cdp; cdp = cdp->GetNext()) - Fields++; + if (!cdp->IsVirtual()) + Fields++; Offset = (int*)PlugSubAlloc(g, NULL, sizeof(int) * Fields); Fldlen = (int*)PlugSubAlloc(g, NULL, sizeof(int) * Fields); @@ -671,25 +672,27 @@ bool TDBCSV::OpenDB(PGLOBAL g) if (Field) // Prepare writing fields - if (Mode != MODE_UPDATE) - for (colp = (PCSVCOL)Columns; colp; colp = (PCSVCOL)colp->Next) { - i = colp->Fldnum; - len = colp->GetLength(); - Field[i] = (PSZ)PlugSubAlloc(g, NULL, len + 1); - Field[i][len] = '\0'; - Fldlen[i] = len; - Fldtyp[i] = IsTypeNum(colp->GetResultType()); - } // endfor colp + if (Mode != MODE_UPDATE) { + for (colp = (PCSVCOL)Columns; colp; colp = (PCSVCOL)colp->Next) + if (!colp->IsSpecial() && !colp->IsVirtual()) { + i = colp->Fldnum; + len = colp->GetLength(); + Field[i] = (PSZ)PlugSubAlloc(g, NULL, len + 1); + Field[i][len] = '\0'; + Fldlen[i] = len; + Fldtyp[i] = IsTypeNum(colp->GetResultType()); + } // endif colp - else // MODE_UPDATE - for (cdp = tdp->GetCols(); cdp; cdp = cdp->GetNext()) { - i = cdp->GetOffset() - 1; - len = cdp->GetLength(); - Field[i] = (PSZ)PlugSubAlloc(g, NULL, len + 1); - Field[i][len] = '\0'; - Fldlen[i] = len; - Fldtyp[i] = IsTypeNum(cdp->GetType()); - } // endfor colp + } else // MODE_UPDATE + for (cdp = tdp->GetCols(); cdp; cdp = cdp->GetNext()) + if (!cdp->IsVirtual()) { + i = cdp->GetOffset() - 1; + len = cdp->GetLength(); + Field[i] = (PSZ)PlugSubAlloc(g, NULL, len + 1); + Field[i][len] = '\0'; + Fldlen[i] = len; + Fldtyp[i] = IsTypeNum(cdp->GetType()); + } // endif cdp } // endif Use @@ -1100,7 +1103,7 @@ bool TDBFMT::OpenDB(PGLOBAL g) PDOSDEF tdp = (PDOSDEF)To_Def; for (colp = (PCSVCOL)Columns; colp; colp = (PCSVCOL)colp->Next) - if (!colp->IsSpecial()) // Not a pseudo column + if (!colp->IsSpecial() && !colp->IsVirtual()) // a true column Fields = MY_MAX(Fields, (int)colp->Fldnum); if (Columns) @@ -1114,7 +1117,7 @@ bool TDBFMT::OpenDB(PGLOBAL g) // Get the column formats for (cdp = tdp->GetCols(); cdp; cdp = cdp->GetNext()) - if ((i = cdp->GetOffset() - 1) < Fields) { + if (!cdp->IsVirtual() && (i = cdp->GetOffset() - 1) < Fields) { if (!(pfm = cdp->GetFmt())) { sprintf(g->Message, MSG(NO_FLD_FORMAT), i + 1, Name); return true; @@ -1336,6 +1339,11 @@ void CSVCOL::ReadColumn(PGLOBAL g) // Field have been copied in TDB Field array PSZ fp = tdbp->Field[Fldnum]; + if (Dsp) + for (int i = 0; fp[i]; i++) + if (fp[i] == Dsp) + fp[i] = '.'; + Value->SetValue_psz(fp); // Set null when applicable @@ -1383,7 +1391,10 @@ void CSVCOL::WriteColumn(PGLOBAL g) sprintf(g->Message, MSG(BAD_FLD_LENGTH), Name, p, flen, tdbp->RowNumber(g), tdbp->GetFile(g)); longjmp(g->jumper[g->jump_level], 34); - } // endif + } else if (Dsp) + for (int i = 0; p[i]; i++) + if (p[i] == '.') + p[i] = Dsp; if (trace > 1) htrc("buffer=%s\n", p); diff --git a/storage/connect/tabmysql.cpp b/storage/connect/tabmysql.cpp index 213929be156..931e78f598e 100644 --- a/storage/connect/tabmysql.cpp +++ b/storage/connect/tabmysql.cpp @@ -190,9 +190,8 @@ bool MYSQLDEF::ParseURL(PGLOBAL g, char *url, bool b) return true; } else - // Otherwise, straight server name, - // use tablename of federatedx table as remote table name - Tabname= Name; + // Otherwise, straight server name, + Tabname = (b) ? GetStringCatInfo(g, "Tabname", Name) : NULL; if (trace) htrc("server: %s Tabname: %s", url, Tabname);