content: package org.apache.lucene.document;
  
  /**
   * Licensed to the Apache Software Foundation (ASF) under one or more
   * contributor license agreements.  See the NOTICE file distributed with
   * this work for additional information regarding copyright ownership.
   * The ASF licenses this file to You under the Apache License, Version 2.0
   * (the "License"); you may not use this file except in compliance with
   * the License.  You may obtain a copy of the License at
   *
   *     http://www.apache.org/licenses/LICENSE-2.0
   *
   * Unless required by applicable law or agreed to in writing, software
   * distributed under the License is distributed on an "AS IS" BASIS,
   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
   * See the License for the specific language governing permissions and
   * limitations under the License.
   */
  
  import java.util.zip.Deflater;
  import java.util.zip.Inflater;
  import java.util.zip.DataFormatException;
  import java.io.ByteArrayOutputStream;
  import org.apache.lucene.util.UnicodeUtil;
  
  /** Simple utility class providing static methods to
   *  compress and decompress binary data for stored fields.
   *  This class uses java.util.zip.Deflater and Inflater
   *  classes to compress and decompress.
   */
  
  public class CompressionTools {
  
    // Export only static methods
    private CompressionTools() {}
  
    /** Compresses the specified byte range using the
     *  specified compressionLevel (constants are defined in
     *  java.util.zip.Deflater). */
    public static byte[] compress(byte[] value, int offset, int length, int compressionLevel) {
  
      /* Create an expandable byte array to hold the compressed data.
       * You cannot use an array that's the same size as the orginal because
       * there is no guarantee that the compressed data will be smaller than
       * the uncompressed data. */
      ByteArrayOutputStream bos = new ByteArrayOutputStream(length);
  
      Deflater compressor = new Deflater();
  
      try {
        compressor.setLevel(compressionLevel);
        compressor.setInput(value, offset, length);
        compressor.finish();
  
        // Compress the data
        final byte[] buf = new byte[1024];
        while (!compressor.finished()) {
          int count = compressor.deflate(buf);
          bos.write(buf, 0, count);
        }
      } finally {
        compressor.end();
      }
  
      return bos.toByteArray();
    }
  
    /** Compresses the specified byte range, with default BEST_COMPRESSION level */
    public static byte[] compress(byte[] value, int offset, int length) {
      return compress(value, offset, length, Deflater.BEST_COMPRESSION);
    }
    
    /** Compresses all bytes in the array, with default BEST_COMPRESSION level */
    public static byte[] compress(byte[] value) {
      return compress(value, 0, value.length, Deflater.BEST_COMPRESSION);
    }
  
    /** Compresses the String value, with default BEST_COMPRESSION level */
    public static byte[] compressString(String value) {
      return compressString(value, Deflater.BEST_COMPRESSION);
    }
  
    /** Compresses the String value using the specified
     *  compressionLevel (constants are defined in
     *  java.util.zip.Deflater). */
    public static byte[] compressString(String value, int compressionLevel) {
      UnicodeUtil.UTF8Result result = new UnicodeUtil.UTF8Result();
      UnicodeUtil.UTF16toUTF8(value, 0, value.length(), result);
      return compress(result.result, 0, result.length, compressionLevel);
    }
  
    /** Decompress the byte array previously returned by
     *  compress */
    public static byte[] decompress(byte[] value) throws DataFormatException {
      // Create an expandable byte array to hold the decompressed data
      ByteArrayOutputStream bos = new ByteArrayOutputStream(value.length);
  
      Inflater decompressor = new Inflater();
  
      try {
        decompressor.setInput(value);
  
        // Decompress the data
        final byte[] buf = new byte[1024];
        while (!decompressor.finished()) {
          int count = decompressor.inflate(buf);
          bos.write(buf, 0, count);
        }
      } finally {  
        decompressor.end();
      }
      
      return bos.toByteArray();
    }
  
    /** Decompress the byte array previously returned by
     *  compressString back into a String */
    public static String decompressString(byte[] value) throws DataFormatException {
      UnicodeUtil.UTF16Result result = new UnicodeUtil.UTF16Result();
      final byte[] bytes = decompress(value);
      UnicodeUtil.UTF8toUTF16(bytes, 0, bytes.length, result);
      return new String(result.result, 0, result.length);
    }
  }
  