getgrav / grav-plugin-admin

Grav Admin Plugin
http://getgrav.org
MIT License
355 stars 225 forks source link

Uploading an image to page media throws a WebKitBlobResource error 4. with latest safari. #1469

Closed iamlinkus closed 3 years ago

iamlinkus commented 6 years ago

When I try to upload an image file through the admin it shows up as an empty file (also empty image files in the file system) and console throws this:

The operation couldn’t be completed. (WebKitBlobResource error 4.)

The image I want to upload is this.

Grav version v1.4.5 Admin version v1.8.4 Safari version 11.1.1 (13605.2.8)

Any ideas why this started happening? It's also impossible to delete the file in normal edit mode, only by switching to expert and deleting it fixes the page.

Sometimes even got an error in the console that trafi-intro-device@2x.png was not found (even though I never uploaded anything with the retina suffix (@2x). I usually upload -retina suffixed retina files, because grav admin seems to not like files with an @ in their name.

rhukster commented 6 years ago

Does it work for you with other browsers? Chrome/ Firefox?

iamlinkus commented 6 years ago

@rhukster I can confirm that chrome works as expected. Seems like it's just a safari issue.

jannejava commented 5 years ago

Did you find a solution to this?

rhukster commented 5 years ago

It works fine in Safari 12 on Mojave, as well as Chrome, Firefox etc. Can you guys try with an updated Safari version or Technology Preview release?

https://developer.apple.com/safari/download/

jannejava commented 5 years ago

I cannot re-create this myself either but got screen dumps from a user (Safari 12) with this error. The only I can find regarding this is that the error can happen when you try to upload a folder in Safari. Works in Chrome BTW.

rhukster commented 5 years ago

I had Googled and found the same issue reported in many places regarding uploading of folders.

thomasliew commented 6 months ago

I've encountered this kind of problem, if you are using too much memory in Safari (you can see it in the timeline), then there is a certain chance that this will happen, and it will not occur after killing Safari and trying again. When I handle more than 2000 photos, I found that Safari was using more and more memory, and I tried to put var img = new Image() in the loop out of the loop, and the memory usage stabilized. It also solves the problem you described. Hope it helps.

// html:
// <input type="file" id="files" name="files" multiple onchange="handleFiles(this.files)" />
//    <img id="img" src="" alt="" />
const img = document.getElementById('img');
        handleFiles = function (files, index = 0) {
            if (index >= files.length) {
                return;
            }

            var file = files[index];
            getThumb(file, function () {
                handleFiles(files, index + 1);
            });
        }

        function getThumb(file, callback) {
            let objectUrl = URL.createObjectURL(file);
            // let img = new Image(); //DO NOT USE THIS!
            img.onload = function () {
                processImage(img, objectUrl);
                URL.revokeObjectURL(objectUrl);
                window.setTimeout(function () {
                    callback();
                }, 0);
            }
            img.onerror = function (error) {
                console.log(file);
                console.log('-'.repeat(20));
                URL.revokeObjectURL(objectUrl);
                window.setTimeout(function () {
                    callback();
                }, 0);
            }
            img.src = objectUrl;
        }

        function processImage(img, objectUrl) {
            let canvas = document.createElement('canvas');
            let ctx = canvas.getContext('2d');
            ctx.drawImage(img, 0, 0);
            let b64 = canvas.toDataURL('image/jpeg', 0.8).replace(/^data:image\/(png|jpg|jpeg);base64,/, '');
            let p = document.createElement('p');
            p.innerHTML = objectUrl;
            document.body.appendChild(p);

            ctx = null;
            dataURL = null;
            canvas = null;
        }
image