00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #include "TeOCICursor.h"
00026 #include "TeOCISDO.h"
00027 #include "TeUtils.h"
00028
00029
00030 #include <cstring>
00031 #include <cstdlib>
00032
00033
00034 string getSQLToLoadBlobLength(const string& sql, const vector<string>& blobNames)
00035 {
00036 string sqlSelectAux, sqlFromAux, sqlWhereAux;
00037
00038
00039 size_t posFrom = sql.find(" FROM ", 0);
00040 sqlSelectAux = sql.substr(0, posFrom);
00041
00042
00043 sqlWhereAux = " ";
00044 size_t posWhere = sql.find(" WHERE ", 0);
00045 if(posWhere != string::npos)
00046 {
00047 sqlFromAux = sql.substr(posFrom, (posWhere-posFrom)+1);
00048 sqlWhereAux = sql.substr(posWhere);
00049 }
00050 else
00051 sqlFromAux = sql.substr(posFrom);
00052
00053 string beforeBlobName="";
00054
00055 size_t pos = sqlSelectAux.find (" *", 0);
00056 if(pos != string::npos)
00057 {
00058
00059
00060
00061 size_t posJoin = sqlFromAux.find(" JOIN ", 0);
00062 size_t posVirg = sqlFromAux.find(",", 0);
00063
00064 if((posJoin!=string::npos) || (posVirg!=string::npos))
00065 {
00066 string aux = " FROM ( SELECT * "+ sqlFromAux + sqlWhereAux +" ) t ";
00067 sqlFromAux = aux;
00068 sqlWhereAux = "";
00069 }
00070 else
00071 sqlFromAux += " t ";
00072
00073 sqlSelectAux.replace(pos+1, 1, " t.* ");
00074 beforeBlobName = "t.";
00075 }
00076
00077 for(unsigned int i=0; i<blobNames.size(); ++i)
00078 sqlSelectAux += " , LENGTH("+ beforeBlobName + blobNames[i] +") ";
00079
00080 return (sqlSelectAux+sqlFromAux+sqlWhereAux);
00081
00082 }
00083
00084
00085 char* StrClean(char *name)
00086 {
00087 int j;
00088
00089 if ((name == NULL))
00090 return 0;
00091
00092 for (j = strlen(name)-1; j>=0; j--)
00093 {
00094 if ( !((name[j]==' ') || (name[j]=='\t') || (name[j]== '\0')) )
00095 break;
00096 }
00097
00098 name[j+1] = '\0';
00099
00100 return name;
00101 }
00102
00103
00104 TeOCICursor::TeOCICursor(TeOCIConnection* connec, const unsigned long& maxBlobSize, const unsigned long& maxRowNum)
00105 {
00106 if(!connec)
00107 return;
00108
00109 maxRows_ = MAX_ROWS;
00110 maxBuflen_ = MAX_BLOB_LENGTH;
00111
00112
00113 if(maxBlobSize>0)
00114 maxBuflen_ = maxBlobSize;
00115
00116 if(maxRowNum>0)
00117 maxRows_ = maxRowNum;
00118
00119 connection_ = connec;
00120 stmthpToQuery_ = NULL;
00121 dschp_ = NULL;
00122 fieldValue_ = "";
00123 ordinates_ = 0;
00124 isOpen_ = false;
00125 hasBlob_ = false;
00126 row_Index_ = -1;
00127 rows_Fetched_ = 0;
00128 rows_Mem_ = 0;
00129 row_Cur_ = -1;
00130 last_Row_ = false;
00131 errorMessage_ = "";
00132 numColls_ = -1;
00133 colBlobName_.clear();
00134
00135 if(connection_->useSDOType())
00136 {
00137 for(int i=0;i<maxRows_;i++)
00138 {
00139 global_geom_obj_[i] = NULL;
00140 global_geom_ind_[i] = NULL;
00141 }
00142 }
00143 }
00144
00145 bool TeOCICursor::open()
00146 {
00147 if(!connection_)
00148 return false;
00149
00150 sword status;
00151 if(isOpen_)
00152 this->close();
00153 isOpen_ = false;
00154
00155
00156 status = SDO_OCIHandleAlloc((dvoid*)connection_->envhp_, (dvoid**)&stmthpToQuery_,
00157 (ub4)OCI_HTYPE_STMT, (size_t)0, (dvoid**)0);
00158 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00159 return false;
00160
00161
00162 status = SDO_OCIHandleAlloc((dvoid*)connection_->envhp_, (dvoid**)&dschp_,
00163 (ub4)OCI_HTYPE_DESCRIBE, (size_t)0, (dvoid **)0);
00164 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00165 {
00166
00167 SDO_OCIHandleFree((dvoid *)stmthpToQuery_, (ub4)OCI_HTYPE_STMT);
00168 return false;
00169 }
00170
00171 if(connection_->useSDOType())
00172 {
00173 status = SDO_OCIObjectNew(connection_->envhp_, connection_->errhp_, connection_->svchp_, OCI_TYPECODE_VARRAY,
00174 connection_->tdo_ordinates_, (dvoid*)NULL, OCI_DURATION_SESSION, TRUE,
00175 (dvoid**)&ordinates_);
00176
00177 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00178 {
00179
00180 SDO_OCIHandleFree((dvoid*)dschp_, (ub4)OCI_HTYPE_DESCRIBE);
00181
00182 SDO_OCIHandleFree((dvoid *)stmthpToQuery_, (ub4)OCI_HTYPE_STMT);
00183 return false;
00184 }
00185 }
00186 isOpen_ = true;
00187 return true;
00188 }
00189
00190
00191 void TeOCICursor::close()
00192 {
00193 freeResult();
00194
00195 if(isOpen_)
00196 {
00197 SDO_OCIHandleFree((dvoid *)stmthpToQuery_, (ub4)OCI_HTYPE_STMT);
00198 SDO_OCIHandleFree((dvoid*)dschp_, (ub4)OCI_HTYPE_DESCRIBE);
00199 stmthpToQuery_ = NULL;
00200 dschp_ = NULL;
00201 }
00202 isOpen_ = false;
00203 numColls_ = -1;
00204 }
00205
00206 void TeOCICursor::freeResult()
00207 {
00208
00209 for(unsigned int b=0; b<lobBuffer_.size(); ++b)
00210 {
00211 if(lobBuffer_[b])
00212 {
00213 delete [] lobBuffer_[b];
00214 lobBuffer_[b] = NULL;
00215 }
00216 }
00217 lobBuffer_.clear();
00218
00219
00220 for(unsigned int i=0; i<buffers_.size();i++)
00221 {
00222 int coltype = colType_[i];
00223 switch (coltype)
00224 {
00225 case 3:
00226 delete [] ((signed int*) buffers_[i]);
00227 break;
00228
00229 case 2:
00230 delete [] ((OCINumber*) buffers_[i]);
00231 break;
00232
00233 case 4:
00234 delete [] ((double*) buffers_[i]);
00235 break;
00236
00237 case 96:
00238 case 9:
00239 case 1:
00240 delete [] ((char *) buffers_[i]);
00241 break;
00242
00243 case 12:
00244 delete [] ((OCIDate *) buffers_[i]);
00245 break;
00246 default:
00247 break;
00248
00249 }
00250 }
00251
00252
00253 if(connection_->useSDOType())
00254 {
00255 for(int i=0;i<maxRows_;i++)
00256 {
00257
00258 OCIObjectFree(connection_->envhp_, connection_->errhp_, (dvoid *)global_geom_obj_[i],
00259 (ub2)OCI_OBJECTFREE_FORCE);
00260
00261 global_geom_obj_[i] = NULL;
00262 global_geom_ind_[i] = NULL;
00263 }
00264
00265 OCIObjectFree(connection_->envhp_, connection_->errhp_, (dvoid *)ordinates_, (ub2)OCI_OBJECTFREE_FORCE);
00266 ordinates_ = 0;
00267 }
00268
00269 buffers_.clear();
00270 defines_.clear();
00271 ind_.clear();
00272 colType_.clear();
00273 colSize_.clear();
00274 colScale_.clear();
00275 colName_.clear();
00276 numColls_ = -1;
00277 hasBlob_ = false;
00278 colBlobName_.clear();
00279 }
00280
00281
00282 void TeOCICursor::defineByPos(int pos, void* value, int size, void* indicator,
00283 int type)
00284 {
00285 OCIDefine *defnp = NULL;
00286
00287 SDO_OCIDefineByPos(stmthpToQuery_, &defnp, connection_->errhp_, (ub4)pos,
00288 (dvoid *)value, (sb4)size, type,
00289 (dvoid *)indicator, (ub2 *)0, (ub2 *)0,
00290 (ub4)OCI_DEFAULT);
00291 }
00292
00293
00294 bool TeOCICursor::fetch(int rows)
00295 {
00296 sword status;
00297 status = OCIStmtFetch(stmthpToQuery_, connection_->errhp_, (ub4) rows, (ub4) OCI_FETCH_NEXT,
00298 (ub4) OCI_DEFAULT);
00299
00300 if (status == OCI_SUCCESS || status == OCI_SUCCESS_WITH_INFO)
00301 return true;
00302 else
00303 return false;
00304
00305 }
00306
00307 bool TeOCICursor::appendOrdinates(const double& val)
00308 {
00309
00310 OCINumber oci_number;
00311 sword status;
00312
00313 if(!ordinates_)
00314 {
00315 status = SDO_OCIObjectNew(connection_->envhp_, connection_->errhp_, connection_->svchp_, OCI_TYPECODE_VARRAY,
00316 connection_->tdo_ordinates_, (dvoid*)NULL, OCI_DURATION_SESSION, TRUE,
00317 (dvoid**)&ordinates_);
00318
00319 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00320 return false;
00321 }
00322
00323 status = OCINumberFromReal(connection_->errhp_, (dvoid *)&(val),
00324 (uword)sizeof(double),&oci_number);
00325
00326 status = OCICollAppend(connection_->envhp_, connection_->errhp_,
00327 (dvoid *) &oci_number,
00328 (dvoid *)0, (OCIColl *)ordinates_);
00329
00330 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00331 return false;
00332
00333 return true;
00334 }
00335
00336 bool TeOCICursor::bindOrdinates()
00337 {
00338 OCIBind *bnd1p = NULL;
00339 sword status;
00340
00341 if(!ordinates_)
00342 {
00343 status = SDO_OCIObjectNew(connection_->envhp_, connection_->errhp_, connection_->svchp_, OCI_TYPECODE_VARRAY,
00344 connection_->tdo_ordinates_, (dvoid*)NULL, OCI_DURATION_SESSION, TRUE,
00345 (dvoid**)&ordinates_);
00346
00347 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00348 return false;
00349 }
00350
00351
00352 status = OCIBindByName(stmthpToQuery_, &bnd1p, connection_->errhp_,
00353 (text *)":ordinates_", (sb4)-1, (dvoid *)0, (sb4)0, SQLT_NTY, (dvoid *)0,
00354 (ub2 *)0, (ub2 *)0, (ub4)0, (ub4 *)0, (ub4)OCI_DEFAULT);
00355 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00356 return false;
00357
00358 status = OCIBindObject(bnd1p, connection_->errhp_, connection_->tdo_ordinates_, (dvoid **)&ordinates_, (ub4 *)0,
00359 (dvoid **)0, (ub4 *)0);
00360 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00361 return false;
00362
00363 return true;
00364 }
00365
00366 bool TeOCICursor::moveFirst()
00367 {
00368 sword status;
00369 if(!hasBlob_)
00370
00371 status = OCIStmtFetch2(stmthpToQuery_, connection_->errhp_, (ub4)maxRows_, OCI_FETCH_FIRST, (sb4) 0, OCI_DEFAULT);
00372 else
00373 status = OCIStmtFetch2(stmthpToQuery_, connection_->errhp_, (ub4)maxRows_, OCI_FETCH_NEXT, (sb4) 0, OCI_DEFAULT);
00374
00375 checkError(status);
00376 if (status == OCI_SUCCESS || status == OCI_SUCCESS_WITH_INFO || status == OCI_NO_DATA)
00377 {
00378 OCIAttrGet((dvoid *)stmthpToQuery_, (ub4)OCI_HTYPE_STMT,
00379 (dvoid *)&rows_Fetched_, (ub4 *)0,
00380 (ub4)OCI_ATTR_ROW_COUNT, connection_->errhp_);
00381
00382 if(!rows_Fetched_)
00383 return false;
00384
00385 if(status == OCI_NO_DATA)
00386 last_Row_ = true;
00387
00388 row_Index_ = 0;
00389
00390 if(rows_Fetched_ < maxRows_)
00391 rows_Mem_ = rows_Fetched_;
00392 else
00393 rows_Mem_ = maxRows_;
00394
00395 row_Cur_ = 0;
00396 return true;
00397 }
00398 return false;
00399 }
00400
00401 bool TeOCICursor::moveNext()
00402 {
00403 sword status;
00404
00405 if((row_Index_+1) >= rows_Mem_)
00406 {
00407 if(last_Row_)
00408 return false;
00409
00410
00411 status = OCIStmtFetch2(stmthpToQuery_, connection_->errhp_, (ub4) maxRows_, OCI_FETCH_NEXT, (sb4) 0, OCI_DEFAULT);
00412
00413 if (status == OCI_SUCCESS || status == OCI_SUCCESS_WITH_INFO || status == OCI_NO_DATA)
00414 {
00415 OCIAttrGet((dvoid *)stmthpToQuery_, (ub4)OCI_HTYPE_STMT,
00416 (dvoid *)&rows_Fetched_, (ub4 *)0,
00417 (ub4)OCI_ATTR_ROWS_FETCHED, connection_->errhp_);
00418
00419 if(!rows_Fetched_)
00420 return false;
00421
00422 if(status == OCI_NO_DATA)
00423 {
00424 if(last_Row_)
00425 return false;
00426 else
00427 last_Row_ = true;
00428 }
00429
00430 row_Index_ = 0;
00431
00432 if(rows_Fetched_ < maxRows_)
00433 rows_Mem_ = rows_Fetched_;
00434 else
00435 rows_Mem_ = maxRows_;
00436
00437 row_Cur_++;
00438 return true;
00439 }
00440 else
00441 return false;
00442 }
00443 else
00444 row_Index_++;
00445
00446 row_Cur_++;
00447 return true;
00448 }
00449
00450 bool TeOCICursor::moveLast()
00451 {
00452 sword status = OCIStmtFetch2(stmthpToQuery_, connection_->errhp_, (ub4) 1,
00453 OCI_FETCH_LAST, (sb4) 0, OCI_DEFAULT);
00454
00455 if (status == OCI_SUCCESS || status == OCI_SUCCESS_WITH_INFO)
00456 {
00457 last_Row_ = true;
00458 return true;
00459 }
00460 else
00461 return false;
00462 }
00463
00464 bool TeOCICursor::moveTo(int pos)
00465 {
00466
00467 if(hasBlob_)
00468 {
00469
00470
00471 int topos;
00472 if(pos > 0)
00473 topos = pos-1;
00474 else
00475 topos = row_Cur_ + pos;
00476 if(topos < 0)
00477 topos = 0;
00478
00479 if(!moveFirst())
00480 return false;
00481
00482 while(row_Cur_ != topos)
00483 {
00484 if(!moveNext())
00485 return false;
00486 }
00487 return true;
00488 }
00489
00490 sword status;
00491 int auxPos = maxRows_*int(pos/maxRows_);
00492
00493
00494
00495 if(int(row_Cur_/maxRows_) == int(pos/maxRows_))
00496 {
00497 row_Index_ = pos - (maxRows_*int(pos/maxRows_));
00498 row_Cur_ = pos;
00499 return true;
00500 }
00501
00502 if(pos<row_Cur_)
00503 {
00504 if(!moveFirst())
00505 return false;
00506 }
00507
00508 status = OCIStmtFetch2(stmthpToQuery_, connection_->errhp_, (ub4) maxRows_, OCI_FETCH_ABSOLUTE, (sb4)auxPos+1, OCI_DEFAULT);
00509 row_Index_ = pos-auxPos;
00510 row_Cur_ = pos;
00511
00512 if (status == OCI_SUCCESS || status == OCI_SUCCESS_WITH_INFO || status == OCI_NO_DATA)
00513 {
00514 OCIAttrGet((dvoid *)stmthpToQuery_, (ub4)OCI_HTYPE_STMT,
00515 (dvoid *)&rows_Fetched_, (ub4 *)0,
00516 (ub4)OCI_ATTR_ROWS_FETCHED, connection_->errhp_);
00517
00518 if(!rows_Fetched_)
00519 return false;
00520
00521 if(status == OCI_NO_DATA)
00522 last_Row_ = true;
00523 return true;
00524 }
00525
00526 return false;
00527 }
00528
00529
00530 bool TeOCICursor::checkError(sword status)
00531 {
00532 sb4 errcode = 0;
00533 char message[256];
00534 bool returnedVal = false;
00535
00536 if (status == OCI_ERROR)
00537 {
00538 SDO_OCIErrorGet((dvoid*)connection_->errhp_, (ub4)1, (text*)NULL, &errcode,
00539 (text*)message, (ub4)256, OCI_HTYPE_ERROR);
00540
00541 errorMessage_ = message;
00542 return false;
00543 }
00544
00545 switch (status)
00546 {
00547 case OCI_SUCCESS:
00548 errorMessage_ = "Success!";
00549 returnedVal = true;
00550 break;
00551
00552 case OCI_SUCCESS_WITH_INFO:
00553 errorMessage_ = "Success with information!";
00554 returnedVal = true;
00555 break;
00556
00557 case OCI_NEED_DATA:
00558 errorMessage_ = "Need data!";
00559 break;
00560
00561 case OCI_NO_DATA:
00562 errorMessage_ = "No data!";
00563 break;
00564
00565
00566
00567 case OCI_INVALID_HANDLE:
00568 errorMessage_ = "Invalid handle!";
00569 break;
00570
00571 case OCI_STILL_EXECUTING:
00572 errorMessage_ = "Still executing!";
00573 break;
00574
00575 case OCI_CONTINUE:
00576 errorMessage_ = "Continue!";
00577 break;
00578 default:
00579 break;
00580 }
00581
00582 return returnedVal;
00583
00584 }
00585
00586
00587 bool TeOCICursor::prepare(const string& stmt)
00588 {
00589 ub4 size = stmt.size();
00590 sword status = SDO_OCIStmtPrepare(connection_->svchp_, (OCIStmt *)stmthpToQuery_, connection_->errhp_, (text*)stmt.c_str(), (ub4)size,
00591 (text*)0, (ub4)0, (ub4)OCI_NTV_SYNTAX, (ub4)OCI_DEFAULT);
00592 if((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00593 return false;
00594
00595 return true;
00596 }
00597
00598
00599 int TeOCICursor::queryType()
00600 {
00601 ub2 querytype_;
00602
00603 sword status = OCIAttrGet((dvoid *)stmthpToQuery_, (ub4)OCI_HTYPE_STMT, (ub2 *)&querytype_,
00604 (ub4*)NULL, (ub4)OCI_ATTR_STMT_TYPE, (OCIError *)connection_->errhp_);
00605 if((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00606 return -1;
00607 return (querytype_);
00608 }
00609
00610 bool TeOCICursor::query(const string& query)
00611 {
00612 if (!isOpen_)
00613 open();
00614
00615 row_Index_ = -1;
00616 rows_Fetched_ = 0;
00617 rows_Mem_ = 0;
00618 row_Cur_ = -1;
00619 last_Row_ = false;
00620
00621 if(!prepare(query))
00622 return false;
00623
00624
00625 if(queryType()!=1)
00626 return false;
00627
00628
00629 sword status = OCIStmtExecute(connection_->svchp_, stmthpToQuery_, connection_->errhp_, (ub4)0, (ub4)0, (OCISnapshot *)NULL,
00630 (OCISnapshot *)NULL, OCI_STMT_SCROLLABLE_READONLY);
00631 checkError(status);
00632 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00633 return false;
00634
00635 loadCollDescription();
00636
00637 if(hasBlob_)
00638 {
00639 vector<string> auxBlobColls;
00640 string sql ="";
00641 for(unsigned int blobIndex=0; blobIndex<colType_.size(); ++blobIndex)
00642 {
00643 if(colType_[blobIndex]==113)
00644 auxBlobColls.push_back(colName_[blobIndex]);
00645 }
00646
00647 if(!auxBlobColls.empty())
00648 sql = getSQLToLoadBlobLength(query, auxBlobColls);
00649
00650 freeResult();
00651 colBlobName_ = auxBlobColls;
00652
00653 maxRows_ = 10;
00654
00655 if(!prepare(sql))
00656 return false;
00657
00658
00659 status = OCIStmtExecute(connection_->svchp_, stmthpToQuery_, connection_->errhp_, (ub4)0, (ub4)0, (OCISnapshot *)NULL,
00660 (OCISnapshot *)NULL, OCI_DEFAULT);
00661 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00662 return false;
00663
00664 loadCollDescription();
00665 }
00666
00667 if(!allocateCursor())
00668 return false;
00669 return true;
00670 }
00671
00672
00673 bool TeOCICursor::querySDO(const string& query)
00674 {
00675 if (!isOpen_)
00676 open();
00677
00678 row_Index_ = -1;
00679 rows_Fetched_ = 0;
00680 rows_Mem_ = 0;
00681 row_Cur_ = -1;
00682 last_Row_ = false;
00683
00684 if(!prepare(query))
00685 return false;
00686
00687 if(!bindOrdinates())
00688 return false;
00689
00690
00691 if (queryType() != 1)
00692 return false;
00693
00694
00695 sword status = OCIStmtExecute(connection_->svchp_, stmthpToQuery_, connection_->errhp_, (ub4)0, (ub4)0, (OCISnapshot *)NULL,
00696 (OCISnapshot *)NULL, OCI_STMT_SCROLLABLE_READONLY);
00697
00698 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00699 return false;
00700
00701 loadCollDescription();
00702
00703 if(hasBlob_)
00704 {
00705 vector<string> auxBlobColls;
00706 string sql ="";
00707 for(unsigned int blobIndex=0; blobIndex<colType_.size(); ++blobIndex)
00708 {
00709 if(colType_[blobIndex]==113)
00710 auxBlobColls.push_back(colName_[blobIndex]);
00711 }
00712
00713 if(!auxBlobColls.empty())
00714 sql = getSQLToLoadBlobLength(query, auxBlobColls);
00715
00716 freeResult();
00717 colBlobName_ = auxBlobColls;
00718
00719 maxRows_ = 10;
00720
00721 if(!prepare(sql))
00722 return false;
00723
00724
00725 status = OCIStmtExecute(connection_->svchp_, stmthpToQuery_, connection_->errhp_, (ub4)0, (ub4)0, (OCISnapshot *)NULL,
00726 (OCISnapshot *)NULL, OCI_DEFAULT);
00727 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00728 return false;
00729
00730 loadCollDescription();
00731 }
00732
00733 if(!allocateCursor())
00734 return false;
00735
00736 return true;
00737 }
00738
00739
00740 int TeOCICursor::numCol()
00741 {
00742 if(numColls_>=0)
00743 return (numColls_-(colBlobName_.size()));
00744
00745
00746 OCIAttrGet(stmthpToQuery_, OCI_HTYPE_STMT, &numColls_,
00747 0, OCI_ATTR_PARAM_COUNT, connection_->errhp_);
00748
00749 return (numColls_-(colBlobName_.size()));
00750 }
00751
00752
00753 int TeOCICursor::numRows()
00754 {
00755 int numrows_ = 0;
00756
00757
00758 SDO_OCIAttrGet((dvoid*)stmthpToQuery_, (ub4)OCI_HTYPE_STMT, (dvoid*)&numrows_,
00759 (ub4*)0, (ub4)OCI_ATTR_ROW_COUNT, (OCIError*)connection_->errhp_);
00760 return (numrows_);
00761
00762 }
00763
00764
00765 void TeOCICursor::loadCollDescription()
00766 {
00767 OCIParam* colhd=NULL;
00768
00769 ub2 dtype = 0;
00770 string colname;
00771
00772 ub2 colsize = (ub2) 0;
00773
00774 sb1 colscale = (sb1) 0;
00775
00776 numCol();
00777 hasBlob_ = false;
00778
00779 int i;
00780 for(i=1; i<=numColls_; ++i)
00781 {
00782
00783 SDO_OCIParamGet((dvoid*)stmthpToQuery_, (ub4)OCI_HTYPE_STMT, (OCIError *)connection_->errhp_, (dvoid**)&colhd, (ub4)i);
00784
00785
00786 SDO_OCIAttrGet((dvoid *)colhd, (ub4)OCI_DTYPE_PARAM, (dvoid *)&dtype, (ub4*)0, (ub4)OCI_ATTR_DATA_TYPE, (OCIError *)connection_->errhp_);
00787
00788
00789 text *colname_ = NULL;
00790 ub4 colnamesz_;
00791
00792 OCIAttrGet((dvoid *)colhd, (ub4)OCI_DTYPE_PARAM, (dvoid **)&colname_, (ub4*)&colnamesz_, (ub4)OCI_ATTR_NAME, (OCIError *)connection_->errhp_ );
00793
00794 char temp[100];
00795 for(int j=0;j<(int)colnamesz_;j++)
00796 temp[j] = colname_[j];
00797 temp[colnamesz_] = '\0';
00798 colname = temp;
00799
00800
00801 SDO_OCIAttrGet((dvoid *)colhd, (ub4)OCI_DTYPE_PARAM, (dvoid *)&colsize, (ub4*)0, (ub4)OCI_ATTR_DATA_SIZE, (OCIError *)connection_->errhp_ );
00802
00803
00804 SDO_OCIAttrGet((dvoid *)colhd, (ub4)OCI_DTYPE_PARAM, (dvoid *)&colscale, (ub4*)0, (ub4)OCI_ATTR_SCALE, (OCIError *)connection_->errhp_ );
00805
00806 colName_.push_back(colname);
00807 colType_.push_back((int)dtype);
00808 colSize_.push_back((int)colsize);
00809 colScale_.push_back((int)colscale);
00810
00811 if(dtype==113)
00812 hasBlob_ = true;
00813 }
00814 }
00815
00816
00817 int TeOCICursor::colType (int colnumber)
00818 {
00819
00820 if((colnumber==0) || (colnumber>(int)colType_.size()))
00821 return 0;
00822
00823 return colType_[colnumber-1];
00824 }
00825
00826
00827 string TeOCICursor::colName (int colnumber)
00828 {
00829
00830 if((colnumber==0) || (colnumber>(int)colName_.size()))
00831 return "";
00832
00833 return colName_[colnumber-1];
00834 }
00835
00836
00837 int TeOCICursor::colSize (int colnumber)
00838 {
00839
00840 if((colnumber==0) || (colnumber>(int)colSize_.size()))
00841 return 0;
00842
00843 return colSize_[colnumber-1];
00844 }
00845
00846
00847 int TeOCICursor::colScale (int colnumber)
00848 {
00849
00850 if((colnumber==0) || (colnumber>(int)colScale_.size()))
00851 return 0;
00852
00853 return colScale_[colnumber-1];
00854 }
00855
00856
00857 bool TeOCICursor::allocateCursor()
00858 {
00859 int size;
00860 int coltype=0;
00861 int colsize=0;
00862 int colscale=0;
00863 sword status;
00864
00865 try
00866 {
00867 ind_.resize(numColls_);
00868
00869 for(int nc=0; nc<numColls_; ++nc)
00870 {
00871 defines_.push_back (0);
00872 buffers_.push_back (0);
00873 }
00874
00875 for(int i=1; i<=numColls_;i++)
00876 {
00877 coltype = colType_[i-1];
00878 colsize = colSize_[i-1];
00879 colscale = colScale_[i-1];
00880
00881 switch (coltype)
00882 {
00883 case 3:
00884 buffers_[i-1] = new signed int[maxRows_];
00885 colsize = sizeof(signed int);
00886
00887 status = OCIDefineByPos(stmthpToQuery_, &(defines_[i-1]), connection_->errhp_, (ub4)i,
00888 (dvoid *)(signed int*)buffers_[i-1], (sb4)colsize, coltype,
00889 (dvoid *)&ind_[i-1], (ub2 *)0, (ub2 *)0,(ub4)OCI_DEFAULT);
00890 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00891 return false;
00892
00893 break;
00894
00895
00896 case 2:
00897
00898 buffers_[i-1] = (OCINumber *) new OCINumber[maxRows_];
00899 status = OCIDefineByPos(stmthpToQuery_, &(defines_[i-1]), connection_->errhp_, (ub4)i,
00900 (dvoid *)buffers_[i-1], sizeof(OCINumber), SQLT_VNU,
00901 (dvoid *)&ind_[i-1], (ub2 *)0, (ub2 *)0,(ub4)OCI_DEFAULT);
00902 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00903 return false;
00904
00905 break;
00906
00907
00908 case 4:
00909
00910 buffers_[i-1] = new double[maxRows_];
00911 colsize = sizeof(double);
00912 coltype = 4;
00913
00914 status = SDO_OCIDefineByPos(stmthpToQuery_, &(defines_[i-1]), connection_->errhp_, (ub4)i,
00915 (dvoid *)(double*)buffers_[i-1], (sb4)colsize, coltype,
00916 (dvoid *)&ind_[i-1], (ub2 *)0, (ub2 *)0, (ub4)OCI_DEFAULT);
00917 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00918 return false;
00919
00920
00921 break;
00922
00923 case 96:
00924 case 9:
00925 case 1:
00926 buffers_[i-1] = (char *) new char[maxRows_*(colsize+1)];
00927
00928 status = SDO_OCIDefineByPos(stmthpToQuery_, &(defines_[i-1]), connection_->errhp_, (ub4)i,
00929 (dvoid *)buffers_[i-1], (sb4)(colsize+1), SQLT_STR,
00930 (dvoid *)&ind_[i-1], (ub2 *)0, (ub2 *)0,(ub4)OCI_DEFAULT);
00931 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00932 return false;
00933
00934 break;
00935
00936 case 12:
00937 buffers_[i-1] = (OCIDate *) new OCIDate[maxRows_];
00938 status = OCIDefineByPos(stmthpToQuery_, &(defines_[i-1]), connection_->errhp_, (ub4)i,
00939 (dvoid *)buffers_[i-1], sizeof(OCIDate), SQLT_ODT,
00940 (dvoid *)&ind_[i-1], (ub2 *)0, (ub2 *)0,(ub4)OCI_DEFAULT);
00941 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00942 return false;
00943
00944 break;
00945
00946
00947 case 108:
00948
00949 status = SDO_OCIObjectNew(connection_->envhp_, connection_->errhp_, connection_->svchp_,
00950 OCI_TYPECODE_OBJECT, connection_->tdo_geometry_, (dvoid*)NULL,
00951 OCI_DURATION_SESSION, TRUE,
00952 (dvoid**)global_geom_obj_);
00953 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00954 return false;
00955
00956 defines_[i-1] = NULL;
00957
00958 status = SDO_OCIDefineByPos(stmthpToQuery_, &(defines_[i-1]), connection_->errhp_, (ub4)i,
00959 (dvoid *)0, (sb4)0, SQLT_NTY, (dvoid *)&ind_[i-1],
00960 (ub2 *)0, (ub2 *)0, (ub4)OCI_DEFAULT);
00961 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00962 return false;
00963
00964 status = OCIDefineObject(defines_[i-1], connection_->errhp_, connection_->tdo_geometry_,
00965 (dvoid **)global_geom_obj_, (ub4 *)0,
00966 (dvoid **)global_geom_ind_, (ub4 *)0);
00967 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00968 return false;
00969
00970 break;
00971
00972 case 113 :
00973
00974 hasBlob_ = true;
00975 lobBuffer_.push_back(NULL);
00976 lobBuffer_[lobBuffer_.size()-1] = new unsigned char[maxBuflen_*maxRows_];
00977 size = sizeof(unsigned char)*maxBuflen_;
00978
00979 status = OCIDefineByPos (stmthpToQuery_, &(defines_[i-1]), connection_->errhp_, (ub4)i,
00980 (dvoid *)lobBuffer_[lobBuffer_.size()-1], size, SQLT_LBI, (void *)&ind_[i-1], (ub2 *)0, (ub2 *)0,
00981 (ub4)OCI_DEFAULT);
00982 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00983 return false;
00984
00985 status = OCIDefineArrayOfStruct(defines_[i-1], connection_->errhp_, size, 0, 0, 0);
00986 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
00987 return false;
00988 break;
00989 default:
00990 break;
00991
00992 }
00993
00994 }
00995 }
00996
00997 catch(...)
00998 {
00999 return false;
01000 }
01001
01002 return true;
01003 }
01004
01005 char* TeOCICursor::getFieldValue(int i)
01006 {
01007
01008 int tempInt;
01009 double tempDouble;
01010 char str[30];
01011 unsigned int size;
01012 string tempDate;
01013 sword status;
01014
01015 if(i < 1)
01016 return (char*)0;
01017
01018 int coltype = colType_[i-1];
01019 int colsize = colSize_[i-1];
01020
01021
01022
01023 int indica = ind_[i-1].sbind[row_Index_];
01024
01025 std::string format = "DD/MM/YYYY HH24:MI:SS";
01026 size = format.size();
01027
01028 switch (coltype)
01029 {
01030 case 3:
01031 if(indica == -1)
01032 return "";
01033
01034 tempInt = *((int*)buffers_[i-1]+row_Index_);
01035 fieldValue_ = Te2String(tempInt);
01036 return ((char*)fieldValue_.c_str());
01037 break;
01038
01039 case 2:
01040
01041 if(indica == -1)
01042 return "";
01043 status = OCINumberToReal(connection_->errhp_, ((OCINumber *)buffers_[i-1]+row_Index_),
01044 (uword)sizeof(double), (dvoid *)&tempDouble);
01045 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
01046 return "";
01047
01048 fieldValue_ = Te2String(tempDouble, 10);
01049 return ((char*)fieldValue_.c_str());
01050 break;
01051
01052
01053 case 4:
01054
01055 if(indica == -1)
01056 return "";
01057
01058 tempDouble = *((const double*)buffers_[i-1]+row_Index_);
01059 fieldValue_ = Te2String(tempDouble, 10);
01060 return ((char*)fieldValue_.c_str());
01061 break;
01062
01063 case 96:
01064 case 9:
01065 case 1:
01066
01067 if(indica == -1)
01068 return "";
01069
01070 fieldValue_ = ((char*)buffers_[i-1]+((colsize+1)*row_Index_));
01071 fieldValue_ = StrClean((char*)fieldValue_.c_str());
01072 return ((char*)fieldValue_.c_str());
01073 break;
01074
01075 case 12:
01076
01077 if(indica == -1)
01078 return "";
01079
01080 fieldValue_ = "";
01081
01082
01083 status = OCIDateToText(connection_->errhp_, ((OCIDate *)buffers_[i-1]+row_Index_),
01084 (unsigned char*)format.c_str(), format.size(), NULL, 0, &size, (unsigned char*)tempDate.c_str());
01085 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
01086 return "";
01087 memcpy(str, tempDate.c_str(), size);
01088 strncat((char*)fieldValue_.c_str(), str, size);
01089
01090 return ((char*)fieldValue_.c_str());
01091 break;
01092
01093 case 108:
01094 default:
01095 break;
01096
01097 }
01098
01099 return (char*)"";
01100 }
01101
01102 int TeOCICursor::getDimArraySize()
01103 {
01104 int ndim=-1;
01105
01106
01107 OCICollSize(connection_->envhp_, connection_->errhp_,
01108 (OCIColl *)(global_geom_obj_[row_Index_]->sdo_elem_info), &ndim);
01109
01110 return(ndim);
01111 }
01112
01113 bool TeOCICursor::getDimElement(int i,int &elem)
01114 {
01115 int exists;
01116 OCINumber *oci_number;
01117 double el;
01118
01119
01120 OCICollGetElem(connection_->envhp_, connection_->errhp_,
01121 (OCIColl *)(global_geom_obj_[row_Index_]->sdo_elem_info),
01122 (sb4)i-1, (boolean *)&exists,
01123 (dvoid **)&oci_number, (dvoid **)0);
01124
01125 OCINumberToReal(connection_->errhp_, oci_number, (uword)sizeof(double),
01126 (dvoid *)&el);
01127
01128 elem = (int)el;
01129 return true;
01130 }
01131
01132
01133 int TeOCICursor::getNumberOrdinates()
01134 {
01135 int nOrds=-1;
01136
01137
01138 OCICollSize(connection_->envhp_, connection_->errhp_,
01139 (OCIColl *)(global_geom_obj_[row_Index_]->sdo_ordinates), &nOrds);
01140
01141 return(nOrds);
01142 }
01143
01144 bool TeOCICursor::getCoordinates(int i, TeCoord2D& coord)
01145 {
01146 int exists;
01147 OCINumber *oci_number;
01148 double coor_x;
01149 double coor_y;
01150
01151 int pos = i;
01152
01153 OCICollGetElem(connection_->envhp_, connection_->errhp_,
01154 (OCIColl *)(global_geom_obj_[row_Index_]->sdo_ordinates),
01155 (sb4)(pos-1), (boolean *)&exists,
01156 (dvoid **)&oci_number, (dvoid **)0);
01157
01158 OCINumberToReal(connection_->errhp_, oci_number, (uword)sizeof(double),
01159 (dvoid *)&coor_x);
01160
01161 pos++;
01162
01163 OCICollGetElem(connection_->envhp_, connection_->errhp_,
01164 (OCIColl *)(global_geom_obj_[row_Index_]->sdo_ordinates),
01165 (sb4)(pos-1), (boolean *)&exists,
01166 (dvoid **)&oci_number, (dvoid **)0);
01167
01168 OCINumberToReal(connection_->errhp_, oci_number, (uword)sizeof(double),
01169 (dvoid *)&coor_y);
01170
01171 coord.x(coor_x);
01172 coord.y(coor_y);
01173
01174 return true;
01175 }
01176
01177
01178 bool TeOCICursor::getCoordinates(vector<TeCoord2D>& result)
01179 {
01180
01181 OCIIter *iterator;
01182 dvoid *elem;
01183 OCIInd *elemind ;
01184 double ordinate1, ordinate2;
01185 OCINumber *aux1;
01186 OCINumber *aux2;
01187
01188 int eoc;
01189
01190 sword status = OCIIterCreate(connection_->envhp_, connection_->errhp_,
01191 (OCIArray *)(global_geom_obj_[row_Index_]->sdo_ordinates), &iterator);
01192 if (status != OCI_SUCCESS)
01193 return false;
01194
01195
01196 status = OCIIterNext(connection_->envhp_, connection_->errhp_, iterator, &elem,
01197 (dvoid **) &elemind, (boolean *)&eoc);
01198 if (eoc || status != OCI_SUCCESS)
01199 {
01200 OCIIterDelete(connection_->envhp_, connection_->errhp_, &iterator);
01201 return false;
01202 }
01203
01204 aux1 = (OCINumber *)elem;
01205 OCINumberToReal(connection_->errhp_, (OCINumber *)aux1, (uword)sizeof(double),
01206 (dvoid *)&ordinate1);
01207
01208 status = OCIIterNext(connection_->envhp_, connection_->errhp_, iterator, &elem,
01209 (dvoid **)&elemind, (boolean *)&eoc);
01210 if (eoc || status != OCI_SUCCESS)
01211 {
01212 OCIIterDelete(connection_->envhp_, connection_->errhp_, &iterator);
01213 return false;
01214 }
01215
01216 aux2 = (OCINumber *)elem;
01217 OCINumberToReal(connection_->errhp_, (OCINumber *) aux2, (uword)sizeof(double),
01218 (dvoid *)&ordinate2);
01219
01220 TeCoord2D coord(ordinate1, ordinate2);
01221 result.push_back (coord);
01222
01223 while (!eoc && status == OCI_SUCCESS)
01224 {
01225 status = OCIIterNext(connection_->envhp_, connection_->errhp_, iterator, &elem,
01226 (dvoid **)&elemind, (boolean *)&eoc);
01227 if (status != OCI_SUCCESS)
01228 {
01229 OCIIterDelete(connection_->envhp_, connection_->errhp_, &iterator);
01230 return false;
01231 }
01232
01233 aux1 = (OCINumber *)elem;
01234 OCINumberToReal(connection_->errhp_, (OCINumber *)aux1, (uword)sizeof(double),
01235 (dvoid *)&ordinate1);
01236
01237 status = OCIIterNext(connection_->envhp_, connection_->errhp_, iterator, &elem,
01238 (dvoid **)&elemind, (boolean *)&eoc);
01239 if (status != OCI_SUCCESS)
01240 {
01241 OCIIterDelete(connection_->envhp_, connection_->errhp_, &iterator);
01242 return false;
01243 }
01244
01245 aux2 = (OCINumber *)elem;
01246 OCINumberToReal(connection_->errhp_, (OCINumber *) aux2, (uword)sizeof(double),
01247 (dvoid *)&ordinate2);
01248
01249 TeCoord2D coord(ordinate1, ordinate2);
01250 result.push_back (coord);
01251 }
01252
01253
01254 status = OCIIterDelete(connection_->envhp_, connection_->errhp_, &iterator);
01255 return true;
01256 }
01257
01258
01259 int
01260 TeOCICursor::getGeometryType()
01261 {
01262 int gtype=-1;
01263
01264 OCINumberToInt(connection_->errhp_, &(global_geom_obj_[row_Index_]->sdo_gtype),
01265 (uword)sizeof(int), OCI_NUMBER_SIGNED,
01266 (dvoid *)>ype);
01267
01268 return gtype;
01269 }
01270
01271 int
01272 TeOCICursor::getSpatialReferenceId()
01273 {
01274 int srid=-1;
01275
01276 OCINumberToInt(connection_->errhp_, &(global_geom_obj_[row_Index_]->sdo_srid),
01277 (uword)sizeof(int), OCI_NUMBER_SIGNED,
01278 (dvoid *)&srid);
01279
01280 return srid;
01281 }
01282
01283 bool
01284 TeOCICursor::getXYZcoord(double& x, double& y)
01285 {
01286 if (global_geom_ind_[row_Index_]->sdo_point._atomic == OCI_IND_NOTNULL)
01287 {
01288 if (global_geom_ind_[row_Index_]->sdo_point.x == OCI_IND_NOTNULL)
01289 {
01290 sword status = OCINumberToReal(connection_->errhp_, &(global_geom_obj_[row_Index_]->sdo_point.x),
01291 (uword)sizeof(double),(dvoid *)&x);
01292
01293 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
01294 return false;
01295 }
01296
01297 if (global_geom_ind_[row_Index_]->sdo_point.y == OCI_IND_NOTNULL)
01298 {
01299 sword status = OCINumberToReal(connection_->errhp_, &(global_geom_obj_[row_Index_]->sdo_point.y),
01300 (uword)sizeof(double),(dvoid *)&y);
01301 if ((status != OCI_SUCCESS) && (status!=OCI_SUCCESS_WITH_INFO))
01302 return false;
01303 }
01304 return true;
01305 }
01306 else
01307 return false;
01308 }
01309
01310 bool
01311 TeOCICursor::readBlob(unsigned char* buffer, unsigned int& bufsize, unsigned int& blobCol)
01312 {
01313 string blobColS = colName_[blobCol];
01314 return(readBlob(buffer, bufsize, blobColS));
01315 }
01316
01317 bool
01318 TeOCICursor::readBlob(unsigned char* buffer, unsigned int& bufsize, const string& blobCol)
01319 {
01320 int blobIndex = -1;
01321 if(colBlobName_.size()==1)
01322 blobIndex=0;
01323 else
01324 {
01325 for(unsigned int j=0; j<colBlobName_.size(); j++)
01326 {
01327 if(TeStringCompare(blobCol, colBlobName_[j]))
01328 {
01329 blobIndex = j;
01330 break;
01331 }
01332 }
01333 }
01334
01335 if(blobIndex<0)
01336 return false;
01337
01338 int index = numColls_-(colBlobName_.size()-(blobIndex+1));
01339
01340
01341 bufsize = atoi(getFieldValue(index))*sizeof(unsigned char);
01342
01343 memcpy(buffer,&(lobBuffer_[blobIndex][row_Index_*maxBuflen_]),bufsize);
01344 return true;
01345 }
01346
01347
01348 bool
01349 TeOCICursor::readBlob(double *buffer, unsigned int& bufsize)
01350 {
01351
01352
01353 int size = bufsize*sizeof(double);
01354 memcpy(buffer,&(lobBuffer_[0][row_Index_*maxBuflen_]),size);
01355 return true;
01356 }
01357
01358 bool
01359 TeOCICursor::readBlob(double **buffer)
01360 {
01361 *buffer = (double*)&(lobBuffer_[0][row_Index_*maxBuflen_]);
01362 return true;
01363 }
01364
01365 unsigned int
01366 TeOCICursor::getBlobSize(const string& blobCol)
01367 {
01368 int blobIndex = -1;
01369 if(colBlobName_.empty())
01370 return 0;
01371 if(colBlobName_.size()==1)
01372 blobIndex=0;
01373 else
01374 {
01375 for(unsigned int j=0; j<colBlobName_.size(); j++)
01376 {
01377 if(TeStringCompare(blobCol, colBlobName_[j]))
01378 {
01379 blobIndex = j;
01380 break;
01381 }
01382 }
01383 }
01384
01385 if(blobIndex<0)
01386 return 0;
01387
01388 int index = numColls_-(colBlobName_.size()-(blobIndex+1));
01389 return (atoi(getFieldValue(index))*sizeof(unsigned char));
01390 }
01391