3 Stimmen

firefox hohen Speicher (RAM) Verbrauch, wie man mit Javascript zu befreien?

Ich bemerke, dass nach der Verwendung von Firefox für ein paar Stunden bekommt es mehr als 2gb RAM-Speicher. Es passiert vor allem, wenn ich große Dateien (100mb-400mb) mit Ajax-Uploader hochladen, und passiert auch, wenn ich zu viele Bilder öffnen (zum Beispiel 16mb der gesamten Bilder auf einer Webseite).

Das Problem ist, dass auch nach dem Upload zu beenden oder nach dem Schließen der Bilder Seiten der Speicher nicht immer frei, Firefox haben noch 2gb ram Speicher. Gibt es eine Möglichkeit, von Javascript zu machen, Firefox frei den Speicher, zum Beispiel beim Upload beenden oder nach Bilder geladen oder geschlossen werden?

EDITAR Von about:memory : 1.172,03 MB (100,0%) -- ausdrücklich

1.000,00 MB (85,32%) -- js

863,97 MB (73,72%) -- compartment([System Principal], 0x5083000)

819,31 MB (69,91%) Zeichenfolgen-Zeichen

Wie kann ich die String-Zeichen dass ich mir ziemlich sicher bin, dass dies geschieht, wenn die Dateien in den Speicher eingelesen und dann mit Ajax hochgeladen werden?

EDIT 2

Hier ist die auffällige Funktion, die diesen Speicherverbrauch verursacht:

function uploadAjax(file, startByte, index)
{
    if(startByte==0)
    {
        $('#progress'+index).html(' ').progressbar( "destroy" ).progressbar();
        $('#asyncuploadsingle'+index).attr('disabled', true);
    }

    var size        = file.size;
    var chunkSize   = 2097152;//2 megabyte
    var endByte     = chunkSize + startByte;
    var isLast      = (size - endByte <= 0);
    var chunk       = file;
    var xhr         = new XMLHttpRequest();//prepare xhr for upload
    var chunkNum    = endByte / chunkSize;

    if(chunkSize == 0)//no divide
    {
        chunk   = file;
        isLast  = true;
    }
    else if(file.mozSlice) // moz slice
    {
        chunk   = file.mozSlice(startByte, endByte);
    }
    else if(file.webkitSlice) //webkit slice
    {
        chunk   = file.webkitSlice(startByte, endByte);
    }
    else if(file.slice) // w3c slice
    {
        chunk   = file.slice(startByte, chunkSize);
    }
    else
    {
        chunk   = file;
        isLast  = true;
    }

    //progress function, with ajax upload progress can be monitored
    xhr.upload.addEventListener('progress', function(e)
    {
        if (e.lengthComputable) 
        {
            var perc = Math.round((e.loaded + chunkNum * chunkSize - chunkSize) * 100 / size);
            //console.log(perc+':'+index);
            $('#progress'+index).progressbar("option", "value", perc);
        }  
    }, false); 

    xhr.upload.onabort=function(e)  {   
        finishUp(index,'Aborted');
    };  

    xhr.upload.addEventListener('error', function(e){
        finishUp(index, this.responseText+'--->'+name);
    }, false);  

    xhr.onreadystatechange=function()
    {
        if(this.readyState == 4 && this.status == 200)
        {
            try
            {
                var ret = JSON.parse(this.responseText);

                if(isLast)
                {
                    finishUp(index,'');
                }
                else if(ret.status == 'error')
                {
                    throw ret.info;
                }
                else
                {
                    uploadAjax(file, endByte, index);
                }
            }
            catch(err)
            {
                finishUp(index, err);
            }

            delete chunk;
        }
    };

    var path    = get_final_path();
    var url     = "filetransfer/uploadfiles.php?ax-file-name="+encodeURIComponent(file.name)+"&ax-file-path="+encodeURIComponent(path)+'&ax-start-byte='+startByte;

    xhr.open("POST", url, true);
    xhr.setRequestHeader('Cache-Control', 'no-cache');
    xhr.setRequestHeader('X-Requested-With', 'XMLHttpRequest');//header
    xhr.setRequestHeader('Content-Type', 'application/octet-stream');//generic stream header

    /*var reader = new FileReader();
    reader.onload = function(evt) {  
        xhr.sendAsBinary(evt.target.result);  
    };  
    reader.readAsBinaryString(chunk);
    */  
    xhr.send(chunk);

    return xhr;
}

