691 lines
21 KiB
PHP
691 lines
21 KiB
PHP
|
<?php
|
||
|
namespace ShortPixel\External\Offload;
|
||
|
|
||
|
use ShortPixel\Model\File\FileModel as FileModel;
|
||
|
|
||
|
if ( ! defined( 'ABSPATH' ) ) {
|
||
|
exit; // Exit if accessed directly.
|
||
|
}
|
||
|
|
||
|
use ShortPixel\ShortPixelLogger\ShortPixelLogger as Log;
|
||
|
use ShortPixel\Notices\NoticeController as Notice;
|
||
|
|
||
|
use ShortPixel\Controller\QuotaController as QuotaController;
|
||
|
use ShortPixel\Controller\ResponseController as ResponseController;
|
||
|
|
||
|
// @integration WP Offload Media Lite
|
||
|
class wpOffload
|
||
|
{
|
||
|
protected $as3cf;
|
||
|
protected $active = false;
|
||
|
protected $offloading = true;
|
||
|
|
||
|
private $itemClassName;
|
||
|
private $useHandlers = false; // Check for newer ItemHandlers or Compat mode.
|
||
|
protected $shouldPrevent = true; // if offload should be prevented. This is turned off when SPIO want to tell S3 to offload. Better than removing filter.
|
||
|
|
||
|
protected $settings;
|
||
|
|
||
|
protected $is_cname = false;
|
||
|
protected $cname;
|
||
|
|
||
|
private static $sources; // cache for url > source_id lookup, to prevent duplicate queries.
|
||
|
|
||
|
private static $offloadPrevented = array();
|
||
|
|
||
|
// if might have to do these checks many times for each thumbnails, keep it fastish.
|
||
|
//protected $retrievedCache = array();
|
||
|
|
||
|
public function __construct($as3cf)
|
||
|
{
|
||
|
// This must be called before WordPress' init.
|
||
|
$this->init($as3cf);
|
||
|
}
|
||
|
|
||
|
public function init($as3cf)
|
||
|
{
|
||
|
|
||
|
if (! class_exists('\DeliciousBrains\WP_Offload_Media\Items\Media_Library_Item'))
|
||
|
{
|
||
|
Notice::addWarning(__('Your S3-Offload plugin version doesn\'t seem to be compatible. Please upgrade the S3-Offload plugin', 'shortpixel-image-optimiser'), true);
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
$this->itemClassName = '\DeliciousBrains\WP_Offload_Media\Items\Media_Library_Item';
|
||
|
|
||
|
if (method_exists($as3cf, 'get_item_handler'))
|
||
|
{
|
||
|
$this->useHandlers = true; // we have a new version
|
||
|
}
|
||
|
else {
|
||
|
Notice::addWarning(__('Your S3-Offload plugin version doesn\'t seem to be compatible. Please upgrade the S3-Offload plugin', 'shortpixel-image-optimiser'), true);
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
$this->as3cf = $as3cf;
|
||
|
$this->active = true;
|
||
|
|
||
|
// if setting to upload to bucket is off, don't hook or do anything really.
|
||
|
if (! $this->as3cf->get_setting( 'copy-to-s3' ))
|
||
|
{
|
||
|
$this->offloading = false;
|
||
|
}
|
||
|
|
||
|
/* // Lets see if this can be without
|
||
|
if ('cloudfront' === $this->as3cf->get_setting( 'domain' ))
|
||
|
{
|
||
|
$this->is_cname = true;
|
||
|
$this->cname = $this->as3cf->get_setting( 'cloudfront' );
|
||
|
} */
|
||
|
|
||
|
// $provider = $this->as3cf->get_provider();
|
||
|
add_action('shortpixel/image/optimised', array($this, 'image_upload'), 10);
|
||
|
add_action('shortpixel/image/after_restore', array($this, 'image_restore'), 10, 3); // hit this when restoring.
|
||
|
add_action('shortpixel-thumbnails-before-regenerate', array($this, 'remove_remote'), 10);
|
||
|
add_action('shortpixel/converter/prevent-offload', array($this, 'preventOffload'), 10);
|
||
|
add_action('shortpixel/converter/prevent-offload-off', array($this, 'preventOffloadOff'), 10);
|
||
|
|
||
|
// add_action('shortpixel_restore_after_pathget', array($this, 'remove_remote')); // not optimal -> has to do w/ doRestore and when URL/PATH is available when not on server .
|
||
|
|
||
|
// Seems this better served by _after? If it fails, it's removed from remote w/o filechange.
|
||
|
// add_action('shortpixel/image/convertpng2jpg_before', array($this, 'remove_remote'));
|
||
|
add_filter('as3cf_attachment_file_paths', array($this, 'add_webp_paths'));
|
||
|
|
||
|
|
||
|
// add_filter('as3cf_remove_source_files_from_provider', array($this, 'remove_webp_paths'), 10);
|
||
|
// add_action('shortpixel/image/convertpng2jpg_success', array($this, 'image_converted'), 10);
|
||
|
add_filter('as3cf_remove_source_files_from_provider', array($this, 'remove_webp_paths'));
|
||
|
|
||
|
|
||
|
// add_filter('shortpixel/restore/targetfile', array($this, 'returnOriginalFile'),10,2);
|
||
|
add_filter('as3cf_pre_update_attachment_metadata', array($this, 'preventUpdateMetaData'), 10,4);
|
||
|
add_filter('as3cf_pre_handle_item_upload', array($this, 'preventInitialUploadHandler'), 10,3);
|
||
|
|
||
|
//add_filter('as3cf_get_attached_file', array($this, 'fixScaledUrl'), 10, 4);
|
||
|
add_filter('shortpixel_get_original_image_path', array($this, 'checkScaledUrl'), 10,2);
|
||
|
// add_filter('as3cf_get_attached_file_noop', array($this, 'fixScaledUrl'), 10,4);
|
||
|
|
||
|
//add_filter('shortpixel_get_attached_file', array($this, 'get_raw_attached_file'),10, 2);
|
||
|
// add_filter('shortpixel_get_original_image_path', array($this, 'get_raw_original_path'), 10, 2);
|
||
|
add_filter('shortpixel/image/urltopath', array($this, 'checkIfOffloaded'), 10,2);
|
||
|
add_filter('shortpixel/file/virtual/translate', array($this, 'getLocalPathByURL'));
|
||
|
|
||
|
// for webp picture paths rendered via output
|
||
|
// add_filter('shortpixel_webp_image_base', array($this, 'checkWebpRemotePath'), 10, 2);
|
||
|
add_filter('shortpixel/front/webp_notfound', array($this, 'fixWebpRemotePath'), 10, 4);
|
||
|
|
||
|
// Fix for updating source paths when converting
|
||
|
add_action('shortpixel/image/convertpng2jpg_success', array($this, 'updateOriginalPath'));
|
||
|
}
|
||
|
|
||
|
public function returnOriginalFile($file, $attach_id)
|
||
|
{
|
||
|
$file = get_attached_file($attach_id, true);
|
||
|
return $file;
|
||
|
}
|
||
|
|
||
|
private function getMediaClass()
|
||
|
{
|
||
|
if ($this->useHandlers)
|
||
|
{
|
||
|
$class = $this->as3cf->get_source_type_class('media-library');
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
$class = $this->itemClassName; //backward compat.
|
||
|
}
|
||
|
|
||
|
return $class;
|
||
|
}
|
||
|
|
||
|
// This is used in the converted. Might be deployed elsewhere for better control.
|
||
|
public function preventOffload($attach_id)
|
||
|
{
|
||
|
self::$offloadPrevented[$attach_id] = true;
|
||
|
}
|
||
|
|
||
|
public function preventOffloadOff($attach_id)
|
||
|
{
|
||
|
unset(self::$offloadPrevented[$attach_id]);
|
||
|
}
|
||
|
|
||
|
// When Offload is not offloaded but is created during the process of generate metadata in WP, wp_create_image_subsizes fires an update metadata after just moving the upload, before making any thumbnails. If this is the case and the file has an -scaled / original image setup, the original_source_path becomes the same as the source_path which creates issue later on when dealing with optimizing it, if the file is deleted on local server. Prevent this, and lean on later update metadata.
|
||
|
public function preventUpdateMetaData($bool, $data, $post_id, $old_provider_object)
|
||
|
{
|
||
|
if (isset(self::$offloadPrevented[$post_id]))
|
||
|
{
|
||
|
return true ; // return true to cancel.
|
||
|
}
|
||
|
|
||
|
return $bool;
|
||
|
|
||
|
}
|
||
|
|
||
|
/**
|
||
|
* @param $id attachment id (WP)
|
||
|
* @param $mediaItem MediaLibraryModel SPIO
|
||
|
* @param $clean - boolean - if restore did all files (clean) or partial (not clean)
|
||
|
*/
|
||
|
public function image_restore($mediaItem, $id, $clean)
|
||
|
{
|
||
|
$settings = \wpSPIO()->settings();
|
||
|
|
||
|
// Only medialibrary offloading supported.
|
||
|
if ('media' !== $mediaItem->get('type') )
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
// If there are excluded sizes, there are not in backups. might not be left on remote, or ( if delete ) on server, so just generate the images and move them.
|
||
|
$mediaItem->wpCreateImageSizes();
|
||
|
|
||
|
$result = $this->remove_remote($id);
|
||
|
$this->image_upload($mediaItem);
|
||
|
}
|
||
|
|
||
|
public function remove_remote($id)
|
||
|
{
|
||
|
$a3cfItem = $this->getItemById($id); // MediaItem is AS3CF Object
|
||
|
if ($a3cfItem === false)
|
||
|
{
|
||
|
Log::addDebug('S3-Offload MediaItem not remote - ' . $id);
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
$remove = \DeliciousBrains\WP_Offload_Media\Items\Remove_Provider_Handler::get_item_handler_key_name();
|
||
|
$itemHandler = $this->as3cf->get_item_handler($remove);
|
||
|
|
||
|
$result = $itemHandler->handle($a3cfItem, array( 'verify_exists_on_local' => false)); //handle it then.
|
||
|
return $result;
|
||
|
}
|
||
|
|
||
|
|
||
|
/** @return Returns S3Ofload MediaItem, or false when this does not exist */
|
||
|
protected function getItemById($id, $create = false)
|
||
|
{
|
||
|
$class = $this->getMediaClass();
|
||
|
$mediaItem = $class::get_by_source_id($id);
|
||
|
|
||
|
if (true === $create && $mediaItem === false)
|
||
|
{
|
||
|
$mediaItem = $class::create_from_source_id($id);
|
||
|
}
|
||
|
|
||
|
return $mediaItem;
|
||
|
}
|
||
|
|
||
|
/** Cache source requests to improve performance
|
||
|
* @param $url string The URL that is being checked
|
||
|
* @param $source_id int Source ID of the item URL to be cached
|
||
|
* @return int|boolean|null Returns source_if or false ( not offloaded ) if found, returns null if not sourcecached.
|
||
|
*/
|
||
|
private function sourceCache($url, $source_id = null)
|
||
|
{
|
||
|
if ($source_id === null && isset(static::$sources[$url]))
|
||
|
{
|
||
|
$source_id = static::$sources[$url];
|
||
|
return $source_id;
|
||
|
}
|
||
|
elseif ($source_id !== null)
|
||
|
{
|
||
|
if (! isset(static::$sources[$url]))
|
||
|
{
|
||
|
static::$sources[$url] = $source_id;
|
||
|
}
|
||
|
|
||
|
return $source_id;
|
||
|
}
|
||
|
|
||
|
return null;
|
||
|
}
|
||
|
|
||
|
public function checkIfOffloaded($bool, $url)
|
||
|
{
|
||
|
|
||
|
$source_id = $this->sourceCache($url);
|
||
|
$orig_url = $url;
|
||
|
|
||
|
if (is_null($source_id))
|
||
|
{
|
||
|
$extension = substr($url, strrpos($url, '.') + 1);
|
||
|
|
||
|
// If these filetypes are not in the cache, they cannot be found via geSourceyIDByUrl method ( not in path DB ), so it's pointless to try. If they are offloaded, at some point the extra-info might load.
|
||
|
if ($extension == 'webp' || $extension == 'avif')
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
$source_id = $this->getSourceIDByURL($url);
|
||
|
|
||
|
}
|
||
|
else {
|
||
|
}
|
||
|
|
||
|
if ($source_id !== false)
|
||
|
{
|
||
|
return FileModel::$VIRTUAL_REMOTE;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
protected function getSourceIDByURL($url)
|
||
|
{
|
||
|
$source_id = $this->sourceCache($url); // check cache first.
|
||
|
$cacheHit = false; // prevent a cache hit to be cached again.
|
||
|
$raw_url = $url; // keep raw. If resolved, add the raw url to the cache.
|
||
|
|
||
|
// If in cache, we are done.
|
||
|
if (! is_null($source_id))
|
||
|
{
|
||
|
return $source_id;
|
||
|
}
|
||
|
|
||
|
if (is_null($source_id)) // check on the raw url.
|
||
|
{
|
||
|
$class = $this->getMediaClass();
|
||
|
|
||
|
$parsedUrl = parse_url($url);
|
||
|
|
||
|
if (! isset($parsedUrl['scheme']) || ! in_array($parsedUrl['scheme'], array('http','https')))
|
||
|
{
|
||
|
$url = 'http://' . $url; //str_replace($parsedUrl['scheme'], 'https', $url);
|
||
|
}
|
||
|
|
||
|
$source_id = $this->sourceCache($url);
|
||
|
|
||
|
if(is_null($source_id))
|
||
|
{
|
||
|
$source = $class::get_item_source_by_remote_url($url);
|
||
|
$source2 = $class::get_item_source_by_remote_url($raw_url);
|
||
|
|
||
|
$source_id = isset($source['id']) ? intval($source['id']) : null;
|
||
|
}
|
||
|
else {
|
||
|
$cacheHit = true; // hit the cache. Yeah.
|
||
|
$this->sourceCache($raw_url, $source_id);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
|
||
|
if (is_null($source_id)) // check now via the thumbnail hocus.
|
||
|
{
|
||
|
$pattern = '/(.*)-\d+[xX]\d+(\.\w+)/m';
|
||
|
$url = preg_replace($pattern, '$1$2', $url);
|
||
|
|
||
|
$source_id = $this->sourceCache($url); // check cache first.
|
||
|
|
||
|
if (is_null($source_id))
|
||
|
{
|
||
|
$source = $class::get_item_source_by_remote_url($url);
|
||
|
$source_id = isset($source['id']) ? intval($source['id']) : null;
|
||
|
}
|
||
|
else {
|
||
|
$cacheHit = true;
|
||
|
$this->sourceCache($raw_url , $source_id);
|
||
|
}
|
||
|
|
||
|
}
|
||
|
|
||
|
// Check issue with double extensions. If say double webp/avif is on, the double extension causes the URL not to be found (ie .jpg)
|
||
|
if (is_null($source_id))
|
||
|
{
|
||
|
if (substr_count($parsedUrl['path'], '.') > 1)
|
||
|
{
|
||
|
// Get extension
|
||
|
$ext = substr(strrchr($url, '.'), 1);
|
||
|
|
||
|
// Remove all extensions from the URL
|
||
|
$checkurl = substr($url, 0, strpos($url,'.')) ;
|
||
|
|
||
|
// Add back the last one.
|
||
|
$checkurl .= '.' . $ext;
|
||
|
|
||
|
// Retry
|
||
|
$source_id = $this->sourceCache($checkurl); // check cache first.
|
||
|
|
||
|
if (is_null($source_id))
|
||
|
{
|
||
|
$source = $class::get_item_source_by_remote_url($url);
|
||
|
$source_id = isset($source['id']) ? intval($source['id']) : null;
|
||
|
}
|
||
|
else {
|
||
|
$cacheHit = true;
|
||
|
$this->sourceCache($raw_url , $source_id);
|
||
|
}
|
||
|
|
||
|
}
|
||
|
}
|
||
|
|
||
|
if(is_null($source_id))
|
||
|
{
|
||
|
$source_id = false;
|
||
|
}
|
||
|
|
||
|
if (false === $cacheHit)
|
||
|
{
|
||
|
$this->sourceCache($url, $source_id); // cache it.
|
||
|
}
|
||
|
|
||
|
if ($source_id !== false && false === $cacheHit)
|
||
|
{
|
||
|
|
||
|
// get item
|
||
|
$item = $this->getItemById($source_id);
|
||
|
if (is_object($item) && method_exists($item, 'extra_info'))
|
||
|
{
|
||
|
$baseUrl = str_replace(basename($url),'', $url);
|
||
|
//$rawBaseUrl =
|
||
|
$extra_info = $item->extra_info();
|
||
|
|
||
|
if (isset($extra_info['objects']))
|
||
|
{
|
||
|
foreach($extra_info['objects'] as $extraItem)
|
||
|
{
|
||
|
if (is_array($extraItem) && isset($extraItem['source_file']))
|
||
|
{
|
||
|
// Add source stuff into cache.
|
||
|
$this->sourceCache($baseUrl . $extraItem['source_file'], $source_id);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return $source_id;
|
||
|
}
|
||
|
|
||
|
// @param s3 based URL that which is needed for finding local path
|
||
|
// @return String Filepath. Translated file path
|
||
|
public function getLocalPathByURL($url)
|
||
|
{
|
||
|
$source_id = $this->getSourceIDByURL($url);
|
||
|
|
||
|
if ($source_id === false)
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
$item = $this->getItemById($source_id);
|
||
|
|
||
|
$original_path = $item->original_source_path(); // $values['original_source_path'];
|
||
|
|
||
|
if (wp_basename($url) !== wp_basename($original_path)) // thumbnails translate to main file.
|
||
|
{
|
||
|
$original_path = str_replace(wp_basename($original_path), wp_basename($url), $original_path);
|
||
|
}
|
||
|
|
||
|
$fs = \wpSPIO()->filesystem();
|
||
|
$base = $fs->getWPUploadBase();
|
||
|
|
||
|
$file = $base . $original_path;
|
||
|
return $file;
|
||
|
}
|
||
|
|
||
|
|
||
|
/** Converted after png2jpg
|
||
|
*
|
||
|
* @param MediaItem Object SPIO
|
||
|
*/
|
||
|
public function image_converted($mediaItem)
|
||
|
{
|
||
|
$fs = \wpSPIO()->fileSystem();
|
||
|
|
||
|
$id = $mediaItem->get('id');
|
||
|
//$this->remove_remote($id);
|
||
|
$this->image_upload($mediaItem);
|
||
|
|
||
|
}
|
||
|
|
||
|
public function image_upload($mediaLibraryObject)
|
||
|
{
|
||
|
$id = $mediaLibraryObject->get('id');
|
||
|
$a3cfItem = $this->getItemById($id);
|
||
|
|
||
|
// Only medialibrary offloading supported.
|
||
|
if ('media' !== $mediaLibraryObject->get('type') )
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
if ( false === $a3cfItem)
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
$item = $this->getItemById($id, true);
|
||
|
|
||
|
if ( $item === false && ! $this->as3cf->get_setting( 'copy-to-s3' ) ) {
|
||
|
// abort if not already uploaded to provider and the copy setting is off
|
||
|
Log::addDebug('As3cf image upload is off and object not previously uploaded');
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
// Add Web/Avifs back under new method.
|
||
|
$this->shouldPrevent = false;
|
||
|
|
||
|
// The Handler doesn't work properly /w local removal if not the exact correct files are passed (?) . Offload does this probably via update metadata function, so let them sort it out with this . (until it breaks)
|
||
|
$meta = wp_get_attachment_metadata($id);
|
||
|
wp_update_attachment_metadata($id, $meta);
|
||
|
|
||
|
$this->shouldPrevent = true;
|
||
|
}
|
||
|
|
||
|
|
||
|
// WP Offload -for some reason - returns the same result of get_attached_file and wp_get_original_image_path , which are different files (one scaled) which then causes a wrong copy action after optimizing the image ( wrong destination download of the remote file ). This happens if offload with delete is on. Attempt to fix the URL to reflect the differences between -scaled and not.
|
||
|
public function checkScaledUrl($filepath, $id)
|
||
|
{
|
||
|
// Original filepath can never have a scaled in there.
|
||
|
// @todo This should probably check -scaled.<extension> as string end preventing issues.
|
||
|
if (strpos($filepath, '-scaled') !== false)
|
||
|
{
|
||
|
$filepath = str_replace('-scaled', '', $filepath);
|
||
|
}
|
||
|
return $filepath;
|
||
|
}
|
||
|
|
||
|
/** This function will cut out the initial upload to S3Offload . This cuts it off in the new handle area, leaving other updating in tact.
|
||
|
*/
|
||
|
public function preventInitialUploadHandler($bool, $as3cf_item, $options)
|
||
|
{
|
||
|
|
||
|
$fs = \wpSPIO()->filesystem();
|
||
|
$settings = \WPSPIO()->settings();
|
||
|
|
||
|
$post_id = $as3cf_item->source_id();
|
||
|
|
||
|
$quotaController = quotaController::getInstance();
|
||
|
if ($quotaController->hasQuota() === false)
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
if (! $this->offloading)
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
if ($this->shouldPrevent === false) // if false is returned, it's NOT prevented, so on-going.
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
if (isset(self::$offloadPrevented[$post_id]))
|
||
|
{
|
||
|
Log::addDebug('Offload Prevented via static for '. $post_id);
|
||
|
$error = new \WP_Error( 'upload-prevented', 'No offloading at this time, thanks' );
|
||
|
return $error;
|
||
|
}
|
||
|
|
||
|
Log::addDebug('Not preventing S3 Offload');
|
||
|
return $bool;
|
||
|
}
|
||
|
|
||
|
public function updateOriginalPath($imageModel)
|
||
|
{
|
||
|
$post_id = $imageModel->get('id');
|
||
|
|
||
|
$item = $this->getItemById($post_id);
|
||
|
|
||
|
if (false === $item) // item not offloaded.
|
||
|
{
|
||
|
return false;
|
||
|
}
|
||
|
|
||
|
$original_path = $item->original_path(); // Original path (non-scaled-)
|
||
|
$original_source_path = $item->original_source_path();
|
||
|
$path = $item->path();
|
||
|
$source_path = $item->source_path();
|
||
|
|
||
|
$wp_original = wp_get_original_image_path($post_id, apply_filters( 'emr_unfiltered_get_attached_file', true ));
|
||
|
$wp_original = apply_filters('emr/replace/original_image_path', $wp_original, $post_id);
|
||
|
$wp_source = trim(get_attached_file($post_id, apply_filters( 'emr_unfiltered_get_attached_file', true )));
|
||
|
|
||
|
$updated = false;
|
||
|
|
||
|
|
||
|
// If image is replaced with another name, the original soruce path will not match. This could also happen when an image is with -scaled as main is replaced by an image that doesn't have it. In all cases update the table to reflect proper changes.
|
||
|
if (wp_basename($wp_original) !== wp_basename($original_path))
|
||
|
{
|
||
|
|
||
|
$newpath = str_replace( wp_basename( $original_path ), wp_basename($wp_original), $original_path );
|
||
|
|
||
|
$item->set_original_path($newpath);
|
||
|
|
||
|
$newpath = str_replace( wp_basename( $original_source_path ), wp_basename($wp_original), $original_source_path );
|
||
|
$updated = true;
|
||
|
|
||
|
$item->set_original_source_path($newpath);
|
||
|
|
||
|
$item->save();
|
||
|
}
|
||
|
}
|
||
|
|
||
|
private function getWebpPaths($paths, $check_exists = true)
|
||
|
{
|
||
|
$newPaths = array();
|
||
|
$fs = \wpSPIO()->fileSystem();
|
||
|
|
||
|
foreach($paths as $size => $path)
|
||
|
{
|
||
|
$file = $fs->getFile($path);
|
||
|
|
||
|
$basedir = $file->getFileDir();
|
||
|
|
||
|
if (is_null($basedir)) // This could only happen if path is completely empty.
|
||
|
{
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
$basepath = $basedir->getPath();
|
||
|
|
||
|
$newPaths[$size] = $path;
|
||
|
|
||
|
$webpformat1 = $basepath . $file->getFileName() . '.webp';
|
||
|
$webpformat2 = $basepath . $file->getFileBase() . '.webp';
|
||
|
|
||
|
$avifformat = $basepath . $file->getFileName() . '.avif';
|
||
|
$avifformat2 = $basepath . $file->getFileBase() . '.avif';
|
||
|
|
||
|
|
||
|
if ($check_exists)
|
||
|
{
|
||
|
if (file_exists($webpformat1))
|
||
|
$newPaths[$size . '_webp'] = $webpformat1;
|
||
|
}
|
||
|
else {
|
||
|
$newPaths[$size . '_webp'] = $webpformat1;
|
||
|
}
|
||
|
|
||
|
if ($check_exists)
|
||
|
{
|
||
|
if(file_exists($webpformat2))
|
||
|
$newPaths[$size . '_webp2'] = $webpformat2;
|
||
|
}
|
||
|
else {
|
||
|
$newPaths[$size . '_webp2'] = $webpformat2;
|
||
|
}
|
||
|
|
||
|
if ($check_exists)
|
||
|
{
|
||
|
if (file_exists($avifformat))
|
||
|
{
|
||
|
$newPaths[$size . '_avif'] = $avifformat;
|
||
|
}
|
||
|
}
|
||
|
else {
|
||
|
$newPaths[$size . '_avif'] = $avifformat;
|
||
|
}
|
||
|
|
||
|
if ($check_exists)
|
||
|
{
|
||
|
if (file_exists($avifformat2))
|
||
|
{
|
||
|
$newPaths[$size . '_avif2'] = $avifformat2;
|
||
|
}
|
||
|
}
|
||
|
else {
|
||
|
$newPaths[$size . '_avif2'] = $avifformat2;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return $newPaths;
|
||
|
}
|
||
|
|
||
|
/** Get Webp Paths that might be generated and offload them as well.
|
||
|
* Paths - size : path values
|
||
|
*/
|
||
|
public function add_webp_paths($paths)
|
||
|
{
|
||
|
$paths = $this->getWebpPaths($paths, true);
|
||
|
//Log::addDebug('Add S3 Paths - ', array($paths));
|
||
|
return $paths;
|
||
|
}
|
||
|
|
||
|
|
||
|
public function remove_webp_paths($paths)
|
||
|
{
|
||
|
$paths = $this->getWebpPaths($paths, false);
|
||
|
//Log::addDebug('Remove S3 Paths', array($paths));
|
||
|
|
||
|
return $paths;
|
||
|
}
|
||
|
|
||
|
// GetbyURL can't find thumbnails, only the main image. Check via extrainfo method if we can find needed filetype
|
||
|
// @param $bool Boolean
|
||
|
// @param $fileObj FileModel The webp file we are searching for
|
||
|
// @param $url string The URL of the main file ( aka .jpg )
|
||
|
// @param $imagebaseDir DirectoryModel The remote path / path this all takes place at.
|
||
|
public function fixWebpRemotePath($bool, $fileObj, $url, $imagebaseDir)
|
||
|
{
|
||
|
$source_id = $this->getSourceIDByURL($url);
|
||
|
if (false === $source_id)
|
||
|
return false;
|
||
|
|
||
|
$item = $this->getItemById($source_id);
|
||
|
$extra_info = $item->extra_info();
|
||
|
|
||
|
if (! isset( $extra_info['objects'] ) || ! is_array( $extra_info['objects'] ) )
|
||
|
return false;
|
||
|
|
||
|
$bool = false;
|
||
|
|
||
|
foreach($extra_info['objects'] as $data)
|
||
|
{
|
||
|
$sourceFile = $data['source_file'];
|
||
|
if ($sourceFile == $fileObj->getFileName())
|
||
|
{
|
||
|
$bool = true;
|
||
|
return $fileObj;
|
||
|
break;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return $bool;
|
||
|
|
||
|
}
|
||
|
|
||
|
}
|