1 | /*
|
---|
2 | * Copyright 2000,2002-2005 The Apache Software Foundation
|
---|
3 | *
|
---|
4 | * Licensed under the Apache License, Version 2.0 (the "License");
|
---|
5 | * you may not use this file except in compliance with the License.
|
---|
6 | * You may obtain a copy of the License at
|
---|
7 | *
|
---|
8 | * http://www.apache.org/licenses/LICENSE-2.0
|
---|
9 | *
|
---|
10 | * Unless required by applicable law or agreed to in writing, software
|
---|
11 | * distributed under the License is distributed on an "AS IS" BASIS,
|
---|
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
---|
13 | * See the License for the specific language governing permissions and
|
---|
14 | * limitations under the License.
|
---|
15 | *
|
---|
16 | */
|
---|
17 |
|
---|
18 | package org.apache.tools.ant.taskdefs;
|
---|
19 |
|
---|
20 | import java.io.IOException;
|
---|
21 | import java.io.InputStream;
|
---|
22 | import java.io.OutputStream;
|
---|
23 |
|
---|
24 | /**
|
---|
25 | * Copies all data from an input stream to an output stream.
|
---|
26 | *
|
---|
27 | * @since Ant 1.2
|
---|
28 | */
|
---|
29 | public class StreamPumper implements Runnable {
|
---|
30 |
|
---|
31 | // TODO: make SIZE an instance variable.
|
---|
32 | // TODO: add a status flag to note if an error occurred in run.
|
---|
33 |
|
---|
34 | private static final int SIZE = 128;
|
---|
35 | private InputStream is;
|
---|
36 | private OutputStream os;
|
---|
37 | private boolean finished;
|
---|
38 | private boolean closeWhenExhausted;
|
---|
39 | private boolean autoflush = false;
|
---|
40 |
|
---|
41 | /**
|
---|
42 | * Create a new stream pumper.
|
---|
43 | *
|
---|
44 | * @param is input stream to read data from
|
---|
45 | * @param os output stream to write data to.
|
---|
46 | * @param closeWhenExhausted if true, the output stream will be closed when
|
---|
47 | * the input is exhausted.
|
---|
48 | */
|
---|
49 | public StreamPumper(InputStream is, OutputStream os,
|
---|
50 | boolean closeWhenExhausted) {
|
---|
51 | this.is = is;
|
---|
52 | this.os = os;
|
---|
53 | this.closeWhenExhausted = closeWhenExhausted;
|
---|
54 | }
|
---|
55 |
|
---|
56 | /**
|
---|
57 | * Create a new stream pumper.
|
---|
58 | *
|
---|
59 | * @param is input stream to read data from
|
---|
60 | * @param os output stream to write data to.
|
---|
61 | */
|
---|
62 | public StreamPumper(InputStream is, OutputStream os) {
|
---|
63 | this(is, os, false);
|
---|
64 | }
|
---|
65 |
|
---|
66 | /**
|
---|
67 | * Set whether data should be flushed through to the output stream.
|
---|
68 | * @param autoflush if true, push through data; if false, let it be buffered
|
---|
69 | * @since Ant 1.6.3
|
---|
70 | */
|
---|
71 | /*public*/ void setAutoflush(boolean autoflush) {
|
---|
72 | this.autoflush = autoflush;
|
---|
73 | }
|
---|
74 |
|
---|
75 | /**
|
---|
76 | * Copies data from the input stream to the output stream.
|
---|
77 | *
|
---|
78 | * Terminates as soon as the input stream is closed or an error occurs.
|
---|
79 | */
|
---|
80 | public void run() {
|
---|
81 | synchronized (this) {
|
---|
82 | // Just in case this object is reused in the future
|
---|
83 | finished = false;
|
---|
84 | }
|
---|
85 |
|
---|
86 | final byte[] buf = new byte[SIZE];
|
---|
87 |
|
---|
88 | int length;
|
---|
89 | try {
|
---|
90 | while ((length = is.read(buf)) > 0 && !finished) {
|
---|
91 | os.write(buf, 0, length);
|
---|
92 | if (autoflush) {
|
---|
93 | os.flush();
|
---|
94 | }
|
---|
95 | }
|
---|
96 | } catch (Exception e) {
|
---|
97 | // ignore errors
|
---|
98 | } finally {
|
---|
99 | if (closeWhenExhausted) {
|
---|
100 | try {
|
---|
101 | os.close();
|
---|
102 | } catch (IOException e) {
|
---|
103 | // ignore
|
---|
104 | }
|
---|
105 | }
|
---|
106 | synchronized (this) {
|
---|
107 | finished = true;
|
---|
108 | notifyAll();
|
---|
109 | }
|
---|
110 | }
|
---|
111 | }
|
---|
112 |
|
---|
113 | /**
|
---|
114 | * Tells whether the end of the stream has been reached.
|
---|
115 | * @return true is the stream has been exhausted.
|
---|
116 | **/
|
---|
117 | public synchronized boolean isFinished() {
|
---|
118 | return finished;
|
---|
119 | }
|
---|
120 |
|
---|
121 | /**
|
---|
122 | * This method blocks until the stream pumper finishes.
|
---|
123 | * @see #isFinished()
|
---|
124 | **/
|
---|
125 | public synchronized void waitFor()
|
---|
126 | throws InterruptedException {
|
---|
127 | while (!isFinished()) {
|
---|
128 | wait();
|
---|
129 | }
|
---|
130 | }
|
---|
131 |
|
---|
132 | /**
|
---|
133 | * Stop the pumper as soon as possible.
|
---|
134 | * Note that it may continue to block on the input stream
|
---|
135 | * but it will really stop the thread as soon as it gets EOF
|
---|
136 | * or any byte, and it will be marked as finished.
|
---|
137 | * @since Ant 1.6.3
|
---|
138 | */
|
---|
139 | /*public*/ synchronized void stop() {
|
---|
140 | finished = true;
|
---|
141 | notifyAll();
|
---|
142 | }
|
---|
143 |
|
---|
144 | }
|
---|