/* Copyright 2017 Google Inc. All Rights Reserved.

   Distributed under MIT license.
   See file LICENSE for detail or copy at https://opensource.org/licenses/MIT
*/

package org.brotli.wrapper.enc;

import org.brotli.enc.PreparedDictionary;
import java.io.IOException;
import java.nio.Buffer;
import java.nio.ByteBuffer;
import java.nio.channels.ClosedChannelException;
import java.nio.channels.WritableByteChannel;

/**
 * WritableByteChannel that wraps native brotli encoder.
 */
public class BrotliEncoderChannel extends Encoder implements WritableByteChannel {
  /** The default internal buffer size used by the decoder. */
  private static final int DEFAULT_BUFFER_SIZE = 16384;

  private final Object mutex = new Object();

  /**
   * Creates a BrotliEncoderChannel.
   *
   * @param destination underlying destination
   * @param params encoding settings
   * @param bufferSize intermediate buffer size
   */
  public BrotliEncoderChannel(WritableByteChannel destination, Encoder.Parameters params,
      int bufferSize) throws IOException {
    super(destination, params, bufferSize);
  }

  public BrotliEncoderChannel(WritableByteChannel destination, Encoder.Parameters params)
      throws IOException {
    this(destination, params, DEFAULT_BUFFER_SIZE);
  }

  public BrotliEncoderChannel(WritableByteChannel destination) throws IOException {
    this(destination, new Encoder.Parameters());
  }

  @Override
  public void attachDictionary(PreparedDictionary dictionary) throws IOException {
    super.attachDictionary(dictionary);
  }

  @Override
  public boolean isOpen() {
    synchronized (mutex) {
      return !closed;
    }
  }

  @Override
  public void close() throws IOException {
    synchronized (mutex) {
      super.close();
    }
  }

  @Override
  public int write(ByteBuffer src) throws IOException {
    synchronized (mutex) {
      if (closed) {
        throw new ClosedChannelException();
      }
      int result = 0;
      while (src.hasRemaining() && encode(EncoderJNI.Operation.PROCESS)) {
        int limit = Math.min(src.remaining(), inputBuffer.remaining());
        ByteBuffer slice = src.slice();
        ((Buffer) slice).limit(limit);
        inputBuffer.put(slice);
        result += limit;
        ((Buffer) src).position(src.position() + limit);
      }
      return result;
    }
  }
}
