CppSQLite3.cpp

Go to the documentation of this file.
00001 
00002 
00003 // CppSQLite3 - A C++ wrapper around the SQLite3 embedded database library.
00004 
00005 //
00006 
00007 // Copyright (c) 2004 Rob Groves. All Rights Reserved. rob.groves@btinternet.com
00008 
00009 // 
00010 
00011 // Permission to use, copy, modify, and distribute this software and its
00012 
00013 // documentation for any purpose, without fee, and without a written
00014 
00015 // agreement, is hereby granted, provided that the above copyright notice, 
00016 
00017 // this paragraph and the following two paragraphs appear in all copies, 
00018 
00019 // modifications, and distributions.
00020 
00021 //
00022 
00023 // IN NO EVENT SHALL THE AUTHOR BE LIABLE TO ANY PARTY FOR DIRECT,
00024 
00025 // INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, INCLUDING LOST
00026 
00027 // PROFITS, ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION,
00028 
00029 // EVEN IF THE AUTHOR HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00030 
00031 //
00032 
00033 // THE AUTHOR SPECIFICALLY DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT
00034 
00035 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
00036 
00037 // PARTICULAR PURPOSE. THE SOFTWARE AND ACCOMPANYING DOCUMENTATION, IF
00038 
00039 // ANY, PROVIDED HEREUNDER IS PROVIDED "AS IS". THE AUTHOR HAS NO OBLIGATION
00040 
00041 // TO PROVIDE MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
00042 
00043 //
00044 
00045 // V3.0         03/08/2004      -Initial Version for sqlite3
00046 
00047 //
00048 
00049 // V3.1         16/09/2004      -Implemented getXXXXField using sqlite3 functions
00050 
00051 //                                              -Added CppSQLiteDB3::tableExists()
00052 
00054 
00055 #include "CppSQLite3.h"
00056 
00057 #include <cstdlib>
00058 
00059 
00060 
00061 
00062 
00063 // Named constant for passing to CppSQLite3Exception when passing it a string
00064 
00065 // that cannot be deleted.
00066 
00067 static const bool DONT_DELETE_MSG=false;
00068 
00069 
00070 
00072 
00073 // Prototypes for SQLite functions not included in SQLite DLL, but copied below
00074 
00075 // from SQLite encode.c
00076 
00078 
00079 int sqlite3_encode_binary(const unsigned char *in, int n, unsigned char *out);
00080 
00081 int sqlite3_decode_binary(const unsigned char *in, unsigned char *out);
00082 
00083 
00084 
00086 
00087 
00088 
00090 
00091 
00092 
00093 CppSQLite3Exception::CppSQLite3Exception(const int nErrCode,
00094 
00095                                          const char* szErrMess,
00096 
00097                                          bool bDeleteMsg/*=true*/) :
00098 
00099   mnErrCode(nErrCode)
00100 
00101 {
00102 
00103   mpszErrMess = sqlite3_mprintf("%s[%d]: %s",
00104 
00105                                 errorCodeAsString(nErrCode),
00106 
00107                                 nErrCode,
00108 
00109                                 szErrMess ? szErrMess : "");
00110 
00111   /*
00112 
00113   if (bDeleteMsg && szErrMess)
00114 
00115     {
00116 
00117       sqlite3_free(szErrMess);
00118 
00119     }
00120 
00121   */
00122 
00123 }
00124 
00125 
00126 
00127 CppSQLite3Exception::CppSQLite3Exception(const int nErrCode,
00128 
00129                                          char* szErrMess,
00130 
00131                                          bool bDeleteMsg/*=true*/) :
00132 
00133   mnErrCode(nErrCode)
00134 
00135 {
00136 
00137   mpszErrMess = sqlite3_mprintf("%s[%d]: %s",
00138 
00139                                 errorCodeAsString(nErrCode),
00140 
00141                                 nErrCode,
00142 
00143                                 szErrMess ? szErrMess : "");
00144 
00145   
00146 
00147   if (bDeleteMsg && szErrMess)
00148 
00149     {
00150 
00151       sqlite3_free(szErrMess);
00152 
00153     }
00154 
00155 }
00156 
00157                                                                         
00158 
00159 CppSQLite3Exception::CppSQLite3Exception(const CppSQLite3Exception&  e) :
00160 
00161                                                                         mnErrCode(e.mnErrCode)
00162 
00163 {
00164 
00165         mpszErrMess = 0;
00166 
00167         if (e.mpszErrMess)
00168 
00169         {
00170 
00171                 mpszErrMess = sqlite3_mprintf("%s", e.mpszErrMess);
00172 
00173         }
00174 
00175 }
00176 
00177 
00178 
00179 
00180 
00181 const char* CppSQLite3Exception::errorCodeAsString(int nErrCode)
00182 
00183 {
00184 
00185         switch (nErrCode)
00186 
00187         {
00188 
00189                 case SQLITE_OK          : return "SQLITE_OK";
00190 
00191                 case SQLITE_ERROR       : return "SQLITE_ERROR";
00192 
00193                 case SQLITE_INTERNAL    : return "SQLITE_INTERNAL";
00194 
00195                 case SQLITE_PERM        : return "SQLITE_PERM";
00196 
00197                 case SQLITE_ABORT       : return "SQLITE_ABORT";
00198 
00199                 case SQLITE_BUSY        : return "SQLITE_BUSY";
00200 
00201                 case SQLITE_LOCKED      : return "SQLITE_LOCKED";
00202 
00203                 case SQLITE_NOMEM       : return "SQLITE_NOMEM";
00204 
00205                 case SQLITE_READONLY    : return "SQLITE_READONLY";
00206 
00207                 case SQLITE_INTERRUPT   : return "SQLITE_INTERRUPT";
00208 
00209                 case SQLITE_IOERR       : return "SQLITE_IOERR";
00210 
00211                 case SQLITE_CORRUPT     : return "SQLITE_CORRUPT";
00212 
00213                 case SQLITE_NOTFOUND    : return "SQLITE_NOTFOUND";
00214 
00215                 case SQLITE_FULL        : return "SQLITE_FULL";
00216 
00217                 case SQLITE_CANTOPEN    : return "SQLITE_CANTOPEN";
00218 
00219                 case SQLITE_PROTOCOL    : return "SQLITE_PROTOCOL";
00220 
00221                 case SQLITE_EMPTY       : return "SQLITE_EMPTY";
00222 
00223                 case SQLITE_SCHEMA      : return "SQLITE_SCHEMA";
00224 
00225                 case SQLITE_TOOBIG      : return "SQLITE_TOOBIG";
00226 
00227                 case SQLITE_CONSTRAINT  : return "SQLITE_CONSTRAINT";
00228 
00229                 case SQLITE_MISMATCH    : return "SQLITE_MISMATCH";
00230 
00231                 case SQLITE_MISUSE      : return "SQLITE_MISUSE";
00232 
00233                 case SQLITE_NOLFS       : return "SQLITE_NOLFS";
00234 
00235                 case SQLITE_AUTH        : return "SQLITE_AUTH";
00236 
00237                 case SQLITE_FORMAT      : return "SQLITE_FORMAT";
00238 
00239                 case SQLITE_RANGE       : return "SQLITE_RANGE";
00240 
00241                 case SQLITE_ROW         : return "SQLITE_ROW";
00242 
00243                 case SQLITE_DONE        : return "SQLITE_DONE";
00244 
00245                 case CPPSQLITE_ERROR    : return "CPPSQLITE_ERROR";
00246 
00247                 default: return "UNKNOWN_ERROR";
00248 
00249         }
00250 
00251 }
00252 
00253 
00254 
00255 
00256 
00257 CppSQLite3Exception::~CppSQLite3Exception()
00258 
00259 {
00260 
00261         if (mpszErrMess)
00262 
00263         {
00264 
00265                 sqlite3_free(mpszErrMess);
00266 
00267                 mpszErrMess = 0;
00268 
00269         }
00270 
00271 }
00272 
00273 
00274 
00275 
00276 
00278 
00279 
00280 
00281 CppSQLite3Buffer::CppSQLite3Buffer()
00282 
00283 {
00284 
00285         mpBuf = 0;
00286 
00287 }
00288 
00289 
00290 
00291 
00292 
00293 CppSQLite3Buffer::~CppSQLite3Buffer()
00294 
00295 {
00296 
00297         clear();
00298 
00299 }
00300 
00301 
00302 
00303 
00304 
00305 void CppSQLite3Buffer::clear()
00306 
00307 {
00308 
00309         if (mpBuf)
00310 
00311         {
00312 
00313                 sqlite3_free(mpBuf);
00314 
00315                 mpBuf = 0;
00316 
00317         }
00318 
00319 
00320 
00321 }
00322 
00323 
00324 
00325 
00326 
00327 const char* CppSQLite3Buffer::format(const char* szFormat, ...)
00328 
00329 {
00330 
00331         clear();
00332 
00333         va_list va;
00334 
00335         va_start(va, szFormat);
00336 
00337         mpBuf = sqlite3_vmprintf(szFormat, va);
00338 
00339         va_end(va);
00340 
00341         return mpBuf;
00342 
00343 }
00344 
00345 
00346 
00347 
00348 
00350 
00351 
00352 
00353 CppSQLite3Binary::CppSQLite3Binary() :
00354 
00355                                                 mpBuf(0),
00356 
00357                                                 mnBinaryLen(0),
00358 
00359                                                 mnBufferLen(0),
00360 
00361                                                 mnEncodedLen(0),
00362 
00363                                                 mbEncoded(false)
00364 
00365 {
00366 
00367 }
00368 
00369 
00370 
00371 
00372 
00373 CppSQLite3Binary::~CppSQLite3Binary()
00374 
00375 {
00376 
00377         clear();
00378 
00379 }
00380 
00381 
00382 
00383 
00384 
00385 void CppSQLite3Binary::setBinary(const unsigned char* pBuf, int nLen)
00386 
00387 {
00388 
00389         mpBuf = allocBuffer(nLen);
00390 
00391         memcpy(mpBuf, pBuf, nLen);
00392 
00393 }
00394 
00395 
00396 
00397 
00398 
00399 void CppSQLite3Binary::setEncoded(const unsigned char* pBuf)
00400 
00401 {
00402 
00403         clear();
00404 
00405 
00406 
00407         mnEncodedLen = strlen((const char*)pBuf);
00408 
00409         mnBufferLen = mnEncodedLen + 1; // Allow for NULL terminator
00410 
00411 
00412 
00413         mpBuf = (unsigned char*)malloc(mnBufferLen);
00414 
00415 
00416 
00417         if (!mpBuf)
00418 
00419         {
00420 
00421                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
00422 
00423                                                                 "Cannot allocate memory",
00424 
00425                                                                 DONT_DELETE_MSG);
00426 
00427         }
00428 
00429 
00430 
00431         memcpy(mpBuf, pBuf, mnBufferLen);
00432 
00433         mbEncoded = true;
00434 
00435 }
00436 
00437 
00438 
00439 
00440 
00441 const unsigned char* CppSQLite3Binary::getEncoded()
00442 
00443 {
00444 
00445         if (!mbEncoded)
00446 
00447         {
00448 
00449                 unsigned char* ptmp = (unsigned char*)malloc(mnBinaryLen);
00450 
00451                 memcpy(ptmp, mpBuf, mnBinaryLen);
00452 
00453                 mnEncodedLen = sqlite3_encode_binary(ptmp, mnBinaryLen, mpBuf);
00454 
00455                 free(ptmp);
00456 
00457                 mbEncoded = true;
00458 
00459         }
00460 
00461 
00462 
00463         return mpBuf;
00464 
00465 }
00466 
00467 
00468 
00469 
00470 
00471 const unsigned char* CppSQLite3Binary::getBinary()
00472 
00473 {
00474 
00475         if (mbEncoded)
00476 
00477         {
00478 
00479                 // in/out buffers can be the same
00480 
00481                 mnBinaryLen = sqlite3_decode_binary(mpBuf, mpBuf);
00482 
00483 
00484 
00485                 if (mnBinaryLen == -1)
00486 
00487                 {
00488 
00489                         throw CppSQLite3Exception(CPPSQLITE_ERROR,
00490 
00491                                                                         "Cannot decode binary",
00492 
00493                                                                         DONT_DELETE_MSG);
00494 
00495                 }
00496 
00497 
00498 
00499                 mbEncoded = false;
00500 
00501         }
00502 
00503 
00504 
00505         return mpBuf;
00506 
00507 }
00508 
00509 
00510 
00511 
00512 
00513 int CppSQLite3Binary::getBinaryLength()
00514 
00515 {
00516 
00517         getBinary();
00518 
00519         return mnBinaryLen;
00520 
00521 }
00522 
00523 
00524 
00525 
00526 
00527 unsigned char* CppSQLite3Binary::allocBuffer(int nLen)
00528 
00529 {
00530 
00531         clear();
00532 
00533 
00534 
00535         // Allow extra space for encoded binary as per comments in
00536 
00537         // SQLite encode.c See bottom of this file for implementation
00538 
00539         // of SQLite functions use 3 instead of 2 just to be sure ;-)
00540 
00541         mnBinaryLen = nLen;
00542 
00543         mnBufferLen = 3 + (257*nLen)/254;
00544 
00545 
00546 
00547         mpBuf = (unsigned char*)malloc(mnBufferLen);
00548 
00549 
00550 
00551         if (!mpBuf)
00552 
00553         {
00554 
00555                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
00556 
00557                                                                 "Cannot allocate memory",
00558 
00559                                                                 DONT_DELETE_MSG);
00560 
00561         }
00562 
00563 
00564 
00565         mbEncoded = false;
00566 
00567 
00568 
00569         return mpBuf;
00570 
00571 }
00572 
00573 
00574 
00575 
00576 
00577 void CppSQLite3Binary::clear()
00578 
00579 {
00580 
00581         if (mpBuf)
00582 
00583         {
00584 
00585                 mnBinaryLen = 0;
00586 
00587                 mnBufferLen = 0;
00588 
00589                 free(mpBuf);
00590 
00591                 mpBuf = 0;
00592 
00593         }
00594 
00595 }
00596 
00597 
00598 
00599 
00600 
00602 
00603 
00604 
00605 CppSQLite3Query::CppSQLite3Query()
00606 
00607 {
00608 
00609         mpVM = 0;
00610 
00611         mbEof = true;
00612 
00613         mnCols = 0;
00614 
00615         mbOwnVM = false;
00616 
00617 }
00618 
00619 
00620 
00621 
00622 
00623 CppSQLite3Query::CppSQLite3Query(const CppSQLite3Query& rQuery)
00624 
00625 {
00626 
00627         mpVM = rQuery.mpVM;
00628 
00629         // Only one object can own the VM
00630 
00631         const_cast<CppSQLite3Query&>(rQuery).mpVM = 0;
00632 
00633         mbEof = rQuery.mbEof;
00634 
00635         mnCols = rQuery.mnCols;
00636 
00637         mbOwnVM = rQuery.mbOwnVM;
00638 
00639 }
00640 
00641 
00642 
00643 
00644 
00645 CppSQLite3Query::CppSQLite3Query(sqlite3* pDB,
00646 
00647                                                         sqlite3_stmt* pVM,
00648 
00649                                                         bool bEof,
00650 
00651                                                         bool bOwnVM/*=true*/)
00652 
00653 {
00654 
00655         mpDB = pDB;
00656 
00657         mpVM = pVM;
00658 
00659         mbEof = bEof;
00660 
00661         mnCols = sqlite3_column_count(mpVM);
00662 
00663         mbOwnVM = bOwnVM;
00664 
00665 }
00666 
00667 
00668 
00669 
00670 
00671 CppSQLite3Query::~CppSQLite3Query()
00672 
00673 {
00674 
00675         try
00676 
00677         {
00678 
00679                 finalize();
00680 
00681         }
00682 
00683         catch (...)
00684 
00685         {
00686 
00687         }
00688 
00689 }
00690 
00691 
00692 
00693 
00694 
00695 CppSQLite3Query& CppSQLite3Query::operator=(const CppSQLite3Query& rQuery)
00696 
00697 {
00698 
00699         try
00700 
00701         {
00702 
00703                 finalize();
00704 
00705         }
00706 
00707         catch (...)
00708 
00709         {
00710 
00711         }
00712 
00713         mpVM = rQuery.mpVM;
00714 
00715         // Only one object can own the VM
00716 
00717         const_cast<CppSQLite3Query&>(rQuery).mpVM = 0;
00718 
00719         mbEof = rQuery.mbEof;
00720 
00721         mnCols = rQuery.mnCols;
00722 
00723         mbOwnVM = rQuery.mbOwnVM;
00724 
00725         return *this;
00726 
00727 }
00728 
00729 
00730 
00731 
00732 
00733 int CppSQLite3Query::numFields()
00734 
00735 {
00736 
00737         checkVM();
00738 
00739         return mnCols;
00740 
00741 }
00742 
00743 
00744 
00745 
00746 
00747 const char* CppSQLite3Query::fieldValue(int nField)
00748 
00749 {
00750 
00751         checkVM();
00752 
00753 
00754 
00755         if (nField < 0 || nField > mnCols-1)
00756 
00757         {
00758 
00759                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
00760 
00761                                                                 "Invalid field index requested",
00762 
00763                                                                 DONT_DELETE_MSG);
00764 
00765         }
00766 
00767 
00768 
00769         return (const char*)sqlite3_column_text(mpVM, nField);
00770 
00771 }
00772 
00773 
00774 
00775 
00776 
00777 const char* CppSQLite3Query::fieldValue(const char* szField)
00778 
00779 {
00780 
00781         int nField = fieldIndex(szField);
00782 
00783         return (const char*)sqlite3_column_text(mpVM, nField);
00784 
00785 }
00786 
00787 
00788 
00789 
00790 
00791 int CppSQLite3Query::getIntField(int nField, int nNullValue/*=0*/)
00792 
00793 {
00794 
00795         if (fieldDataType(nField) == SQLITE_NULL)
00796 
00797         {
00798 
00799                 return nNullValue;
00800 
00801         }
00802 
00803         else
00804 
00805         {
00806 
00807                 return sqlite3_column_int(mpVM, nField);
00808 
00809         }
00810 
00811 }
00812 
00813 
00814 
00815 
00816 
00817 int CppSQLite3Query::getIntField(const char* szField, int nNullValue/*=0*/)
00818 
00819 {
00820 
00821         int nField = fieldIndex(szField);
00822 
00823         return getIntField(nField, nNullValue);
00824 
00825 }
00826 
00827 
00828 
00829 
00830 
00831 double CppSQLite3Query::getFloatField(int nField, double fNullValue/*=0.0*/)
00832 
00833 {
00834 
00835         if (fieldDataType(nField) == SQLITE_NULL)
00836 
00837         {
00838 
00839                 return fNullValue;
00840 
00841         }
00842 
00843         else
00844 
00845         {
00846 
00847                 return sqlite3_column_double(mpVM, nField);
00848 
00849         }
00850 
00851 }
00852 
00853 
00854 
00855 
00856 
00857 double CppSQLite3Query::getFloatField(const char* szField, double fNullValue/*=0.0*/)
00858 
00859 {
00860 
00861         int nField = fieldIndex(szField);
00862 
00863         return getFloatField(nField, fNullValue);
00864 
00865 }
00866 
00867 
00868 
00869 
00870 
00871 const char* CppSQLite3Query::getStringField(int nField, const char* szNullValue/*=""*/)
00872 
00873 {
00874 
00875         if (fieldDataType(nField) == SQLITE_NULL)
00876 
00877         {
00878 
00879                 return szNullValue;
00880 
00881         }
00882 
00883         else
00884 
00885         {
00886 
00887                 return (const char*)sqlite3_column_text(mpVM, nField);
00888 
00889         }
00890 
00891 }
00892 
00893 
00894 
00895 
00896 
00897 const char* CppSQLite3Query::getStringField(const char* szField, const char* szNullValue/*=""*/)
00898 
00899 {
00900 
00901         int nField = fieldIndex(szField);
00902 
00903         return getStringField(nField, szNullValue);
00904 
00905 }
00906 
00907 
00908 
00909 
00910 
00911 const unsigned char* CppSQLite3Query::getBlobField(int nField, int& nLen)
00912 
00913 {
00914 
00915         checkVM();
00916 
00917 
00918 
00919         if (nField < 0 || nField > mnCols-1)
00920 
00921         {
00922 
00923                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
00924 
00925                                                                 "Invalid field index requested",
00926 
00927                                                                 DONT_DELETE_MSG);
00928 
00929         }
00930 
00931 
00932 
00933         nLen = sqlite3_column_bytes(mpVM, nField);
00934 
00935         return (const unsigned char*)sqlite3_column_blob(mpVM, nField);
00936 
00937 }
00938 
00939 
00940 
00941 
00942 
00943 const unsigned char* CppSQLite3Query::getBlobField(const char* szField, int& nLen)
00944 
00945 {
00946 
00947         int nField = fieldIndex(szField);
00948 
00949         return getBlobField(nField, nLen);
00950 
00951 }
00952 
00953 
00954 
00955 
00956 
00957 bool CppSQLite3Query::fieldIsNull(int nField)
00958 
00959 {
00960 
00961         return (fieldDataType(nField) == SQLITE_NULL);
00962 
00963 }
00964 
00965 
00966 
00967 
00968 
00969 bool CppSQLite3Query::fieldIsNull(const char* szField)
00970 
00971 {
00972 
00973         int nField = fieldIndex(szField);
00974 
00975         return (fieldDataType(nField) == SQLITE_NULL);
00976 
00977 }
00978 
00979 
00980 
00981 
00982 
00983 int CppSQLite3Query::fieldIndex(const char* szField)
00984 
00985 {
00986 
00987         checkVM();
00988 
00989 
00990 
00991         if (szField)
00992 
00993         {
00994 
00995                 for (int nField = 0; nField < mnCols; nField++)
00996 
00997                 {
00998 
00999                         const char* szTemp = sqlite3_column_name(mpVM, nField);
01000 
01001 
01002 
01003                         if (strcmp(szField, szTemp) == 0)
01004 
01005                         {
01006 
01007                                 return nField;
01008 
01009                         }
01010 
01011                 }
01012 
01013         }
01014 
01015 
01016 
01017         throw CppSQLite3Exception(CPPSQLITE_ERROR,
01018 
01019                                                         "Invalid field name requested",
01020 
01021                                                         DONT_DELETE_MSG);
01022 
01023 }
01024 
01025 
01026 
01027 
01028 
01029 const char* CppSQLite3Query::fieldName(int nCol)
01030 
01031 {
01032 
01033         checkVM();
01034 
01035 
01036 
01037         if (nCol < 0 || nCol > mnCols-1)
01038 
01039         {
01040 
01041                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01042 
01043                                                                 "Invalid field index requested",
01044 
01045                                                                 DONT_DELETE_MSG);
01046 
01047         }
01048 
01049 
01050 
01051         return sqlite3_column_name(mpVM, nCol);
01052 
01053 }
01054 
01055 
01056 
01057 
01058 
01059 const char* CppSQLite3Query::fieldDeclType(int nCol)
01060 
01061 {
01062 
01063         checkVM();
01064 
01065 
01066 
01067         if (nCol < 0 || nCol > mnCols-1)
01068 
01069         {
01070 
01071                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01072 
01073                                                                 "Invalid field index requested",
01074 
01075                                                                 DONT_DELETE_MSG);
01076 
01077         }
01078 
01079 
01080 
01081         return sqlite3_column_decltype(mpVM, nCol);
01082 
01083 }
01084 
01085 
01086 
01087 
01088 
01089 int CppSQLite3Query::fieldDataType(int nCol)
01090 
01091 {
01092 
01093         checkVM();
01094 
01095 
01096 
01097         if (nCol < 0 || nCol > mnCols-1)
01098 
01099         {
01100 
01101                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01102 
01103                                                                 "Invalid field index requested",
01104 
01105                                                                 DONT_DELETE_MSG);
01106 
01107         }
01108 
01109 
01110 
01111         return sqlite3_column_type(mpVM, nCol);
01112 
01113 }
01114 
01115 
01116 
01117 
01118 
01119 bool CppSQLite3Query::eof()
01120 
01121 {
01122 
01123         checkVM();
01124 
01125         return mbEof;
01126 
01127 }
01128 
01129 
01130 
01131 
01132 
01133 void CppSQLite3Query::nextRow()
01134 
01135 {
01136 
01137         checkVM();
01138 
01139 
01140 
01141         int nRet = sqlite3_step(mpVM);
01142 
01143 
01144 
01145         if (nRet == SQLITE_DONE)
01146 
01147         {
01148 
01149                 // no rows
01150 
01151                 mbEof = true;
01152 
01153         }
01154 
01155         else if (nRet == SQLITE_ROW)
01156 
01157         {
01158 
01159                 // more rows, nothing to do
01160 
01161         }
01162 
01163         else
01164 
01165         {
01166 
01167                 nRet = sqlite3_finalize(mpVM);
01168 
01169                 mpVM = 0;
01170 
01171                 const char* szError = sqlite3_errmsg(mpDB);
01172 
01173                 throw CppSQLite3Exception(nRet,
01174 
01175                                                                 (char*)szError,
01176 
01177                                                                 DONT_DELETE_MSG);
01178 
01179         }
01180 
01181 }
01182 
01183 
01184 
01185 
01186 
01187 void CppSQLite3Query::finalize()
01188 
01189 {
01190 
01191         if (mpVM && mbOwnVM)
01192 
01193         {
01194 
01195                 int nRet = sqlite3_finalize(mpVM);
01196 
01197                 mpVM = 0;
01198 
01199                 if (nRet != SQLITE_OK)
01200 
01201                 {
01202 
01203                         const char* szError = sqlite3_errmsg(mpDB);
01204 
01205                         throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
01206 
01207                 }
01208 
01209         }
01210 
01211 }
01212 
01213 
01214 
01215 
01216 
01217 void CppSQLite3Query::checkVM()
01218 
01219 {
01220 
01221         if (mpVM == 0)
01222 
01223         {
01224 
01225                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01226 
01227                                                                 "Null Virtual Machine pointer",
01228 
01229                                                                 DONT_DELETE_MSG);
01230 
01231         }
01232 
01233 }
01234 
01235 
01236 
01237 
01238 
01240 
01241 
01242 
01243 CppSQLite3Table::CppSQLite3Table()
01244 
01245 {
01246 
01247         mpaszResults = 0;
01248 
01249         mnRows = 0;
01250 
01251         mnCols = 0;
01252 
01253         mnCurrentRow = 0;
01254 
01255 }
01256 
01257 
01258 
01259 
01260 
01261 CppSQLite3Table::CppSQLite3Table(const CppSQLite3Table& rTable)
01262 
01263 {
01264 
01265         mpaszResults = rTable.mpaszResults;
01266 
01267         // Only one object can own the results
01268 
01269         const_cast<CppSQLite3Table&>(rTable).mpaszResults = 0;
01270 
01271         mnRows = rTable.mnRows;
01272 
01273         mnCols = rTable.mnCols;
01274 
01275         mnCurrentRow = rTable.mnCurrentRow;
01276 
01277 }
01278 
01279 
01280 
01281 
01282 
01283 CppSQLite3Table::CppSQLite3Table(char** paszResults, int nRows, int nCols)
01284 
01285 {
01286 
01287         mpaszResults = paszResults;
01288 
01289         mnRows = nRows;
01290 
01291         mnCols = nCols;
01292 
01293         mnCurrentRow = 0;
01294 
01295 }
01296 
01297 
01298 
01299 
01300 
01301 CppSQLite3Table::~CppSQLite3Table()
01302 
01303 {
01304 
01305         try
01306 
01307         {
01308 
01309                 finalize();
01310 
01311         }
01312 
01313         catch (...)
01314 
01315         {
01316 
01317         }
01318 
01319 }
01320 
01321 
01322 
01323 
01324 
01325 CppSQLite3Table& CppSQLite3Table::operator=(const CppSQLite3Table& rTable)
01326 
01327 {
01328 
01329         try
01330 
01331         {
01332 
01333                 finalize();
01334 
01335         }
01336 
01337         catch (...)
01338 
01339         {
01340 
01341         }
01342 
01343         mpaszResults = rTable.mpaszResults;
01344 
01345         // Only one object can own the results
01346 
01347         const_cast<CppSQLite3Table&>(rTable).mpaszResults = 0;
01348 
01349         mnRows = rTable.mnRows;
01350 
01351         mnCols = rTable.mnCols;
01352 
01353         mnCurrentRow = rTable.mnCurrentRow;
01354 
01355         return *this;
01356 
01357 }
01358 
01359 
01360 
01361 
01362 
01363 void CppSQLite3Table::finalize()
01364 
01365 {
01366 
01367         if (mpaszResults)
01368 
01369         {
01370 
01371                 sqlite3_free_table(mpaszResults);
01372 
01373                 mpaszResults = 0;
01374 
01375         }
01376 
01377 }
01378 
01379 
01380 
01381 
01382 
01383 int CppSQLite3Table::numFields()
01384 
01385 {
01386 
01387         checkResults();
01388 
01389         return mnCols;
01390 
01391 }
01392 
01393 
01394 
01395 
01396 
01397 int CppSQLite3Table::numRows()
01398 
01399 {
01400 
01401         checkResults();
01402 
01403         return mnRows;
01404 
01405 }
01406 
01407 
01408 
01409 
01410 
01411 const char* CppSQLite3Table::fieldValue(int nField)
01412 
01413 {
01414 
01415         checkResults();
01416 
01417 
01418 
01419         if (nField < 0 || nField > mnCols-1)
01420 
01421         {
01422 
01423                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01424 
01425                                                                 "Invalid field index requested",
01426 
01427                                                                 DONT_DELETE_MSG);
01428 
01429         }
01430 
01431 
01432 
01433         int nIndex = (mnCurrentRow*mnCols) + mnCols + nField;
01434 
01435         return mpaszResults[nIndex];
01436 
01437 }
01438 
01439 
01440 
01441 
01442 
01443 const char* CppSQLite3Table::fieldValue(const char* szField)
01444 
01445 {
01446 
01447         checkResults();
01448 
01449 
01450 
01451         if (szField)
01452 
01453         {
01454 
01455                 for (int nField = 0; nField < mnCols; nField++)
01456 
01457                 {
01458 
01459                         if (strcmp(szField, mpaszResults[nField]) == 0)
01460 
01461                         {
01462 
01463                                 int nIndex = (mnCurrentRow*mnCols) + mnCols + nField;
01464 
01465                                 return mpaszResults[nIndex];
01466 
01467                         }
01468 
01469                 }
01470 
01471         }
01472 
01473 
01474 
01475         throw CppSQLite3Exception(CPPSQLITE_ERROR,
01476 
01477                                                         "Invalid field name requested",
01478 
01479                                                         DONT_DELETE_MSG);
01480 
01481 }
01482 
01483 
01484 
01485 
01486 
01487 int CppSQLite3Table::getIntField(int nField, int nNullValue/*=0*/)
01488 
01489 {
01490 
01491         if (fieldIsNull(nField))
01492 
01493         {
01494 
01495                 return nNullValue;
01496 
01497         }
01498 
01499         else
01500 
01501         {
01502 
01503                 return atoi(fieldValue(nField));
01504 
01505         }
01506 
01507 }
01508 
01509 
01510 
01511 
01512 
01513 int CppSQLite3Table::getIntField(const char* szField, int nNullValue/*=0*/)
01514 
01515 {
01516 
01517         if (fieldIsNull(szField))
01518 
01519         {
01520 
01521                 return nNullValue;
01522 
01523         }
01524 
01525         else
01526 
01527         {
01528 
01529                 return atoi(fieldValue(szField));
01530 
01531         }
01532 
01533 }
01534 
01535 
01536 
01537 
01538 
01539 double CppSQLite3Table::getFloatField(int nField, double fNullValue/*=0.0*/)
01540 
01541 {
01542 
01543         if (fieldIsNull(nField))
01544 
01545         {
01546 
01547                 return fNullValue;
01548 
01549         }
01550 
01551         else
01552 
01553         {
01554 
01555                 return atof(fieldValue(nField));
01556 
01557         }
01558 
01559 }
01560 
01561 
01562 
01563 
01564 
01565 double CppSQLite3Table::getFloatField(const char* szField, double fNullValue/*=0.0*/)
01566 
01567 {
01568 
01569         if (fieldIsNull(szField))
01570 
01571         {
01572 
01573                 return fNullValue;
01574 
01575         }
01576 
01577         else
01578 
01579         {
01580 
01581                 return atof(fieldValue(szField));
01582 
01583         }
01584 
01585 }
01586 
01587 
01588 
01589 
01590 
01591 const char* CppSQLite3Table::getStringField(int nField, const char* szNullValue/*=""*/)
01592 
01593 {
01594 
01595         if (fieldIsNull(nField))
01596 
01597         {
01598 
01599                 return szNullValue;
01600 
01601         }
01602 
01603         else
01604 
01605         {
01606 
01607                 return fieldValue(nField);
01608 
01609         }
01610 
01611 }
01612 
01613 
01614 
01615 
01616 
01617 const char* CppSQLite3Table::getStringField(const char* szField, const char* szNullValue/*=""*/)
01618 
01619 {
01620 
01621         if (fieldIsNull(szField))
01622 
01623         {
01624 
01625                 return szNullValue;
01626 
01627         }
01628 
01629         else
01630 
01631         {
01632 
01633                 return fieldValue(szField);
01634 
01635         }
01636 
01637 }
01638 
01639 
01640 
01641 
01642 
01643 bool CppSQLite3Table::fieldIsNull(int nField)
01644 
01645 {
01646 
01647         checkResults();
01648 
01649         return (fieldValue(nField) == 0);
01650 
01651 }
01652 
01653 
01654 
01655 
01656 
01657 bool CppSQLite3Table::fieldIsNull(const char* szField)
01658 
01659 {
01660 
01661         checkResults();
01662 
01663         return (fieldValue(szField) == 0);
01664 
01665 }
01666 
01667 
01668 
01669 
01670 
01671 const char* CppSQLite3Table::fieldName(int nCol)
01672 
01673 {
01674 
01675         checkResults();
01676 
01677 
01678 
01679         if (nCol < 0 || nCol > mnCols-1)
01680 
01681         {
01682 
01683                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01684 
01685                                                                 "Invalid field index requested",
01686 
01687                                                                 DONT_DELETE_MSG);
01688 
01689         }
01690 
01691 
01692 
01693         return mpaszResults[nCol];
01694 
01695 }
01696 
01697 
01698 
01699 
01700 
01701 void CppSQLite3Table::setRow(int nRow)
01702 
01703 {
01704 
01705         checkResults();
01706 
01707 
01708 
01709         if (nRow < 0 || nRow > mnRows-1)
01710 
01711         {
01712 
01713                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01714 
01715                                                                 "Invalid row index requested",
01716 
01717                                                                 DONT_DELETE_MSG);
01718 
01719         }
01720 
01721 
01722 
01723         mnCurrentRow = nRow;
01724 
01725 }
01726 
01727 
01728 
01729 
01730 
01731 void CppSQLite3Table::checkResults()
01732 
01733 {
01734 
01735         if (mpaszResults == 0)
01736 
01737         {
01738 
01739                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
01740 
01741                                                                 "Null Results pointer",
01742 
01743                                                                 DONT_DELETE_MSG);
01744 
01745         }
01746 
01747 }
01748 
01749 
01750 
01751 
01752 
01754 
01755 
01756 
01757 CppSQLite3Statement::CppSQLite3Statement()
01758 
01759 {
01760 
01761         mpDB = 0;
01762 
01763         mpVM = 0;
01764 
01765 }
01766 
01767 
01768 
01769 
01770 
01771 CppSQLite3Statement::CppSQLite3Statement(const CppSQLite3Statement& rStatement)
01772 
01773 {
01774 
01775         mpDB = rStatement.mpDB;
01776 
01777         mpVM = rStatement.mpVM;
01778 
01779         // Only one object can own VM
01780 
01781         const_cast<CppSQLite3Statement&>(rStatement).mpVM = 0;
01782 
01783 }
01784 
01785 
01786 
01787 
01788 
01789 CppSQLite3Statement::CppSQLite3Statement(sqlite3* pDB, sqlite3_stmt* pVM)
01790 
01791 {
01792 
01793         mpDB = pDB;
01794 
01795         mpVM = pVM;
01796 
01797 }
01798 
01799 
01800 
01801 
01802 
01803 CppSQLite3Statement::~CppSQLite3Statement()
01804 
01805 {
01806 
01807         try
01808 
01809         {
01810 
01811                 finalize();
01812 
01813         }
01814 
01815         catch (...)
01816 
01817         {
01818 
01819         }
01820 
01821 }
01822 
01823 
01824 
01825 
01826 
01827 CppSQLite3Statement& CppSQLite3Statement::operator=(const CppSQLite3Statement& rStatement)
01828 
01829 {
01830 
01831         mpDB = rStatement.mpDB;
01832 
01833         mpVM = rStatement.mpVM;
01834 
01835         // Only one object can own VM
01836 
01837         const_cast<CppSQLite3Statement&>(rStatement).mpVM = 0;
01838 
01839         return *this;
01840 
01841 }
01842 
01843 
01844 
01845 
01846 
01847 int CppSQLite3Statement::execDML()
01848 
01849 {
01850 
01851         checkDB();
01852 
01853         checkVM();
01854 
01855 
01856 
01857         const char* szError=0;
01858 
01859 
01860 
01861         int nRet = sqlite3_step(mpVM);
01862 
01863 
01864 
01865         if (nRet == SQLITE_DONE)
01866 
01867         {
01868 
01869                 int nRowsChanged = sqlite3_changes(mpDB);
01870 
01871 
01872 
01873                 nRet = sqlite3_reset(mpVM);
01874 
01875 
01876 
01877                 if (nRet != SQLITE_OK)
01878 
01879                 {
01880 
01881                         szError = sqlite3_errmsg(mpDB);
01882 
01883                         throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
01884 
01885                 }
01886 
01887 
01888 
01889                 return nRowsChanged;
01890 
01891         }
01892 
01893         else
01894 
01895         {
01896 
01897                 nRet = sqlite3_reset(mpVM);
01898 
01899                 szError = sqlite3_errmsg(mpDB);
01900 
01901                 throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
01902 
01903         }
01904 
01905 }
01906 
01907 
01908 
01909 
01910 
01911 CppSQLite3Query CppSQLite3Statement::execQuery()
01912 
01913 {
01914 
01915         checkDB();
01916 
01917         checkVM();
01918 
01919 
01920 
01921         int nRet = sqlite3_step(mpVM);
01922 
01923 
01924 
01925         if (nRet == SQLITE_DONE)
01926 
01927         {
01928 
01929                 // no rows
01930 
01931                 return CppSQLite3Query(mpDB, mpVM, true/*eof*/, false);
01932 
01933         }
01934 
01935         else if (nRet == SQLITE_ROW)
01936 
01937         {
01938 
01939                 // at least 1 row
01940 
01941                 return CppSQLite3Query(mpDB, mpVM, false/*eof*/, false);
01942 
01943         }
01944 
01945         else
01946 
01947         {
01948 
01949                 nRet = sqlite3_reset(mpVM);
01950 
01951                 const char* szError = sqlite3_errmsg(mpDB);
01952 
01953                 throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
01954 
01955         }
01956 
01957 }
01958 
01959 
01960 
01961 
01962 
01963 void CppSQLite3Statement::bind(int nParam, const char* szValue)
01964 
01965 {
01966 
01967         checkVM();
01968 
01969         int nRes = sqlite3_bind_text(mpVM, nParam, szValue, -1, SQLITE_TRANSIENT);
01970 
01971 
01972 
01973         if (nRes != SQLITE_OK)
01974 
01975         {
01976 
01977                 throw CppSQLite3Exception(nRes,
01978 
01979                                                                 "Error binding string param",
01980 
01981                                                                 DONT_DELETE_MSG);
01982 
01983         }
01984 
01985 }
01986 
01987 
01988 
01989 
01990 
01991 void CppSQLite3Statement::bind(int nParam, const int nValue)
01992 
01993 {
01994 
01995         checkVM();
01996 
01997         int nRes = sqlite3_bind_int(mpVM, nParam, nValue);
01998 
01999 
02000 
02001         if (nRes != SQLITE_OK)
02002 
02003         {
02004 
02005                 throw CppSQLite3Exception(nRes,
02006 
02007                                                                 "Error binding int param",
02008 
02009                                                                 DONT_DELETE_MSG);
02010 
02011         }
02012 
02013 }
02014 
02015 
02016 
02017 
02018 
02019 void CppSQLite3Statement::bind(int nParam, const double dValue)
02020 
02021 {
02022 
02023         checkVM();
02024 
02025         int nRes = sqlite3_bind_double(mpVM, nParam, dValue);
02026 
02027 
02028 
02029         if (nRes != SQLITE_OK)
02030 
02031         {
02032 
02033                 throw CppSQLite3Exception(nRes,
02034 
02035                                                                 "Error binding double param",
02036 
02037                                                                 DONT_DELETE_MSG);
02038 
02039         }
02040 
02041 }
02042 
02043 
02044 
02045 
02046 
02047 void CppSQLite3Statement::bind(int nParam, const unsigned char* blobValue, int nLen)
02048 
02049 {
02050 
02051         checkVM();
02052 
02053         int nRes = sqlite3_bind_blob(mpVM, nParam,
02054 
02055                                                                 (const void*)blobValue, nLen, SQLITE_TRANSIENT);
02056 
02057 
02058 
02059         if (nRes != SQLITE_OK)
02060 
02061         {
02062 
02063                 throw CppSQLite3Exception(nRes,
02064 
02065                                                                 "Error binding blob param",
02066 
02067                                                                 DONT_DELETE_MSG);
02068 
02069         }
02070 
02071 }
02072 
02073 
02074 
02075         
02076 
02077 void CppSQLite3Statement::bindNull(int nParam)
02078 
02079 {
02080 
02081         checkVM();
02082 
02083         int nRes = sqlite3_bind_null(mpVM, nParam);
02084 
02085 
02086 
02087         if (nRes != SQLITE_OK)
02088 
02089         {
02090 
02091                 throw CppSQLite3Exception(nRes,
02092 
02093                                                                 "Error binding NULL param",
02094 
02095                                                                 DONT_DELETE_MSG);
02096 
02097         }
02098 
02099 }
02100 
02101 
02102 
02103 
02104 
02105 void CppSQLite3Statement::reset()
02106 
02107 {
02108 
02109         if (mpVM)
02110 
02111         {
02112 
02113                 int nRet = sqlite3_reset(mpVM);
02114 
02115 
02116 
02117                 if (nRet != SQLITE_OK)
02118 
02119                 {
02120 
02121                         const char* szError = sqlite3_errmsg(mpDB);
02122 
02123                         throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
02124 
02125                 }
02126 
02127         }
02128 
02129 }
02130 
02131 
02132 
02133 
02134 
02135 void CppSQLite3Statement::finalize()
02136 
02137 {
02138 
02139         if (mpVM)
02140 
02141         {
02142 
02143                 int nRet = sqlite3_finalize(mpVM);
02144 
02145                 mpVM = 0;
02146 
02147 
02148 
02149                 if (nRet != SQLITE_OK)
02150 
02151                 {
02152 
02153                         const char* szError = sqlite3_errmsg(mpDB);
02154 
02155                         throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
02156 
02157                 }
02158 
02159         }
02160 
02161 }
02162 
02163 
02164 
02165 
02166 
02167 void CppSQLite3Statement::checkDB()
02168 
02169 {
02170 
02171         if (mpDB == 0)
02172 
02173         {
02174 
02175                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
02176 
02177                                                                 "Database not open",
02178 
02179                                                                 DONT_DELETE_MSG);
02180 
02181         }
02182 
02183 }
02184 
02185 
02186 
02187 
02188 
02189 void CppSQLite3Statement::checkVM()
02190 
02191 {
02192 
02193         if (mpVM == 0)
02194 
02195         {
02196 
02197                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
02198 
02199                                                                 "Null Virtual Machine pointer",
02200 
02201                                                                 DONT_DELETE_MSG);
02202 
02203         }
02204 
02205 }
02206 
02207 
02208 
02209 
02210 
02212 
02213 
02214 
02215 CppSQLite3DB::CppSQLite3DB()
02216 
02217 {
02218 
02219         mpDB = 0;
02220 
02221         mnBusyTimeoutMs = 60000; // 60 seconds
02222 
02223 }
02224 
02225 
02226 
02227 
02228 
02229 CppSQLite3DB::CppSQLite3DB(const CppSQLite3DB& db)
02230 
02231 {
02232 
02233         mpDB = db.mpDB;
02234 
02235         mnBusyTimeoutMs = 60000; // 60 seconds
02236 
02237 }
02238 
02239 
02240 
02241 
02242 
02243 CppSQLite3DB::~CppSQLite3DB()
02244 
02245 {
02246 
02247         close();
02248 
02249 }
02250 
02251 
02252 
02253 
02254 
02255 CppSQLite3DB& CppSQLite3DB::operator=(const CppSQLite3DB& db)
02256 
02257 {
02258 
02259         mpDB = db.mpDB;
02260 
02261         mnBusyTimeoutMs = 60000; // 60 seconds
02262 
02263         return *this;
02264 
02265 }
02266 
02267 
02268 
02269 
02270 
02271 void CppSQLite3DB::open(const char* szFile)
02272 
02273 {
02274 
02275         int nRet = sqlite3_open(szFile, &mpDB);
02276 
02277 
02278 
02279         if (nRet != SQLITE_OK)
02280 
02281         {
02282 
02283                 const char* szError = sqlite3_errmsg(mpDB);
02284 
02285                 throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
02286 
02287         }
02288 
02289 
02290 
02291         setBusyTimeout(mnBusyTimeoutMs);
02292 
02293 }
02294 
02295 
02296 
02297 
02298 
02299 void CppSQLite3DB::close()
02300 
02301 {
02302 
02303         if (mpDB)
02304 
02305         {
02306 
02307                 sqlite3_close(mpDB);
02308 
02309                 mpDB = 0;
02310 
02311         }
02312 
02313 }
02314 
02315 
02316 
02317 
02318 
02319 CppSQLite3Statement CppSQLite3DB::compileStatement(const char* szSQL)
02320 
02321 {
02322 
02323         checkDB();
02324 
02325 
02326 
02327         sqlite3_stmt* pVM = compile(szSQL);
02328 
02329         return CppSQLite3Statement(mpDB, pVM);
02330 
02331 }
02332 
02333 
02334 
02335 
02336 
02337 bool CppSQLite3DB::tableExists(const char* szTable)
02338 
02339 {
02340 
02341         char szSQL[128];
02342 
02343         sprintf(szSQL,
02344 
02345                         "select count(*) from sqlite_master where type='table' and name='%s'",
02346 
02347                         szTable);
02348 
02349         int nRet = execScalar(szSQL);
02350 
02351         return (nRet > 0);
02352 
02353 }
02354 
02355 
02356 
02357 
02358 
02359 int CppSQLite3DB::execDML(const char* szSQL)
02360 
02361 {
02362 
02363         checkDB();
02364 
02365 
02366 
02367         char* szError=0;
02368 
02369 
02370 
02371         int nRet = sqlite3_exec(mpDB, szSQL, 0, 0, &szError);
02372 
02373 
02374 
02375         if (nRet == SQLITE_OK)
02376 
02377         {
02378 
02379                 return sqlite3_changes(mpDB);
02380 
02381         }
02382 
02383         else
02384 
02385         {
02386 
02387                 throw CppSQLite3Exception(nRet, szError);
02388 
02389         }
02390 
02391 }
02392 
02393 
02394 
02395 
02396 
02397 CppSQLite3Query CppSQLite3DB::execQuery(const char* szSQL)
02398 
02399 {
02400 
02401         checkDB();
02402 
02403 
02404 
02405         sqlite3_stmt* pVM = compile(szSQL);
02406 
02407 
02408 
02409         int nRet = sqlite3_step(pVM);
02410 
02411 
02412 
02413         if (nRet == SQLITE_DONE)
02414 
02415         {
02416 
02417                 // no rows
02418 
02419                 return CppSQLite3Query(mpDB, pVM, true/*eof*/);
02420 
02421         }
02422 
02423         else if (nRet == SQLITE_ROW)
02424 
02425         {
02426 
02427                 // at least 1 row
02428 
02429                 return CppSQLite3Query(mpDB, pVM, false/*eof*/);
02430 
02431         }
02432 
02433         else
02434 
02435         {
02436 
02437                 nRet = sqlite3_finalize(pVM);
02438 
02439                 const char* szError= sqlite3_errmsg(mpDB);
02440 
02441                 throw CppSQLite3Exception(nRet, (char*)szError, DONT_DELETE_MSG);
02442 
02443         }
02444 
02445 }
02446 
02447 
02448 
02449 
02450 
02451 int CppSQLite3DB::execScalar(const char* szSQL)
02452 
02453 {
02454 
02455         CppSQLite3Query q = execQuery(szSQL);
02456 
02457 
02458 
02459         if (q.eof() || q.numFields() < 1)
02460 
02461         {
02462 
02463                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
02464 
02465                                                                 "Invalid scalar query",
02466 
02467                                                                 DONT_DELETE_MSG);
02468 
02469         }
02470 
02471 
02472 
02473         return atoi(q.fieldValue(0));
02474 
02475 }
02476 
02477 
02478 
02479 
02480 
02481 CppSQLite3Table CppSQLite3DB::getTable(const char* szSQL)
02482 
02483 {
02484 
02485         checkDB();
02486 
02487 
02488 
02489         char* szError=0;
02490 
02491         char** paszResults=0;
02492 
02493         int nRet;
02494 
02495         int nRows(0);
02496 
02497         int nCols(0);
02498 
02499 
02500 
02501         nRet = sqlite3_get_table(mpDB, szSQL, &paszResults, &nRows, &nCols, &szError);
02502 
02503 
02504 
02505         if (nRet == SQLITE_OK)
02506 
02507         {
02508 
02509                 return CppSQLite3Table(paszResults, nRows, nCols);
02510 
02511         }
02512 
02513         else
02514 
02515         {
02516 
02517                 throw CppSQLite3Exception(nRet, szError);
02518 
02519         }
02520 
02521 }
02522 
02523 
02524 
02525 
02526 
02527 sqlite_int64 CppSQLite3DB::lastRowId()
02528 
02529 {
02530 
02531         return sqlite3_last_insert_rowid(mpDB);
02532 
02533 }
02534 
02535 
02536 
02537 
02538 
02539 void CppSQLite3DB::setBusyTimeout(int nMillisecs)
02540 
02541 {
02542 
02543         mnBusyTimeoutMs = nMillisecs;
02544 
02545         sqlite3_busy_timeout(mpDB, mnBusyTimeoutMs);
02546 
02547 }
02548 
02549 
02550 
02551 
02552 
02553 void CppSQLite3DB::checkDB()
02554 
02555 {
02556 
02557         if (!mpDB)
02558 
02559         {
02560 
02561                 throw CppSQLite3Exception(CPPSQLITE_ERROR,
02562 
02563                                                                 "Database not open",
02564 
02565                                                                 DONT_DELETE_MSG);
02566 
02567         }
02568 
02569 }
02570 
02571 
02572 
02573 
02574 
02575 sqlite3_stmt* CppSQLite3DB::compile(const char* szSQL)
02576 
02577 {
02578 
02579         checkDB();
02580 
02581 
02582 
02583         char* szError=0;
02584 
02585         const char* szTail=0;
02586 
02587         sqlite3_stmt* pVM;
02588 
02589 
02590 
02591         int nRet = sqlite3_prepare(mpDB, szSQL, -1, &pVM, &szTail);
02592 
02593 
02594 
02595         if (nRet != SQLITE_OK)
02596 
02597         {
02598 
02599                 throw CppSQLite3Exception(nRet, szError);
02600 
02601         }
02602 
02603 
02604 
02605         return pVM;
02606 
02607 }
02608 
02609 
02610 
02611 
02612 
02614 
02615 // SQLite encode.c reproduced here, containing implementation notes and source
02616 
02617 // for sqlite3_encode_binary() and sqlite3_decode_binary() 
02618 
02620 
02621 
02622 
02623 /*
02624 
02625 ** 2002 April 25
02626 
02627 **
02628 
02629 ** The author disclaims copyright to this source code.  In place of
02630 
02631 ** a legal notice, here is a blessing:
02632 
02633 **
02634 
02635 **    May you do good and not evil.
02636 
02637 **    May you find forgiveness for yourself and forgive others.
02638 
02639 **    May you share freely, never taking more than you give.
02640 
02641 **
02642 
02643 *************************************************************************
02644 
02645 ** This file contains helper routines used to translate binary data into
02646 
02647 ** a null-terminated string (suitable for use in SQLite) and back again.
02648 
02649 ** These are convenience routines for use by people who want to store binary
02650 
02651 ** data in an SQLite database.  The code in this file is not used by any other
02652 
02653 ** part of the SQLite library.
02654 
02655 **
02656 
02657 ** $Id: CppSQLite3.cpp,v 1.4 2010/03/16 15:46:13 cervenansky Exp $
02658 
02659 */
02660 
02661 
02662 
02663 /*
02664 
02665 ** How This Encoder Works
02666 
02667 **
02668 
02669 ** The output is allowed to contain any character except 0x27 (') and
02670 
02671 ** 0x00.  This is accomplished by using an escape character to encode
02672 
02673 ** 0x27 and 0x00 as a two-byte sequence.  The escape character is always
02674 
02675 ** 0x01.  An 0x00 is encoded as the two byte sequence 0x01 0x01.  The
02676 
02677 ** 0x27 character is encoded as the two byte sequence 0x01 0x03.  Finally,
02678 
02679 ** the escape character itself is encoded as the two-character sequence
02680 
02681 ** 0x01 0x02.
02682 
02683 **
02684 
02685 ** To summarize, the encoder works by using an escape sequences as follows:
02686 
02687 **
02688 
02689 **       0x00  ->  0x01 0x01
02690 
02691 **       0x01  ->  0x01 0x02
02692 
02693 **       0x27  ->  0x01 0x03
02694 
02695 **
02696 
02697 ** If that were all the encoder did, it would work, but in certain cases
02698 
02699 ** it could double the size of the encoded string.  For example, to
02700 
02701 ** encode a string of 100 0x27 characters would require 100 instances of
02702 
02703 ** the 0x01 0x03 escape sequence resulting in a 200-character output.
02704 
02705 ** We would prefer to keep the size of the encoded string smaller than
02706 
02707 ** this.
02708 
02709 **
02710 
02711 ** To minimize the encoding size, we first add a fixed offset value to each 
02712 
02713 ** byte in the sequence.  The addition is modulo 256.  (That is to say, if
02714 
02715 ** the sum of the original character value and the offset exceeds 256, then
02716 
02717 ** the higher order bits are truncated.)  The offset is chosen to minimize
02718 
02719 ** the number of characters in the string that need to be escaped.  For
02720 
02721 ** example, in the case above where the string was composed of 100 0x27
02722 
02723 ** characters, the offset might be 0x01.  Each of the 0x27 characters would
02724 
02725 ** then be converted into an 0x28 character which would not need to be
02726 
02727 ** escaped at all and so the 100 character input string would be converted
02728 
02729 ** into just 100 characters of output.  Actually 101 characters of output - 
02730 
02731 ** we have to record the offset used as the first byte in the sequence so
02732 
02733 ** that the string can be decoded.  Since the offset value is stored as
02734 
02735 ** part of the output string and the output string is not allowed to contain
02736 
02737 ** characters 0x00 or 0x27, the offset cannot be 0x00 or 0x27.
02738 
02739 **
02740 
02741 ** Here, then, are the encoding steps:
02742 
02743 **
02744 
02745 **     (1)   Choose an offset value and make it the first character of
02746 
02747 **           output.
02748 
02749 **
02750 
02751 **     (2)   Copy each input character into the output buffer, one by
02752 
02753 **           one, adding the offset value as you copy.
02754 
02755 **
02756 
02757 **     (3)   If the value of an input character plus offset is 0x00, replace
02758 
02759 **           that one character by the two-character sequence 0x01 0x01.
02760 
02761 **           If the sum is 0x01, replace it with 0x01 0x02.  If the sum
02762 
02763 **           is 0x27, replace it with 0x01 0x03.
02764 
02765 **
02766 
02767 **     (4)   Put a 0x00 terminator at the end of the output.
02768 
02769 **
02770 
02771 ** Decoding is obvious:
02772 
02773 **
02774 
02775 **     (5)   Copy encoded characters except the first into the decode 
02776 
02777 **           buffer.  Set the first encoded character aside for use as
02778 
02779 **           the offset in step 7 below.
02780 
02781 **
02782 
02783 **     (6)   Convert each 0x01 0x01 sequence into a single character 0x00.
02784 
02785 **           Convert 0x01 0x02 into 0x01.  Convert 0x01 0x03 into 0x27.
02786 
02787 **
02788 
02789 **     (7)   Subtract the offset value that was the first character of
02790 
02791 **           the encoded buffer from all characters in the output buffer.
02792 
02793 **
02794 
02795 ** The only tricky part is step (1) - how to compute an offset value to
02796 
02797 ** minimize the size of the output buffer.  This is accomplished by testing
02798 
02799 ** all offset values and picking the one that results in the fewest number
02800 
02801 ** of escapes.  To do that, we first scan the entire input and count the
02802 
02803 ** number of occurances of each character value in the input.  Suppose
02804 
02805 ** the number of 0x00 characters is N(0), the number of occurances of 0x01
02806 
02807 ** is N(1), and so forth up to the number of occurances of 0xff is N(255).
02808 
02809 ** An offset of 0 is not allowed so we don't have to test it.  The number
02810 
02811 ** of escapes required for an offset of 1 is N(1)+N(2)+N(40).  The number
02812 
02813 ** of escapes required for an offset of 2 is N(2)+N(3)+N(41).  And so forth.
02814 
02815 ** In this way we find the offset that gives the minimum number of escapes,
02816 
02817 ** and thus minimizes the length of the output string.
02818 
02819 */
02820 
02821 
02822 
02823 /*
02824 
02825 ** Encode a binary buffer "in" of size n bytes so that it contains
02826 
02827 ** no instances of characters '\'' or '\000'.  The output is 
02828 
02829 ** null-terminated and can be used as a string value in an INSERT
02830 
02831 ** or UPDATE statement.  Use sqlite3_decode_binary() to convert the
02832 
02833 ** string back into its original binary.
02834 
02835 **
02836 
02837 ** The result is written into a preallocated output buffer "out".
02838 
02839 ** "out" must be able to hold at least 2 +(257*n)/254 bytes.
02840 
02841 ** In other words, the output will be expanded by as much as 3
02842 
02843 ** bytes for every 254 bytes of input plus 2 bytes of fixed overhead.
02844 
02845 ** (This is approximately 2 + 1.0118*n or about a 1.2% size increase.)
02846 
02847 **
02848 
02849 ** The return value is the number of characters in the encoded
02850 
02851 ** string, excluding the "\000" terminator.
02852 
02853 */
02854 
02855 int sqlite3_encode_binary(const unsigned char *in, int n, unsigned char *out){
02856 
02857   int i, j, e, m;
02858 
02859   int cnt[256];
02860 
02861   if( n<=0 ){
02862 
02863     out[0] = 'x';
02864 
02865     out[1] = 0;
02866 
02867     return 1;
02868 
02869   }
02870 
02871   memset(cnt, 0, sizeof(cnt));
02872 
02873   for(i=n-1; i>=0; i--){ cnt[in[i]]++; }
02874 
02875   m = n;
02876 
02877   for(i=1; i<256; i++){
02878 
02879     int sum;
02880 
02881     if( i=='\'' ) continue;
02882 
02883     sum = cnt[i] + cnt[(i+1)&0xff] + cnt[(i+'\'')&0xff];
02884 
02885     if( sum<m ){
02886 
02887       m = sum;
02888 
02889       e = i;
02890 
02891       if( m==0 ) break;
02892 
02893     }
02894 
02895   }
02896 
02897   out[0] = e;
02898 
02899   j = 1;
02900 
02901   for(i=0; i<n; i++){
02902 
02903     int c = (in[i] - e)&0xff;
02904 
02905     if( c==0 ){
02906 
02907       out[j++] = 1;
02908 
02909       out[j++] = 1;
02910 
02911     }else if( c==1 ){
02912 
02913       out[j++] = 1;
02914 
02915       out[j++] = 2;
02916 
02917     }else if( c=='\'' ){
02918 
02919       out[j++] = 1;
02920 
02921       out[j++] = 3;
02922 
02923     }else{
02924 
02925       out[j++] = c;
02926 
02927     }
02928 
02929   }
02930 
02931   out[j] = 0;
02932 
02933   return j;
02934 
02935 }
02936 
02937 
02938 
02939 /*
02940 
02941 ** Decode the string "in" into binary data and write it into "out".
02942 
02943 ** This routine reverses the encoding created by sqlite3_encode_binary().
02944 
02945 ** The output will always be a few bytes less than the input.  The number
02946 
02947 ** of bytes of output is returned.  If the input is not a well-formed
02948 
02949 ** encoding, -1 is returned.
02950 
02951 **
02952 
02953 ** The "in" and "out" parameters may point to the same buffer in order
02954 
02955 ** to decode a string in place.
02956 
02957 */
02958 
02959 int sqlite3_decode_binary(const unsigned char *in, unsigned char *out){
02960 
02961   int i, c, e;
02962 
02963   e = *(in++);
02964 
02965   i = 0;
02966 
02967   while( (c = *(in++))!=0 ){
02968 
02969     if( c==1 ){
02970 
02971       c = *(in++);
02972 
02973       if( c==1 ){
02974 
02975         c = 0;
02976 
02977       }else if( c==2 ){
02978 
02979         c = 1;
02980 
02981       }else if( c==3 ){
02982 
02983         c = '\'';
02984 
02985       }else{
02986 
02987         return -1;
02988 
02989       }
02990 
02991     }
02992 
02993     out[i++] = (c + e)&0xff;
02994 
02995   }
02996 
02997   return i;
02998 
02999 }
03000