bookmark.php 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380
  1. <?php
  2. /**
  3. * WordPress Bookmark Administration API
  4. *
  5. * @package WordPress
  6. * @subpackage Administration
  7. */
  8. /**
  9. * Add a link to using values provided in $_POST.
  10. *
  11. * @since 2.0.0
  12. *
  13. * @return int|WP_Error Value 0 or WP_Error on failure. The link ID on success.
  14. */
  15. function add_link() {
  16. return edit_link();
  17. }
  18. /**
  19. * Updates or inserts a link using values provided in $_POST.
  20. *
  21. * @since 2.0.0
  22. *
  23. * @param int $link_id Optional. ID of the link to edit. Default 0.
  24. * @return int|WP_Error Value 0 or WP_Error on failure. The link ID on success.
  25. */
  26. function edit_link( $link_id = 0 ) {
  27. if ( ! current_user_can( 'manage_links' ) ) {
  28. wp_die(
  29. '<h1>' . __( 'You need a higher level of permission.' ) . '</h1>' .
  30. '<p>' . __( 'Sorry, you are not allowed to edit the links for this site.' ) . '</p>',
  31. 403
  32. );
  33. }
  34. $_POST['link_url'] = esc_html( $_POST['link_url'] );
  35. $_POST['link_url'] = esc_url( $_POST['link_url'] );
  36. $_POST['link_name'] = esc_html( $_POST['link_name'] );
  37. $_POST['link_image'] = esc_html( $_POST['link_image'] );
  38. $_POST['link_rss'] = esc_url( $_POST['link_rss'] );
  39. if ( ! isset( $_POST['link_visible'] ) || 'N' !== $_POST['link_visible'] ) {
  40. $_POST['link_visible'] = 'Y';
  41. }
  42. if ( ! empty( $link_id ) ) {
  43. $_POST['link_id'] = $link_id;
  44. return wp_update_link( $_POST );
  45. } else {
  46. return wp_insert_link( $_POST );
  47. }
  48. }
  49. /**
  50. * Retrieves the default link for editing.
  51. *
  52. * @since 2.0.0
  53. *
  54. * @return stdClass Default link object.
  55. */
  56. function get_default_link_to_edit() {
  57. $link = new stdClass;
  58. if ( isset( $_GET['linkurl'] ) ) {
  59. $link->link_url = esc_url( wp_unslash( $_GET['linkurl'] ) );
  60. } else {
  61. $link->link_url = '';
  62. }
  63. if ( isset( $_GET['name'] ) ) {
  64. $link->link_name = esc_attr( wp_unslash( $_GET['name'] ) );
  65. } else {
  66. $link->link_name = '';
  67. }
  68. $link->link_visible = 'Y';
  69. return $link;
  70. }
  71. /**
  72. * Deletes a specified link from the database.
  73. *
  74. * @since 2.0.0
  75. *
  76. * @global wpdb $wpdb WordPress database abstraction object.
  77. *
  78. * @param int $link_id ID of the link to delete
  79. * @return true Always true.
  80. */
  81. function wp_delete_link( $link_id ) {
  82. global $wpdb;
  83. /**
  84. * Fires before a link is deleted.
  85. *
  86. * @since 2.0.0
  87. *
  88. * @param int $link_id ID of the link to delete.
  89. */
  90. do_action( 'delete_link', $link_id );
  91. wp_delete_object_term_relationships( $link_id, 'link_category' );
  92. $wpdb->delete( $wpdb->links, array( 'link_id' => $link_id ) );
  93. /**
  94. * Fires after a link has been deleted.
  95. *
  96. * @since 2.2.0
  97. *
  98. * @param int $link_id ID of the deleted link.
  99. */
  100. do_action( 'deleted_link', $link_id );
  101. clean_bookmark_cache( $link_id );
  102. return true;
  103. }
  104. /**
  105. * Retrieves the link category IDs associated with the link specified.
  106. *
  107. * @since 2.1.0
  108. *
  109. * @param int $link_id Link ID to look up.
  110. * @return int[] The IDs of the requested link's categories.
  111. */
  112. function wp_get_link_cats( $link_id = 0 ) {
  113. $cats = wp_get_object_terms( $link_id, 'link_category', array( 'fields' => 'ids' ) );
  114. return array_unique( $cats );
  115. }
  116. /**
  117. * Retrieves link data based on its ID.
  118. *
  119. * @since 2.0.0
  120. *
  121. * @param int|stdClass $link Link ID or object to retrieve.
  122. * @return object Link object for editing.
  123. */
  124. function get_link_to_edit( $link ) {
  125. return get_bookmark( $link, OBJECT, 'edit' );
  126. }
  127. /**
  128. * Inserts a link into the database, or updates an existing link.
  129. *
  130. * Runs all the necessary sanitizing, provides default values if arguments are missing,
  131. * and finally saves the link.
  132. *
  133. * @since 2.0.0
  134. *
  135. * @global wpdb $wpdb WordPress database abstraction object.
  136. *
  137. * @param array $linkdata {
  138. * Elements that make up the link to insert.
  139. *
  140. * @type int $link_id Optional. The ID of the existing link if updating.
  141. * @type string $link_url The URL the link points to.
  142. * @type string $link_name The title of the link.
  143. * @type string $link_image Optional. A URL of an image.
  144. * @type string $link_target Optional. The target element for the anchor tag.
  145. * @type string $link_description Optional. A short description of the link.
  146. * @type string $link_visible Optional. 'Y' means visible, anything else means not.
  147. * @type int $link_owner Optional. A user ID.
  148. * @type int $link_rating Optional. A rating for the link.
  149. * @type string $link_rel Optional. A relationship of the link to you.
  150. * @type string $link_notes Optional. An extended description of or notes on the link.
  151. * @type string $link_rss Optional. A URL of an associated RSS feed.
  152. * @type int $link_category Optional. The term ID of the link category.
  153. * If empty, uses default link category.
  154. * }
  155. * @param bool $wp_error Optional. Whether to return a WP_Error object on failure. Default false.
  156. * @return int|WP_Error Value 0 or WP_Error on failure. The link ID on success.
  157. */
  158. function wp_insert_link( $linkdata, $wp_error = false ) {
  159. global $wpdb;
  160. $defaults = array(
  161. 'link_id' => 0,
  162. 'link_name' => '',
  163. 'link_url' => '',
  164. 'link_rating' => 0,
  165. );
  166. $parsed_args = wp_parse_args( $linkdata, $defaults );
  167. $parsed_args = wp_unslash( sanitize_bookmark( $parsed_args, 'db' ) );
  168. $link_id = $parsed_args['link_id'];
  169. $link_name = $parsed_args['link_name'];
  170. $link_url = $parsed_args['link_url'];
  171. $update = false;
  172. if ( ! empty( $link_id ) ) {
  173. $update = true;
  174. }
  175. if ( '' === trim( $link_name ) ) {
  176. if ( '' !== trim( $link_url ) ) {
  177. $link_name = $link_url;
  178. } else {
  179. return 0;
  180. }
  181. }
  182. if ( '' === trim( $link_url ) ) {
  183. return 0;
  184. }
  185. $link_rating = ( ! empty( $parsed_args['link_rating'] ) ) ? $parsed_args['link_rating'] : 0;
  186. $link_image = ( ! empty( $parsed_args['link_image'] ) ) ? $parsed_args['link_image'] : '';
  187. $link_target = ( ! empty( $parsed_args['link_target'] ) ) ? $parsed_args['link_target'] : '';
  188. $link_visible = ( ! empty( $parsed_args['link_visible'] ) ) ? $parsed_args['link_visible'] : 'Y';
  189. $link_owner = ( ! empty( $parsed_args['link_owner'] ) ) ? $parsed_args['link_owner'] : get_current_user_id();
  190. $link_notes = ( ! empty( $parsed_args['link_notes'] ) ) ? $parsed_args['link_notes'] : '';
  191. $link_description = ( ! empty( $parsed_args['link_description'] ) ) ? $parsed_args['link_description'] : '';
  192. $link_rss = ( ! empty( $parsed_args['link_rss'] ) ) ? $parsed_args['link_rss'] : '';
  193. $link_rel = ( ! empty( $parsed_args['link_rel'] ) ) ? $parsed_args['link_rel'] : '';
  194. $link_category = ( ! empty( $parsed_args['link_category'] ) ) ? $parsed_args['link_category'] : array();
  195. // Make sure we set a valid category.
  196. if ( ! is_array( $link_category ) || 0 === count( $link_category ) ) {
  197. $link_category = array( get_option( 'default_link_category' ) );
  198. }
  199. if ( $update ) {
  200. if ( false === $wpdb->update( $wpdb->links, compact( 'link_url', 'link_name', 'link_image', 'link_target', 'link_description', 'link_visible', 'link_owner', 'link_rating', 'link_rel', 'link_notes', 'link_rss' ), compact( 'link_id' ) ) ) {
  201. if ( $wp_error ) {
  202. return new WP_Error( 'db_update_error', __( 'Could not update link in the database.' ), $wpdb->last_error );
  203. } else {
  204. return 0;
  205. }
  206. }
  207. } else {
  208. if ( false === $wpdb->insert( $wpdb->links, compact( 'link_url', 'link_name', 'link_image', 'link_target', 'link_description', 'link_visible', 'link_owner', 'link_rating', 'link_rel', 'link_notes', 'link_rss' ) ) ) {
  209. if ( $wp_error ) {
  210. return new WP_Error( 'db_insert_error', __( 'Could not insert link into the database.' ), $wpdb->last_error );
  211. } else {
  212. return 0;
  213. }
  214. }
  215. $link_id = (int) $wpdb->insert_id;
  216. }
  217. wp_set_link_cats( $link_id, $link_category );
  218. if ( $update ) {
  219. /**
  220. * Fires after a link was updated in the database.
  221. *
  222. * @since 2.0.0
  223. *
  224. * @param int $link_id ID of the link that was updated.
  225. */
  226. do_action( 'edit_link', $link_id );
  227. } else {
  228. /**
  229. * Fires after a link was added to the database.
  230. *
  231. * @since 2.0.0
  232. *
  233. * @param int $link_id ID of the link that was added.
  234. */
  235. do_action( 'add_link', $link_id );
  236. }
  237. clean_bookmark_cache( $link_id );
  238. return $link_id;
  239. }
  240. /**
  241. * Update link with the specified link categories.
  242. *
  243. * @since 2.1.0
  244. *
  245. * @param int $link_id ID of the link to update.
  246. * @param int[] $link_categories Array of link category IDs to add the link to.
  247. */
  248. function wp_set_link_cats( $link_id = 0, $link_categories = array() ) {
  249. // If $link_categories isn't already an array, make it one:
  250. if ( ! is_array( $link_categories ) || 0 === count( $link_categories ) ) {
  251. $link_categories = array( get_option( 'default_link_category' ) );
  252. }
  253. $link_categories = array_map( 'intval', $link_categories );
  254. $link_categories = array_unique( $link_categories );
  255. wp_set_object_terms( $link_id, $link_categories, 'link_category' );
  256. clean_bookmark_cache( $link_id );
  257. }
  258. /**
  259. * Updates a link in the database.
  260. *
  261. * @since 2.0.0
  262. *
  263. * @param array $linkdata Link data to update. See wp_insert_link() for accepted arguments.
  264. * @return int|WP_Error Value 0 or WP_Error on failure. The updated link ID on success.
  265. */
  266. function wp_update_link( $linkdata ) {
  267. $link_id = (int) $linkdata['link_id'];
  268. $link = get_bookmark( $link_id, ARRAY_A );
  269. // Escape data pulled from DB.
  270. $link = wp_slash( $link );
  271. // Passed link category list overwrites existing category list if not empty.
  272. if ( isset( $linkdata['link_category'] ) && is_array( $linkdata['link_category'] )
  273. && count( $linkdata['link_category'] ) > 0
  274. ) {
  275. $link_cats = $linkdata['link_category'];
  276. } else {
  277. $link_cats = $link['link_category'];
  278. }
  279. // Merge old and new fields with new fields overwriting old ones.
  280. $linkdata = array_merge( $link, $linkdata );
  281. $linkdata['link_category'] = $link_cats;
  282. return wp_insert_link( $linkdata );
  283. }
  284. /**
  285. * Outputs the 'disabled' message for the WordPress Link Manager.
  286. *
  287. * @since 3.5.0
  288. * @access private
  289. *
  290. * @global string $pagenow The filename of the current screen.
  291. */
  292. function wp_link_manager_disabled_message() {
  293. global $pagenow;
  294. if ( ! in_array( $pagenow, array( 'link-manager.php', 'link-add.php', 'link.php' ), true ) ) {
  295. return;
  296. }
  297. add_filter( 'pre_option_link_manager_enabled', '__return_true', 100 );
  298. $really_can_manage_links = current_user_can( 'manage_links' );
  299. remove_filter( 'pre_option_link_manager_enabled', '__return_true', 100 );
  300. if ( $really_can_manage_links ) {
  301. $plugins = get_plugins();
  302. if ( empty( $plugins['link-manager/link-manager.php'] ) ) {
  303. if ( current_user_can( 'install_plugins' ) ) {
  304. $install_url = wp_nonce_url(
  305. self_admin_url( 'update.php?action=install-plugin&plugin=link-manager' ),
  306. 'install-plugin_link-manager'
  307. );
  308. wp_die(
  309. sprintf(
  310. /* translators: %s: A link to install the Link Manager plugin. */
  311. __( 'If you are looking to use the link manager, please install the <a href="%s">Link Manager plugin</a>.' ),
  312. esc_url( $install_url )
  313. )
  314. );
  315. }
  316. } elseif ( is_plugin_inactive( 'link-manager/link-manager.php' ) ) {
  317. if ( current_user_can( 'activate_plugins' ) ) {
  318. $activate_url = wp_nonce_url(
  319. self_admin_url( 'plugins.php?action=activate&plugin=link-manager/link-manager.php' ),
  320. 'activate-plugin_link-manager/link-manager.php'
  321. );
  322. wp_die(
  323. sprintf(
  324. /* translators: %s: A link to activate the Link Manager plugin. */
  325. __( 'Please activate the <a href="%s">Link Manager plugin</a> to use the link manager.' ),
  326. esc_url( $activate_url )
  327. )
  328. );
  329. }
  330. }
  331. }
  332. wp_die( __( 'Sorry, you are not allowed to edit the links for this site.' ) );
  333. }