Не удается получить данные из вновь созданных столбцов в SQLite - PullRequest
0 голосов
/ 09 сентября 2011

Текущее значение для столбцов countProductSelect и countProductInput - INTEGER NOT NULL;

Необходимо сделать INTEGER DEFAULT NULL;

приведенный ниже PHP-код.

Проблема в том, чтопри попытке обновить данные и countProductSelect countProductInput из столбца времени и countProductSelectTmp countProductInputTmp, получая ошибку - « нет такого столбца: countProductSelectTmp ».

Как бороться с этой ошибкой?Или, может быть, есть более образованные алгоритмы для решения исходной задачи?

/**
 * Updating the database
 * 
 * @return bool
 */
protected function _updateDB()
{
    $version = '3.8.4.0';

    $this->_pdo->exec('
        ALTER TABLE data ADD optionalCountProduct INTEGER DEFAULT NULL;
        ALTER TABLE data ADD countProductSelectTmp INTEGER DEFAULT NULL;
        ALTER TABLE data ADD countProductInputTmp INTEGER DEFAULT NULL;
        UPDATE data SET countProductSelectTmp = countProductSelect, countProductInputTmp = countProductInput;
    ');

    $this->_deleteSQLiteColumn(array('countProductSelect', 'countProductInput'));

    // BUG
    // countProductSelect and countProductInput can not get the value countProductSelectTmp and countProductInputTmp
    $this->_pdo->exec('
        ALTER TABLE data ADD countProductSelect INTEGER DEFAULT NULL;
        ALTER TABLE data ADD countProductInput INTEGER DEFAULT NULL;
        UPDATE data SET countProductSelect = countProductSelectTmp, countProductInput = countProductInputTmp;
        UPDATE version SET id = "' . $version . '";
    ');

    $this->_deleteSQLiteColumn(array('countProductSelectTmp', 'countProductInputTmp'));

    return true;
}


/**
 * Remove column from a SQLite Table
 * 
 * @param array $column name of the column to remove
 * @return bool
 */
protected function _deleteSQLiteColumn(array $column)
{
    return (bool)$this->_pdo->exec('
        BEGIN TRANSACTION;
        CREATE TEMPORARY TABLE backup(' . $this->_getFullColumnsString() . ');
        INSERT INTO backup SELECT ' . $this->_getShortColumnsString() . ' FROM data;
        DROP TABLE data;
        CREATE TABLE data(' . $this->_getFullColumnsString($column) . ');
        INSERT INTO data SELECT ' . $this->_getShortColumnsString($column) . ' FROM backup;
        DROP TABLE backup;
        COMMIT;
    ');
}

1 Ответ

0 голосов
/ 09 сентября 2011

Из тонкой инструкции :

PDO :: exec - выполнить инструкцию SQL и вернуть количество затронутых строк

Но вы пытаетесь выполнить несколько операторов одновременно, так что, возможно, это выполняется только последний оператор. Попытка использовать exec по назначению и выполнение ваших заявлений по одному:

$this->_pdo->exec('ALTER TABLE data ADD optionalCountProduct INTEGER DEFAULT NULL');
$this->_pdo->exec('ALTER TABLE data ADD countProductSelectTmp INTEGER DEFAULT NULL');
$this->_pdo->exec('ALTER TABLE data ADD countProductInputTmp INTEGER DEFAULT NULL');
$this->_pdo->exec('UPDATE data SET countProductSelectTmp = countProductSelect, countProductInputTmp = countProductInput');

А затем снова с вашим следующим многократным утверждением exec и вашим _deleteSQLiteColumn.

Что касается лучшего способа, то, похоже, все, что вам нужно сделать, это удалить ограничение NOT NULL, но ALTER TABLE * SQLite * немного ограничено, поэтому ваш "добавить столбец, скопировать столбец, удалить" подход «копирование столбца через таблицу» - лучшее, что вы можете сделать; из FAQ по SQLite :

Например, предположим, что у вас есть таблица с именем "t1" с именами столбцов "a", "b" и "c" и которую вы хотите удалить из этой таблицы столбец "c". Следующие шаги иллюстрируют, как это можно сделать:

BEGIN TRANSACTION;
CREATE TEMPORARY TABLE t1_backup(a,b);
INSERT INTO t1_backup SELECT a,b FROM t1;
DROP TABLE t1;
CREATE TABLE t1(a,b);
INSERT INTO t1 SELECT a,b FROM t1_backup;
DROP TABLE t1_backup;
COMMIT;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...