Skip to content

Commit

Permalink
Merge pull request #42 from xwp/fix/hotlink-apis
Browse files Browse the repository at this point in the history
Hotlink in APIs
  • Loading branch information
pierlon authored Mar 25, 2020
2 parents 67cc1c9 + 1593ef9 commit 06434ae
Show file tree
Hide file tree
Showing 5 changed files with 334 additions and 45 deletions.
89 changes: 88 additions & 1 deletion php/class-hotlink.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
namespace Unsplash;

use WP_Query;
use WP_Post;

/**
* WordPress hotlink interface.
Expand Down Expand Up @@ -56,6 +57,90 @@ public function wp_get_attachment_url( $url, $id ) {
return $original_url;
}

/**
* Add unsplash image sizes to admin ajax.
*
* @param array $response Data for admin ajax.
* @param WP_Post $attachment Attachment object.
*
* @filter wp_prepare_attachment_for_js, 99, 2
*
* @return mixed
*/
public function wp_prepare_attachment_for_js( array $response, $attachment ) {
if ( ! $attachment instanceof WP_Post ) {
return $response;
}
$original_url = $this->get_original_url( $attachment->ID );
if ( ! $original_url ) {
return $response;
}
$response['sizes'] = $this->plugin->add_image_sizes( $original_url, $response['width'], $response['height'] );


return $response;
}

/**
* Add unsplash image sizes to REST API.
*
* @param WP_Response $wp_response Data for REST API.
* @param WP_Post $attachment Attachment object.
*
* @filter rest_prepare_attachment, 99, 2
*
* @return mixed
*/
public function rest_prepare_attachment( $wp_response, $attachment ) {
if ( ! $attachment instanceof WP_Post ) {
return $wp_response;
}
$original_url = $this->get_original_url( $attachment->ID );
if ( ! $original_url ) {
return $wp_response;
}
$response = $wp_response->get_data();
if ( isset( $response['media_details'] ) ) {
$response['media_details']['sizes'] = $this->plugin->add_image_sizes( $original_url, $response['media_details']['width'], $response['media_details']['height'] );
// Reformat image sizes as REST API response is a little differently formatted.
$response['media_details']['sizes'] = $this->change_fields( $response['media_details']['sizes'], $response['media_details']['file'] );
// No image sizes missing.
if ( isset( $response['missing_image_sizes'] ) ) {
$response['missing_image_sizes'] = [];
}
}

// Return raw image url in REST API.
if ( isset( $response['source_url'] ) ) {
remove_filter( 'wp_get_attachment_url', [ $this, 'wp_get_attachment_url' ], 10 );
$response['source_url'] = wp_get_attachment_url( $attachment->ID );
add_filter( 'wp_get_attachment_url', [ $this, 'wp_get_attachment_url' ], 10, 2 );
}

$wp_response->set_data( $response );

return $wp_response;
}

/**
* Reformat image sizes as REST API response is a little differently formatted.
*
* @param array $sizes List of sizes.
* @param String $file File name.
* @return array
*/
public function change_fields( array $sizes, $file ) {
foreach ( $sizes as $size => $details ) {
$details['file'] = $file;
$details['source_url'] = $details['url'];
$details['mime_type'] = 'image/jpeg';
unset( $details['url'], $details['orientation'] );
$sizes[ $size ] = $details;
}

return $sizes;
}

