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

📄 sqltransaction.cpp

📁 linux下开源浏览器WebKit的源码,市面上的很多商用浏览器都是移植自WebKit
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/* * Copyright (C) 2007, 2008 Apple Inc. All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions * are met: * * 1.  Redistributions of source code must retain the above copyright *     notice, this list of conditions and the following disclaimer. * 2.  Redistributions in binary form must reproduce the above copyright *     notice, this list of conditions and the following disclaimer in the *     documentation and/or other materials provided with the distribution. * 3.  Neither the name of Apple Computer, Inc. ("Apple") nor the names of *     its contributors may be used to endorse or promote products derived *     from this software without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */#include "config.h"#include "SQLTransaction.h"#include "ChromeClient.h"#include "Database.h"#include "DatabaseAuthorizer.h"#include "DatabaseDetails.h"#include "DatabaseTracker.h"#include "Document.h"#include "ExceptionCode.h"#include "Logging.h"#include "OriginQuotaManager.h"#include "Page.h"#include "PlatformString.h"#include "SecurityOrigin.h"#include "SQLError.h"#include "SQLiteTransaction.h"#include "SQLResultSet.h"#include "SQLStatement.h"#include "SQLStatementCallback.h"#include "SQLStatementErrorCallback.h"#include "SQLValue.h"// There's no way of knowing exactly how much more space will be required when a statement hits the quota limit.  // For now, we'll arbitrarily choose currentQuota + 1mb.// In the future we decide to track if a size increase wasn't enough, and ask for larger-and-larger increases until its enough.static const int DefaultQuotaSizeIncrease = 1048576;namespace WebCore {PassRefPtr<SQLTransaction> SQLTransaction::create(Database* db, PassRefPtr<SQLTransactionCallback> callback, PassRefPtr<SQLTransactionErrorCallback> errorCallback,                                            PassRefPtr<VoidCallback> successCallback, PassRefPtr<SQLTransactionWrapper> wrapper){    return adoptRef(new SQLTransaction(db, callback, errorCallback, successCallback, wrapper));}SQLTransaction::SQLTransaction(Database* db, PassRefPtr<SQLTransactionCallback> callback, PassRefPtr<SQLTransactionErrorCallback> errorCallback, PassRefPtr<VoidCallback> successCallback,                                PassRefPtr<SQLTransactionWrapper> wrapper)    : m_nextStep(&SQLTransaction::openTransactionAndPreflight)    , m_executeSqlAllowed(false)    , m_database(db)    , m_wrapper(wrapper)    , m_callback(callback)    , m_successCallback(successCallback)    , m_errorCallback(errorCallback)    , m_shouldRetryCurrentStatement(false)    , m_shouldCommitAfterErrorCallback(true)    , m_modifiedDatabase(false){    ASSERT(m_database);}SQLTransaction::~SQLTransaction(){}void SQLTransaction::executeSQL(const String& sqlStatement, const Vector<SQLValue>& arguments, PassRefPtr<SQLStatementCallback> callback, PassRefPtr<SQLStatementErrorCallback> callbackError, ExceptionCode& e){    if (!m_executeSqlAllowed || m_database->stopped()) {        e = INVALID_STATE_ERR;        return;    }        RefPtr<SQLStatement> statement = SQLStatement::create(sqlStatement.copy(), arguments, callback, callbackError);    if (m_database->deleted())        statement->setDatabaseDeletedError();    if (!m_database->versionMatchesExpected())        statement->setVersionMismatchedError();            enqueueStatement(statement);}void SQLTransaction::enqueueStatement(PassRefPtr<SQLStatement> statement){    MutexLocker locker(m_statementMutex);    m_statementQueue.append(statement);}#ifndef NDEBUGconst char* SQLTransaction::debugStepName(SQLTransaction::TransactionStepMethod step){    if (step == &SQLTransaction::openTransactionAndPreflight)        return "openTransactionAndPreflight";    else if (step == &SQLTransaction::runStatements)        return "runStatements";    else if (step == &SQLTransaction::postflightAndCommit)        return "postflightAndCommit";    else if (step == &SQLTransaction::cleanupAfterTransactionErrorCallback)        return "cleanupAfterTransactionErrorCallback";    else if (step == &SQLTransaction::deliverTransactionCallback)        return "deliverTransactionCallback";    else if (step == &SQLTransaction::deliverTransactionErrorCallback)        return "deliverTransactionErrorCallback";    else if (step == &SQLTransaction::deliverStatementCallback)        return "deliverStatementCallback";    else if (step == &SQLTransaction::deliverQuotaIncreaseCallback)        return "deliverQuotaIncreaseCallback";    else if (step == &SQLTransaction::deliverSuccessCallback)        return "deliverSuccessCallback";    else if (step == &SQLTransaction::cleanupAfterSuccessCallback)        return "cleanupAfterSuccessCallback";    else        return "UNKNOWN";}#endifvoid SQLTransaction::checkAndHandleClosedDatabase(){    if (!m_database->stopped())        return;            // If the database was stopped, don't do anything and cancel queued work    LOG(StorageAPI, "Database was stopped - cancelling work for this transaction");    MutexLocker locker(m_statementMutex);    m_statementQueue.clear();    m_nextStep = 0;        // The current SQLite transaction should be stopped, as well    if (m_sqliteTransaction) {        m_sqliteTransaction->stop();        m_sqliteTransaction.clear();    }}bool SQLTransaction::performNextStep(){    LOG(StorageAPI, "Step %s\n", debugStepName(m_nextStep));    ASSERT(m_nextStep == &SQLTransaction::openTransactionAndPreflight ||           m_nextStep == &SQLTransaction::runStatements ||           m_nextStep == &SQLTransaction::postflightAndCommit ||           m_nextStep == &SQLTransaction::cleanupAfterSuccessCallback ||           m_nextStep == &SQLTransaction::cleanupAfterTransactionErrorCallback);        checkAndHandleClosedDatabase();        if (m_nextStep)        (this->*m_nextStep)();    // If there is no nextStep after performing the above step, the transaction is complete    return !m_nextStep;}void SQLTransaction::performPendingCallback(){    LOG(StorageAPI, "Callback %s\n", debugStepName(m_nextStep));    ASSERT(m_nextStep == &SQLTransaction::deliverTransactionCallback ||           m_nextStep == &SQLTransaction::deliverTransactionErrorCallback ||           m_nextStep == &SQLTransaction::deliverStatementCallback ||           m_nextStep == &SQLTransaction::deliverQuotaIncreaseCallback ||           m_nextStep == &SQLTransaction::deliverSuccessCallback);    checkAndHandleClosedDatabase();        if (m_nextStep)        (this->*m_nextStep)();}void SQLTransaction::openTransactionAndPreflight(){    ASSERT(!m_database->m_sqliteDatabase.transactionInProgress());    LOG(StorageAPI, "Opening and preflighting transaction %p", this);    // If the database was deleted, jump to the error callback    if (m_database->deleted()) {        m_transactionError = SQLError::create(0, "unable to open a transaction, because the user deleted the database");        handleTransactionError(false);        return;    }    // Set the maximum usage for this transaction    m_database->m_sqliteDatabase.setMaximumSize(m_database->maximumSize());        ASSERT(!m_sqliteTransaction);    m_sqliteTransaction.set(new SQLiteTransaction(m_database->m_sqliteDatabase));        m_database->m_databaseAuthorizer->disable();    m_sqliteTransaction->begin();    m_database->m_databaseAuthorizer->enable();            // Transaction Steps 1+2 - Open a transaction to the database, jumping to the error callback if that fails    if (!m_sqliteTransaction->inProgress()) {        ASSERT(!m_database->m_sqliteDatabase.transactionInProgress());        m_sqliteTransaction.clear();        m_transactionError = SQLError::create(0, "unable to open a transaction to the database");        handleTransactionError(false);        return;    }        // Transaction Steps 3 - Peform preflight steps, jumping to the error callback if they fail    if (m_wrapper && !m_wrapper->performPreflight(this)) {        ASSERT(!m_database->m_sqliteDatabase.transactionInProgress());        m_sqliteTransaction.clear();        m_transactionError = m_wrapper->sqlError();        if (!m_transactionError)            m_transactionError = SQLError::create(0, "unknown error occured setting up transaction");        handleTransactionError(false);        return;    }        // Transaction Step 4 - Invoke the transaction callback with the new SQLTransaction object    m_nextStep = &SQLTransaction::deliverTransactionCallback;    LOG(StorageAPI, "Scheduling deliverTransactionCallback for transaction %p\n", this);    m_database->scheduleTransactionCallback(this);}void SQLTransaction::deliverTransactionCallback(){    bool shouldDeliverErrorCallback = false;    if (m_callback) {        m_executeSqlAllowed = true;        m_callback->handleEvent(this, shouldDeliverErrorCallback);        m_executeSqlAllowed = false;    } else        shouldDeliverErrorCallback = true;    // Transaction Step 5 - If the transaction callback was null or raised an exception, jump to the error callback    if (shouldDeliverErrorCallback) {        m_transactionError = SQLError::create(0, "the SQLTransactionCallback was null or threw an exception");        deliverTransactionErrorCallback();    } else        scheduleToRunStatements();}void SQLTransaction::scheduleToRunStatements(){    m_nextStep = &SQLTransaction::runStatements;    LOG(StorageAPI, "Scheduling runStatements for transaction %p\n", this);    m_database->scheduleTransactionStep(this);}void SQLTransaction::runStatements(){    // If there is a series of statements queued up that are all successful and have no associated    // SQLStatementCallback objects, then we can burn through the queue    do {        if (m_shouldRetryCurrentStatement) {            m_shouldRetryCurrentStatement = false;            // FIXME - Another place that needs fixing up after <rdar://problem/5628468> is addressed.            // See ::openTransactionAndPreflight() for discussion            

⌨️ 快捷键说明

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