diff options
author | David Rothstein <drothstein@gmail.com> | 2013-12-25 14:57:44 -0500 |
---|---|---|
committer | David Rothstein <drothstein@gmail.com> | 2013-12-25 14:57:44 -0500 |
commit | cbabb1a24bf40e74363efbf0401ba8d37b8c9799 (patch) | |
tree | 6bee867bdb60e2ceacf02ca670026f7dd2bcdd83 | |
parent | 6c89f3924e7e375e634b52f539520b9125789431 (diff) | |
download | brdo-cbabb1a24bf40e74363efbf0401ba8d37b8c9799.tar.gz brdo-cbabb1a24bf40e74363efbf0401ba8d37b8c9799.tar.bz2 |
Issue #2056363 by yched, Sweetchuck, chx: INSERT INTO table SELECT * FROM ... not supported.
-rw-r--r-- | CHANGELOG.txt | 2 | ||||
-rw-r--r-- | includes/database/mysql/query.inc | 3 | ||||
-rw-r--r-- | includes/database/pgsql/query.inc | 3 | ||||
-rw-r--r-- | includes/database/query.inc | 9 | ||||
-rw-r--r-- | includes/database/sqlite/query.inc | 3 | ||||
-rw-r--r-- | modules/simpletest/tests/database_test.install | 3 | ||||
-rw-r--r-- | modules/simpletest/tests/database_test.test | 26 |
7 files changed, 40 insertions, 9 deletions
diff --git a/CHANGELOG.txt b/CHANGELOG.txt index e7817422b..0397e258a 100644 --- a/CHANGELOG.txt +++ b/CHANGELOG.txt @@ -1,6 +1,8 @@ Drupal 7.25, xxxx-xx-xx (development version) ----------------------- +- Changed the database API to allow inserts based on a SELECT * query to work + correctly. - Changed the database schema of the {file_managed} table to allow Drupal to manage files larger than 4 GB. - Changed the File module's hook_field_load() implementation to prevent file diff --git a/includes/database/mysql/query.inc b/includes/database/mysql/query.inc index fa698d90c..d3d2d9eec 100644 --- a/includes/database/mysql/query.inc +++ b/includes/database/mysql/query.inc @@ -51,7 +51,8 @@ class InsertQuery_mysql extends InsertQuery { // If we're selecting from a SelectQuery, finish building the query and // pass it back, as any remaining options are irrelevant. if (!empty($this->fromQuery)) { - return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') ' . $this->fromQuery; + $insert_fields_string = $insert_fields ? ' (' . implode(', ', $insert_fields) . ') ' : ' '; + return $comments . 'INSERT INTO {' . $this->table . '}' . $insert_fields_string . $this->fromQuery; } $query = $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') VALUES '; diff --git a/includes/database/pgsql/query.inc b/includes/database/pgsql/query.inc index f3783a9ca..9902b1643 100644 --- a/includes/database/pgsql/query.inc +++ b/includes/database/pgsql/query.inc @@ -112,7 +112,8 @@ class InsertQuery_pgsql extends InsertQuery { // If we're selecting from a SelectQuery, finish building the query and // pass it back, as any remaining options are irrelevant. if (!empty($this->fromQuery)) { - return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') ' . $this->fromQuery; + $insert_fields_string = $insert_fields ? ' (' . implode(', ', $insert_fields) . ') ' : ' '; + return $comments . 'INSERT INTO {' . $this->table . '}' . $insert_fields_string . $this->fromQuery; } $query = $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $insert_fields) . ') VALUES '; diff --git a/includes/database/query.inc b/includes/database/query.inc index 66495273e..ce242beb7 100644 --- a/includes/database/query.inc +++ b/includes/database/query.inc @@ -710,10 +710,11 @@ class InsertQuery extends Query { // first call to fields() does have an effect. $this->fields(array_merge(array_keys($this->fromQuery->getFields()), array_keys($this->fromQuery->getExpressions()))); } - - // Don't execute query without fields. - if (count($this->insertFields) + count($this->defaultFields) == 0) { - throw new NoFieldsException('There are no fields available to insert with.'); + else { + // Don't execute query without fields. + if (count($this->insertFields) + count($this->defaultFields) == 0) { + throw new NoFieldsException('There are no fields available to insert with.'); + } } // If no values have been added, silently ignore this query. This can happen diff --git a/includes/database/sqlite/query.inc b/includes/database/sqlite/query.inc index 1bf609db1..1c6289bd7 100644 --- a/includes/database/sqlite/query.inc +++ b/includes/database/sqlite/query.inc @@ -41,7 +41,8 @@ class InsertQuery_sqlite extends InsertQuery { // If we're selecting from a SelectQuery, finish building the query and // pass it back, as any remaining options are irrelevant. if (!empty($this->fromQuery)) { - return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $this->insertFields) . ') ' . $this->fromQuery; + $insert_fields_string = $this->insertFields ? ' (' . implode(', ', $this->insertFields) . ') ' : ' '; + return $comments . 'INSERT INTO {' . $this->table . '}' . $insert_fields_string . $this->fromQuery; } return $comments . 'INSERT INTO {' . $this->table . '} (' . implode(', ', $this->insertFields) . ') VALUES (' . implode(', ', $placeholders) . ')'; diff --git a/modules/simpletest/tests/database_test.install b/modules/simpletest/tests/database_test.install index 867d81323..11361151f 100644 --- a/modules/simpletest/tests/database_test.install +++ b/modules/simpletest/tests/database_test.install @@ -87,6 +87,9 @@ function database_test_schema() { ), ); + $schema['test_people_copy'] = $schema['test_people']; + $schema['test_people_copy']['description'] = 'A duplicate version of the test_people table, used for additional tests.'; + $schema['test_one_blob'] = array( 'description' => 'A simple table including a BLOB field for testing BLOB behavior.', 'fields' => array( diff --git a/modules/simpletest/tests/database_test.test b/modules/simpletest/tests/database_test.test index b58578e99..aa390bd43 100644 --- a/modules/simpletest/tests/database_test.test +++ b/modules/simpletest/tests/database_test.test @@ -23,6 +23,7 @@ class DatabaseTestCase extends DrupalWebTestCase { $schema['test'] = drupal_get_schema('test'); $schema['test_people'] = drupal_get_schema('test_people'); + $schema['test_people_copy'] = drupal_get_schema('test_people_copy'); $schema['test_one_blob'] = drupal_get_schema('test_one_blob'); $schema['test_two_blobs'] = drupal_get_schema('test_two_blobs'); $schema['test_task'] = drupal_get_schema('test_task'); @@ -603,9 +604,9 @@ class DatabaseInsertTestCase extends DatabaseTestCase { } /** - * Test that the INSERT INTO ... SELECT ... syntax works. + * Test that the INSERT INTO ... SELECT (fields) ... syntax works. */ - function testInsertSelect() { + function testInsertSelectFields() { $query = db_select('test_people', 'tp'); // The query builder will always append expressions after fields. // Add the expression first to test that the insert fields are correctly @@ -627,6 +628,27 @@ class DatabaseInsertTestCase extends DatabaseTestCase { $saved_age = db_query('SELECT age FROM {test} WHERE name = :name', array(':name' => 'Meredith'))->fetchField(); $this->assertIdentical($saved_age, '30', 'Can retrieve after inserting.'); } + + /** + * Tests that the INSERT INTO ... SELECT * ... syntax works. + */ + function testInsertSelectAll() { + $query = db_select('test_people', 'tp') + ->fields('tp') + ->condition('tp.name', 'Meredith'); + + // The resulting query should be equivalent to: + // INSERT INTO test_people_copy + // SELECT * + // FROM test_people tp + // WHERE tp.name = 'Meredith' + db_insert('test_people_copy') + ->from($query) + ->execute(); + + $saved_age = db_query('SELECT age FROM {test_people_copy} WHERE name = :name', array(':name' => 'Meredith'))->fetchField(); + $this->assertIdentical($saved_age, '30', 'Can retrieve after inserting.'); + } } /** |