Package com.fasterxml.storemate.shared.compress

Source Code of com.fasterxml.storemate.shared.compress.Compressors

package com.fasterxml.storemate.shared.compress;

import java.io.*;

import com.fasterxml.storemate.shared.ByteContainer;
import com.fasterxml.storemate.shared.util.WithBytesCallback;
import com.ning.compress.gzip.OptimizedGZIPInputStream;
import com.ning.compress.gzip.OptimizedGZIPOutputStream;
import com.ning.compress.lzf.ChunkDecoder;
import com.ning.compress.lzf.LZFChunk;
import com.ning.compress.lzf.LZFEncoder;
import com.ning.compress.lzf.LZFInputStream;
import com.ning.compress.lzf.LZFOutputStream;
import com.ning.compress.lzf.util.ChunkDecoderFactory;

public class Compressors
{
    // TODO: perhaps make pluggable?
    protected final static ChunkDecoder lzfDecoder;
    static {
        lzfDecoder = ChunkDecoderFactory.optimalInstance();
    }
   
    /*
    /**********************************************************************
    /* Verification
    /**********************************************************************
     */

    public static boolean isCompressed(byte[] data, int offset, int len) {
        return findCompression(data, offset, len) != null;
    }

    public static boolean isCompressed(ByteContainer data) {
        return findCompression(data) != null;
    }
   
    public static Compression findCompression(byte[] data, int offset, int len)
    {
        if (len < 3) {
            return null;
        }
        byte b = data[offset];
        if (b == LZFChunk.BYTE_Z) { // LZF: // starts with 'ZV' == 0x5A, 0x56
            if (data[offset+1] == LZFChunk.BYTE_V) {
                byte third = data[offset+2];
                if (third == LZFChunk.BLOCK_TYPE_COMPRESSED || third == LZFChunk.BLOCK_TYPE_NON_COMPRESSED) {
                    return Compression.LZF;
                }
            }
        } else if (b == 0x1F) { // GZIP: // starts with 0x1F, 0x8B (0x8B1F, little-endian)
            if ((data[offset+1] & 0xFF) == 0x8B) {
                return Compression.GZIP;
            }
        }
        return null;
    }

    public static Compression findCompression(ByteContainer data)
    {
        if (data.byteLength() < 3) {
            return null;
        }
        byte b = data.get(0);
        if (b == LZFChunk.BYTE_Z) { // LZF: // starts with 'ZV' == 0x5A, 0x56
            if (data.get(1) == LZFChunk.BYTE_V) {
                byte third = data.get(2);
                if (third == LZFChunk.BLOCK_TYPE_COMPRESSED || third == LZFChunk.BLOCK_TYPE_NON_COMPRESSED) {
                    return Compression.LZF;
                }
            }
        } else if (b == 0x1F) { // GZIP: // starts with 0x1F, 0x8B (0x8B1F, little-endian)
            if ((data.get(1) & 0xFF) == 0x8B) {
                return Compression.GZIP;
            }
        }
        return null;
    }
   
    /*
    /**********************************************************************
    /* Compress
    /**********************************************************************
     */

    public static byte[] gzipCompress(byte[] data) throws IOException {
        return gzipCompress(data, 0, data.length);
    }

    public static byte[] gzipCompress(byte[] data, int offset, int len) throws IOException
    {
        // assume 50% compression rate
        ByteArrayOutputStream bytes = new ByteArrayOutputStream(len>>1);
        OptimizedGZIPOutputStream out = new OptimizedGZIPOutputStream(bytes);
        out.write(data, offset, len);
        out.close();
        return bytes.toByteArray();
    }

    public static byte[] gzipCompress(ByteContainer data) throws IOException
    {
        // assume 50% compression rate
        ByteArrayOutputStream bytes = new ByteArrayOutputStream(data.byteLength()>>1);
        OptimizedGZIPOutputStream out = new OptimizedGZIPOutputStream(bytes);
        data.writeBytes(out);
        out.close();
        return bytes.toByteArray();
    }
   
    public static byte[] lzfCompress(byte[] data) throws IOException {
        return lzfCompress(data, 0, data.length);
    }

    public static byte[] lzfCompress(byte[] data, int offset, int len) throws IOException {
        return LZFEncoder.encode(data, offset, len);
    }

