TeOCICursor.cpp

Go to the documentation of this file.
00001 /************************************************************************************
00002 TerraLib - a library for developing GIS applications.
00003 Copyright � 2001-2007 INPE and Tecgraf/PUC-Rio.
00004 
00005 This code is part of the TerraLib library.
00006 This library is free software; you can redistribute it and/or
00007 modify it under the terms of the GNU Lesser General Public
00008 License as published by the Free Software Foundation; either
00009 version 2.1 of the License, or (at your option) any later version.
00010 
00011 You should have received a copy of the GNU Lesser General Public
00012 License along with this library.
00013 
00014 The authors reassure the license terms regarding the warranties.
00015 They specifically disclaim any warranties, including, but not limited to,
00016 the implied warranties of merchantability and fitness for a particular purpose.
00017 The library provided hereunder is on an "as is" basis, and the authors have no
00018 obligation to provide maintenance, support, updates, enhancements, or modifications.
00019 In no event shall INPE and Tecgraf / PUC-Rio be held liable to any party for direct,
00020 indirect, special, incidental, or consequential damages arising out of the use
00021 of this library and its documentation.
00022 *************************************************************************************/
00023 
00024 
00025 #include "TeOCICursor.h"
00026 #include "TeOCISDO.h"
00027 #include "TeUtils.h"
00028 
00029 //C include files
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         //Select clause
00039         size_t posFrom = sql.find(" FROM ", 0);
00040         sqlSelectAux = sql.substr(0, posFrom);
00041         
00042         //From and Where clause
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         //Verify if there is  string "SELECT *" 
00055         size_t pos =  sqlSelectAux.find (" *", 0);
00056         if(pos != string::npos) 
00057         {
00058                 //two option:
00059                 //1: if there is only 1 table -> include an alias in the FROM clause  
00060                 //2: if there are more than 1 table -> include SELECT * ... and alias in the FROM clause
00061                 size_t posJoin = sqlFromAux.find(" JOIN ", 0);
00062                 size_t posVirg = sqlFromAux.find(",", 0);
00063 
00064                 if((posJoin!=string::npos) || (posVirg!=string::npos)) //there are more than 1
00065                 {
00066                         string aux = " FROM ( SELECT * "+ sqlFromAux + sqlWhereAux +" ) t ";
00067                         sqlFromAux = aux;
00068                         sqlWhereAux = "";
00069                 }
00070                 else //there are only 1
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 //Given a string, remove all blanks and tabs (rigth)
00085 char* StrClean(char *name)
00086 {
00087     int j;
00088         
00089         if ((name == NULL)) /*SGError.Handler(NULLPOINTER,FATAL);*/ 
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         //size in bytes to each blob
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         // Initialize statement handle 
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         // describe spatial object types (OCIDescribe)
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                 //free stmthpToQuery_ located previously
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                         //free dschp_ located previously
00180                         SDO_OCIHandleFree((dvoid*)dschp_, (ub4)OCI_HTYPE_DESCRIBE);
00181                         //free stmthpToQuery_ located previously
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(); //free all located memory
00194         // Finalize stmthpToQuery_ and dschp_
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         //vector of buffers to store blob
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         //buffer to store alphanumeric data
00220         for(unsigned int i=0; i<buffers_.size();i++)
00221         {
00222                 int coltype = colType_[i];
00223                 switch (coltype)
00224                 {
00225                         case 3: //INTEGER
00226                                 delete [] ((signed int*) buffers_[i]);
00227                                 break;
00228                         
00229                         case 2: //NUMBER
00230                                 delete [] ((OCINumber*) buffers_[i]);
00231                                 break;
00232                         
00233                         case 4: //FLOAT DOUBLE
00234                                 delete [] ((double*) buffers_[i]);
00235                                 break;
00236                         
00237                         case 96: //CHAR
00238                         case 9: //VARCHAR:
00239                         case 1: //VARCHAR2:     
00240                                 delete [] ((char *) buffers_[i]);
00241                                 break;
00242                         
00243                         case 12: //Date
00244                                         delete [] ((OCIDate *) buffers_[i]);
00245                                         break;
00246                         default:
00247                                         break;
00248                         
00249                 } //switch
00250         } //for
00251 
00252         //sdo geometry
00253         if(connection_->useSDOType())  
00254         {
00255                 for(int i=0;i<maxRows_;i++) 
00256                 {
00257                         /// free the spatial object instance 
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(); // ver se o freestmtp desaloca os OCIDefines 
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         /* bind coordinate varray object */
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                 // this is for scroolable cursor
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                 // this is for scroolable cursor
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         //podemos pegar informacao da ultima linha
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) //begin in 0
00465 {
00466         // It is not possible use scrollable cursor with blob
00467         if(hasBlob_) 
00468         {
00469                 // for non-scroolable cursor, needs to query again
00470                 // if pos is at the end of recordset may be slow
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         // row_Cur_ = absolute current row 
00494         // row_Index_ = relative current row - client side
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 // Throw CCursorException if OCI error found
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                 //An invalid handle was passed as a parameter or a user callback is passed an
00566                 //invalid handle or invalid context. No further diagnostics are available.
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         // query type equal to 1 = OCI_STMT_SELECT
00625         if(queryType()!=1) 
00626                 return false;
00627                 
00628          //iters equal to zero because the defines_ (OCIDefines) have not located yet 
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(); // load columns description
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) //blob type
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; //get only 10 rows from server when there is blob type.
00654                 
00655                 if(!prepare(sql))
00656                         return false;
00657                 
00658                 // Is is not possible use the scrollable cursor with blob data type
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(); // to get the new attribute in SQL
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         // query type equal to 1 = OCI_STMT_SELECT
00691         if (queryType() != 1) //must be executed by TeOCIConnect->execute()
00692                 return false;
00693                 
00694         //iters equal to zero because the defines_ (OCIDefines) have not located yet 
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(); // load columns description
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) //blob type
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; //get only 10 rows from server when there is blob type.
00720 
00721                 if(!prepare(sql))
00722                         return false;
00723                 
00724                 // Is is not possible use the scrollable cursor with blob data type
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(); // to get the new attribute in SQL
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         /* Get the number of columns in the query */
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         /* Get the number of rows in the query */
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         //int           dtype;
00769         ub2     dtype = 0;
00770         string  colname;
00771         //int           colsize;
00772         ub2  colsize = (ub2) 0;
00773         //int           colscale;
00774         sb1  colscale = (sb1) 0;
00775         
00776         numCol(); // atualize the numColls_ variable
00777         hasBlob_ = false;
00778 
00779         int i;
00780         for(i=1; i<=numColls_; ++i)
00781         {
00782                 // get parameter for i-th column
00783                 SDO_OCIParamGet((dvoid*)stmthpToQuery_, (ub4)OCI_HTYPE_STMT, (OCIError *)connection_->errhp_, (dvoid**)&colhd, (ub4)i);
00784 
00785                 // get data type 
00786                 SDO_OCIAttrGet((dvoid *)colhd, (ub4)OCI_DTYPE_PARAM, (dvoid *)&dtype, (ub4*)0, (ub4)OCI_ATTR_DATA_TYPE, (OCIError *)connection_->errhp_);
00787 
00788                 // get coll name 
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                 // retrieve the column size attribute
00801                 SDO_OCIAttrGet((dvoid *)colhd, (ub4)OCI_DTYPE_PARAM, (dvoid *)&colsize, (ub4*)0, (ub4)OCI_ATTR_DATA_SIZE, (OCIError *)connection_->errhp_ );
00802 
00803                 // retrieve the column scale attribute
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         //first coll number is 1
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         //first coll number is 1
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         //first coll number is 1
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         //first coll number is 1
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: //INTEGER
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: //NUMBER
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: //FLOAT DOUBLE
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: //CHAR
00924                                 case 9: //VARCHAR:
00925                                 case 1: //VARCHAR2:
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: //Date
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: //OBJECT SDO_GEOMETRY
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 :      //SQLT_BLOB
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                         } //switch
00993         
00994                 } //for
00995         }//try
00996 
00997         catch(...) 
00998         {
00999                 return false;
01000         }
01001 
01002         return true;
01003 }       
01004 
01005 char* TeOCICursor::getFieldValue(int i)  //inicia em 1
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         //OBS:  When the SQL use grouping functions (MAX, MIN, etc), the returned value always has
01022         //              colscale equal to zero, even when it is double
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: //INTEGER
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: //NUMBER
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: //FLOAT DOUBLE
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: //CHAR
01064                 case 9: //VARCHAR:
01065                 case 1: //VARCHAR2:
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: //Date
01076                         
01077                         if(indica == -1)
01078                                 return "";
01079 
01080                         fieldValue_ = "";
01081                         //size = sizeof(OCIDate);
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: //OBJECT SDO_GEOMETRY
01094                 default:
01095                         break;
01096                                                         
01097         } //switch
01098                 
01099         return (char*)"";
01100 }
01101 
01102 int TeOCICursor::getDimArraySize()
01103 {
01104         int ndim=-1;
01105 
01106         // Get the size of the elem info array
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         /* Get the size of the ordinates_ array */
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         //boolean               eoc;
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         /* Get the first and second element of the clients varray */
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         /* destroy the iterator */
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 *)&gtype);
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         //bufsize em bytes
01341         bufsize = atoi(getFieldValue(index))*sizeof(unsigned char);
01342         //buffer = new unsigned char[bufsize];
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         //bufsize em double
01352         //size em bytes
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 

Generated on Sun Jul 29 04:01:22 2012 for TerraLib - Development Source by  doxygen 1.5.3