balmet.com

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs

class-wp-oembed-controller.php (6827B)


      1 <?php
      2 /**
      3  * WP_oEmbed_Controller class, used to provide an oEmbed endpoint.
      4  *
      5  * @package WordPress
      6  * @subpackage Embeds
      7  * @since 4.4.0
      8  */
      9 
     10 /**
     11  * oEmbed API endpoint controller.
     12  *
     13  * Registers the REST API route and delivers the response data.
     14  * The output format (XML or JSON) is handled by the REST API.
     15  *
     16  * @since 4.4.0
     17  */
     18 final class WP_oEmbed_Controller {
     19 	/**
     20 	 * Register the oEmbed REST API route.
     21 	 *
     22 	 * @since 4.4.0
     23 	 */
     24 	public function register_routes() {
     25 		/**
     26 		 * Filters the maxwidth oEmbed parameter.
     27 		 *
     28 		 * @since 4.4.0
     29 		 *
     30 		 * @param int $maxwidth Maximum allowed width. Default 600.
     31 		 */
     32 		$maxwidth = apply_filters( 'oembed_default_width', 600 );
     33 
     34 		register_rest_route(
     35 			'oembed/1.0',
     36 			'/embed',
     37 			array(
     38 				array(
     39 					'methods'             => WP_REST_Server::READABLE,
     40 					'callback'            => array( $this, 'get_item' ),
     41 					'permission_callback' => '__return_true',
     42 					'args'                => array(
     43 						'url'      => array(
     44 							'description' => __( 'The URL of the resource for which to fetch oEmbed data.' ),
     45 							'required'    => true,
     46 							'type'        => 'string',
     47 							'format'      => 'uri',
     48 						),
     49 						'format'   => array(
     50 							'default'           => 'json',
     51 							'sanitize_callback' => 'wp_oembed_ensure_format',
     52 						),
     53 						'maxwidth' => array(
     54 							'default'           => $maxwidth,
     55 							'sanitize_callback' => 'absint',
     56 						),
     57 					),
     58 				),
     59 			)
     60 		);
     61 
     62 		register_rest_route(
     63 			'oembed/1.0',
     64 			'/proxy',
     65 			array(
     66 				array(
     67 					'methods'             => WP_REST_Server::READABLE,
     68 					'callback'            => array( $this, 'get_proxy_item' ),
     69 					'permission_callback' => array( $this, 'get_proxy_item_permissions_check' ),
     70 					'args'                => array(
     71 						'url'       => array(
     72 							'description' => __( 'The URL of the resource for which to fetch oEmbed data.' ),
     73 							'required'    => true,
     74 							'type'        => 'string',
     75 							'format'      => 'uri',
     76 						),
     77 						'format'    => array(
     78 							'description' => __( 'The oEmbed format to use.' ),
     79 							'type'        => 'string',
     80 							'default'     => 'json',
     81 							'enum'        => array(
     82 								'json',
     83 								'xml',
     84 							),
     85 						),
     86 						'maxwidth'  => array(
     87 							'description'       => __( 'The maximum width of the embed frame in pixels.' ),
     88 							'type'              => 'integer',
     89 							'default'           => $maxwidth,
     90 							'sanitize_callback' => 'absint',
     91 						),
     92 						'maxheight' => array(
     93 							'description'       => __( 'The maximum height of the embed frame in pixels.' ),
     94 							'type'              => 'integer',
     95 							'sanitize_callback' => 'absint',
     96 						),
     97 						'discover'  => array(
     98 							'description' => __( 'Whether to perform an oEmbed discovery request for unsanctioned providers.' ),
     99 							'type'        => 'boolean',
    100 							'default'     => true,
    101 						),
    102 					),
    103 				),
    104 			)
    105 		);
    106 	}
    107 
    108 	/**
    109 	 * Callback for the embed API endpoint.
    110 	 *
    111 	 * Returns the JSON object for the post.
    112 	 *
    113 	 * @since 4.4.0
    114 	 *
    115 	 * @param WP_REST_Request $request Full data about the request.
    116 	 * @return array|WP_Error oEmbed response data or WP_Error on failure.
    117 	 */
    118 	public function get_item( $request ) {
    119 		$post_id = url_to_postid( $request['url'] );
    120 
    121 		/**
    122 		 * Filters the determined post ID.
    123 		 *
    124 		 * @since 4.4.0
    125 		 *
    126 		 * @param int    $post_id The post ID.
    127 		 * @param string $url     The requested URL.
    128 		 */
    129 		$post_id = apply_filters( 'oembed_request_post_id', $post_id, $request['url'] );
    130 
    131 		$data = get_oembed_response_data( $post_id, $request['maxwidth'] );
    132 
    133 		if ( ! $data ) {
    134 			return new WP_Error( 'oembed_invalid_url', get_status_header_desc( 404 ), array( 'status' => 404 ) );
    135 		}
    136 
    137 		return $data;
    138 	}
    139 
    140 	/**
    141 	 * Checks if current user can make a proxy oEmbed request.
    142 	 *
    143 	 * @since 4.8.0
    144 	 *
    145 	 * @return true|WP_Error True if the request has read access, WP_Error object otherwise.
    146 	 */
    147 	public function get_proxy_item_permissions_check() {
    148 		if ( ! current_user_can( 'edit_posts' ) ) {
    149 			return new WP_Error( 'rest_forbidden', __( 'Sorry, you are not allowed to make proxied oEmbed requests.' ), array( 'status' => rest_authorization_required_code() ) );
    150 		}
    151 		return true;
    152 	}
    153 
    154 	/**
    155 	 * Callback for the proxy API endpoint.
    156 	 *
    157 	 * Returns the JSON object for the proxied item.
    158 	 *
    159 	 * @since 4.8.0
    160 	 *
    161 	 * @see WP_oEmbed::get_html()
    162 	 * @global WP_Embed $wp_embed
    163 	 *
    164 	 * @param WP_REST_Request $request Full data about the request.
    165 	 * @return object|WP_Error oEmbed response data or WP_Error on failure.
    166 	 */
    167 	public function get_proxy_item( $request ) {
    168 		global $wp_embed;
    169 
    170 		$args = $request->get_params();
    171 
    172 		// Serve oEmbed data from cache if set.
    173 		unset( $args['_wpnonce'] );
    174 		$cache_key = 'oembed_' . md5( serialize( $args ) );
    175 		$data      = get_transient( $cache_key );
    176 		if ( ! empty( $data ) ) {
    177 			return $data;
    178 		}
    179 
    180 		$url = $request['url'];
    181 		unset( $args['url'] );
    182 
    183 		// Copy maxwidth/maxheight to width/height since WP_oEmbed::fetch() uses these arg names.
    184 		if ( isset( $args['maxwidth'] ) ) {
    185 			$args['width'] = $args['maxwidth'];
    186 		}
    187 		if ( isset( $args['maxheight'] ) ) {
    188 			$args['height'] = $args['maxheight'];
    189 		}
    190 
    191 		// Short-circuit process for URLs belonging to the current site.
    192 		$data = get_oembed_response_data_for_url( $url, $args );
    193 
    194 		if ( $data ) {
    195 			return $data;
    196 		}
    197 
    198 		$data = _wp_oembed_get_object()->get_data( $url, $args );
    199 
    200 		if ( false === $data ) {
    201 			// Try using a classic embed, instead.
    202 			/* @var WP_Embed $wp_embed */
    203 			$html = $wp_embed->get_embed_handler_html( $args, $url );
    204 
    205 			if ( $html ) {
    206 				global $wp_scripts;
    207 				// Check if any scripts were enqueued by the shortcode, and include them in the response.
    208 				$enqueued_scripts = array();
    209 
    210 				foreach ( $wp_scripts->queue as $script ) {
    211 					$enqueued_scripts[] = $wp_scripts->registered[ $script ]->src;
    212 				}
    213 
    214 				return (object) array(
    215 					'provider_name' => __( 'Embed Handler' ),
    216 					'html'          => $html,
    217 					'scripts'       => $enqueued_scripts,
    218 				);
    219 			}
    220 
    221 			return new WP_Error( 'oembed_invalid_url', get_status_header_desc( 404 ), array( 'status' => 404 ) );
    222 		}
    223 
    224 		/** This filter is documented in wp-includes/class-wp-oembed.php */
    225 		$data->html = apply_filters( 'oembed_result', _wp_oembed_get_object()->data2html( (object) $data, $url ), $url, $args );
    226 
    227 		/**
    228 		 * Filters the oEmbed TTL value (time to live).
    229 		 *
    230 		 * Similar to the {@see 'oembed_ttl'} filter, but for the REST API
    231 		 * oEmbed proxy endpoint.
    232 		 *
    233 		 * @since 4.8.0
    234 		 *
    235 		 * @param int    $time    Time to live (in seconds).
    236 		 * @param string $url     The attempted embed URL.
    237 		 * @param array  $args    An array of embed request arguments.
    238 		 */
    239 		$ttl = apply_filters( 'rest_oembed_ttl', DAY_IN_SECONDS, $url, $args );
    240 
    241 		set_transient( $cache_key, $data, $ttl );
    242 
    243 		return $data;
    244 	}
    245 }