    public static byte[] lzfCompress(ByteContainer data) throws IOException {
        return data.withBytes(new WithBytesCallback<byte[]>() {
            @Override
            public byte[] withBytes(byte[] buffer, int offset, int length) {
                try {
                    return LZFEncoder.encode(buffer, offset, length);
                } catch (Exception e) {
                    throw new IllegalArgumentException(e);
                }
            }
        });
    }
   
    public static OutputStream compressingStream(OutputStream out, Compression comp) throws IOException
    {
        if (comp != null) {
            switch (comp) {
            case NONE:
                break;
            case LZF:
                return new LZFOutputStream(out);
            case GZIP:
                return new OptimizedGZIPOutputStream(out);
            default: // sanity check
                throw new IllegalArgumentException("Unrecognized compression type: "+comp);
            }
        }
        return out;
    }
   
    /*
    /**********************************************************************
    /* Uncompress
    /**********************************************************************
     */
   
    public static InputStream uncompressingStream(InputStream in, Compression comp)
        throws IOException
    {
        if (comp != null) {
            switch (comp) {
            case NONE:
                break;
            case LZF:
                return new LZFInputStream(in);
            case GZIP:
                return new OptimizedGZIPInputStream(in);
            default: // sanity check
                throw new IllegalArgumentException("Unrecognized compression type: "+comp);
            }
        }
        return in;
    }

    public static ByteContainer uncompress(ByteContainer data, Compression comp, int expSize)
            throws IOException
    {
        if (comp != null) {
            switch (comp) {
            case NONE:
                break;
            case LZF:
                return lzfUncompress(data);
            case GZIP:
                return gzipUncompress(data, expSize);
            default: // sanity check
                throw new IllegalArgumentException("Unrecognized compression type: "+comp);
            }
        }
        return data;
    }

    public static ByteContainer gzipUncompress(ByteContainer compData, int expSize)
        throws IOException
    {
      return ByteContainer.simple(gzipUncompress(compData.asBytes(), expSize));
    }
   
    public static byte[] gzipUncompress(byte[] compData, int expSize)
            throws IOException
    {
        if (expSize <= 0) {
            return gzipUncompress(compData);
        }
        byte[] buffer = new byte[expSize];
        OptimizedGZIPInputStream in = new OptimizedGZIPInputStream(new ByteArrayInputStream(compData));
        int offset = 0;
        int left = buffer.length;
        int count;

        while (left > 0 && (count = in.read(buffer, offset, left)) > 0) {
            offset += count;
            left -= count;
        }
        // should have gotten exactly expected amount
        try {
            if (offset < expSize) {
                throw new IOException("Corrupt GZIP/Deflate data: expected "+expSize+" bytes, got "+offset);
            }
            // and no more
            if (in.read() != -1) {
                throw new IOException("Corrupt GZIP/Deflate data: expected "+expSize+" bytes, got at least one more");
            }
        } finally {
            try { in.close(); } catch (IOException e) { }
        }
        return buffer;
    }

    public static byte[] gzipUncompress(byte[] compData)
        throws IOException
    {
        OptimizedGZIPInputStream in = new OptimizedGZIPInputStream(new ByteArrayInputStream(compData));
        ByteArrayOutputStream bytes = new ByteArrayOutputStream(16 + (compData.length << 1));
        byte[] buffer = new byte[500];
        int count;

        while ((count = in.read(buffer)) > 0) {
            bytes.write(buffer, 0, count);
        }
        in.close();
        bytes.close();
        return bytes.toByteArray();
    }
   
    public static byte[] lzfUncompress(byte[] data) throws IOException
    {
        return lzfDecoder.decode(data);
    }

    public static ByteContainer lzfUncompress(ByteContainer data) throws IOException
    {
        return data.withBytes(new WithBytesCallback<ByteContainer>() {
      @Override
      public ByteContainer withBytes(byte[] buffer, int offset, int length)
        throws IllegalArgumentException
      {
        try {
          return ByteContainer.simple(lzfDecoder.decode(buffer, offset, length));
        } catch (IOException e) {
          throw new IllegalArgumentException("Bad LZF data to uncompress ("+length+" bytes): "+e.getMessage(), e);
        }
      }
      });
    }
}
TOP

Related Classes of com.fasterxml.storemate.shared.compress.Compressors

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.