List:Commits« Previous MessageNext Message »
From:pharvey Date:July 14 2006 12:16am
Subject:Connector/ODBC 5 commit: r441 - trunk/MYSQLPlus/MYSQLPlusLib
View as plain text  
Modified:
   trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp
Log:
more work to integrate MCommands

Modified: trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp
===================================================================
--- trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp	2006-07-13 23:17:46 UTC (rev 440)
+++ trunk/MYSQLPlus/MYSQLPlusLib/MStatement.cpp	2006-07-14 00:16:58 UTC (rev 441)
@@ -3007,44 +3007,73 @@
         doStateRollBack( STATE_S1 );
 
     /* get our statement text into a friendly QString */
-    QString stringStatementText;
+    QString stringStatement;
+    if ( nLength1 == SQL_NTS )
+        stringStatement = QString::fromUtf16( psStatementText );
+    else
+        stringStatement = QString::fromUtf16( psStatementText, nLength1 );
 
     /* get our statement text into an MCommand (preprocess it) */
     pCommands = new MCommands( this );
 
-    SQLRETURN nReturn = pCommands->setCommands( stringStatementText );
+    SQLRETURN nReturn = pCommands->setCommands( stringStatement );
     if ( !SQL_SUCCEEDED( nReturn ) )
     {
-        delete pCommands;
-        pCommands = NULL;
+        goto doPrepareExit1;
     }
 
