0

I currently have a script that uses curl to check the file size of about 3000 images every time the a user visits the page.. this is because every time the content might change.

If it matches the size of 7442 bytes it changes the path of the image, if it doesn't it, maintains it's source.

The image URL is stored on $variable, mysql, and both remote and local xml file. But the image iself is always stored remotely.

$image = 'http://remoteserver.com/user22.jpg';
//Check if all thumbs are ok real and available
$ch = curl_init($image);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, TRUE);
curl_setopt($ch, CURLOPT_HEADER, TRUE);
curl_setopt($ch, CURLOPT_NOBODY, TRUE);

$data = curl_exec($ch);
$size = curl_getinfo($ch, CURLINFO_CONTENT_LENGTH_DOWNLOAD);
curl_close($ch);
if($size == 7442){
    echo '<img src="https://www.newdomain.com/tmp.jpg" height="190.11"/></a>';
} else {
    echo '<img src="' . $image . '" alt="' . $user . '" /></a>';
}

When it's activated the page takes about 40 seconds to load, when it's commented out, it takes 3 seconds. But it gets executed every time any user visits the webpage or if I execute curl before adding data to mysql and change address in mysql,it causes a massive delay in loading that info onto that mysql and thus not showing all the images.

I know there's a lot depending on this check, both server response times, php config, and so on.. But I really need this image file check to work, and can't afford to have a 40 second load time every time a user visits the page.

Any suggestions/help? Thank you

Matt S
  • 14,976
  • 6
  • 57
  • 76
Ageless
  • 5
  • 3
  • 3
    Run it as a background process, not as part of a web request – Mark Baker Oct 11 '17 at 12:09
  • 1
    You could use memcache or something to store the collection of image URL reroutes. A scheduled background service (PHP script) could run periodically to check the files sizes and add the rerouted URLs to memcache. You get the image URL for a function that looks in memcache and returns the key if it's found or returns the original URL if it's not. – John Corry Oct 11 '17 at 12:11
  • Thank you Mark Baker and Jcorry. The original urls are actually stored in mysql, but only the url, no size info. That would banish the need for memcache ? – Ageless Oct 11 '17 at 12:37

1 Answers1

0

As others have suggested in comments, I would create a background process to check file sizes and update mysql completely separate from the page request. This is far more efficient if multiple users request the same images.

However, if it really needs to done on page load, another option for a better user experience is to do the check from the browser. Load the page with the stored image paths, then use JS to request the file sizes and change the image paths as needed. E.g.

var images = document.getElementsByTagName('img'); 
for(var i = 0; i < images.length; i++) {
    var xhr = new XMLHttpRequest();
    xhr.open("HEAD", images[i].src, true);
    xhr.onreadystatechange = function() {
        if (this.readyState == this.DONE) {
            if (parseInt(xhr.getResponseHeader("Content-Length"))) === 7442) {
                images[i].src = 'https://www...'; // New path
            }
        }
    };
    xhr.send();
}

(Untested, but you get the idea. Adapted from another SO answer.)

Then when it's all done you can make one AJAX POST to your web app to update MySQL if needed. Also keep in mind this will attempt to make many concurrent requests to the server hosting the images, so it may have a performance impact.

Matt S
  • 14,976
  • 6
  • 57
  • 76
  • Thank you Matt, I will try with Javascript/Ajax, since with curl everything seems to stall, it might be the best option. Will say something a.s.a.p. – Ageless Oct 12 '17 at 08:53