⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sqltransaction.cpp

📁 linux下开源浏览器WebKit的源码,市面上的很多商用浏览器都是移植自WebKit
💻 CPP
📖 第 1 页 / 共 2 页
字号:
            // Reset the maximum size here, as it was increased to allow us to retry this statement            m_database->m_sqliteDatabase.setMaximumSize(m_database->maximumSize());        } else {            // If the current statement has already been run, failed due to quota constraints, and we're not retrying it,            // that means it ended in an error.  Handle it now            if (m_currentStatement && m_currentStatement->lastExecutionFailedDueToQuota()) {                handleCurrentStatementError();                break;            }                        // Otherwise, advance to the next statement            getNextStatement();        }    } while (runCurrentStatement());        // If runCurrentStatement() returned false, that means either there was no current statement to run,    // or the current statement requires a callback to complete.  In the later case, it also scheduled     // the callback or performed any other additional work so we can return    if (!m_currentStatement)        postflightAndCommit();}void SQLTransaction::getNextStatement(){    m_currentStatement = 0;        MutexLocker locker(m_statementMutex);    if (!m_statementQueue.isEmpty()) {        m_currentStatement = m_statementQueue.first();        m_statementQueue.removeFirst();    }}bool SQLTransaction::runCurrentStatement(){    if (!m_currentStatement)        return false;            m_database->m_databaseAuthorizer->reset();        if (m_currentStatement->execute(m_database.get())) {        if (m_database->m_databaseAuthorizer->lastActionChangedDatabase()) {            // Flag this transaction as having changed the database for later delegate notification            m_modifiedDatabase = true;            // Also dirty the size of this database file for calculating quota usage            OriginQuotaManager& manager(DatabaseTracker::tracker().originQuotaManager());            Locker<OriginQuotaManager> locker(manager);                        manager.markDatabase(m_database.get());        }                    if (m_currentStatement->hasStatementCallback()) {            m_nextStep = &SQLTransaction::deliverStatementCallback;            LOG(StorageAPI, "Scheduling deliverStatementCallback for transaction %p\n", this);            m_database->scheduleTransactionCallback(this);            return false;        }        return true;    }        if (m_currentStatement->lastExecutionFailedDueToQuota()) {        m_nextStep = &SQLTransaction::deliverQuotaIncreaseCallback;        LOG(StorageAPI, "Scheduling deliverQuotaIncreaseCallback for transaction %p\n", this);        m_database->scheduleTransactionCallback(this);        return false;    }        handleCurrentStatementError();        return false;}void SQLTransaction::handleCurrentStatementError(){    // Transaction Steps 6.error - Call the statement's error callback, but if there was no error callback,    // jump to the transaction error callback    if (m_currentStatement->hasStatementErrorCallback()) {        m_nextStep = &SQLTransaction::deliverStatementCallback;        LOG(StorageAPI, "Scheduling deliverStatementCallback for transaction %p\n", this);        m_database->scheduleTransactionCallback(this);    } else {        m_transactionError = m_currentStatement->sqlError();        if (!m_transactionError)            m_transactionError = SQLError::create(1, "the statement failed to execute");        handleTransactionError(false);    }}void SQLTransaction::deliverStatementCallback(){    ASSERT(m_currentStatement);        // Transaction Step 6.6 and 6.3(error) - If the statement callback went wrong, jump to the transaction error callback    // Otherwise, continue to loop through the statement queue    m_executeSqlAllowed = true;    bool result = m_currentStatement->performCallback(this);    m_executeSqlAllowed = false;    if (result) {        m_transactionError = SQLError::create(0, "the statement callback raised an exception or statement error callback did not return false");        handleTransactionError(true);    } else        scheduleToRunStatements();}void SQLTransaction::deliverQuotaIncreaseCallback(){    ASSERT(m_currentStatement);    ASSERT(!m_shouldRetryCurrentStatement);        Page* page = m_database->document()->page();    ASSERT(page);        RefPtr<SecurityOrigin> origin = m_database->securityOriginCopy();        unsigned long long currentQuota = DatabaseTracker::tracker().quotaForOrigin(origin.get());    page->chrome()->client()->exceededDatabaseQuota(m_database->document()->frame(), m_database->stringIdentifier());    unsigned long long newQuota = DatabaseTracker::tracker().quotaForOrigin(origin.get());        // If the new quota ended up being larger than the old quota, we will retry the statement.    if (newQuota > currentQuota)        m_shouldRetryCurrentStatement = true;            m_nextStep = &SQLTransaction::runStatements;    LOG(StorageAPI, "Scheduling runStatements for transaction %p\n", this);    m_database->scheduleTransactionStep(this);}void SQLTransaction::postflightAndCommit(){        // Transaction Step 7 - Peform postflight steps, jumping to the error callback if they fail    if (m_wrapper && !m_wrapper->performPostflight(this)) {        m_transactionError = m_wrapper->sqlError();        if (!m_transactionError)            m_transactionError = SQLError::create(0, "unknown error occured setting up transaction");        handleTransactionError(false);        return;    }        // Transacton Step 8+9 - Commit the transaction, jumping to the error callback if that fails    ASSERT(m_sqliteTransaction);        m_database->m_databaseAuthorizer->disable();    m_sqliteTransaction->commit();    m_database->m_databaseAuthorizer->enable();    // If the commit failed, the transaction will still be marked as "in progress"    if (m_sqliteTransaction->inProgress()) {        m_shouldCommitAfterErrorCallback = false;        m_transactionError = SQLError::create(0, "failed to commit the transaction");        handleTransactionError(false);        return;    }        // The commit was successful, notify the delegates if the transaction modified this database    if (m_modifiedDatabase)        DatabaseTracker::tracker().scheduleNotifyDatabaseChanged(m_database->m_securityOrigin.get(), m_database->m_name);        // Now release our unneeded callbacks, to break reference cycles.    m_callback = 0;    m_errorCallback = 0;        // Transaction Step 10 - Deliver success callback, if there is one    if (m_successCallback) {        m_nextStep = &SQLTransaction::deliverSuccessCallback;        LOG(StorageAPI, "Scheduling deliverSuccessCallback for transaction %p\n", this);        m_database->scheduleTransactionCallback(this);    } else         cleanupAfterSuccessCallback();}void SQLTransaction::deliverSuccessCallback(){    // Transaction Step 10 - Deliver success callback    ASSERT(m_successCallback);    m_successCallback->handleEvent();        // Release the last callback to break reference cycle    m_successCallback = 0;    // Schedule a "post-success callback" step to return control to the database thread in case there    // are further transactions queued up for this Database    m_nextStep = &SQLTransaction::cleanupAfterSuccessCallback;    LOG(StorageAPI, "Scheduling cleanupAfterSuccessCallback for transaction %p\n", this);    m_database->scheduleTransactionStep(this);}void SQLTransaction::cleanupAfterSuccessCallback(){    // Transaction Step 11 - End transaction steps    // There is no next step    LOG(StorageAPI, "Transaction %p is complete\n", this);    ASSERT(!m_database->m_sqliteDatabase.transactionInProgress());    m_nextStep = 0;}void SQLTransaction::handleTransactionError(bool inCallback){    if (m_errorCallback) {        if (inCallback)            deliverTransactionErrorCallback();        else {            m_nextStep = &SQLTransaction::deliverTransactionErrorCallback;            LOG(StorageAPI, "Scheduling deliverTransactionErrorCallback for transaction %p\n", this);            m_database->scheduleTransactionCallback(this);        }        return;    }        // Transaction Step 12 - If the callback couldn't be called, then rollback the transaction.    m_shouldCommitAfterErrorCallback = false;    if (inCallback) {        m_nextStep = &SQLTransaction::cleanupAfterTransactionErrorCallback;        LOG(StorageAPI, "Scheduling cleanupAfterTransactionErrorCallback for transaction %p\n", this);        m_database->scheduleTransactionStep(this);    } else {        cleanupAfterTransactionErrorCallback();    }}void SQLTransaction::deliverTransactionErrorCallback(){    ASSERT(m_transactionError);        // Transaction Step 12 - If the callback didn't return false, then rollback the transaction.    // This includes the callback not existing, returning true, or throwing an exception    if (!m_errorCallback || m_errorCallback->handleEvent(m_transactionError.get()))        m_shouldCommitAfterErrorCallback = false;    m_nextStep = &SQLTransaction::cleanupAfterTransactionErrorCallback;    LOG(StorageAPI, "Scheduling cleanupAfterTransactionErrorCallback for transaction %p\n", this);    m_database->scheduleTransactionStep(this);}void SQLTransaction::cleanupAfterTransactionErrorCallback(){    m_database->m_databaseAuthorizer->disable();    if (m_sqliteTransaction) {        // Transaction Step 12 -If the error callback returned false, and the last error wasn't itself a         // failure when committing the transaction, then try to commit the transaction        if (m_shouldCommitAfterErrorCallback)            m_sqliteTransaction->commit();                if (m_sqliteTransaction->inProgress()) {            // Transaction Step 12 - If that fails, or if the callback couldn't be called             // or if it didn't return false, then rollback the transaction.            m_sqliteTransaction->rollback();        } else if (m_modifiedDatabase) {            // But if the commit was successful, notify the delegates if the transaction modified this database            DatabaseTracker::tracker().scheduleNotifyDatabaseChanged(m_database->m_securityOrigin.get(), m_database->m_name);        }                ASSERT(!m_database->m_sqliteDatabase.transactionInProgress());        m_sqliteTransaction.clear();    }    m_database->m_databaseAuthorizer->enable();        // Transaction Step 12 - Any still-pending statements in the transaction are discarded.    {        MutexLocker locker(m_statementMutex);        m_statementQueue.clear();    }        // Transaction is complete!  There is no next step    LOG(StorageAPI, "Transaction %p is complete with an error\n", this);    ASSERT(!m_database->m_sqliteDatabase.transactionInProgress());    m_nextStep = 0;    // Now release our callbacks, to break reference cycles.    m_callback = 0;    m_errorCallback = 0;}} // namespace WebCore

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -