Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 16 additions & 8 deletions packages/mysql-on-sqlite/src/sqlite/class-wp-mysql-on-sqlite.php
Original file line number Diff line number Diff line change
Expand Up @@ -2925,14 +2925,22 @@ private function execute_create_table_statement( WP_Parser_Node $node ): void {

// Handle IF NOT EXISTS.
if ( $subnode->has_child_node( 'ifNotExists' ) ) {
$tables_table = $this->information_schema_builder->get_table_name( $table_is_temporary, 'tables' );
$table_exists = $this->execute_sqlite_query(
sprintf(
'SELECT 1 FROM %s WHERE table_schema = ? AND table_name = ?',
$this->quote_sqlite_identifier( $tables_table )
),
array( $this->get_saved_db_name(), $table_name )
)->fetchColumn();
if ( $table_is_temporary ) {
/*
* The temporary information schema tables are created with the
* first temporary table of a session, so they may not exist yet.
*/
$table_exists = $this->information_schema_builder->temporary_table_exists( $table_name );
} else {
$tables_table = $this->information_schema_builder->get_table_name( false, 'tables' );
$table_exists = $this->execute_sqlite_query(
sprintf(
'SELECT 1 FROM %s WHERE table_schema = ? AND table_name = ?',
$this->quote_sqlite_identifier( $tables_table )
),
array( $this->get_saved_db_name(), $table_name )
)->fetchColumn();
}

if ( $table_exists ) {
$this->last_result_statement = $this->create_result_statement_from_data( array(), array() );
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -781,7 +781,16 @@ public function record_drop_table( WP_Parser_Node $node ): void {
$table_refs = $child_node->get_first_child_node( 'tableRefList' )->get_child_nodes();
foreach ( $table_refs as $table_ref ) {
$table_name = $this->get_table_name_from_node( $table_ref );
$table_is_temporary = $has_temporary_keyword || $this->temporary_table_exists( $table_name );
$table_is_temporary = $this->temporary_table_exists( $table_name );

/*
* DROP TEMPORARY TABLE drops only temporary tables. When there is no
* such table, there is nothing to record. The temporary information
* schema tables may not even exist yet.
*/
if ( $has_temporary_keyword && ! $table_is_temporary ) {
continue;
}

$this->delete_values(
$this->get_table_name( $table_is_temporary, 'tables' ),
Expand Down
62 changes: 62 additions & 0 deletions packages/mysql-on-sqlite/tests/WP_MySQL_On_SQLite_Tests.php
Original file line number Diff line number Diff line change
Expand Up @@ -4433,6 +4433,68 @@ public function testCreateTemporaryTableIfNotExists(): void {
);
}

public function testCreateTemporaryTableIfNotExistsAsFirstTemporaryTable(): void {
// No temporary table exists in this session yet.
$this->assertQuery(
'CREATE TEMPORARY TABLE IF NOT EXISTS t (ID INTEGER, name TEXT)'
);
$this->assertQuery( "INSERT INTO t (ID, name) VALUES (1, 'a')" );

// A repeated statement is a no-op and keeps the existing data,
// also when the table name is cased differently.
$this->assertQuery(
'CREATE TEMPORARY TABLE IF NOT EXISTS t (ID INTEGER, name TEXT)'
);
$this->assertQuery(
'CREATE TEMPORARY TABLE IF NOT EXISTS T (ID INTEGER, name TEXT)'
);
$result = $this->assertQuery( 'SELECT ID, name FROM t' );
$this->assertEquals(
array(
(object) array(
'ID' => '1',
'name' => 'a',
),
),
$result
);
}

public function testCreateTemporaryTableIfNotExistsWithStandardTableOfSameName(): void {
$this->assertQuery( 'CREATE TABLE t (a INT)' );

// The standard table doesn't prevent creating the temporary table.
$this->assertQuery( 'CREATE TEMPORARY TABLE IF NOT EXISTS t (b INT)' );
$result = $this->assertQuery( 'SHOW COLUMNS FROM t' );
$this->assertCount( 1, $result );
$this->assertEquals( 'b', $result[0]->Field );

// The standard table is unchanged.
$this->assertQuery( 'DROP TEMPORARY TABLE t' );
$result = $this->assertQuery( 'SHOW COLUMNS FROM t' );
$this->assertCount( 1, $result );
$this->assertEquals( 'a', $result[0]->Field );
}

public function testDropTemporaryTableIfExistsAsFirstTemporaryTable(): void {
// No temporary table exists in this session yet.
$this->assertQuery( 'DROP TEMPORARY TABLE IF EXISTS t' );

// A standard table with the same name is not dropped.
$this->assertQuery( 'CREATE TABLE t (a INT)' );
$this->assertQuery( 'DROP TEMPORARY TABLE IF EXISTS t' );
$result = $this->assertQuery( 'SHOW COLUMNS FROM t' );
$this->assertCount( 1, $result );
$this->assertEquals( 'a', $result[0]->Field );
}

public function testDropTemporaryTableAsFirstTemporaryTable(): void {
// No temporary table exists in this session yet.
$this->expectException( WP_MySQL_On_SQLite_Exception::class );
$this->expectExceptionMessage( "Table 'temp.t' doesn't exist" );
$this->assertQuery( 'DROP TEMPORARY TABLE t' );
}

public function testTranslatesComplexDelete() {
$this->sqlite->query(
"CREATE TABLE wptests_dummy (
Expand Down
Loading