001package org.codehaus.plexus.util.cli;
002
003/*
004 * Copyright The Codehaus Foundation.
005 *
006 * Licensed under the Apache License, Version 2.0 (the "License");
007 * you may not use this file except in compliance with the License.
008 * You may obtain a copy of the License at
009 *
010 *     http://www.apache.org/licenses/LICENSE-2.0
011 *
012 * Unless required by applicable law or agreed to in writing, software
013 * distributed under the License is distributed on an "AS IS" BASIS,
014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
015 * See the License for the specific language governing permissions and
016 * limitations under the License.
017 */
018
019import java.io.IOException;
020import java.io.InputStream;
021import java.io.OutputStream;
022
023import org.apache.commons.io.IOUtils;
024
025/**
026 * Read from an InputStream and write the output to an OutputStream.
027 * 
028 * @author <a href="mailto:trygvis@inamo.no">Trygve Laugst&oslash;l</a>
029 * @version $Id$
030 */
031public class StreamFeeder extends AbstractStreamHandler {
032
033        private InputStream input;
034        private OutputStream output;
035
036        /**
037         * Create a new StreamFeeder
038         * 
039         * @param input
040         *            Stream to read from
041         * @param output
042         *            Stream to write to
043         */
044        public StreamFeeder(InputStream input, OutputStream output) {
045                this.input = input;
046                this.output = output;
047        }
048
049        // ----------------------------------------------------------------------
050        // Runnable implementation
051        // ----------------------------------------------------------------------
052
053        @Override
054        public void run() {
055                try {
056                        feed();
057                } catch (Throwable ex) {
058                        // Catch everything so the streams will be closed and flagged as done.
059                } finally {
060                        close();
061                        synchronized (this) {
062                                setDone();
063                                this.notifyAll();
064                        }
065                }
066        }
067
068        // ----------------------------------------------------------------------
069        //
070        // ----------------------------------------------------------------------
071
072        public void close() {
073                if (input != null) {
074                        synchronized (input) {
075                                IOUtils.closeQuietly(input);
076                                input = null;
077                        }
078                }
079
080                if (output != null) {
081                        synchronized (output) {
082                                IOUtils.closeQuietly(output);
083                                output = null;
084                        }
085                }
086        }
087
088        // ----------------------------------------------------------------------
089        //
090        // ----------------------------------------------------------------------
091
092        private void feed() throws IOException {
093                int data = input.read();
094
095                while (!isDone() && data != -1) {
096                        synchronized (output) {
097                                if (!isDisabled()) {
098                                        output.write(data);
099                                }
100
101                                data = input.read();
102                        }
103                }
104        }
105
106}