Search in sources :

Example 16 with FlowFileAccessException

use of org.apache.nifi.processor.exception.FlowFileAccessException in project nifi by apache.

the class StandardProcessSession method importFrom.

@Override
public FlowFile importFrom(final InputStream source, FlowFile destination) {
    verifyTaskActive();
    destination = validateRecordState(destination);
    final StandardRepositoryRecord record = records.get(destination);
    ContentClaim newClaim = null;
    final long claimOffset = 0L;
    final long newSize;
    try {
        try {
            newClaim = context.getContentRepository().create(context.getConnectable().isLossTolerant());
            claimLog.debug("Creating ContentClaim {} for 'importFrom' for {}", newClaim, destination);
            newSize = context.getContentRepository().importFrom(createTaskTerminationStream(source), newClaim);
            bytesWritten += newSize;
        } catch (final IOException e) {
            throw new FlowFileAccessException("Unable to create ContentClaim due to " + e.toString(), e);
        }
    } catch (final Throwable t) {
        if (newClaim != null) {
            destroyContent(newClaim);
        }
        throw new FlowFileAccessException("Failed to import data from " + source + " for " + destination + " due to " + t.toString(), t);
    }
    removeTemporaryClaim(record);
    final FlowFileRecord newFile = new StandardFlowFileRecord.Builder().fromFlowFile(record.getCurrent()).contentClaim(newClaim).contentClaimOffset(claimOffset).size(newSize).build();
    record.setWorking(newFile);
    return newFile;
}
Also used : ContentClaim(org.apache.nifi.controller.repository.claim.ContentClaim) FlowFileAccessException(org.apache.nifi.processor.exception.FlowFileAccessException) IOException(java.io.IOException)

Example 17 with FlowFileAccessException

use of org.apache.nifi.processor.exception.FlowFileAccessException in project nifi by apache.

the class StandardProcessSession method read.

@Override
public InputStream read(FlowFile source) {
    verifyTaskActive();
    source = validateRecordState(source, true);
    final StandardRepositoryRecord record = records.get(source);
    try {
        ensureNotAppending(record.getCurrentClaim());
    } catch (final IOException e) {
        throw new FlowFileAccessException("Failed to access ContentClaim for " + source.toString(), e);
    }
    final InputStream rawIn = getInputStream(source, record.getCurrentClaim(), record.getCurrentClaimOffset(), true);
    final InputStream limitedIn = new LimitedInputStream(rawIn, source.getSize());
    final ByteCountingInputStream countingStream = new ByteCountingInputStream(limitedIn);
    final FlowFileAccessInputStream ffais = new FlowFileAccessInputStream(countingStream, source, record.getCurrentClaim());
    final FlowFile sourceFlowFile = source;
    final InputStream errorHandlingStream = new InputStream() {

        private boolean closed = false;

        @Override
        public int read() throws IOException {
            try {
                return ffais.read();
            } catch (final ContentNotFoundException cnfe) {
                handleContentNotFound(cnfe, record);
                close();
                throw cnfe;
            } catch (final FlowFileAccessException ffae) {
                LOG.error("Failed to read content from " + sourceFlowFile + "; rolling back session", ffae);
                rollback(true);
                close();
                throw ffae;
            }
        }

        @Override
        public int read(final byte[] b) throws IOException {
            return read(b, 0, b.length);
        }

        @Override
        public int read(final byte[] b, final int off, final int len) throws IOException {
            try {
                return ffais.read(b, off, len);
            } catch (final ContentNotFoundException cnfe) {
                handleContentNotFound(cnfe, record);
                close();
                throw cnfe;
            } catch (final FlowFileAccessException ffae) {
                LOG.error("Failed to read content from " + sourceFlowFile + "; rolling back session", ffae);
                rollback(true);
                close();
                throw ffae;
            }
        }

        @Override
        public void close() throws IOException {
            decrementReadCount(sourceFlowFile);
            if (!closed) {
                StandardProcessSession.this.bytesRead += countingStream.getBytesRead();
                closed = true;
            }
            ffais.close();
            openInputStreams.remove(sourceFlowFile);
        }

        @Override
        public int available() throws IOException {
            return ffais.available();
        }

        @Override
        public long skip(long n) throws IOException {
            return ffais.skip(n);
        }

        @Override
        public boolean markSupported() {
            return ffais.markSupported();
        }

        @Override
        public synchronized void mark(int readlimit) {
            ffais.mark(readlimit);
        }

        @Override
        public synchronized void reset() throws IOException {
            ffais.reset();
        }

        @Override
        public String toString() {
            return "ErrorHandlingInputStream[FlowFile=" + sourceFlowFile + "]";
        }
    };
    incrementReadCount(sourceFlowFile);
    openInputStreams.put(sourceFlowFile, errorHandlingStream);
    return createTaskTerminationStream(errorHandlingStream);
}
Also used : FlowFile(org.apache.nifi.flowfile.FlowFile) FlowFileAccessException(org.apache.nifi.processor.exception.FlowFileAccessException) ByteArrayInputStream(java.io.ByteArrayInputStream) TaskTerminationInputStream(org.apache.nifi.controller.repository.io.TaskTerminationInputStream) ByteCountingInputStream(org.apache.nifi.stream.io.ByteCountingInputStream) FlowFileAccessInputStream(org.apache.nifi.controller.repository.io.FlowFileAccessInputStream) LimitedInputStream(org.apache.nifi.controller.repository.io.LimitedInputStream) DisableOnCloseInputStream(org.apache.nifi.controller.repository.io.DisableOnCloseInputStream) InputStream(java.io.InputStream) LimitedInputStream(org.apache.nifi.controller.repository.io.LimitedInputStream) ByteCountingInputStream(org.apache.nifi.stream.io.ByteCountingInputStream) FlowFileAccessInputStream(org.apache.nifi.controller.repository.io.FlowFileAccessInputStream) IOException(java.io.IOException)

