001 package com.mockrunner.util.common; 002 003 import java.io.BufferedReader; 004 import java.io.ByteArrayInputStream; 005 import java.io.ByteArrayOutputStream; 006 import java.io.IOException; 007 import java.io.InputStream; 008 import java.io.Reader; 009 import java.io.StringReader; 010 import java.util.ArrayList; 011 import java.util.Arrays; 012 import java.util.List; 013 014 import org.apache.commons.logging.Log; 015 import org.apache.commons.logging.LogFactory; 016 017 import com.mockrunner.base.NestedApplicationException; 018 019 /** 020 * Simple util class for manipulating streams 021 */ 022 public class StreamUtil 023 { 024 private final static Log log = LogFactory.getLog(StreamUtil.class); 025 026 /** 027 * Returns the contents of the input stream as byte array. 028 * @param stream the <code>InputStream</code> 029 * @return the stream content as byte array 030 */ 031 public static byte[] getStreamAsByteArray(InputStream stream) 032 { 033 return getStreamAsByteArray(stream, -1); 034 } 035 036 /** 037 * Returns the contents of the input stream as byte array. 038 * @param stream the <code>InputStream</code> 039 * @param length the number of bytes to copy, if length < 0, 040 * the number is unlimited 041 * @return the stream content as byte array 042 */ 043 public static byte[] getStreamAsByteArray(InputStream stream, int length) 044 { 045 if(length == 0) return new byte[0]; 046 boolean checkLength = true; 047 if(length < 0) 048 { 049 length = Integer.MAX_VALUE; 050 checkLength = false; 051 } 052 ByteArrayOutputStream byteStream = new ByteArrayOutputStream(); 053 try 054 { 055 int nextValue = stream.read(); 056 if(checkLength) length--; 057 while(-1 != nextValue && length >= 0) 058 { 059 byteStream.write(nextValue); 060 nextValue = stream.read(); 061 if(checkLength) length--; 062 } 063 byteStream.flush(); 064 } 065 catch(IOException exc) 066 { 067 log.error("Exception while reading from stream", exc); 068 } 069 return byteStream.toByteArray(); 070 } 071 072 /** 073 * Returns the contents of the reader as a string. 074 * @param reader the <code>Reader</code> 075 * @return the reader content as <code>String</code> 076 */ 077 public static String getReaderAsString(Reader reader) 078 { 079 return getReaderAsString(reader, -1); 080 } 081 082 /** 083 * Returns the contents of the reader as a string. 084 * @param reader the <code>Reader</code> 085 * @param length the number of chars to copy, if length < 0, 086 * the number is unlimited 087 * @return the reader content as <code>String</code> 088 */ 089 public static String getReaderAsString(Reader reader, int length) 090 { 091 if(length == 0) return ""; 092 boolean checkLength = true; 093 if(length < 0) 094 { 095 length = Integer.MAX_VALUE; 096 checkLength = false; 097 } 098 StringBuffer buffer = new StringBuffer(); 099 try 100 { 101 int nextValue = reader.read(); 102 if(checkLength) length--; 103 while(-1 != nextValue && length >= 0) 104 { 105 buffer.append((char)nextValue); 106 nextValue = reader.read(); 107 if(checkLength) length--; 108 } 109 } 110 catch(IOException exc) 111 { 112 log.error("Exception while reading from reader", exc); 113 } 114 return buffer.toString(); 115 } 116 117 /** 118 * Returns a copy of the specified stream. If the specified stream supports 119 * marking, it will be reset after the copy. 120 * @param sourceStream the stream to copy 121 * @return a copy of the stream 122 */ 123 public static InputStream copyStream(InputStream sourceStream) 124 { 125 try 126 { 127 if(sourceStream.markSupported()) sourceStream.mark(sourceStream.available()); 128 byte[] sourceData = getStreamAsByteArray(sourceStream); 129 if(sourceStream.markSupported()) sourceStream.reset(); 130 return new ByteArrayInputStream(sourceData); 131 } 132 catch(IOException exc) 133 { 134 log.error("Exception while copying stream", exc); 135 return null; 136 } 137 } 138 139 /** 140 * Returns a copy of the specified reader. If the specified reader supports 141 * marking, it will be reset after the copy. 142 * @param sourceReader the stream to reader 143 * @return a copy of the reader 144 */ 145 public static Reader copyReader(Reader sourceReader) 146 { 147 try 148 { 149 if(sourceReader.markSupported()) sourceReader.mark(Integer.MAX_VALUE); 150 String sourceData = getReaderAsString(sourceReader); 151 if(sourceReader.markSupported()) sourceReader.reset(); 152 return new StringReader(sourceData); 153 } 154 catch(IOException exc) 155 { 156 log.error("Exception while copying reader", exc); 157 return null; 158 } 159 } 160 161 /** 162 * Compares the content of the streams. If the streams support 163 * marking, they will be reset after the comparison. 164 * @param sourceStream the source stream 165 * @param targetStream the target stream 166 * @return <code>true</code>, if the streams are identical, <code>false</code> otherwise 167 */ 168 public static boolean compareStreams(InputStream sourceStream, InputStream targetStream) 169 { 170 try 171 { 172 if(sourceStream.markSupported()) sourceStream.mark(sourceStream.available()); 173 if(targetStream.markSupported()) targetStream.mark(targetStream.available()); 174 byte[] sourceArray = getStreamAsByteArray(sourceStream); 175 byte[] targetArray = getStreamAsByteArray(targetStream); 176 if(sourceStream.markSupported()) sourceStream.reset(); 177 if(targetStream.markSupported()) targetStream.reset(); 178 return Arrays.equals(sourceArray, targetArray); 179 } 180 catch(IOException exc) 181 { 182 log.error("Exception while comparing streams", exc); 183 return false; 184 } 185 } 186 187 /** 188 * Compares the content of the readers. If the readers support 189 * marking, they will be reset after the comparison. 190 * @param sourceReader the source stream 191 * @param targetReader the target stream 192 * @return <code>true</code>, if the streams are identical, <code>false</code> otherwise 193 */ 194 public static boolean compareReaders(Reader sourceReader, Reader targetReader) 195 { 196 try 197 { 198 if(sourceReader.markSupported()) sourceReader.mark(Integer.MAX_VALUE); 199 if(targetReader.markSupported()) targetReader.mark(Integer.MAX_VALUE); 200 String sourceString = getReaderAsString(sourceReader); 201 String targetString = getReaderAsString(targetReader); 202 if(sourceReader.markSupported()) sourceReader.reset(); 203 if(targetReader.markSupported()) targetReader.reset(); 204 return sourceString.equals(targetString); 205 } 206 catch(IOException exc) 207 { 208 log.error("Exception while comparing readers", exc); 209 return false; 210 } 211 } 212 213 /** 214 * Reads the lines from the specified reader and adds them to a <code>List</code>. 215 * @param reader the reader 216 * @return the <code>List</code> with the lines 217 */ 218 public static List getLinesFromReader(Reader reader) 219 { 220 List resultList = new ArrayList(); 221 try 222 { 223 BufferedReader bufferedReader = new BufferedReader(reader); 224 String line = bufferedReader.readLine(); 225 while(line != null) 226 { 227 resultList.add(line); 228 line = bufferedReader.readLine(); 229 } 230 } 231 catch(IOException exc) 232 { 233 throw new NestedApplicationException(exc); 234 } 235 return resultList; 236 } 237 }