From d534d7dab55b5aacef92eda792083edeeacc24de Mon Sep 17 00:00:00 2001 From: Khokan Sardar Date: Wed, 2 Sep 2026 13:02:19 +0530 Subject: [PATCH] Tests: Add unit tests for the Bookmark Administration API. Adds coverage for the functions in `src/wp-admin/includes/bookmark.php`, none of which were previously exercised directly: `add_link()`, `edit_link()`, `get_default_link_to_edit()`, `wp_delete_link()`, `wp_get_link_cats()`, `get_link_to_edit()`, `wp_insert_link()`, `wp_set_link_cats()`, `wp_update_link()`, and `wp_link_manager_disabled_message()`. Fixes #66019. --- .../admin/includes/bookmark/AddLink_Test.php | 31 +++ .../admin/includes/bookmark/EditLink_Test.php | 156 ++++++++++++++ .../bookmark/GetDefaultLinkToEdit_Test.php | 34 +++ .../includes/bookmark/GetLinkToEdit_Test.php | 28 +++ .../includes/bookmark/WpDeleteLink_Test.php | 83 ++++++++ .../includes/bookmark/WpGetLinkCats_Test.php | 32 +++ .../includes/bookmark/WpInsertLink_Test.php | 193 ++++++++++++++++++ .../WpLinkManagerDisabledMessage_Test.php | 124 +++++++++++ .../includes/bookmark/WpSetLinkCats_Test.php | 65 ++++++ .../includes/bookmark/WpUpdateLink_Test.php | 85 ++++++++ 10 files changed, 831 insertions(+) create mode 100644 tests/phpunit/tests/admin/includes/bookmark/AddLink_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/EditLink_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/GetDefaultLinkToEdit_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/GetLinkToEdit_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/WpDeleteLink_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/WpGetLinkCats_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/WpInsertLink_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/WpLinkManagerDisabledMessage_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/WpSetLinkCats_Test.php create mode 100644 tests/phpunit/tests/admin/includes/bookmark/WpUpdateLink_Test.php diff --git a/tests/phpunit/tests/admin/includes/bookmark/AddLink_Test.php b/tests/phpunit/tests/admin/includes/bookmark/AddLink_Test.php new file mode 100644 index 0000000000000..305232f08b1e3 --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/AddLink_Test.php @@ -0,0 +1,31 @@ +user->create( array( 'role' => 'administrator' ) ) ); + + add_filter( 'pre_option_link_manager_enabled', '__return_true' ); + + $_POST = array( + 'link_url' => 'https://example.com/', + 'link_name' => 'Example', + 'link_image' => '', + 'link_rss' => '', + ); + + $link_id = add_link(); + + $this->assertIsInt( $link_id, 'The link ID should be an integer.' ); + $this->assertSame( 'Example', get_bookmark( $link_id )->link_name, 'The link name was not stored.' ); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/EditLink_Test.php b/tests/phpunit/tests/admin/includes/bookmark/EditLink_Test.php new file mode 100644 index 0000000000000..ff58885c75e7e --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/EditLink_Test.php @@ -0,0 +1,156 @@ +user->create( array( 'role' => 'administrator' ) ); + self::$subscriber_id = $factory->user->create( array( 'role' => 'subscriber' ) ); + } + + public function set_up() { + parent::set_up(); + + // The 'manage_links' capability is only granted while the Link Manager is enabled. + add_filter( 'pre_option_link_manager_enabled', '__return_true' ); + } + + /** + * @ticket 66019 + */ + public function test_should_die_for_users_who_cannot_manage_links() { + wp_set_current_user( self::$subscriber_id ); + $this->set_up_post_data(); + + $this->expectException( 'WPDieException' ); + $this->expectExceptionCode( 403 ); + + edit_link(); + } + + /** + * @ticket 66019 + */ + public function test_should_insert_a_link_from_the_post_data() { + wp_set_current_user( self::$admin_id ); + $this->set_up_post_data(); + + $link_id = edit_link(); + + $this->assertIsInt( $link_id, 'The link ID should be an integer.' ); + $this->assertSame( 'Example', get_bookmark( $link_id )->link_name, 'The link name was not stored.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_update_the_link_when_a_link_id_is_passed() { + wp_set_current_user( self::$admin_id ); + $link_id = self::factory()->bookmark->create( array( 'link_name' => 'Original' ) ); + $this->set_up_post_data( array( 'link_name' => 'Updated' ) ); + + $result = edit_link( $link_id ); + + $this->assertSame( $link_id, $result, 'The existing link ID should be returned.' ); + $this->assertSame( 'Updated', get_bookmark( $link_id )->link_name, 'The link was not updated.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_escape_the_posted_link_name() { + wp_set_current_user( self::$admin_id ); + $this->set_up_post_data( array( 'link_name' => 'Bold' ) ); + + $link_id = edit_link(); + + $this->assertSame( '<b>Bold</b>', get_bookmark( $link_id )->link_name ); + } + + /** + * @ticket 66019 + */ + public function test_should_escape_the_posted_link_url() { + wp_set_current_user( self::$admin_id ); + $this->set_up_post_data( array( 'link_url' => 'https://example.com/?a=1&b=2' ) ); + + $link_id = edit_link(); + + $this->assertSame( 'https://example.com/?a=1&b=2', get_bookmark( $link_id )->link_url ); + } + + /** + * @ticket 66019 + * + * @dataProvider data_link_visible + * + * @param array $post_data Values to add to the posted link data. + * @param string $expected The expected stored visibility. + */ + public function test_should_normalize_the_posted_visibility( $post_data, $expected ) { + wp_set_current_user( self::$admin_id ); + $this->set_up_post_data( $post_data ); + + $link_id = edit_link(); + + $this->assertSame( $expected, get_bookmark( $link_id )->link_visible ); + } + + /** + * Data provider. + * + * @return array, expected: string}> + */ + public function data_link_visible() { + return array( + 'no value' => array( + 'post_data' => array(), + 'expected' => 'Y', + ), + 'an uppercase N' => array( + 'post_data' => array( 'link_visible' => 'N' ), + 'expected' => 'N', + ), + 'a lowercase n' => array( + 'post_data' => array( 'link_visible' => 'n' ), + 'expected' => 'Y', + ), + ); + } + + /** + * Populates $_POST with the fields edit_link() reads unconditionally. + * + * @param array $post_data Optional. Values to add to the posted link data. + */ + private function set_up_post_data( $post_data = array() ) { + $_POST = array_merge( + array( + 'link_url' => 'https://example.com/', + 'link_name' => 'Example', + 'link_image' => '', + 'link_rss' => '', + ), + $post_data + ); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/GetDefaultLinkToEdit_Test.php b/tests/phpunit/tests/admin/includes/bookmark/GetDefaultLinkToEdit_Test.php new file mode 100644 index 0000000000000..c37aa48987190 --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/GetDefaultLinkToEdit_Test.php @@ -0,0 +1,34 @@ +assertSame( '', $link->link_url, 'The link URL should be empty.' ); + $this->assertSame( '', $link->link_name, 'The link name should be empty.' ); + $this->assertSame( 'Y', $link->link_visible, 'The link should be visible.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_use_the_url_and_name_from_the_request() { + $_GET['linkurl'] = 'https://example.com/?a=1&b=2'; + $_GET['name'] = 'O\\\'Brien & Sons'; + + $link = get_default_link_to_edit(); + + $this->assertSame( 'https://example.com/?a=1&b=2', $link->link_url, 'The link URL was not escaped.' ); + $this->assertSame( 'O'Brien & Sons', $link->link_name, 'The link name was not unslashed and escaped.' ); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/GetLinkToEdit_Test.php b/tests/phpunit/tests/admin/includes/bookmark/GetLinkToEdit_Test.php new file mode 100644 index 0000000000000..8dbf18f2f482d --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/GetLinkToEdit_Test.php @@ -0,0 +1,28 @@ +bookmark->create( array( 'link_name' => 'Tom & "Jerry"' ) ); + + $this->assertSame( 'Tom & "Jerry"', get_link_to_edit( $link_id )->link_name ); + } + + /** + * @ticket 66019 + */ + public function test_should_accept_a_link_object() { + $link_id = self::factory()->bookmark->create( array( 'link_name' => 'Tom & "Jerry"' ) ); + + $this->assertSame( 'Tom & "Jerry"', get_link_to_edit( get_bookmark( $link_id ) )->link_name ); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/WpDeleteLink_Test.php b/tests/phpunit/tests/admin/includes/bookmark/WpDeleteLink_Test.php new file mode 100644 index 0000000000000..a84df71bf8ac9 --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/WpDeleteLink_Test.php @@ -0,0 +1,83 @@ +bookmark->create(); + + $this->assertTrue( wp_delete_link( $link_id ), 'wp_delete_link() should return true.' ); + $this->assertNull( get_bookmark( $link_id ), 'The link was not deleted.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_remove_the_link_category_relationships() { + $term_id = self::factory()->term->create( array( 'taxonomy' => 'link_category' ) ); + $link_id = self::factory()->bookmark->create( array( 'link_category' => array( $term_id ) ) ); + + wp_delete_link( $link_id ); + + $this->assertSame( array(), wp_get_object_terms( $link_id, 'link_category', array( 'fields' => 'ids' ) ) ); + } + + /** + * @ticket 66019 + */ + public function test_should_clear_the_bookmark_cache() { + $link_id = self::factory()->bookmark->create(); + + // Prime the cache. + get_bookmark( $link_id ); + + wp_delete_link( $link_id ); + + $this->assertFalse( wp_cache_get( $link_id, 'bookmark' ) ); + } + + /** + * @ticket 66019 + */ + public function test_should_fire_the_delete_actions_around_the_deletion() { + global $wpdb; + + $link_id = self::factory()->bookmark->create(); + + $link_exists = static function () use ( $wpdb, $link_id ) { + return (bool) $wpdb->get_var( $wpdb->prepare( "SELECT link_id FROM $wpdb->links WHERE link_id = %d", $link_id ) ); + }; + + $fired = array(); + add_action( + 'delete_link', + static function ( $id ) use ( &$fired, $link_exists ) { + $fired[] = array( 'delete_link', $id, $link_exists() ); + } + ); + add_action( + 'deleted_link', + static function ( $id ) use ( &$fired, $link_exists ) { + $fired[] = array( 'deleted_link', $id, $link_exists() ); + } + ); + + wp_delete_link( $link_id ); + + $this->assertSame( + array( + array( 'delete_link', $link_id, true ), + array( 'deleted_link', $link_id, false ), + ), + $fired + ); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/WpGetLinkCats_Test.php b/tests/phpunit/tests/admin/includes/bookmark/WpGetLinkCats_Test.php new file mode 100644 index 0000000000000..f7dcdf852143d --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/WpGetLinkCats_Test.php @@ -0,0 +1,32 @@ +term->create( + array( + 'taxonomy' => 'link_category', + 'name' => 'Alpha', + ) + ); + $beta = self::factory()->term->create( + array( + 'taxonomy' => 'link_category', + 'name' => 'Beta', + ) + ); + + $link_id = self::factory()->bookmark->create( array( 'link_category' => array( $alpha, $beta ) ) ); + + $this->assertSame( array( $alpha, $beta ), wp_get_link_cats( $link_id ) ); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/WpInsertLink_Test.php b/tests/phpunit/tests/admin/includes/bookmark/WpInsertLink_Test.php new file mode 100644 index 0000000000000..4cab410a13c3d --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/WpInsertLink_Test.php @@ -0,0 +1,193 @@ + 'https://example.com/', + 'link_name' => 'Example', + ) + ); + + $this->assertIsInt( $link_id, 'The link ID should be an integer.' ); + + $link = get_bookmark( $link_id ); + + $this->assertSame( 'https://example.com/', $link->link_url, 'The link URL was not stored.' ); + $this->assertSame( 'Example', $link->link_name, 'The link name was not stored.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_return_zero_when_the_url_is_empty() { + $this->assertSame( 0, wp_insert_link( array( 'link_name' => 'Example' ) ) ); + } + + /** + * @ticket 66019 + */ + public function test_should_use_the_url_as_the_name_when_the_name_is_empty() { + $link_id = wp_insert_link( array( 'link_url' => 'https://example.com/' ) ); + + $this->assertSame( 'https://example.com/', get_bookmark( $link_id )->link_name ); + } + + /** + * @ticket 66019 + */ + public function test_should_default_link_visible_to_yes() { + $link_id = wp_insert_link( + array( + 'link_url' => 'https://example.com/', + 'link_name' => 'Example', + ) + ); + + $this->assertSame( 'Y', get_bookmark( $link_id )->link_visible ); + } + + /** + * @ticket 66019 + */ + public function test_should_default_the_owner_to_the_current_user() { + $user_id = self::factory()->user->create(); + wp_set_current_user( $user_id ); + + $link_id = wp_insert_link( + array( + 'link_url' => 'https://example.com/', + 'link_name' => 'Example', + ) + ); + + $this->assertSame( $user_id, (int) get_bookmark( $link_id )->link_owner ); + } + + /** + * @ticket 66019 + */ + public function test_should_update_the_existing_link_when_a_link_id_is_provided() { + $link_id = self::factory()->bookmark->create( array( 'link_name' => 'Original' ) ); + + $result = wp_insert_link( + array( + 'link_id' => $link_id, + 'link_url' => 'https://example.com/', + 'link_name' => 'Updated', + ) + ); + + $this->assertSame( $link_id, $result, 'The existing link ID should be returned.' ); + $this->assertSame( 'Updated', get_bookmark( $link_id )->link_name, 'The link was not updated.' ); + $this->assertCount( 1, get_bookmarks( array( 'hide_invisible' => false ) ), 'A second link was inserted.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_return_zero_when_the_database_insert_fails() { + $this->assertSame( 0, $this->insert_link_with_a_failing_query( false ) ); + } + + /** + * @ticket 66019 + */ + public function test_should_return_an_error_when_the_database_insert_fails_and_wp_error_is_true() { + $result = $this->insert_link_with_a_failing_query( true ); + + $this->assertWPError( $result ); + $this->assertSame( 'db_insert_error', $result->get_error_code() ); + } + + /** + * @ticket 66019 + */ + public function test_should_fire_the_add_link_action_when_inserting() { + $fired = array(); + add_action( + 'add_link', + static function ( $link_id ) use ( &$fired ) { + $fired[] = $link_id; + } + ); + + $link_id = wp_insert_link( + array( + 'link_url' => 'https://example.com/', + 'link_name' => 'Example', + ) + ); + + $this->assertSame( array( $link_id ), $fired ); + } + + /** + * @ticket 66019 + */ + public function test_should_fire_the_edit_link_action_when_updating() { + $link_id = self::factory()->bookmark->create(); + + $fired = array(); + add_action( + 'edit_link', + static function ( $link_id ) use ( &$fired ) { + $fired[] = $link_id; + } + ); + + wp_insert_link( + array( + 'link_id' => $link_id, + 'link_url' => 'https://example.com/', + 'link_name' => 'Example', + ) + ); + + $this->assertSame( array( $link_id ), $fired ); + } + + /** + * Calls wp_insert_link() with the link insert query rewritten to fail. + * + * @param bool $wp_error Whether to request a WP_Error object on failure. + * @return int|WP_Error The value returned by wp_insert_link(). + */ + private function insert_link_with_a_failing_query( $wp_error ) { + global $wpdb; + + $rewrite_query = static function ( $query ) use ( $wpdb ) { + if ( str_starts_with( $query, "INSERT INTO `$wpdb->links`" ) ) { + return "INSERT INTO `{$wpdb->prefix}links_no_such_table` (`link_id`) VALUES (1)"; + } + + return $query; + }; + + $wpdb->suppress_errors( true ); + add_filter( 'query', $rewrite_query ); + + $result = wp_insert_link( + array( + 'link_url' => 'https://example.com/', + 'link_name' => 'Example', + ), + $wp_error + ); + + remove_filter( 'query', $rewrite_query ); + $wpdb->suppress_errors( false ); + + return $result; + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/WpLinkManagerDisabledMessage_Test.php b/tests/phpunit/tests/admin/includes/bookmark/WpLinkManagerDisabledMessage_Test.php new file mode 100644 index 0000000000000..ad5c27d30dc6b --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/WpLinkManagerDisabledMessage_Test.php @@ -0,0 +1,124 @@ +user->create( array( 'role' => 'administrator' ) ); + self::$subscriber_id = $factory->user->create( array( 'role' => 'subscriber' ) ); + } + + public function set_up() { + parent::set_up(); + + $this->original_pagenow = $GLOBALS['pagenow']; + } + + public function tear_down() { + $GLOBALS['pagenow'] = $this->original_pagenow; + + parent::tear_down(); + } + + /** + * @ticket 66019 + */ + public function test_should_do_nothing_outside_the_link_manager_screens() { + $GLOBALS['pagenow'] = 'index.php'; + wp_set_current_user( self::$subscriber_id ); + + $this->assertNull( wp_link_manager_disabled_message() ); + } + + /** + * @ticket 66019 + * + * @dataProvider data_link_manager_screens + * + * @param string $pagenow The screen to test. + */ + public function test_should_die_for_users_who_cannot_manage_links( $pagenow ) { + $GLOBALS['pagenow'] = $pagenow; + wp_set_current_user( self::$subscriber_id ); + + $this->expectException( 'WPDieException' ); + $this->expectExceptionMessage( 'Sorry, you are not allowed to edit the links for this site.' ); + + wp_link_manager_disabled_message(); + } + + /** + * Data provider. + * + * @return array + */ + public function data_link_manager_screens() { + return array( + 'the link manager' => array( 'pagenow' => 'link-manager.php' ), + 'adding a link' => array( 'pagenow' => 'link-add.php' ), + 'editing a link' => array( 'pagenow' => 'link.php' ), + ); + } + + /** + * @ticket 66019 + * + * @group ms-excluded + */ + public function test_should_offer_to_install_the_plugin_when_it_is_not_installed() { + $GLOBALS['pagenow'] = 'link-manager.php'; + wp_set_current_user( self::$admin_id ); + wp_cache_set( 'plugins', array( '' => array() ), 'plugins' ); + + $this->expectException( 'WPDieException' ); + $this->expectExceptionMessage( 'action=install-plugin' ); + + wp_link_manager_disabled_message(); + } + + /** + * @ticket 66019 + * + * @group ms-excluded + */ + public function test_should_offer_to_activate_the_plugin_when_it_is_inactive() { + $GLOBALS['pagenow'] = 'link-manager.php'; + wp_set_current_user( self::$admin_id ); + wp_cache_set( + 'plugins', + array( '' => array( 'link-manager/link-manager.php' => array( 'Name' => 'Link Manager' ) ) ), + 'plugins' + ); + + $this->expectException( 'WPDieException' ); + $this->expectExceptionMessage( 'action=activate' ); + + wp_link_manager_disabled_message(); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/WpSetLinkCats_Test.php b/tests/phpunit/tests/admin/includes/bookmark/WpSetLinkCats_Test.php new file mode 100644 index 0000000000000..31b35153005f4 --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/WpSetLinkCats_Test.php @@ -0,0 +1,65 @@ +term->create_many( 2, array( 'taxonomy' => 'link_category' ) ); + $link_id = self::factory()->bookmark->create( array( 'link_category' => array( $term_ids[0] ) ) ); + + wp_set_link_cats( $link_id, array( $term_ids[1] ) ); + + $this->assertSame( array( $term_ids[1] ), wp_get_link_cats( $link_id ) ); + } + + /** + * @ticket 66019 + */ + public function test_should_cast_category_ids_to_integers() { + $term_id = self::factory()->term->create( array( 'taxonomy' => 'link_category' ) ); + $link_id = self::factory()->bookmark->create(); + + wp_set_link_cats( $link_id, array( (string) $term_id ) ); + + $this->assertSame( array( $term_id ), wp_get_link_cats( $link_id ) ); + } + + /** + * @ticket 66019 + * + * @dataProvider data_categories_that_fall_back_to_the_default + * + * @param mixed $link_categories Value passed as the list of link categories. + */ + public function test_should_use_the_default_category( $link_categories ) { + $assigned_id = self::factory()->term->create( array( 'taxonomy' => 'link_category' ) ); + $link_id = self::factory()->bookmark->create( array( 'link_category' => array( $assigned_id ) ) ); + + $default_id = self::factory()->term->create( array( 'taxonomy' => 'link_category' ) ); + update_option( 'default_link_category', $default_id ); + + wp_set_link_cats( $link_id, $link_categories ); + + $this->assertSame( array( $default_id ), wp_get_link_cats( $link_id ) ); + } + + /** + * Data provider. + * + * @return array + */ + public function data_categories_that_fall_back_to_the_default() { + return array( + 'an empty array' => array( 'link_categories' => array() ), + 'a string' => array( 'link_categories' => 'not-an-array' ), + ); + } +} diff --git a/tests/phpunit/tests/admin/includes/bookmark/WpUpdateLink_Test.php b/tests/phpunit/tests/admin/includes/bookmark/WpUpdateLink_Test.php new file mode 100644 index 0000000000000..8ac5106bc77af --- /dev/null +++ b/tests/phpunit/tests/admin/includes/bookmark/WpUpdateLink_Test.php @@ -0,0 +1,85 @@ +bookmark->create( array( 'link_name' => 'Original' ) ); + + $result = wp_update_link( + array( + 'link_id' => $link_id, + 'link_name' => 'Updated', + ) + ); + + $this->assertSame( $link_id, $result, 'The link ID should be returned.' ); + $this->assertSame( 'Updated', get_bookmark( $link_id )->link_name, 'The link name was not updated.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_keep_the_fields_that_are_not_passed() { + $link_id = self::factory()->bookmark->create( + array( + 'link_url' => 'https://example.com/', + 'link_description' => 'A description.', + ) + ); + + wp_update_link( + array( + 'link_id' => $link_id, + 'link_name' => 'Updated', + ) + ); + + $link = get_bookmark( $link_id ); + + $this->assertSame( 'https://example.com/', $link->link_url, 'The link URL was not kept.' ); + $this->assertSame( 'A description.', $link->link_description, 'The link description was not kept.' ); + } + + /** + * @ticket 66019 + */ + public function test_should_keep_the_existing_categories_when_none_are_passed() { + $term_id = self::factory()->term->create( array( 'taxonomy' => 'link_category' ) ); + $link_id = self::factory()->bookmark->create( array( 'link_category' => array( $term_id ) ) ); + + wp_update_link( + array( + 'link_id' => $link_id, + 'link_name' => 'Updated', + ) + ); + + $this->assertSame( array( $term_id ), wp_get_link_cats( $link_id ) ); + } + + /** + * @ticket 66019 + */ + public function test_should_replace_the_categories_when_they_are_passed() { + $term_ids = self::factory()->term->create_many( 2, array( 'taxonomy' => 'link_category' ) ); + $link_id = self::factory()->bookmark->create( array( 'link_category' => array( $term_ids[0] ) ) ); + + wp_update_link( + array( + 'link_id' => $link_id, + 'link_category' => array( $term_ids[1] ), + ) + ); + + $this->assertSame( array( $term_ids[1] ), wp_get_link_cats( $link_id ) ); + } +}