-    MCommand command = pCommands->
+    /*!
+        \internal MYODBC RULE
 
-    /* what flavour of resultset do we want? */
-    switch ( getConnection()->getStatementType() )
+        We must have at least one command.
+    */
+    if ( !pCommands->count() )
     {
-        case MConnection::STATEMENT_DYNAMIC:
-            /*!
-                \internal
-                \todo
+        nReturn = getDiagnostic()->doAppend( MDiagnostic::DIA_HY000, 0, tr("Failed to
find a command to execute.") );
+        goto doPrepareExit1;
+    }
 
-                Make us smart enough to decide based upon the;
+    /* get 1st command - this is the one we will prepare for execute now */
+    MCommand command = pCommands->at( pCommands->getCurrent() );
 
-                - environment attributes
-                - connection attributes
-                - statement attributes 
-                - client feature support
-                - server feature support
-                - SQL statement
-                - resultset characteristics expected (if possible)
-            */
-            getDiagnostic()->doAppend( MDiagnostic::DIA_01000, 0,
tr("STATEMENT_DYNAMIC is same as STATEMENT_RES at this time") );
-        isServerSidePreparePossible()
-            if ( pCommands->at( getCurrent() ).)
-            {
-            }
+    /* what flavour of resultset do we want? */
+    int nStatementType = getConnection()->getStatementType();
 
+    /*!
+        \internal
+        \todo
+
+        Make us smart enough to decide based upon the;
+
+        - environment attributes
+        - connection attributes
+        - statement attributes 
+        - client feature support
+        - server feature support
+        - SQL statement
+        - resultset characteristics expected (if possible)
+
+        Our bias is toward using server-side prepared.
+    */
+    if ( nStatementType == MConnection::STATEMENT_DYNAMIC )
+    {
+        if ( command.isServerSidePreparePossible() )
+            nStatementType = MConnection::STATEMENT_STMT;
+        else
+            nStatementType = MConnection::STATEMENT_RES;
+    }
+
+    /* if app wants server-side prepare but we can not use it then we fall back to
client-side and throw a warning */
+    if ( nStatementType == MConnection::STATEMENT_STMT &&
!command.isServerSidePreparePossible() )
+    {
+        getDiagnostic()->doAppend( MDiagnostic::DIA_01000, 0, tr("STATEMENT_STMT will
not support command - will use STATEMENT_RES instead") );
+        nStatementType = MConnection::STATEMENT_RES;
+    }
+
+    /* create appropriate resultset object */
+    switch ( nStatementType )
+    {
+        case MConnection::STATEMENT_DYNAMIC:
         case MConnection::STATEMENT_RES:     
             pResult = new MResultRes( this );
             break;
@@ -3052,104 +3081,71 @@
         case MConnection::STATEMENT_STMT:
             pResult = new MResultStmt( this );
             break;
+
+        default:
+            nReturn = getDiagnostic()->doAppend( MDiagnostic::DIA_HY000, 0, QString(
tr("Unknown statement type %1") ).arg( nStatementType ) );
+            goto doPrepareExit1;
     }
 
-    /* do it */
-    SQLRETURN nReturn = pResult->doPrepare( psStatementText );
+    /* ask resultset to do any further prepare */
+    nReturn = pResult->doPrepare( psStatementText );
     if ( !SQL_SUCCEEDED( nReturn ) )
     {
-        Q_ASSERT( !pResult );
-        delete pResult;
-        pResult = NULL;
+        goto doPrepareExit2;
     }
 
     /*!
         \internal
-        \todo
+        \note
 
-        Set SQL_DIAG_DYNAMIC_FUNCTION and SQL_DIAG_DYNAMIC_FUNCTION_CODE diagnostic
header fields and possibly use them instead
-        of MResult statement type.
+        We silently start a transaction as needed. We do not rely upon the server doing
this for us but perhaps we should - will see.
     */
-    switch ( pResult->getStatementType() )
-    {
-        case MResult::STATEMENT_TYPE_UPDATE:
-        case MResult::STATEMENT_TYPE_DELETE:
-        case MResult::STATEMENT_TYPE_INSERT:
-            setState( STATE_S2 );
-            break;
-        case MResult::STATEMENT_TYPE_NULL:
-            getDiagnostic()->doAppend( MDiagnostic::DIA_01000, 0,
tr("STATEMENT_TYPE_NULL should not happen here") );
-        case MResult::STATEMENT_TYPE_MULTI:
-        case MResult::STATEMENT_TYPE_SELECT:
-        case MResult::STATEMENT_TYPE_SHOW:
-        case MResult::STATEMENT_TYPE_PLUS:
-        case MResult::STATEMENT_TYPE_OTHER:
-            setState( STATE_S3 );
-            break;
-    }
-
-    /*
-        Handle transaction.
-    */
-    MConnection *pConnection = getConnection();
-    switch ( pConnection->getInfoTxnCapable() )
-    {
-        case SQL_TC_NONE:
-            break;
-        case SQL_TC_DML:
-            /*!
-                \internal ODBC RULE
-
-                Transactions can contain only Data Manipulation Language (DML) statements
(SELECT, INSERT, UPDATE, 
-                DELETE). Data Definition Language (DDL) statements encountered in a
transaction cause an error. 
-            */
-            switch ( pResult->getStatementType() )
-            {
-                case MResult::STATEMENT_TYPE_SELECT:
-                case MResult::STATEMENT_TYPE_UPDATE:
-                case MResult::STATEMENT_TYPE_DELETE:
-                case MResult::STATEMENT_TYPE_INSERT:
-                    if ( pConnection->getInfoTxnCapable() == SQL_TC_DML ||
pConnection->getInfoTxnCapable() == SQL_TC_ALL )
-                    break;
-                case MResult::STATEMENT_TYPE_NULL:
-                case MResult::STATEMENT_TYPE_MULTI:
-                case MResult::STATEMENT_TYPE_SHOW:
-                case MResult::STATEMENT_TYPE_PLUS:
-                case MResult::STATEMENT_TYPE_OTHER:
-            }
-        case SQL_TC_DDL_COMMIT:
-        case SQL_TC_DDL_IGNORE:
-        case SQL_TC_ALL:
-    }
-
-SQLRETURN MConnection::doTransactionStart()
-
     if ( pConnection->isTransaction() == false )
     {
-        /* do we support transactions? */
-        if ( pConnection->getInfoTxnCapable() == SQL_TC_NONE )
+        MConnection *pConnection = getConnection();
+        SQLRETURN nReturnTransactionStart = SQL_SUCCESS;
+        switch ( pConnection->getInfoTxnCapable() )
         {
-            /* should we start a transaction? */
-            switch ( pResult->getStatementType() )
-            {
-                case MResult::STATEMENT_TYPE_SELECT:
-                case MResult::STATEMENT_TYPE_UPDATE:
-                case MResult::STATEMENT_TYPE_DELETE:
-                case MResult::STATEMENT_TYPE_INSERT:
-                    if ( pConnection->getInfoTxnCapable() == SQL_TC_DML ||
pConnection->getInfoTxnCapable() == SQL_TC_ALL )
-                    break;
-                case MResult::STATEMENT_TYPE_NULL:
-                case MResult::STATEMENT_TYPE_MULTI:
-                case MResult::STATEMENT_TYPE_SHOW:
-                case MResult::STATEMENT_TYPE_PLUS:
-                case MResult::STATEMENT_TYPE_OTHER:
-            }
+            case SQL_TC_NONE:
+                break;
+            case SQL_TC_DML:
+                if ( command.isDataManipulationLanguage() )
+                    nReturnTransactionStart = MConnection::doTransactionStart();
+                break;
+            case SQL_TC_DDL_COMMIT:
+            case SQL_TC_DDL_IGNORE:
+                break;
+            case SQL_TC_ALL:
+                nReturnTransactionStart = MConnection::doTransactionStart();
+            default:
+                nReturn = getDiagnostic()->doAppend( MDiagnostic::DIA_HY000, 0,
tr("Unknown value from getInfoTxnCapable()") );
+                goto doPrepareExit2;
         }
     }
 
+    /*!
+        \internal
+        \todo
 
+        Set SQL_DIAG_DYNAMIC_FUNCTION and SQL_DIAG_DYNAMIC_FUNCTION_CODE diagnostic
header fields and possibly use them instead
+        of statement type.
+    */
+    if ( command.isResultSetPossible() )
+        setState( STATE_S3 );
+    else
+        setState( STATE_S2 );
 
     MYODBCDbgReturn( nReturn );
+
+doPrepareExit2:
+        delete pResult;
+        pResult = NULL;
+
+doPrepareExit1:
+        delete pCommands;
+        pCommands = NULL;
+
+    MYODBCDbgReturn( nReturn );
 }
 
 SQLRETURN MStatement::doPrimaryKeys( SQLWCHAR *psCatalog, SQLSMALLINT nLength1, SQLWCHAR
*psSchema, SQLSMALLINT nLength2, SQLWCHAR *psTable, SQLSMALLINT nLength3 )

Thread
Connector/ODBC 5 commit: r441 - trunk/MYSQLPlus/MYSQLPlusLibpharvey14 Jul