ajax - Gzip'in JavaScript ile uygulanması


Küçük, sabit boyutlu bir sunucu tarafı önbelleğine JSON verisi depolaması gereken bir Web uygulaması yazıyorum (düşünün: Opensocial kotaları). Sunucu üzerinde kontrolüm yok.

Sunucu tarafı kotasında kalmak için saklanan verinin boyutunu azaltmam gerekiyor ve bunu sunucuya göndermeden önce tarayıcıda JSON olarak stringify edilmiş veriyi gzipleyebilmeyi umuyordum.

Ancak, Gzip'in JavaScript ile uygulanmasına dair pek bir şey bulamıyorum. Verileri yukarı göndermeden önce istemci tarafında nasıl sıkıştırabileceğim konusunda herhangi bir öneriniz var mı?

Cevap #1

Düzenle Unicode dizelerini doğru bir şekilde işleyen daha iyi bir LZW çözümü http://pieroxy.net/blog/pages/lz-string/index.html adresinde görünüyor (Yorumlar için pieroxy’ye teşekkürler).

Herhangi bir gzip uygulamasını bilmiyorum, ancak jsolait kütüphanesi (site görünüşe göre kaybolmuş) LZW sıkıştırma/ açma fonksiyonlarına sahip. Kod LGPL kapsamında korunmaktadır.

// LZW-compress a string
function lzw_encode(s) {
    var dict = {};
    var data = (s + "").split("");
    var out = [];
    var currChar;
    var phrase = data[0];
    var code = 256;
    for (var i=1; i<data.length; i++) {
        currChar=data[i];
        if (dict[phrase + currChar] != null) {
            phrase += currChar;
        }
        else {
            out.push(phrase.length > 1 ? dict[phrase] : phrase.charCodeAt(0));
            dict[phrase + currChar] = code;
            code++;
            phrase=currChar;
        }
    }
    out.push(phrase.length > 1 ? dict[phrase] : phrase.charCodeAt(0));
    for (var i=0; i<out.length; i++) {
        out[i] = String.fromCharCode(out[i]);
    }
    return out.join("");
}

// Decompress an LZW-encoded string
function lzw_decode(s) {
    var dict = {};
    var data = (s + "").split("");
    var currChar = data[0];
    var oldPhrase = currChar;
    var out = [currChar];
    var code = 256;
    var phrase;
    for (var i=1; i<data.length; i++) {
        var currCode = data[i].charCodeAt(0);
        if (currCode < 256) {
            phrase = data[i];
        }
        else {
           phrase = dict[currCode] ? dict[currCode] : (oldPhrase + currChar);
        }
        out.push(phrase);
        currChar = phrase.charAt(0);
        dict[code] = oldPhrase + currChar;
        code++;
        oldPhrase = phrase;
    }
    return out.join("");
}

Cevap #2

Başka bir sorunum vardı, verileri gzip ile kodlamak istemiyordum ama gziplenmiş verileri çözmek istiyordum. Tarayıcı dışında javascript kodu çalıştırıyorum, bu yüzden bunu saf javascript kullanarak çözmem gerekiyor.

Biraz zaman aldı ama JSXGraph kütüphanesinde gziplenmiş verileri okumanın bir yolu olduğunu buldum.

İşte kütüphaneyi bulduğum yer: http://jsxgraph.uni-bayreuth.de/wp/2009/09/29/jsxcompressor-zlib-compressed-javascript-code/ Bunu yapabilecek bağımsız bir araç bile var, JSXCompressor, ve kod LGPL lisanslıdır.

Sadece jsxcompressor.js dosyasını projenize dahil edin ve ardından base 64 ile kodlanmış gziplenmiş veriyi okuyabileceksiniz:

<!doctype html>
</head>
<title>Test gzip decompression page</title>
<script src="jsxcompressor.js"></script>
</head>
<body>
<script>
    document.write(JXG.decompress('<?php 
        echo base64_encode(gzencode("Try not. Do, or do not. There is no try.")); 
    ?>'));
</script>
</html>

Anladım bu istediğiniz şey değil ama yine de burada cevaplıyorum çünkü bunun bazı insanlara yardımcı olacağını düşünüyorum.

Cevap #3

Az önce pako https://github.com/nodeca/pako adresinde zlib'in JavaScript'e portunu yayınladık. Sanırım bu, şimdi deflate/inflate/gzip/ungzip işlemlerinin en hızlı js uygulaması. Ayrıca, demokratik MIT lisansına sahip. Pako tüm zlib seçeneklerini destekliyor ve sonuçları ikili olarak eşit.

Örnek :

var inflate = require('pako/lib/inflate').inflate; 
var text = inflate(zipped, {to: 'string'});

Cevap #4

Bir LZMA uygulamasını bir GWT modülünden bağımsız JavaScript'e taşıdım. Buna LZMA-JS deniyor.

Cevap #5

İşte Javascript ile uygulanmış bazı diğer sıkıştırma algoritmaları:

  • Huffman
  • LZ77

İlgili makaleler