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
4 changes: 3 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,9 @@ All notable changes to this project will be documented in this file. This projec

## [unreleased] Unreleased

## [1.1.2] 2022-11-22
* Feature - Added `Table::has_foreign_key()` method.

## [1.1.2] 2022-11-2

* Tweak - Set the composer's `config.platform.php` to `7.0`.

Expand Down
34 changes: 26 additions & 8 deletions docs/schemas-field.md
Original file line number Diff line number Diff line change
Expand Up @@ -147,17 +147,35 @@ public function after_update() {
$table_name = static::table_name( true );
$updated = false;

if ( $this->exists() && $this->has_index( 'boom' ) ) {
$udpated = $wpdb->query( "ALTER TABLE `{$table_name}` ADD UNIQUE( `name` )" );
}
// Add a UNIQUE constraint on the name column.
if ( $this->exists() && ! $this->has_index( 'boom' ) ) {
$updated = $wpdb->query( "ALTER TABLE `{$table_name}` ADD UNIQUE( `name` )" );

if ( $updated ) {
$message = "Added UNIQUE constraint to the {$table_name} table on name.";
} else {
$message = "Failed to add a unique constraint on the {$table_name} table.";
}

if ( $updated ) {
$message = "Added UNIQUE constraint to the {$table_name} table on name.";
} else {
$message = "Failed to add a unique constraint on the {$table_name} table.";
$results[ $table_name . '.name' ] = $message;
}

$results[ $table_name . '.name' ] = $message;
// Add a FOREIGN KEY constraint on the reseller_id column.
if ( $this->exists() && ! $this->has_foreign_key( 'reseller_id' ) ) {
$referenced_table = $wpdb->prefix . 'resellers';
$updated = $wpdb->query( "ALTER TABLE `{$table_name}`
ADD FOREIGN KEY ( `reseller_id` )
REFERENCES `$referenced_table` ( `id` )"
);

if ( $updated ) {
$message = "Added FOREIGN KEY constraint to the {$table_name} table on reseller_id.";
} else {
$message = "Failed to add a FOREIGN KEY constraint on the {$table_name} table.";
}

$results[ $table_name . '.reseller_id' ] = $message;
}

return $results;
}
Expand Down
34 changes: 26 additions & 8 deletions docs/schemas-table.md
Original file line number Diff line number Diff line change
Expand Up @@ -162,17 +162,35 @@ public function after_update() {
$table_name = static::table_name( true );
$updated = false;

if ( $this->exists() && $this->has_index( 'boom' ) ) {
$udpated = $wpdb->query( "ALTER TABLE `{$table_name}` ADD UNIQUE( `name` )" );
}
// Add a UNIQUE constraint on the name column.
if ( $this->exists() && ! $this->has_index( 'boom' ) ) {
$updated = $wpdb->query( "ALTER TABLE `{$table_name}` ADD UNIQUE( `name` )" );

if ( $updated ) {
$message = "Added UNIQUE constraint to the {$table_name} table on name.";
} else {
$message = "Failed to add a unique constraint on the {$table_name} table.";
}

if ( $updated ) {
$message = "Added UNIQUE constraint to the {$table_name} table on name.";
} else {
$message = "Failed to add a unique constraint on the {$table_name} table.";
$results[ $table_name . '.name' ] = $message;
}

$results[ $table_name . '.name' ] = $message;
// Add a FOREIGN KEY constraint on the reseller_id column.
if ( $this->exists() && ! $this->has_foreign_key( 'reseller_id' ) ) {
$referenced_table = $wpdb->prefix . 'resellers';
$updated = $wpdb->query( "ALTER TABLE `{$table_name}`
ADD FOREIGN KEY ( `reseller_id` )
REFERENCES `$referenced_table` ( `id` )"
);

if ( $updated ) {
$message = "Added FOREIGN KEY constraint to the {$table_name} table on reseller_id.";
} else {
$message = "Failed to add a FOREIGN KEY constraint on the {$table_name} table.";
}

$results[ $table_name . '.reseller_id' ] = $message;
}

return $results;
}
Expand Down
22 changes: 22 additions & 0 deletions src/Schema/Tables/Contracts/Table.php
Original file line number Diff line number Diff line change
Expand Up @@ -531,4 +531,26 @@ public function update() {

return $results;
}

/**
* Checks if a foreign key exists on a table.
*
* @since TBD
*
* @param string $foreign_key The foreign key to check for.
* @param string|null $table_name The table name to check. Defaults to the current table.
*
* @return bool Whether the foreign key exists on the table.
*/
public function has_foreign_key( string $foreign_key, string $table_name = null ): bool {
$table_name = $table_name ?: static::table_name();

$count = $this->db::table( $this->db::raw( 'information_schema.statistics' ) )
->whereRaw( 'WHERE TABLE_SCHEMA = DATABASE()' )
->where( 'TABLE_NAME', $table_name )
->where( 'INDEX_NAME', $foreign_key )
->count();

return $count >= 1;
}
}
46 changes: 46 additions & 0 deletions tests/_support/Traits/Table_Fixtures.php
Original file line number Diff line number Diff line change
Expand Up @@ -163,4 +163,50 @@ protected function get_definition() {

return $field;
}

public function get_foreign_key_table() {
$table = new class extends Table {
const SCHEMA_VERSION = '1.0.0';

protected static $base_table_name = 'foreignkey';
protected static $group = 'bork';
protected static $schema_slug = 'bork-with-foreignkey';
protected static $uid_column = 'id';

protected function get_definition() {
global $wpdb;
$table_name = self::table_name( true );
$charset_collate = $wpdb->get_charset_collate();

return "
CREATE TABLE `{$table_name}` (
`id` int(11) UNSIGNED NOT NULL,
`name` varchar(25) NOT NULL,
`simple_id` int(11) UNSIGNED NOT NULL
) {$charset_collate};
";
}

protected function after_update( array $results ) {
if ( $this->has_foreign_key( 'simple_id' ) ) {
return $results;
}

global $wpdb;
$table_name = $this->table_name();
$simple_table = $wpdb->prefix . 'simple';
$updated = $wpdb->query( "ALTER TABLE $table_name ADD FOREIGN KEY (simple_id) REFERENCES $simple_table(id)" );

$result = $updated ?
'FOREIGN KEY added to ' . $table_name . ' on column simple_id to table ' . $simple_table . ' on column id' :
'Failed to add FOREIGN KEY NOT to ' . $table_name . ' on column simple_id to table ' . $simple_table . ' on column id';

$results[] = $result;

return $results;
}
};

return $table;
}
}
46 changes: 44 additions & 2 deletions tests/wpunit/Tables/TableTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,21 @@
class TableTest extends SchemaTestCase {
use Table_Fixtures;

/**
* @before
*/
public function drop_tables() {
$this->get_simple_table()->drop();
$this->get_foreign_key_table()->drop();
}

/**
* Should have index.
*
* @test
*/
public function should_have_index() {
$table = $this->get_simple_table();
$table = $this->get_simple_table();

Register::table( $table );

Expand All @@ -28,11 +36,45 @@ public function should_have_index() {
* @test
*/
public function should_have_fake_index() {
$table = $this->get_simple_table();
$table = $this->get_simple_table();

Register::table( $table );

$this->assertFalse( $table->has_index( 'bork' ) );
}

/**
* It should not have foreign key
*
* @test
*/
public function should_not_have_foreign_key() {
$simple_table = $this->get_simple_table();
$foreign_key_table = $this->get_foreign_key_table();

Register::table( $simple_table );
Register::table( $foreign_key_table );

$this->assertFalse( $simple_table->has_foreign_key( 'simple_id' ) );
$this->assertFalse( $foreign_key_table->has_foreign_key( 'not_really' ) );
}

/**
* It should have foreign key
*
* @test
*/
public function should_have_foreign_key() {
$simple_table = $this->get_simple_table();
$foreign_key_table = $this->get_foreign_key_table();

Register::table( $simple_table );
Register::table( $foreign_key_table );

$this->assertFalse( $simple_table->has_foreign_key( 'simple_id' ) );
$this->assertFalse( $foreign_key_table->has_foreign_key( 'not_really' ) );

$this->assertTrue( $foreign_key_table->has_foreign_key( 'simple_id' ) );
}
}