Example 18 with FlowFileAccessException

use of org.apache.nifi.processor.exception.FlowFileAccessException in project nifi by apache.

the class StandardProcessSession method exportTo.

@Override
public void exportTo(FlowFile source, final OutputStream destination) {
    verifyTaskActive();
    source = validateRecordState(source);
    final StandardRepositoryRecord record = records.get(source);
    if (record.getCurrentClaim() == null) {
        return;
    }
    try {
        ensureNotAppending(record.getCurrentClaim());
        claimCache.flush(record.getCurrentClaim());
    } catch (final IOException e) {
        throw new FlowFileAccessException("Failed to access ContentClaim for " + source.toString(), e);
    }
    try (final InputStream rawIn = getInputStream(source, record.getCurrentClaim(), record.getCurrentClaimOffset(), true);
        final InputStream limitedIn = new LimitedInputStream(rawIn, source.getSize());
        final InputStream disableOnCloseIn = new DisableOnCloseInputStream(limitedIn);
        final ByteCountingInputStream countingStream = new ByteCountingInputStream(disableOnCloseIn, this.bytesRead)) {
        // but in reality, if it is thrown, we want to know about it and handle it, even if the Processor code catches it.
        try (final FlowFileAccessInputStream ffais = new FlowFileAccessInputStream(countingStream, source, record.getCurrentClaim())) {
            boolean cnfeThrown = false;
            try {
                incrementReadCount(source);
                StreamUtils.copy(ffais, createTaskTerminationStream(destination), source.getSize());
            } catch (final ContentNotFoundException cnfe) {
                cnfeThrown = true;
                throw cnfe;
            } finally {
                decrementReadCount(source);
                // if cnfeThrown is true, we don't need to re-throw the Exception; it will propagate.
                if (!cnfeThrown && ffais.getContentNotFoundException() != null) {
                    throw ffais.getContentNotFoundException();
                }
            }
        }
    } catch (final ContentNotFoundException nfe) {
        handleContentNotFound(nfe, record);
    } catch (final IOException ex) {
        throw new ProcessException("IOException thrown from " + connectableDescription + ": " + ex.toString(), ex);
    }
}
Also used : FlowFileAccessException(org.apache.nifi.processor.exception.FlowFileAccessException) ProcessException(org.apache.nifi.processor.exception.ProcessException) ByteArrayInputStream(java.io.ByteArrayInputStream) TaskTerminationInputStream(org.apache.nifi.controller.repository.io.TaskTerminationInputStream) ByteCountingInputStream(org.apache.nifi.stream.io.ByteCountingInputStream) FlowFileAccessInputStream(org.apache.nifi.controller.repository.io.FlowFileAccessInputStream) LimitedInputStream(org.apache.nifi.controller.repository.io.LimitedInputStream) DisableOnCloseInputStream(org.apache.nifi.controller.repository.io.DisableOnCloseInputStream) InputStream(java.io.InputStream) LimitedInputStream(org.apache.nifi.controller.repository.io.LimitedInputStream) DisableOnCloseInputStream(org.apache.nifi.controller.repository.io.DisableOnCloseInputStream) ByteCountingInputStream(org.apache.nifi.stream.io.ByteCountingInputStream) FlowFileAccessInputStream(org.apache.nifi.controller.repository.io.FlowFileAccessInputStream) IOException(java.io.IOException)

