TDbiTableMetaData.cxx
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007 #include <cassert>
00008 #include <cctype>
00009 #include <sstream>
00010
00011 #include "TString.h"
00012
00013 #include "TDbi.hxx"
00014 #include "TDbiString.hxx"
00015 #include "TDbiTableMetaData.hxx"
00016 #include <TSK_DBI_Log.hxx>
00017 #include <MsgFormat.h>
00018 using std::endl;
00019
00020 ClassImp(TDbiTableMetaData)
00021
00022
00023
00024
00025
00026 TDbiTableMetaData::ColumnAttributes TDbiTableMetaData::fgDummy;
00027
00028
00029
00030
00031
00032
00033
00034
00035 TDbiTableMetaData::TDbiTableMetaData(const string& tableName) :
00036 fNumCols(0),
00037 fTableName(tableName)
00038 {
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050 SK_DBI_Trace( "Creating TDbiTableMetaData" << " ");
00051
00052 }
00053
00054
00055
00056 TDbiTableMetaData::~TDbiTableMetaData() {
00057
00058
00059
00060
00061
00062 SK_DBI_Trace( "Destroying TDbiTableMetaData" << " ");
00063
00064 }
00065
00066
00067
00068 void TDbiTableMetaData::Clear() {
00069
00070
00071
00072
00073
00074
00075 fColAttr.clear();
00076 fNumCols = 0;
00077
00078 }
00079
00080
00081
00082 void TDbiTableMetaData::ExpandTo(UInt_t colNum) {
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104 assert ( colNum < MAXCOL );
00105 while ( fNumCols < colNum ) {
00106 fColAttr.push_back(ColumnAttributes());
00107 ++fNumCols;
00108 }
00109 }
00110
00111
00112
00113 const TDbiTableMetaData::ColumnAttributes& TDbiTableMetaData::GetAttributes(Int_t colNum) const {
00114
00115
00116
00117 if ( colNum > 0 && colNum <= (signed) fNumCols ) return fColAttr[colNum-1];
00118 fgDummy.SetDefault();
00119 return fgDummy;
00120
00121 }
00122
00123
00124
00125 string TDbiTableMetaData::GetToken(const char*& strPtr) {
00126
00127
00128
00129
00130 string token;
00131
00132
00133 while ( isspace(*strPtr) ) ++strPtr;
00134 if ( *strPtr == 0 ) return token;
00135
00136
00137 char firstChar = *strPtr++;
00138 token = firstChar;
00139 if ( ! isalnum(firstChar) && firstChar != '_' ) return token;
00140
00141
00142 while ( isalnum(*strPtr) || *strPtr == '_' ) token += *strPtr++;
00143 return token;
00144
00145 }
00146
00147
00148
00149 TDbiTableMetaData::ColumnAttributes& TDbiTableMetaData::SetAttributes(Int_t colNum) {
00150
00151
00152
00153 this->ExpandTo(colNum);
00154
00155 return const_cast<TDbiTableMetaData::ColumnAttributes&>(this->GetAttributes(colNum));
00156
00157 }
00158
00159
00160
00161
00162 void TDbiTableMetaData::SetColFieldType(const TDbiFieldType& fieldType,
00163 Int_t colNum) {
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173 ColumnAttributes& attrib(this->SetAttributes(colNum));
00174 UInt_t concept = fieldType.GetConcept();
00175 attrib.Type = fieldType;
00176 attrib.MustDelimit = concept == TDbi::kString || concept == TDbi::kDate || concept == TDbi::kChar;
00177 attrib.Concept = concept;
00178
00179 }
00180
00181
00182
00183 void TDbiTableMetaData::SetFromSql(const string& sql) {
00184
00185
00186
00187
00188
00189 TString SqlUpper(sql);
00190 SqlUpper.ToUpper();
00191
00192 const char* strPtr = SqlUpper.Data();
00193
00194 string token1(TDbiTableMetaData::GetToken(strPtr));
00195 string token2(TDbiTableMetaData::GetToken(strPtr));
00196 string token3(TDbiTableMetaData::GetToken(strPtr));
00197 string token4(TDbiTableMetaData::GetToken(strPtr));
00198
00199 if ( token1 != "CREATE" || token2 != "TABLE" || token4 != "(" ) {
00200 SK_DBI_Severe( "Cannot recreate: SQL " << SqlUpper
00201 << " does not start CREATE TABLE ... (" << " ");
00202 return;
00203 }
00204
00205 this->Clear();
00206 fTableName = token3;
00207 SK_DBI_Log( "Recreating TDbiTableMetaData for table " << fTableName << " ");
00208
00209
00210 Int_t col = 0;
00211
00212 string delim;
00213 while ( delim != ")" ) {
00214 string name = TDbiTableMetaData::GetToken(strPtr);
00215
00216
00217 if ( name == "INDEX" || name == "KEY" || name == "PRIMARY" ) {
00218 if ( name == "PRIMARY" || name == "KEY" )delim = TDbiTableMetaData::GetToken(strPtr);
00219 delim = TDbiTableMetaData::GetToken(strPtr);
00220 if ( delim == "(" ) while ( delim != ")" ) delim = TDbiTableMetaData::GetToken(strPtr);
00221 delim = TDbiTableMetaData::GetToken(strPtr);
00222 continue;
00223 }
00224
00225
00226 ++col;
00227 this->SetColName(name,col);
00228 this->SetColIsNullable(col);
00229
00230 string type = TDbiTableMetaData::GetToken(strPtr);
00231 int precision = 0;
00232 delim = TDbiTableMetaData::GetToken(strPtr);
00233 if ( delim == "(" ) {
00234 delim = TDbiTableMetaData::GetToken(strPtr);
00235 istringstream is(delim);
00236 is >> precision;
00237 delim = TDbiTableMetaData::GetToken(strPtr);
00238 delim = TDbiTableMetaData::GetToken(strPtr);
00239 }
00240 TDbiFieldType ft(type,precision);
00241 this->SetColFieldType(ft,col);
00242 SK_DBI_Log( " Column: " << col << " name " << this->ColName(col)
00243 << " type " << this->ColFieldType(col).AsString()
00244 << " precision " << precision << " ");
00245
00246
00247
00248 while ( delim != "," && delim != ")" ) {
00249 string opt2 = TDbiTableMetaData::GetToken(strPtr);
00250 if ( delim == "NOT" && opt2 == "NULL") {
00251 this->SetColIsNullable(col,false);
00252 delim = TDbiTableMetaData::GetToken(strPtr);
00253 }
00254 else if ( delim == "PRIMARY" && opt2 == "KEY") {
00255 delim = TDbiTableMetaData::GetToken(strPtr);
00256 }
00257 else if ( delim == "AUTO_INCREMENT") {
00258 delim = opt2;
00259 }
00260 else if ( delim == "UNSIGNED") {
00261 delim = opt2;
00262 }
00263 else {
00264 SK_DBI_Warn( "Column: " << col << " name " << name << " type " << ft.AsString()
00265 << " ignoring unknown option: " << delim << " ");
00266 delim = opt2;
00267 }
00268 }
00269 }
00270
00271 }
00272
00273
00274
00275
00276 string TDbiTableMetaData::Sql() const {
00277
00278
00279
00280
00281
00282
00283 Bool_t mainTable = fTableName.substr(fTableName.size()-3,3) != "VLD";
00284
00285 string tableName = fTableName;
00286 TDbiString sql;
00287 sql.GetString() = "";
00288 sql << "create table " << tableName << "(";
00289
00290
00291
00292
00293 int numCols = this->NumCols();
00294 for(int i=1; i<= numCols; i++) {
00295
00296 sql << this->ColName(i) << " " ;
00297 sql << this->ColFieldType(i).AsSQLString();
00298
00299 if( this->ColName(i) == "SEQNO"
00300 && ! mainTable ) sql << " not null primary key" ;
00301
00302 else if( ! this->ColIsNullable(i)
00303 || this->ColName(i) == "SEQNO"
00304 || this->ColName(i) == "ROW_COUNTER"
00305 ) sql << " not null" ;
00306
00307 if (i < numCols) sql << ", ";
00308
00309 }
00310
00311
00312
00313
00314 if ( fTableName == "GLOBALSEQNO" || fTableName == "LOCALSEQNO" ) {
00315 sql << ")";
00316 }
00317
00318 else {
00319 if ( mainTable ) {
00320 sql << ", primary key (SEQNO,ROW_COUNTER)";
00321 }
00322 else {
00323 sql << ", key TIMESTART (TIMESTART), key TIMEEND (TIMEEND)";
00324 }
00325 sql << ")";
00326 }
00327
00328 return sql.GetString();
00329
00330 }
00331
00332