/**
* Filter image downsize.
*
Expand Down Expand Up @@ -106,9 +191,10 @@ public function image_downsize( $should_resize, $id, $size ) {
*
* @see wp_image_add_srcset_and_sizes()
*
* @param string $content The raw post content to be filtered.
*
* @filter the_content, 99, 1
*
* @param string $content The raw post content to be filtered.
* @return string Converted content with hotlinked images.
*/
public function hotlink_images_in_content( $content ) {
Expand Down Expand Up @@ -153,6 +239,7 @@ public function hotlink_images_in_content( $content ) {
*
* @param string $image An HTML 'img' element to be filtered.
* @param int $attachment_id Image attachment ID.
*
* @return string Converted 'img' element with 'srcset' and 'sizes' attributes added.
*/
public function replace_image( $image, $attachment_id ) {
Expand Down
71 changes: 48 additions & 23 deletions php/class-plugin.php
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,17 @@ class Plugin extends Plugin_Base {
*/
const POST_TYPE = 'attachment';

/**
* Default image args.
*
* @var array
*/
public $default_img_attrs = [
'fm' => 'jpg',
'q' => '85',
'fit' => 'crop',
];

/**
* Initiate the plugin resources.
*
Expand Down Expand Up @@ -129,12 +140,6 @@ public function enqueue_media_scripts() {
* @return array
*/
public function wp_prepare_attachment_for_js( array $photo ) {
$attrs = [
'fm' => 'jpg',
'q' => '85',
'fit' => 'crop',
];

$image = new Image( $photo );

$response = [
Expand All @@ -158,7 +163,7 @@ public function wp_prepare_attachment_for_js( array $photo ) {
'mime' => $image->get_field( 'mime_type' ),
'type' => 'image',
'subtype' => $image->get_field( 'ext' ),
'icon' => ! empty( $image->get_image_url( 'thumb' ) ) ? $this->get_original_url_with_size( $image->get_image_url( 'thumb' ), 150, 150, $attrs ) : null,
'icon' => ! empty( $image->get_image_url( 'thumb' ) ) ? $this->get_original_url_with_size( $image->get_image_url( 'thumb' ), 150, 150, $this->default_img_attrs ) : null,
'dateFormatted' => mysql2date( __( 'F j, Y', 'unsplash' ), $image->get_field( 'created_at' ) ),
'nonces' => [
'update' => false,
Expand All @@ -168,36 +173,56 @@ public function wp_prepare_attachment_for_js( array $photo ) {
'editLink' => false,
'meta' => false,
];
$width = 400;
$height = (int) ceil( $image->get_field( 'height' ) / ( $image->get_field( 'width' ) / $width ) );
$url = ! empty( $image->get_image_url( 'small' ) ) ? $image->get_image_url( 'small' ) : $this->get_original_url_with_size( $image->get_field( 'original_url' ), $width, $height, $attrs );
$sizes = [

$response['sizes'] = $this->add_image_sizes( $image->get_field( 'original_url' ), $image->get_field( 'width' ), $image->get_field( 'height' ) );

return $response;
}

/**
* Generate image sizes for Admin ajax / REST api.
*
* @param String $url Image URL.
* @param Int $width Width of Image.
* @param Int $height Height of Image.
*
* @return array
*/
public function add_image_sizes( $url, $width, $height ) {
$width_medium = 400;
$height_medium = (int) ( ( $height / ( $width / $width_medium ) ) );
$url_medium = $this->get_original_url_with_size( $url, $width_medium, $height_medium, $this->default_img_attrs );
$sizes = [
'full' => [
'url' => $image->get_field( 'original_url' ),
'height' => $image->get_field( 'height' ),
'width' => $image->get_field( 'width' ),
'url' => $url,
'height' => $height,
'width' => $width,
'orientation' => 0,
],
'medium' => [
'url' => $url,
'height' => $height,
'width' => $width,
'url' => $url_medium,
'height' => $height_medium,
'width' => $width_medium,
'orientation' => 0,
],
];

foreach ( $this->image_sizes() as $name => $size ) {
if ( array_key_exists( $name, $sizes ) ) {
continue;
}
$url = $this->get_original_url_with_size( $image->get_field( 'original_url' ), $size['width'], $size['height'], $attrs );

$_url = $this->get_original_url_with_size( $url, $size['width'], $size['height'], $this->default_img_attrs );

$sizes[ $name ] = [
'url' => $url,
'height' => $size['height'],
'width' => $size['width'],
'url' => $_url,
'height' => $size['height'],
'width' => $size['width'],
'orientation' => 0,
];
}
$response['sizes'] = $sizes;

return $response;
return $sizes;
}

/**
Expand Down
137 changes: 137 additions & 0 deletions tests/phpunit/php/class-test-hotlink.php
Original file line number Diff line number Diff line change
Expand Up @@ -146,4 +146,141 @@ public function test_prime_post_caches() {
$primed_attachments = $this->hotlink->prime_post_caches( $attachment_ids );
$this->assertEqualSets( $primed_attachments, [ get_post( self::$attachment_id ) ] );
}

/**
* Test wp_prepare_attachment_for_js.
*
* @covers ::wp_prepare_attachment_for_js()
*/
public function test_no_wp_prepare_attachment_for_js_1() {
$data = [ 'foo' => 'bar' ];
$result = $this->hotlink->wp_prepare_attachment_for_js( $data, false );
$this->assertEqualSets( $result, $data );
}

/**
* Test wp_prepare_attachment_for_js.
*
* @covers ::wp_prepare_attachment_for_js()
*/
public function test_no_wp_prepare_attachment_for_js_2() {
$second_id = $this->factory->attachment->create_object(
'/tmp/melon.jpg',
0,
[
'post_mime_type' => 'image/jpeg',
'post_excerpt' => 'A sample caption 2',
]
);
$image = get_post( $second_id );
$data = [ 'foo' => 'bar' ];
$result = $this->hotlink->wp_prepare_attachment_for_js( $data, $image );
$this->assertEqualSets( $result, $data );
}

/**
* Test wp_prepare_attachment_for_js.
*
* @covers ::wp_prepare_attachment_for_js()
*/
public function test_wp_prepare_attachment_for_js() {
$image = get_post( self::$attachment_id );
$photo = [
'width' => 999,
'height' => 999,
'urls' => [ 'raw' => 'http://www.example.com/test.jpg' ],
];
$result = $this->hotlink->wp_prepare_attachment_for_js( $photo, $image );
$plugin = new Plugin();
$expected = $plugin->add_image_sizes( $photo['urls']['raw'], $photo['width'], $photo['height'] );
$this->assertEqualSets( $result['sizes'], $expected );
}


/**
* Test rest_prepare_attachment.
*
* @covers ::rest_prepare_attachment()
*/
public function test_no_rest_prepare_attachment() {
$data = [ 'foo' => 'bar' ];
$reponse = new \WP_REST_Response( $data );
$result = $this->hotlink->rest_prepare_attachment( $reponse, false );
$this->assertEqualSets( $result->get_data(), $reponse->get_data() );
}

/**
* Test rest_prepare_attachment.
*
* @covers ::rest_prepare_attachment()
*/
public function test_no_rest_prepare_attachment_1() {
$second_id = $this->factory->attachment->create_object(
'/tmp/melon.jpg',
0,
[
'post_mime_type' => 'image/jpeg',
'post_excerpt' => 'A sample caption 2',
]
);
$image = get_post( $second_id );
$data = [ 'foo' => 'bar' ];
$reponse = new \WP_REST_Response( $data );
$result = $this->hotlink->rest_prepare_attachment( $reponse, $image );
$this->assertEqualSets( $result->get_data(), $reponse->get_data() );
}

/**
* Test rest_prepare_attachment.
*
* @covers ::rest_prepare_attachment()
* @covers ::change_fields()
*/
public function test_rest_prepare_attachment_2() {
$image = get_post( self::$attachment_id );
$photo = [

'urls' => [ 'raw' => 'http://www.example.com/test.jpg' ],
'media_details' => [
'width' => 999,
'height' => 999,
'file' => 'test.jpg',
],
'missing_image_sizes' => [
'large',
],
];
$reponse = new \WP_REST_Response( $photo );
$result = $this->hotlink->rest_prepare_attachment( $reponse, $image );
$plugin = new Plugin();
$sizes = $plugin->add_image_sizes( $photo['urls']['raw'], $photo['media_details']['width'], $photo['media_details']['height'] );
$expected = $this->hotlink->change_fields( $sizes, $photo['media_details']['file'] );
$data = $result->get_data();
$this->assertEqualSets( $data['media_details']['sizes'], $expected );
$this->assertEqualSets( $data['missing_image_sizes'], [] );
}

/**
* Test rest_prepare_attachment.
*
* @covers ::rest_prepare_attachment()
*/
public function test_rest_prepare_attachment_3() {
$image = get_post( self::$attachment_id );
$photo = [

'urls' => [ 'raw' => 'http://www.example.com/nothing.jpg' ],
'media_details' => [
'width' => 999,
'height' => 999,
'file' => 'test.jpg',
],
'source_url' => 'http://unsplash.com/test',
];
$reponse = new \WP_REST_Response( $photo );
$result = $this->hotlink->rest_prepare_attachment( $reponse, $image );
$data = $result->get_data();
$this->assertEquals( $data['source_url'], 'http://www.example.com/test.jpg' );
}

}
Loading

0 comments on commit 06434ae

Please sign in to comment.