Example 19 with FlowFileAccessException

use of org.apache.nifi.processor.exception.FlowFileAccessException in project nifi by apache.

the class StandardProcessSession method write.

@Override
public FlowFile write(FlowFile source, final OutputStreamCallback writer) {
    verifyTaskActive();
    source = validateRecordState(source);
    final StandardRepositoryRecord record = records.get(source);
    long writtenToFlowFile = 0L;
    ContentClaim newClaim = null;
    try {
        newClaim = claimCache.getContentClaim();
        claimLog.debug("Creating ContentClaim {} for 'write' for {}", newClaim, source);
        ensureNotAppending(newClaim);
        try (final OutputStream stream = claimCache.write(newClaim);
            final OutputStream disableOnClose = new DisableOnCloseOutputStream(stream);
            final ByteCountingOutputStream countingOut = new ByteCountingOutputStream(disableOnClose)) {
            try {
                writeRecursionSet.add(source);
                final OutputStream ffaos = new FlowFileAccessOutputStream(countingOut, source);
                writer.process(createTaskTerminationStream(ffaos));
            } finally {
                writtenToFlowFile = countingOut.getBytesWritten();
                bytesWritten += countingOut.getBytesWritten();
            }
        } finally {
            writeRecursionSet.remove(source);
        }
    } catch (final ContentNotFoundException nfe) {
        // need to reset write claim before we can remove the claim
        resetWriteClaims();
        destroyContent(newClaim);
        handleContentNotFound(nfe, record);
    } catch (final FlowFileAccessException ffae) {
        // need to reset write claim before we can remove the claim
        resetWriteClaims();
        destroyContent(newClaim);
        throw ffae;
    } catch (final IOException ioe) {
        // need to reset write claim before we can remove the claim
        resetWriteClaims();
        destroyContent(newClaim);
        throw new ProcessException("IOException thrown from " + connectableDescription + ": " + ioe.toString(), ioe);
    } catch (final Throwable t) {
        // need to reset write claim before we can remove the claim
        resetWriteClaims();
        destroyContent(newClaim);
        throw t;
    }
    removeTemporaryClaim(record);
    final FlowFileRecord newFile = new StandardFlowFileRecord.Builder().fromFlowFile(record.getCurrent()).contentClaim(newClaim).contentClaimOffset(Math.max(0, newClaim.getLength() - writtenToFlowFile)).size(writtenToFlowFile).build();
    record.setWorking(newFile);
    return newFile;
}
Also used : FlowFileAccessOutputStream(org.apache.nifi.controller.repository.io.FlowFileAccessOutputStream) FlowFileAccessException(org.apache.nifi.processor.exception.FlowFileAccessException) ByteCountingOutputStream(org.apache.nifi.stream.io.ByteCountingOutputStream) DisableOnCloseOutputStream(org.apache.nifi.controller.repository.io.DisableOnCloseOutputStream) BufferedOutputStream(java.io.BufferedOutputStream) FlowFileAccessOutputStream(org.apache.nifi.controller.repository.io.FlowFileAccessOutputStream) OutputStream(java.io.OutputStream) TaskTerminationOutputStream(org.apache.nifi.controller.repository.io.TaskTerminationOutputStream) DisableOnCloseOutputStream(org.apache.nifi.controller.repository.io.DisableOnCloseOutputStream) IOException(java.io.IOException) ByteCountingOutputStream(org.apache.nifi.stream.io.ByteCountingOutputStream) ContentClaim(org.apache.nifi.controller.repository.claim.ContentClaim) ProcessException(org.apache.nifi.processor.exception.ProcessException)

