722
724
/************************************************************************/
725
/* ProcessSQLDropTable() */
727
/* The correct syntax for dropping a table (layer) in the OGR SQL */
730
/* DROP TABLE <layername> */
731
/************************************************************************/
733
OGRErr OGRDataSource::ProcessSQLDropTable( const char *pszSQLCommand )
736
char **papszTokens = CSLTokenizeString( pszSQLCommand );
738
/* -------------------------------------------------------------------- */
739
/* Do some general syntax checking. */
740
/* -------------------------------------------------------------------- */
741
if( CSLCount(papszTokens) != 3
742
|| !EQUAL(papszTokens[0],"DROP")
743
|| !EQUAL(papszTokens[1],"TABLE") )
745
CSLDestroy( papszTokens );
746
CPLError( CE_Failure, CPLE_AppDefined,
747
"Syntax error in DROP TABLE command.\n"
749
"Should be of form 'DROP TABLE <table>'",
751
return OGRERR_FAILURE;
754
/* -------------------------------------------------------------------- */
755
/* Find the named layer. */
756
/* -------------------------------------------------------------------- */
758
OGRLayer *poLayer=NULL;
760
for( i = 0; i < GetLayerCount(); i++ )
762
poLayer = GetLayer(i);
764
if( EQUAL(poLayer->GetName(),papszTokens[2]) )
768
if( i >= GetLayerCount() )
770
CPLError( CE_Failure, CPLE_AppDefined,
771
"DROP TABLE failed, no such layer as `%s'.",
773
CSLDestroy( papszTokens );
774
return OGRERR_FAILURE;
777
CSLDestroy( papszTokens );
779
/* -------------------------------------------------------------------- */
781
/* -------------------------------------------------------------------- */
783
return DeleteLayer( i );
786
/************************************************************************/
787
/* OGRDataSourceParseSQLType() */
788
/************************************************************************/
790
/* All arguments will be altered */
791
static OGRFieldType OGRDataSourceParseSQLType(char* pszType, int& nWidth, int &nPrecision)
793
char* pszParenthesis = strchr(pszType, '(');
796
nWidth = atoi(pszParenthesis + 1);
797
*pszParenthesis = '\0';
798
char* pszComma = strchr(pszParenthesis + 1, ',');
800
nPrecision = atoi(pszComma + 1);
803
OGRFieldType eType = OFTString;
804
if (EQUAL(pszType, "INTEGER"))
806
else if (EQUAL(pszType, "INTEGER[]"))
807
eType = OFTIntegerList;
808
else if (EQUAL(pszType, "FLOAT") ||
809
EQUAL(pszType, "NUMERIC") ||
810
EQUAL(pszType, "DOUBLE") /* unofficial alias */ ||
811
EQUAL(pszType, "REAL") /* unofficial alias */)
813
else if (EQUAL(pszType, "FLOAT[]") ||
814
EQUAL(pszType, "NUMERIC[]") ||
815
EQUAL(pszType, "DOUBLE[]") /* unofficial alias */ ||
816
EQUAL(pszType, "REAL[]") /* unofficial alias */)
818
else if (EQUAL(pszType, "CHARACTER") ||
819
EQUAL(pszType, "TEXT") /* unofficial alias */ ||
820
EQUAL(pszType, "STRING") /* unofficial alias */ ||
821
EQUAL(pszType, "VARCHAR") /* unofficial alias */)
823
else if (EQUAL(pszType, "TEXT[]") ||
824
EQUAL(pszType, "STRING[]") /* unofficial alias */||
825
EQUAL(pszType, "VARCHAR[]") /* unofficial alias */)
826
eType = OFTStringList;
827
else if (EQUAL(pszType, "DATE"))
829
else if (EQUAL(pszType, "TIME"))
831
else if (EQUAL(pszType, "TIMESTAMP") ||
832
EQUAL(pszType, "DATETIME") /* unofficial alias */ )
836
CPLError(CE_Warning, CPLE_NotSupported,
837
"Unsupported column type '%s'. Defaulting to VARCHAR",
843
/************************************************************************/
844
/* ProcessSQLAlterTableAddColumn() */
846
/* The correct syntax for adding a column in the OGR SQL */
849
/* ALTER TABLE <layername> ADD [COLUMN] <columnname> <columntype>*/
850
/************************************************************************/
852
OGRErr OGRDataSource::ProcessSQLAlterTableAddColumn( const char *pszSQLCommand )
855
char **papszTokens = CSLTokenizeString( pszSQLCommand );
857
/* -------------------------------------------------------------------- */
858
/* Do some general syntax checking. */
859
/* -------------------------------------------------------------------- */
860
const char* pszLayerName = NULL;
861
const char* pszColumnName = NULL;
862
char* pszType = NULL;
864
int nTokens = CSLCount(papszTokens);
867
&& EQUAL(papszTokens[0],"ALTER")
868
&& EQUAL(papszTokens[1],"TABLE")
869
&& EQUAL(papszTokens[3],"ADD")
870
&& EQUAL(papszTokens[4],"COLUMN"))
872
pszLayerName = papszTokens[2];
873
pszColumnName = papszTokens[5];
876
else if( nTokens >= 6
877
&& EQUAL(papszTokens[0],"ALTER")
878
&& EQUAL(papszTokens[1],"TABLE")
879
&& EQUAL(papszTokens[3],"ADD"))
881
pszLayerName = papszTokens[2];
882
pszColumnName = papszTokens[4];
887
CSLDestroy( papszTokens );
888
CPLError( CE_Failure, CPLE_AppDefined,
889
"Syntax error in ALTER TABLE ADD COLUMN command.\n"
891
"Should be of form 'ALTER TABLE <layername> ADD [COLUMN] <columnname> <columntype>'",
893
return OGRERR_FAILURE;
896
/* -------------------------------------------------------------------- */
897
/* Merge type components into a single string if there were split */
899
/* -------------------------------------------------------------------- */
901
for(int i=iTypeIndex;i<nTokens;i++)
903
osType += papszTokens[i];
904
CPLFree(papszTokens[i]);
906
pszType = papszTokens[iTypeIndex] = CPLStrdup(osType);
907
papszTokens[iTypeIndex + 1] = NULL;
909
/* -------------------------------------------------------------------- */
910
/* Find the named layer. */
911
/* -------------------------------------------------------------------- */
912
OGRLayer *poLayer = GetLayerByName(pszLayerName);
913
if( poLayer == NULL )
915
CPLError( CE_Failure, CPLE_AppDefined,
916
"%s failed, no such layer as `%s'.",
919
CSLDestroy( papszTokens );
920
return OGRERR_FAILURE;
923
/* -------------------------------------------------------------------- */
925
/* -------------------------------------------------------------------- */
927
int nWidth = 0, nPrecision = 0;
928
OGRFieldType eType = OGRDataSourceParseSQLType(pszType, nWidth, nPrecision);
929
OGRFieldDefn oFieldDefn(pszColumnName, eType);
930
oFieldDefn.SetWidth(nWidth);
931
oFieldDefn.SetPrecision(nPrecision);
933
CSLDestroy( papszTokens );
935
return poLayer->CreateField( &oFieldDefn );
938
/************************************************************************/
939
/* ProcessSQLAlterTableDropColumn() */
941
/* The correct syntax for droping a column in the OGR SQL */
944
/* ALTER TABLE <layername> DROP [COLUMN] <columnname> */
945
/************************************************************************/
947
OGRErr OGRDataSource::ProcessSQLAlterTableDropColumn( const char *pszSQLCommand )
950
char **papszTokens = CSLTokenizeString( pszSQLCommand );
952
/* -------------------------------------------------------------------- */
953
/* Do some general syntax checking. */
954
/* -------------------------------------------------------------------- */
955
const char* pszLayerName = NULL;
956
const char* pszColumnName = NULL;
957
if( CSLCount(papszTokens) == 6
958
&& EQUAL(papszTokens[0],"ALTER")
959
&& EQUAL(papszTokens[1],"TABLE")
960
&& EQUAL(papszTokens[3],"DROP")
961
&& EQUAL(papszTokens[4],"COLUMN"))
963
pszLayerName = papszTokens[2];
964
pszColumnName = papszTokens[5];
966
else if( CSLCount(papszTokens) == 5
967
&& EQUAL(papszTokens[0],"ALTER")
968
&& EQUAL(papszTokens[1],"TABLE")
969
&& EQUAL(papszTokens[3],"DROP"))
971
pszLayerName = papszTokens[2];
972
pszColumnName = papszTokens[4];
976
CSLDestroy( papszTokens );
977
CPLError( CE_Failure, CPLE_AppDefined,
978
"Syntax error in ALTER TABLE DROP COLUMN command.\n"
980
"Should be of form 'ALTER TABLE <layername> DROP [COLUMN] <columnname>'",
982
return OGRERR_FAILURE;
985
/* -------------------------------------------------------------------- */
986
/* Find the named layer. */
987
/* -------------------------------------------------------------------- */
988
OGRLayer *poLayer = GetLayerByName(pszLayerName);
989
if( poLayer == NULL )
991
CPLError( CE_Failure, CPLE_AppDefined,
992
"%s failed, no such layer as `%s'.",
995
CSLDestroy( papszTokens );
996
return OGRERR_FAILURE;
999
/* -------------------------------------------------------------------- */
1000
/* Find the field. */
1001
/* -------------------------------------------------------------------- */
1003
int nFieldIndex = poLayer->GetLayerDefn()->GetFieldIndex(pszColumnName);
1004
if( nFieldIndex < 0 )
1006
CPLError( CE_Failure, CPLE_AppDefined,
1007
"%s failed, no such field as `%s'.",
1010
CSLDestroy( papszTokens );
1011
return OGRERR_FAILURE;
1015
/* -------------------------------------------------------------------- */
1017
/* -------------------------------------------------------------------- */
1019
CSLDestroy( papszTokens );
1021
return poLayer->DeleteField( nFieldIndex );
1024
/************************************************************************/
1025
/* ProcessSQLAlterTableRenameColumn() */
1027
/* The correct syntax for renaming a column in the OGR SQL */
1030
/* ALTER TABLE <layername> RENAME [COLUMN] <oldname> TO <newname> */
1031
/************************************************************************/
1033
OGRErr OGRDataSource::ProcessSQLAlterTableRenameColumn( const char *pszSQLCommand )
1036
char **papszTokens = CSLTokenizeString( pszSQLCommand );
1038
/* -------------------------------------------------------------------- */
1039
/* Do some general syntax checking. */
1040
/* -------------------------------------------------------------------- */
1041
const char* pszLayerName = NULL;
1042
const char* pszOldColName = NULL;
1043
const char* pszNewColName = NULL;
1044
if( CSLCount(papszTokens) == 8
1045
&& EQUAL(papszTokens[0],"ALTER")
1046
&& EQUAL(papszTokens[1],"TABLE")
1047
&& EQUAL(papszTokens[3],"RENAME")
1048
&& EQUAL(papszTokens[4],"COLUMN")
1049
&& EQUAL(papszTokens[6],"TO"))
1051
pszLayerName = papszTokens[2];
1052
pszOldColName = papszTokens[5];
1053
pszNewColName = papszTokens[7];
1055
else if( CSLCount(papszTokens) == 7
1056
&& EQUAL(papszTokens[0],"ALTER")
1057
&& EQUAL(papszTokens[1],"TABLE")
1058
&& EQUAL(papszTokens[3],"RENAME")
1059
&& EQUAL(papszTokens[5],"TO"))
1061
pszLayerName = papszTokens[2];
1062
pszOldColName = papszTokens[4];
1063
pszNewColName = papszTokens[6];
1067
CSLDestroy( papszTokens );
1068
CPLError( CE_Failure, CPLE_AppDefined,
1069
"Syntax error in ALTER TABLE RENAME COLUMN command.\n"
1071
"Should be of form 'ALTER TABLE <layername> RENAME [COLUMN] <columnname> <columntype>'",
1073
return OGRERR_FAILURE;
1076
/* -------------------------------------------------------------------- */
1077
/* Find the named layer. */
1078
/* -------------------------------------------------------------------- */
1079
OGRLayer *poLayer = GetLayerByName(pszLayerName);
1080
if( poLayer == NULL )
1082
CPLError( CE_Failure, CPLE_AppDefined,
1083
"%s failed, no such layer as `%s'.",
1086
CSLDestroy( papszTokens );
1087
return OGRERR_FAILURE;
1090
/* -------------------------------------------------------------------- */
1091
/* Find the field. */
1092
/* -------------------------------------------------------------------- */
1094
int nFieldIndex = poLayer->GetLayerDefn()->GetFieldIndex(pszOldColName);
1095
if( nFieldIndex < 0 )
1097
CPLError( CE_Failure, CPLE_AppDefined,
1098
"%s failed, no such field as `%s'.",
1101
CSLDestroy( papszTokens );
1102
return OGRERR_FAILURE;
1105
/* -------------------------------------------------------------------- */
1106
/* Rename column. */
1107
/* -------------------------------------------------------------------- */
1108
OGRFieldDefn* poOldFieldDefn = poLayer->GetLayerDefn()->GetFieldDefn(nFieldIndex);
1109
OGRFieldDefn oNewFieldDefn(poOldFieldDefn);
1110
oNewFieldDefn.SetName(pszNewColName);
1112
CSLDestroy( papszTokens );
1114
return poLayer->AlterFieldDefn( nFieldIndex, &oNewFieldDefn, ALTER_NAME_FLAG );
1117
/************************************************************************/
1118
/* ProcessSQLAlterTableAlterColumn() */
1120
/* The correct syntax for altering the type of a column in the */
1121
/* OGR SQL dialect is: */
1123
/* ALTER TABLE <layername> ALTER [COLUMN] <columnname> TYPE <newtype> */
1124
/************************************************************************/
1126
OGRErr OGRDataSource::ProcessSQLAlterTableAlterColumn( const char *pszSQLCommand )
1129
char **papszTokens = CSLTokenizeString( pszSQLCommand );
1131
/* -------------------------------------------------------------------- */
1132
/* Do some general syntax checking. */
1133
/* -------------------------------------------------------------------- */
1134
const char* pszLayerName = NULL;
1135
const char* pszColumnName = NULL;
1136
char* pszType = NULL;
1138
int nTokens = CSLCount(papszTokens);
1141
&& EQUAL(papszTokens[0],"ALTER")
1142
&& EQUAL(papszTokens[1],"TABLE")
1143
&& EQUAL(papszTokens[3],"ALTER")
1144
&& EQUAL(papszTokens[4],"COLUMN")
1145
&& EQUAL(papszTokens[6],"TYPE"))
1147
pszLayerName = papszTokens[2];
1148
pszColumnName = papszTokens[5];
1151
else if( nTokens >= 7
1152
&& EQUAL(papszTokens[0],"ALTER")
1153
&& EQUAL(papszTokens[1],"TABLE")
1154
&& EQUAL(papszTokens[3],"ALTER")
1155
&& EQUAL(papszTokens[5],"TYPE"))
1157
pszLayerName = papszTokens[2];
1158
pszColumnName = papszTokens[4];
1163
CSLDestroy( papszTokens );
1164
CPLError( CE_Failure, CPLE_AppDefined,
1165
"Syntax error in ALTER TABLE ALTER COLUMN command.\n"
1167
"Should be of form 'ALTER TABLE <layername> ALTER [COLUMN] <columnname> TYPE <columntype>'",
1169
return OGRERR_FAILURE;
1172
/* -------------------------------------------------------------------- */
1173
/* Merge type components into a single string if there were split */
1175
/* -------------------------------------------------------------------- */
1177
for(int i=iTypeIndex;i<nTokens;i++)
1179
osType += papszTokens[i];
1180
CPLFree(papszTokens[i]);
1182
pszType = papszTokens[iTypeIndex] = CPLStrdup(osType);
1183
papszTokens[iTypeIndex + 1] = NULL;
1185
/* -------------------------------------------------------------------- */
1186
/* Find the named layer. */
1187
/* -------------------------------------------------------------------- */
1188
OGRLayer *poLayer = GetLayerByName(pszLayerName);
1189
if( poLayer == NULL )
1191
CPLError( CE_Failure, CPLE_AppDefined,
1192
"%s failed, no such layer as `%s'.",
1195
CSLDestroy( papszTokens );
1196
return OGRERR_FAILURE;
1199
/* -------------------------------------------------------------------- */
1200
/* Find the field. */
1201
/* -------------------------------------------------------------------- */
1203
int nFieldIndex = poLayer->GetLayerDefn()->GetFieldIndex(pszColumnName);
1204
if( nFieldIndex < 0 )
1206
CPLError( CE_Failure, CPLE_AppDefined,
1207
"%s failed, no such field as `%s'.",
1210
CSLDestroy( papszTokens );
1211
return OGRERR_FAILURE;
1214
/* -------------------------------------------------------------------- */
1216
/* -------------------------------------------------------------------- */
1218
OGRFieldDefn* poOldFieldDefn = poLayer->GetLayerDefn()->GetFieldDefn(nFieldIndex);
1219
OGRFieldDefn oNewFieldDefn(poOldFieldDefn);
1221
int nWidth = 0, nPrecision = 0;
1222
OGRFieldType eType = OGRDataSourceParseSQLType(pszType, nWidth, nPrecision);
1223
oNewFieldDefn.SetType(eType);
1224
oNewFieldDefn.SetWidth(nWidth);
1225
oNewFieldDefn.SetPrecision(nPrecision);
1228
if (poOldFieldDefn->GetType() != oNewFieldDefn.GetType())
1229
nFlags |= ALTER_TYPE_FLAG;
1230
if (poOldFieldDefn->GetWidth() != oNewFieldDefn.GetWidth() ||
1231
poOldFieldDefn->GetPrecision() != oNewFieldDefn.GetPrecision())
1232
nFlags |= ALTER_WIDTH_PRECISION_FLAG;
1234
CSLDestroy( papszTokens );
1239
return poLayer->AlterFieldDefn( nFieldIndex, &oNewFieldDefn, nFlags );
1242
/************************************************************************/
723
1243
/* ExecuteSQL() */
724
1244
/************************************************************************/