Gibt es einen Punkt, an dem man es optimieren kann oder an dem Objekte frei werden?

2voto

Bob Davies Punkte 2181

Ich verwende das Addon Memoryfox, um den Speicher von Firefox auf ein Minimum zu reduzieren. Allerdings verwende ich es nur für den Browser (und aktiviere die Option "Alle Prozesse" nicht), da ich Photoshop/Lightroom häufig verwende und es im Modus "Alle Prozesse" dazu neigt, diese zu stören (es ist ziemlich aggressiv).

Gedächtnisfuchs

Aber auch damit bläht sich Firefox immer noch auf. Am besten entfernen Sie alle Addons, die Sie nicht verwenden, und deaktivieren Sie die, die Sie nicht oft verwenden. Wenn Sie viele Plugins haben, gibt es einige, die große Speicherprobleme mit Firefox verursachen, und einige von ihnen sind unter dem Punkt MemShrink-Projekt .

In Bezug auf den Code in Ihren Änderungen gibt es mehrere Gründe, warum Sie möglicherweise zusätzlichen Speicherbedarf haben:

1) Die Verwendung anonymer Funktionen bedeutet, dass bei jeder Ausführung von uploadAjax für jede einzelne Funktion eine neue Funktion im Speicher erstellt wird. Definieren Sie Ihre Funktionen außerhalb von uploadAjax und verweisen Sie dann auf sie, um Duplikate im Speicher zu vermeiden.

2) delete xhr; wenn Sie damit fertig sind. Normalerweise ist das nicht erforderlich, aber wenn Sie viele Uploads durchführen, kann es sein, dass einige Daten zurückbleiben.

3) Sie rufen im Wesentlichen uploadAjax(file, endByte, index); sowohl rekursiv als auch innerhalb einer anonymen Funktion, was bedeutet, dass alles, was Sie in den Aufrufen der höheren Ebene erstellen, noch existieren kann, während die Aufrufe der niedrigeren Ebene ausgeführt werden. Dies führt zu mehreren In-Memory xhr y chunk . Erwägen Sie einen Anruf uploadAjax auf eine andere Art und Weise (z. B. durch Auslösen eines Ereignisses und anschließenden Zugriff auf dieselbe Datei und xhr von einem Global aus oder mit einem kurzen Timer, um eine Ausführungsunterbrechung einzuführen). Ich würde wahrscheinlich ersteres bevorzugen, obwohl es schwer zu sagen ist, ohne es selbst zu testen).

1voto

JAB Punkte 19937

Es ist nicht das, was Sie wollen, aber es klingt so, als ob Sie es brauchen:

https://addons.mozilla.org/en-US/firefox/addon/memory-restart/

Sie können Schwellenwerte für Warnungen festlegen und sogar einen automatischen Neustart veranlassen.

(Obwohl, wie ich gerade mit freundlicher Genehmigung von Rob W. entdeckt habe, about:memory erlaubt es Ihnen, Müll zu sammeln und andere Speicherbereinigungen vorzunehmen (zumindest in Firefox 13; ich habe nicht überprüft, wie weit zurück es geht, da ich keine früheren Versionen von Firefox auf diesem Rechner habe und ich nicht wirklich die Zeit habe, frühere Versionen herunterzuladen und zu installieren, um sie zu testen). Ziemlich klasse. Sie sollten das vielleicht zuerst ausprobieren, auch wenn es nicht automatisch ist, wenn Ihnen die automatischen Neustarts von Firefox nicht zusagen).

0voto

Someth Victory Punkte 4372

Das ist das Schlimmste, was hinter Firefox passiert... Ich hatte dieses Problem früher auch. Die Sache ist die, dass man den Browser neu starten muss, damit etwas Speicher frei wird, aber nicht alles. Das ist das Hauptproblem für eine One Page Application, die hauptsächlich Dom-Ersatz verwendet, ohne die Seite zu aktualisieren.

0voto

STW Punkte 42452

Es gibt keine Javascript-API in Firefox, die Ihr Problem lösen könnte. Die Speichernutzung in Firefox ist eine der am längsten bestehenden Beschwerden, trotz vieler Bemühungen, den Fußabdruck zu verbessern. Ihre Möglichkeiten sind größtenteils beschränkt auf:

(a) Neustart von Firefox, um den Prozess zu beenden

(

(

F h

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X