Example 20 with FlowFileAccessException

use of org.apache.nifi.processor.exception.FlowFileAccessException in project nifi by apache.

the class SmtpConsumer method data.

@Override
public void data(final InputStream data) throws RejectException, TooMuchDataException, IOException {
    final ProcessSession processSession = sessionFactory.createSession();
    final StopWatch watch = new StopWatch();
    watch.start();
    try {
        FlowFile flowFile = processSession.create();
        final AtomicBoolean limitExceeded = new AtomicBoolean(false);
        flowFile = processSession.write(flowFile, (OutputStream out) -> {
            final LimitingInputStream lis = new LimitingInputStream(data, maxMessageSize);
            IOUtils.copy(lis, out);
            if (lis.hasReachedLimit()) {
                limitExceeded.set(true);
            }
        });
        if (limitExceeded.get()) {
            throw new TooMuchDataException("Maximum message size limit reached - client must send smaller messages");
        }
        flowFile = processSession.putAllAttributes(flowFile, extractMessageAttributes());
        watch.stop();
        processSession.getProvenanceReporter().receive(flowFile, "smtp://" + host + ":" + port + "/", watch.getDuration(TimeUnit.MILLISECONDS));
        processSession.transfer(flowFile, ListenSMTP.REL_SUCCESS);
        processSession.commit();
    } catch (FlowFileAccessException | IllegalStateException | RejectException | IOException ex) {
        log.error("Unable to fully process input due to " + ex.getMessage(), ex);
        throw ex;
    } finally {
        // make sure this happens no matter what - is safe
        processSession.rollback();
    }
}
Also used : ProcessSession(org.apache.nifi.processor.ProcessSession) FlowFile(org.apache.nifi.flowfile.FlowFile) AtomicBoolean(java.util.concurrent.atomic.AtomicBoolean) TooMuchDataException(org.subethamail.smtp.TooMuchDataException) FlowFileAccessException(org.apache.nifi.processor.exception.FlowFileAccessException) OutputStream(java.io.OutputStream) RejectException(org.subethamail.smtp.RejectException) LimitingInputStream(org.apache.nifi.stream.io.LimitingInputStream) IOException(java.io.IOException) StopWatch(org.apache.nifi.util.StopWatch)

Aggregations

FlowFileAccessException (org.apache.nifi.processor.exception.FlowFileAccessException)25 IOException (java.io.IOException)23 FlowFile (org.apache.nifi.flowfile.FlowFile)11 ProcessException (org.apache.nifi.processor.exception.ProcessException)11 InputStream (java.io.InputStream)9 OutputStream (java.io.OutputStream)7 ContentClaim (org.apache.nifi.controller.repository.claim.ContentClaim)6 BufferedOutputStream (java.io.BufferedOutputStream)5 ByteArrayInputStream (java.io.ByteArrayInputStream)5 HashMap (java.util.HashMap)5 DisableOnCloseInputStream (org.apache.nifi.controller.repository.io.DisableOnCloseInputStream)5 FlowFileAccessInputStream (org.apache.nifi.controller.repository.io.FlowFileAccessInputStream)5 LimitedInputStream (org.apache.nifi.controller.repository.io.LimitedInputStream)5 TaskTerminationInputStream (org.apache.nifi.controller.repository.io.TaskTerminationInputStream)5 ByteCountingInputStream (org.apache.nifi.stream.io.ByteCountingInputStream)5 Map (java.util.Map)4 AtomicReference (java.util.concurrent.atomic.AtomicReference)4 DisableOnCloseOutputStream (org.apache.nifi.controller.repository.io.DisableOnCloseOutputStream)4 FlowFileAccessOutputStream (org.apache.nifi.controller.repository.io.FlowFileAccessOutputStream)4 TaskTerminationOutputStream (org.apache.nifi.controller.repository.io.TaskTerminationOutputStream)4