Tworzę aplikację za pomocą edytora Bespin i localStorage HTML5. Przechowuje wszystkie pliki lokalnie i pomaga w gramatyce, używa JSLint i kilku innych parserów CSS i HTML, aby pomóc użytkownikowi.
Chcę obliczyć, jaka część limitu localStorage została wykorzystana i ile w rzeczywistości zostało. Czy jest to dziś możliwe? Myślałem, żeby nie po prostu obliczać przechowywanych bitów. Ale z drugiej strony nie jestem pewien, co więcej jest tego, czego nie potrafię zmierzyć.
javascript
size
storage
local-storage
capacity
JeroenEijkhof
źródło
źródło
Odpowiedzi:
Możesz uzyskać przybliżony pomysł, używając metod JSON, aby zamienić cały obiekt localStorage na ciąg JSON:
JSON.stringify(localStorage).length
Nie wiem, jak dokładny byłby bajt, zwłaszcza z kilkoma bajtami dodanych znaczników, jeśli używasz dodatkowych obiektów - ale myślę, że to lepsze niż myślenie, że przesuwasz tylko 28 KB, a zamiast tego robisz 280 KB (lub vice- versa).
źródło
Nie znalazłem uniwersalnego sposobu na uzyskanie pozostałego limitu w przeglądarkach, których potrzebowałem, ale odkryłem, że po osiągnięciu limitu pojawia się komunikat o błędzie. W każdej przeglądarce jest to oczywiście inne.
Aby to osiągnąć, użyłem tego małego skryptu:
for (var i = 0, data = "m"; i < 40; i++) { try { localStorage.setItem("DATA", data); data = data + data; } catch(e) { var storageSize = Math.round(JSON.stringify(localStorage).length / 1024); console.log("LIMIT REACHED: (" + i + ") " + storageSize + "K"); console.log(e); break; } } localStorage.removeItem("DATA");
Stąd otrzymałem te informacje:
Google Chrome
Mozilla Firefox
Safari
Internet Explorer, Edge (społeczność)
Moje rozwiązanie
Jak dotąd moim rozwiązaniem jest dodawanie dodatkowego połączenia za każdym razem, gdy użytkownik coś zapisał. A jeśli wyjątek zostanie przechwycony, powiedziałbym im, że kończy im się pojemność pamięci.
Edytuj: Usuń dodane dane
Zapomniałem wspomnieć, że aby to zadziałało, musisz usunąć
DATA
pierwotnie ustawiony element. Zmiana jest odzwierciedlona powyżej za pomocą funkcji removeItem () .źródło
i
kiedy to zostało osiągnięte w każdym przypadku?IE8 implementuje
remainingSpace
właściwość w tym celu:alert(window.localStorage.remainingSpace); // should return 5000000 when empty
Niestety wydaje się, że nie jest to dostępne w innych przeglądarkach. Nie jestem jednak pewien, czy realizują coś podobnego.
źródło
Możesz użyć poniższej linii, aby dokładnie obliczyć tę wartość, a tutaj znajduje się jsfiddle, aby zilustrować jej użycie
alert(1024 * 1024 * 5 - escape(encodeURIComponent(JSON.stringify(localStorage))).length);
źródło
Wpadłem na to dzisiaj podczas testowania (przekraczając limit miejsca) i przygotowałem rozwiązanie. IMO, wiedząc, jaki jest limit i gdzie jesteśmy w stosunku, jest znacznie mniej wartościowe niż wdrożenie funkcjonalnego sposobu na dalsze przechowywanie poza limitem.
Dlatego zamiast próbować porównywać rozmiary i sprawdzać pojemność, reagujmy, gdy osiągniemy limit, zmniejszamy naszą obecną pamięć o jedną trzecią i wznawiamy przechowywanie. Jeśli wspomniana redukcja się nie powiedzie, przestań przechowywać.
set: function( param, val ) { try{ localStorage.setItem( param, typeof value == 'object' ? JSON.stringify(value) : value ) localStorage.setItem( 'lastStore', new Date().getTime() ) } catch(e){ if( e.code === 22 ){ // we've hit our local storage limit! lets remove 1/3rd of the entries (hopefully chronologically) // and try again... If we fail to remove entries, lets silently give up console.log('Local storage capacity reached.') var maxLength = localStorage.length , reduceBy = ~~(maxLength / 3); for( var i = 0; i < reduceBy; i++ ){ if( localStorage.key(0) ){ localStorage.removeItem( localStorage.key(0) ); } else break; } if( localStorage.length < maxLength ){ console.log('Cache data reduced to fit new entries. (' + maxLength + ' => ' + localStorage.length + ')'); public.set( param, value ); } else { console.log('Could not reduce cache size. Removing session cache setting from this instance.'); public.set = function(){} } } } }
Ta funkcja znajduje się w obiekcie opakowującym, więc public.set po prostu wywołuje samą siebie. Teraz możemy dodać miejsce do przechowywania i nie martwić się, jaki jest przydział ani jak blisko jesteśmy. Jeśli pojedynczy sklep przekracza 1/3, wielkość przydziału to miejsce, w którym ta funkcja przestanie wybierać i zakończy przechowywanie, a w tym momencie nie powinieneś i tak buforować, prawda?
źródło
Aby dodać do wyników testu przeglądarki:
Firefox i = 22.
Safari w wersji 5.0.4 na moim Macu nie zawiesiło się. Błąd jako Chrome. i = 21.
Opera informuje użytkownika, że witryna chce przechowywać dane, ale nie ma wystarczająco dużo miejsca. Użytkownik może odrzucić wniosek, zwiększyć limit do wymaganej kwoty lub do kilku innych limitów lub ustawić go na nieograniczony. Idź do opera: webstorage, aby powiedzieć, czy ta wiadomość się pojawi, czy nie. i = 20. Zgłoszony błąd jest taki sam jak w Chrome.
Tryb standardów IE9 Błąd jako Chrome. i = 22.
Przeglądarka IE9 w trybie standardów IE8 Komunikat konsoli „Błąd: za mało miejsca na wykonanie tej operacji”. i = 22
IE9 w starszych trybach błąd obiektu. i = 22.
IE8 Nie mam kopii do przetestowania, ale pamięć lokalna jest obsługiwana (http://stackoverflow.com/questions/3452816/does-ie8-support-out-of-the-box-in-localstorage)
IE7 i starsze Nie obsługuje pamięci lokalnej.
źródło
Możesz przetestować swoją przeglądarkę za pomocą tego testu obsługi magazynu internetowego
Przetestowałem Firefoksa zarówno na moim tablecie z Androidem, jak i laptopie z systemem Windows oraz Chromium tylko w wynikach Windows:
Firefox (Windows):
Firefox (Android):
Chrom (Windows):
Aktualizacja
W przeglądarce Google Chrome w wersji 52.0.2743.116 m (64-bitowe) limity są nieco niższe dla
5101k
znaków. Oznacza to, że maksymalna dostępna liczba może ulec zmianie w wersjach.źródło
Chciałbym móc to dodać w komentarzu - za mało przedstawiciela, przepraszam.
Przeprowadziłem kilka testów perf - spodziewając się, że JSON.stringify (localStorage) .length będzie kosztowną operacją przy dużym obłożeniu localStorage.
http://jsperf.com/occupied-localstorage-json-stringify-length
Rzeczywiście tak jest - około 50 razy droższe niż śledzenie tego, co przechowujesz, i pogarsza się, im pełniejsza jest pamięć lokalna.
źródło
Ta funkcja pobiera dokładną dostępną / pozostałą pamięć:
Zrobiłem zestaw przydatnych funkcji dla localStorage * tutaj *
http://jsfiddle.net/kzq6jgqa/3/
function getLeftStorageSize() { var itemBackup = localStorage.getItem(""); var increase = true; var data = "1"; var totalData = ""; var trytotalData = ""; while (true) { try { trytotalData = totalData + data; localStorage.setItem("", trytotalData); totalData = trytotalData; if (increase) data += data; } catch (e) { if (data.length < 2) break; increase = false; data = data.substr(data.length / 2); } } localStorage.setItem("", itemBackup); return totalData.length; } // Examples document.write("calculating.."); var storageLeft = getLeftStorageSize(); console.log(storageLeft); document.write(storageLeft + ""); // to get the maximum possible *clear* the storage localStorage.clear(); var storageMax = getLeftStorageSize();
Pamiętaj, że nie jest to bardzo szybkie, więc nie używaj go cały czas.
Dzięki temu dowiedziałem się również, że: nazwa przedmiotu zajmie tyle miejsca, ile jego długość, wartość przedmiotu również zajmie tyle miejsca, ile ich długość.
Maksymalne miejsce, które mam - wszystko około 5M:
Na skrzypcach znajdziesz kod z komentarzem, aby zobaczyć postęp w konsoli.
Zajęło mi to trochę czasu, mam nadzieję, że to pomoże ☺
źródło
try { var count = 100; var message = "LocalStorageIsNOTFull"; for (var i = 0; i <= count; count + 250) { message += message; localStorage.setItem("stringData", message); console.log(localStorage); console.log(count); } } catch (e) { console.log("Local Storage is full, Please empty data"); // fires When localstorage gets full // you can handle error here ot emply the local storage }
źródło
Musiałem faktycznie zasymulować i przetestować, co zrobi mój moduł, gdy pamięć jest pełna, więc musiałem uzyskać dokładną dokładność, kiedy pamięć jest pełna, a nie akceptowaną odpowiedź, która traci tę precyzję w tempie i ^ 2.
Oto mój skrypt, który powinien zawsze dawać precyzję 10 po osiągnięciu limitu pamięci i dość szybko, pomimo kilku łatwych optymalizacji ... EDYCJA: Poprawiłem skrypt z dokładną precyzją:
function fillStorage() { var originalStr = "1010101010"; var unfold = function(str, times) { for(var i = 0; i < times; i++) str += str; return str; } var fold = function(str, times) { for(var i = 0; i < times; i++) { var mid = str.length/2; str = str.substr(0, mid); } return str; } var runningStr = originalStr; localStorage.setItem("filler", runningStr); while(true) { try { runningStr = unfold(runningStr, 1); console.log("unfolded str: ", runningStr.length) localStorage.setItem("filler", runningStr); } catch (err) { break; } } runningStr = fold(runningStr, 1); var linearFill = function (str1) { localStorage.setItem("filler", localStorage.getItem("filler") + str1); } //keep linear filling until running string is no more... while(true) { try { linearFill(runningStr) } catch (err) { runningStr = fold(runningStr, 1); console.log("folded str: ", runningStr.length) if(runningStr.length == 0) break; } } console.log("Final length: ", JSON.stringify(localStorage).length) }
źródło
To może komuś pomóc. W chrome można poprosić użytkownika o zezwolenie na użycie większej ilości miejsca na dysku w razie potrzeby:
// Request Quota (only for File System API) window.webkitStorageInfo.requestQuota(PERSISTENT, 1024*1024, function(grantedBytes) { window.webkitRequestFileSystem(PERSISTENT, grantedBytes, onInitFs, errorHandler); }, function(e) { console.log('Error', e); });
Odwiedź https://developers.google.com/chrome/whitepapers/storage#asking_more, aby uzyskać więcej informacji.
źródło