// Copyright 2011 Google Inc.
//
// Licensed 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.
package com.google.enterprise.connector.common;
import java.io.FilterInputStream;
import java.io.IOException;
import java.io.InputStream;
/**
* A {@code FilterInputStream} that protects against large documents and empty
* documents.
* If we have read more than {@link FileSizeLimitInfo.maxDocumentSize}
* bytes from the input, or if we get EOF after reading zero bytes,
* we throw a subclass of {@code IOException} that is used as a signal for
* {@link AlternateContentFilterInputStream} to switch to alternate content.
*/
public class BigEmptyDocumentFilterInputStream extends FilterInputStream {
private final long maxDocumentSize;
private long currentDocumentSize;
/**
* @param in InputStream containing raw document content
* @param maxDocumentSize maximum allowed size in bytes of data read from in
*/
public BigEmptyDocumentFilterInputStream(InputStream in,
long maxDocumentSize) {
super(in);
this.maxDocumentSize = maxDocumentSize;
this.currentDocumentSize = 0;
}
@Override
public int read() throws IOException {
if (in == null) {
throw new EmptyDocumentException();
}
int val = super.read();
if (val == -1) {
if (currentDocumentSize == 0) {
throw new EmptyDocumentException();
}
} else if (++currentDocumentSize > maxDocumentSize) {
throw new BigDocumentException();
}
return val;
}
@Override
public int read(byte b[], int off, int len) throws IOException {
if (in == null) {
throw new EmptyDocumentException();
}
int bytesRead = super.read(b, off, (maxDocumentSize == Long.MAX_VALUE) ?
len : (int) Math.min(len, maxDocumentSize - currentDocumentSize + 1));
if (bytesRead == -1) {
if (currentDocumentSize == 0) {
throw new EmptyDocumentException();
} else {
return bytesRead;
}
} else if ((currentDocumentSize += bytesRead) > maxDocumentSize) {
throw new BigDocumentException();
}
return bytesRead;
}
@Override
public boolean markSupported() {
return false;
}
@Override
public void close() throws IOException {
if (in != null) {
super.close();
}
}
}