001/*
002 * Licensed to the Apache Software Foundation (ASF) under one or more
003 * contributor license agreements.  See the NOTICE file distributed with
004 * this work for additional information regarding copyright ownership.
005 * The ASF licenses this file to You under the Apache License, Version 2.0
006 * (the "License"); you may not use this file except in compliance with
007 * the License.  You may obtain a copy of the License at
008 *
009 *      http://www.apache.org/licenses/LICENSE-2.0
010 *
011 * Unless required by applicable law or agreed to in writing, software
012 * distributed under the License is distributed on an "AS IS" BASIS,
013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
014 * See the License for the specific language governing permissions and
015 * limitations under the License.
016 */
017package org.apache.commons.io;
018
019import java.io.BufferedInputStream;
020import java.io.BufferedOutputStream;
021import java.io.BufferedReader;
022import java.io.BufferedWriter;
023import java.io.ByteArrayInputStream;
024import java.io.CharArrayWriter;
025import java.io.Closeable;
026import java.io.EOFException;
027import java.io.File;
028import java.io.IOException;
029import java.io.InputStream;
030import java.io.InputStreamReader;
031import java.io.OutputStream;
032import java.io.OutputStreamWriter;
033import java.io.Reader;
034import java.io.UncheckedIOException;
035import java.io.Writer;
036import java.net.HttpURLConnection;
037import java.net.ServerSocket;
038import java.net.Socket;
039import java.net.URI;
040import java.net.URL;
041import java.net.URLConnection;
042import java.nio.ByteBuffer;
043import java.nio.CharBuffer;
044import java.nio.channels.Channels;
045import java.nio.channels.ReadableByteChannel;
046import java.nio.channels.Selector;
047import java.nio.charset.Charset;
048import java.nio.file.Files;
049import java.util.Arrays;
050import java.util.Collection;
051import java.util.Iterator;
052import java.util.List;
053import java.util.Objects;
054import java.util.function.Consumer;
055import java.util.stream.Collectors;
056import java.util.stream.Stream;
057
058import org.apache.commons.io.function.IOConsumer;
059import org.apache.commons.io.function.IOSupplier;
060import org.apache.commons.io.input.QueueInputStream;
061import org.apache.commons.io.output.AppendableWriter;
062import org.apache.commons.io.output.ByteArrayOutputStream;
063import org.apache.commons.io.output.NullOutputStream;
064import org.apache.commons.io.output.NullWriter;
065import org.apache.commons.io.output.StringBuilderWriter;
066import org.apache.commons.io.output.ThresholdingOutputStream;
067import org.apache.commons.io.output.UnsynchronizedByteArrayOutputStream;
068
069/**
070 * General IO stream manipulation utilities.
071 * <p>
072 * This class provides static utility methods for input/output operations.
073 * </p>
074 * <ul>
075 * <li>closeQuietly - these methods close a stream ignoring nulls and exceptions
076 * <li>toXxx/read - these methods read data from a stream
077 * <li>write - these methods write data to a stream
078 * <li>copy - these methods copy all the data from one stream to another
079 * <li>contentEquals - these methods compare the content of two streams
080 * </ul>
081 * <p>
082 * The byte-to-char methods and char-to-byte methods involve a conversion step.
083 * Two methods are provided in each case, one that uses the platform default
084 * encoding and the other which allows you to specify an encoding. You are
085 * encouraged to always specify an encoding because relying on the platform
086 * default can lead to unexpected results, for example when moving from
087 * development to production.
088 * </p>
089 * <p>
090 * All the methods in this class that read a stream are buffered internally.
091 * This means that there is no cause to use a {@link BufferedInputStream}
092 * or {@link BufferedReader}. The default buffer size of 4K has been shown
093 * to be efficient in tests.
094 * </p>
095 * <p>
096 * The various copy methods all delegate the actual copying to one of the following methods:
097 * </p>
098 * <ul>
099 * <li>{@link #copyLarge(InputStream, OutputStream, byte[])}</li>
100 * <li>{@link #copyLarge(InputStream, OutputStream, long, long, byte[])}</li>
101 * <li>{@link #copyLarge(Reader, Writer, char[])}</li>
102 * <li>{@link #copyLarge(Reader, Writer, long, long, char[])}</li>
103 * </ul>
104 * For example, {@link #copy(InputStream, OutputStream)} calls {@link #copyLarge(InputStream, OutputStream)}
105 * which calls {@link #copy(InputStream, OutputStream, int)} which creates the buffer and calls
106 * {@link #copyLarge(InputStream, OutputStream, byte[])}.
107 * <p>
108 * Applications can re-use buffers by using the underlying methods directly.
109 * This may improve performance for applications that need to do a lot of copying.
110 * </p>
111 * <p>
112 * Wherever possible, the methods in this class do <em>not</em> flush or close
113 * the stream. This is to avoid making non-portable assumptions about the
114 * streams' origin and further use. Thus the caller is still responsible for
115 * closing streams after use.
116 * </p>
117 * <p>
118 * Origin of code: Excalibur.
119 * </p>
120 */
121public class IOUtils {
122    // NOTE: This class is focused on InputStream, OutputStream, Reader and
123    // Writer. Each method should take at least one of these as a parameter,
124    // or return one of them.
125
126    /**
127     * CR char.
128     *
129     * @since 2.9.0
130     */
131    public static final int CR = '\r';
132
133    /**
134     * The default buffer size ({@value}) to use in copy methods.
135     */
136    public static final int DEFAULT_BUFFER_SIZE = 8192;
137
138    /**
139     * The system directory separator character.
140     */
141    public static final char DIR_SEPARATOR = File.separatorChar;
142
143    /**
144     * The Unix directory separator character.
145     */
146    public static final char DIR_SEPARATOR_UNIX = '/';
147
148    /**
149     * The Windows directory separator character.
150     */
151    public static final char DIR_SEPARATOR_WINDOWS = '\\';
152
153    /**
154     * A singleton empty byte array.
155     *
156     *  @since 2.9.0
157     */
158    public static final byte[] EMPTY_BYTE_ARRAY = {};
159
160    /**
161     * Represents the end-of-file (or stream).
162     * @since 2.5 (made public)
163     */
164    public static final int EOF = -1;
165
166    /**
167     * LF char.
168     *
169     * @since 2.9.0
170     */
171    public static final int LF = '\n';
172
173    /**
174     * The system line separator string.
175     *
176     * @deprecated Use {@link System#lineSeparator()}.
177     */
178    @Deprecated
179    public static final String LINE_SEPARATOR = System.lineSeparator();
180
181    /**
182     * The Unix line separator string.
183     *
184     * @see StandardLineSeparator#LF
185     */
186    public static final String LINE_SEPARATOR_UNIX = StandardLineSeparator.LF.getString();
187
188    /**
189     * The Windows line separator string.
190     *
191     * @see StandardLineSeparator#CRLF
192     */
193    public static final String LINE_SEPARATOR_WINDOWS = StandardLineSeparator.CRLF.getString();
194
195    /**
196     * Internal byte array buffer, intended for both reading and writing.
197     */
198    private static final ThreadLocal<byte[]> SCRATCH_BYTE_BUFFER_RW = ThreadLocal.withInitial(IOUtils::byteArray);
199
200    /**
201     * Internal byte array buffer, intended for write only operations.
202     */
203    private static final byte[] SCRATCH_BYTE_BUFFER_WO = byteArray();
204
205    /**
206     * Internal char array buffer, intended for both reading and writing.
207     */
208    private static final ThreadLocal<char[]> SCRATCH_CHAR_BUFFER_RW = ThreadLocal.withInitial(IOUtils::charArray);
209
210    /**
211     * Internal char array buffer, intended for write only operations.
212     */
213    private static final char[] SCRATCH_CHAR_BUFFER_WO = charArray();
214
215    /**
216     * Returns the given InputStream if it is already a {@link BufferedInputStream}, otherwise creates a
217     * BufferedInputStream from the given InputStream.
218     *
219     * @param inputStream the InputStream to wrap or return (not null)
220     * @return the given InputStream or a new {@link BufferedInputStream} for the given InputStream
221     * @throws NullPointerException if the input parameter is null
222     * @since 2.5
223     */
224    @SuppressWarnings("resource") // parameter null check
225    public static BufferedInputStream buffer(final InputStream inputStream) {
226        // reject null early on rather than waiting for IO operation to fail
227        // not checked by BufferedInputStream
228        Objects.requireNonNull(inputStream, "inputStream");
229        return inputStream instanceof BufferedInputStream ?
230                (BufferedInputStream) inputStream : new BufferedInputStream(inputStream);
231    }
232
233    /**
234     * Returns the given InputStream if it is already a {@link BufferedInputStream}, otherwise creates a
235     * BufferedInputStream from the given InputStream.
236     *
237     * @param inputStream the InputStream to wrap or return (not null)
238     * @param size the buffer size, if a new BufferedInputStream is created.
239     * @return the given InputStream or a new {@link BufferedInputStream} for the given InputStream
240     * @throws NullPointerException if the input parameter is null
241     * @since 2.5
242     */
243    @SuppressWarnings("resource") // parameter null check
244    public static BufferedInputStream buffer(final InputStream inputStream, final int size) {
245        // reject null early on rather than waiting for IO operation to fail
246        // not checked by BufferedInputStream
247        Objects.requireNonNull(inputStream, "inputStream");
248        return inputStream instanceof BufferedInputStream ?
249                (BufferedInputStream) inputStream : new BufferedInputStream(inputStream, size);
250    }
251
252    /**
253     * Returns the given OutputStream if it is already a {@link BufferedOutputStream}, otherwise creates a
254     * BufferedOutputStream from the given OutputStream.
255     *
256     * @param outputStream the OutputStream to wrap or return (not null)
257     * @return the given OutputStream or a new {@link BufferedOutputStream} for the given OutputStream
258     * @throws NullPointerException if the input parameter is null
259     * @since 2.5
260     */
261    @SuppressWarnings("resource") // parameter null check
262    public static BufferedOutputStream buffer(final OutputStream outputStream) {
263        // reject null early on rather than waiting for IO operation to fail
264        // not checked by BufferedInputStream
265        Objects.requireNonNull(outputStream, "outputStream");
266        return outputStream instanceof BufferedOutputStream ?
267                (BufferedOutputStream) outputStream : new BufferedOutputStream(outputStream);
268    }
269
270    /**
271     * Returns the given OutputStream if it is already a {@link BufferedOutputStream}, otherwise creates a
272     * BufferedOutputStream from the given OutputStream.
273     *
274     * @param outputStream the OutputStream to wrap or return (not null)
275     * @param size the buffer size, if a new BufferedOutputStream is created.
276     * @return the given OutputStream or a new {@link BufferedOutputStream} for the given OutputStream
277     * @throws NullPointerException if the input parameter is null
278     * @since 2.5
279     */
280    @SuppressWarnings("resource") // parameter null check
281    public static BufferedOutputStream buffer(final OutputStream outputStream, final int size) {
282        // reject null early on rather than waiting for IO operation to fail
283        // not checked by BufferedInputStream
284        Objects.requireNonNull(outputStream, "outputStream");
285        return outputStream instanceof BufferedOutputStream ?
286                (BufferedOutputStream) outputStream : new BufferedOutputStream(outputStream, size);
287    }
288
289    /**
290     * Returns the given reader if it is already a {@link BufferedReader}, otherwise creates a BufferedReader from
291     * the given reader.
292     *
293     * @param reader the reader to wrap or return (not null)
294     * @return the given reader or a new {@link BufferedReader} for the given reader
295     * @throws NullPointerException if the input parameter is null
296     * @since 2.5
297     */
298    public static BufferedReader buffer(final Reader reader) {
299        return reader instanceof BufferedReader ? (BufferedReader) reader : new BufferedReader(reader);
300    }
301
302    /**
303     * Returns the given reader if it is already a {@link BufferedReader}, otherwise creates a BufferedReader from the
304     * given reader.
305     *
306     * @param reader the reader to wrap or return (not null)
307     * @param size the buffer size, if a new BufferedReader is created.
308     * @return the given reader or a new {@link BufferedReader} for the given reader
309     * @throws NullPointerException if the input parameter is null
310     * @since 2.5
311     */
312    public static BufferedReader buffer(final Reader reader, final int size) {
313        return reader instanceof BufferedReader ? (BufferedReader) reader : new BufferedReader(reader, size);
314    }
315
316    /**
317     * Returns the given Writer if it is already a {@link BufferedWriter}, otherwise creates a BufferedWriter from the
318     * given Writer.
319     *
320     * @param writer the Writer to wrap or return (not null)
321     * @return the given Writer or a new {@link BufferedWriter} for the given Writer
322     * @throws NullPointerException if the input parameter is null
323     * @since 2.5
324     */
325    public static BufferedWriter buffer(final Writer writer) {
326        return writer instanceof BufferedWriter ? (BufferedWriter) writer : new BufferedWriter(writer);
327    }
328
329    /**
330     * Returns the given Writer if it is already a {@link BufferedWriter}, otherwise creates a BufferedWriter from the
331     * given Writer.
332     *
333     * @param writer the Writer to wrap or return (not null)
334     * @param size the buffer size, if a new BufferedWriter is created.
335     * @return the given Writer or a new {@link BufferedWriter} for the given Writer
336     * @throws NullPointerException if the input parameter is null
337     * @since 2.5
338     */
339    public static BufferedWriter buffer(final Writer writer, final int size) {
340        return writer instanceof BufferedWriter ? (BufferedWriter) writer : new BufferedWriter(writer, size);
341    }
342
343    /**
344     * Returns a new byte array of size {@link #DEFAULT_BUFFER_SIZE}.
345     *
346     * @return a new byte array of size {@link #DEFAULT_BUFFER_SIZE}.
347     * @since 2.9.0
348     */
349    public static byte[] byteArray() {
350        return byteArray(DEFAULT_BUFFER_SIZE);
351    }
352
353    /**
354     * Returns a new byte array of the given size.
355     *
356     * TODO Consider guarding or warning against large allocations...
357     *
358     * @param size array size.
359     * @return a new byte array of the given size.
360     * @throws NegativeArraySizeException if the size is negative.
361     * @since 2.9.0
362     */
363    public static byte[] byteArray(final int size) {
364        return new byte[size];
365    }
366
367    /**
368     * Returns a new char array of size {@link #DEFAULT_BUFFER_SIZE}.
369     *
370     * @return a new char array of size {@link #DEFAULT_BUFFER_SIZE}.
371     * @since 2.9.0
372     */
373    private static char[] charArray() {
374        return charArray(DEFAULT_BUFFER_SIZE);
375    }
376
377    /**
378     * Returns a new char array of the given size.
379     *
380     * TODO Consider guarding or warning against large allocations...
381     *
382     * @param size array size.
383     * @return a new char array of the given size.
384     * @since 2.9.0
385     */
386    private static char[] charArray(final int size) {
387        return new char[size];
388    }
389
390    /**
391     * Clears any state.
392     * <ul>
393     * <li>Removes the current thread's value for thread-local variables.</li>
394     * <li>Sets static scratch arrays to 0s.</li>
395     * </ul>
396     * @see IO#clear()
397     */
398    static void clear() {
399        SCRATCH_BYTE_BUFFER_RW.remove();
400        SCRATCH_CHAR_BUFFER_RW.remove();
401        Arrays.fill(SCRATCH_BYTE_BUFFER_WO, (byte) 0);
402        Arrays.fill(SCRATCH_CHAR_BUFFER_WO, (char) 0);
403    }
404
405    /**
406     * Closes the given {@link Closeable} as a null-safe operation.
407     *
408     * @param closeable The resource to close, may be null.
409     * @throws IOException if an I/O error occurs.
410     * @since 2.7
411     */
412    public static void close(final Closeable closeable) throws IOException {
413        if (closeable != null) {
414            closeable.close();
415        }
416    }
417
418    /**
419     * Closes the given {@link Closeable}s as null-safe operations.
420     *
421     * @param closeables The resource(s) to close, may be null.
422     * @throws IOExceptionList if an I/O error occurs.
423     * @since 2.8.0
424     */
425    public static void close(final Closeable... closeables) throws IOExceptionList {
426        IOConsumer.forAll(IOUtils::close, closeables);
427    }
428
429    /**
430     * Closes the given {@link Closeable} as a null-safe operation.
431     *
432     * @param closeable The resource to close, may be null.
433     * @param consumer Consume the IOException thrown by {@link Closeable#close()}.
434     * @throws IOException if an I/O error occurs.
435     * @since 2.7
436     */
437    public static void close(final Closeable closeable, final IOConsumer<IOException> consumer) throws IOException {
438        if (closeable != null) {
439            try {
440                closeable.close();
441            } catch (final IOException e) {
442                if (consumer != null) {
443                    consumer.accept(e);
444                }
445            }
446        }
447    }
448
449    /**
450     * Closes a URLConnection.
451     *
452     * @param conn the connection to close.
453     * @since 2.4
454     */
455    public static void close(final URLConnection conn) {
456        if (conn instanceof HttpURLConnection) {
457            ((HttpURLConnection) conn).disconnect();
458        }
459    }
460
461    /**
462     * Avoids the need to type cast.
463     *
464     * @param closeable the object to close, may be null
465     */
466    private static void closeQ(final Closeable closeable) {
467        closeQuietly(closeable, null);
468    }
469
470    /**
471     * Closes a {@link Closeable} unconditionally.
472     *
473     * <p>
474     * Equivalent to {@link Closeable#close()}, except any exceptions will be ignored. This is typically used in
475     * finally blocks.
476     * <p>
477     * Example code:
478     * </p>
479     * <pre>
480     * Closeable closeable = null;
481     * try {
482     *     closeable = new FileReader(&quot;foo.txt&quot;);
483     *     // process closeable
484     *     closeable.close();
485     * } catch (Exception e) {
486     *     // error handling
487     * } finally {
488     *     IOUtils.closeQuietly(closeable);
489     * }
490     * </pre>
491     * <p>
492     * Closing all streams:
493     * </p>
494     * <pre>
495     * try {
496     *     return IOUtils.copy(inputStream, outputStream);
497     * } finally {
498     *     IOUtils.closeQuietly(inputStream);
499     *     IOUtils.closeQuietly(outputStream);
500     * }
501     * </pre>
502     * <p>
503     * Also consider using a try-with-resources statement where appropriate.
504     * </p>
505     *
506     * @param closeable the objects to close, may be null or already closed
507     * @since 2.0
508     *
509     * @see Throwable#addSuppressed(Throwable)
510     */
511    public static void closeQuietly(final Closeable closeable) {
512        closeQuietly(closeable, null);
513    }
514
515    /**
516     * Closes a {@link Closeable} unconditionally.
517     * <p>
518     * Equivalent to {@link Closeable#close()}, except any exceptions will be ignored.
519     * <p>
520     * This is typically used in finally blocks to ensure that the closeable is closed
521     * even if an Exception was thrown before the normal close statement was reached.
522     * <br>
523     * <b>It should not be used to replace the close statement(s)
524     * which should be present for the non-exceptional case.</b>
525     * <br>
526     * It is only intended to simplify tidying up where normal processing has already failed
527     * and reporting close failure as well is not necessary or useful.
528     * <p>
529     * Example code:
530     * </p>
531     * <pre>
532     * Closeable closeable = null;
533     * try {
534     *     closeable = new FileReader(&quot;foo.txt&quot;);
535     *     // processing using the closeable; may throw an Exception
536     *     closeable.close(); // Normal close - exceptions not ignored
537     * } catch (Exception e) {
538     *     // error handling
539     * } finally {
540     *     <b>IOUtils.closeQuietly(closeable); // In case normal close was skipped due to Exception</b>
541     * }
542     * </pre>
543     * <p>
544     * Closing all streams:
545     * <br>
546     * <pre>
547     * try {
548     *     return IOUtils.copy(inputStream, outputStream);
549     * } finally {
550     *     IOUtils.closeQuietly(inputStream, outputStream);
551     * }
552     * </pre>
553     * <p>
554     * Also consider using a try-with-resources statement where appropriate.
555     * </p>
556     * @param closeables the objects to close, may be null or already closed
557     * @see #closeQuietly(Closeable)
558     * @since 2.5
559     * @see Throwable#addSuppressed(Throwable)
560     */
561    public static void closeQuietly(final Closeable... closeables) {
562        if (closeables != null) {
563            closeQuietly(Arrays.stream(closeables));
564        }
565    }
566
567    /**
568     * Closes the given {@link Closeable} as a null-safe operation while consuming IOException by the given {@code consumer}.
569     *
570     * @param closeable The resource to close, may be null.
571     * @param consumer Consumes the IOException thrown by {@link Closeable#close()}.
572     * @since 2.7
573     */
574    public static void closeQuietly(final Closeable closeable, final Consumer<IOException> consumer) {
575        if (closeable != null) {
576            try {
577                closeable.close();
578            } catch (final IOException e) {
579                if (consumer != null) {
580                    consumer.accept(e);
581                }
582            }
583        }
584    }
585
586    /**
587     * Closes an {@link InputStream} unconditionally.
588     * <p>
589     * Equivalent to {@link InputStream#close()}, except any exceptions will be ignored.
590     * This is typically used in finally blocks.
591     * </p>
592     * <p>
593     * Example code:
594     * </p>
595     * <pre>
596     *   byte[] data = new byte[1024];
597     *   InputStream in = null;
598     *   try {
599     *       in = new FileInputStream("foo.txt");
600     *       in.read(data);
601     *       in.close(); //close errors are handled
602     *   } catch (Exception e) {
603     *       // error handling
604     *   } finally {
605     *       IOUtils.closeQuietly(in);
606     *   }
607     * </pre>
608     * <p>
609     * Also consider using a try-with-resources statement where appropriate.
610     * </p>
611     *
612     * @param input the InputStream to close, may be null or already closed
613     * @see Throwable#addSuppressed(Throwable)
614     */
615    public static void closeQuietly(final InputStream input) {
616        closeQ(input);
617    }
618
619    /**
620     * Closes an iterable of {@link Closeable} unconditionally.
621     * <p>
622     * Equivalent calling {@link Closeable#close()} on each element, except any exceptions will be ignored.
623     * </p>
624     *
625     * @param closeables the objects to close, may be null or already closed
626     * @see #closeQuietly(Closeable)
627     * @since 2.12.0
628     */
629    public static void closeQuietly(final Iterable<Closeable> closeables) {
630        if (closeables != null) {
631            closeables.forEach(IOUtils::closeQuietly);
632        }
633    }
634
635    /**
636     * Closes an {@link OutputStream} unconditionally.
637     * <p>
638     * Equivalent to {@link OutputStream#close()}, except any exceptions will be ignored.
639     * This is typically used in finally blocks.
640     * </p>
641     * <p>
642     * Example code:
643     * </p>
644     * <pre>
645     * byte[] data = "Hello, World".getBytes();
646     *
647     * OutputStream out = null;
648     * try {
649     *     out = new FileOutputStream("foo.txt");
650     *     out.write(data);
651     *     out.close(); //close errors are handled
652     * } catch (IOException e) {
653     *     // error handling
654     * } finally {
655     *     IOUtils.closeQuietly(out);
656     * }
657     * </pre>
658     * <p>
659     * Also consider using a try-with-resources statement where appropriate.
660     * </p>
661     *
662     * @param output the OutputStream to close, may be null or already closed
663     * @see Throwable#addSuppressed(Throwable)
664     */
665    public static void closeQuietly(final OutputStream output) {
666        closeQ(output);
667    }
668
669    /**
670     * Closes an {@link Reader} unconditionally.
671     * <p>
672     * Equivalent to {@link Reader#close()}, except any exceptions will be ignored.
673     * This is typically used in finally blocks.
674     * </p>
675     * <p>
676     * Example code:
677     * </p>
678     * <pre>
679     *   char[] data = new char[1024];
680     *   Reader in = null;
681     *   try {
682     *       in = new FileReader("foo.txt");
683     *       in.read(data);
684     *       in.close(); //close errors are handled
685     *   } catch (Exception e) {
686     *       // error handling
687     *   } finally {
688     *       IOUtils.closeQuietly(in);
689     *   }
690     * </pre>
691     * <p>
692     * Also consider using a try-with-resources statement where appropriate.
693     * </p>
694     *
695     * @param reader the Reader to close, may be null or already closed
696     * @see Throwable#addSuppressed(Throwable)
697     */
698    public static void closeQuietly(final Reader reader) {
699        closeQ(reader);
700    }
701
702    /**
703     * Closes a {@link Selector} unconditionally.
704     * <p>
705     * Equivalent to {@link Selector#close()}, except any exceptions will be ignored.
706     * This is typically used in finally blocks.
707     * </p>
708     * <p>
709     * Example code:
710     * </p>
711     * <pre>
712     *   Selector selector = null;
713     *   try {
714     *       selector = Selector.open();
715     *       // process socket
716     *
717     *   } catch (Exception e) {
718     *       // error handling
719     *   } finally {
720     *       IOUtils.closeQuietly(selector);
721     *   }
722     * </pre>
723     * <p>
724     * Also consider using a try-with-resources statement where appropriate.
725     * </p>
726     *
727     * @param selector the Selector to close, may be null or already closed
728     * @since 2.2
729     * @see Throwable#addSuppressed(Throwable)
730     */
731    public static void closeQuietly(final Selector selector) {
732        closeQ(selector);
733    }
734
735    /**
736     * Closes a {@link ServerSocket} unconditionally.
737     * <p>
738     * Equivalent to {@link ServerSocket#close()}, except any exceptions will be ignored.
739     * This is typically used in finally blocks.
740     * </p>
741     * <p>
742     * Example code:
743     * </p>
744     * <pre>
745     *   ServerSocket socket = null;
746     *   try {
747     *       socket = new ServerSocket();
748     *       // process socket
749     *       socket.close();
750     *   } catch (Exception e) {
751     *       // error handling
752     *   } finally {
753     *       IOUtils.closeQuietly(socket);
754     *   }
755     * </pre>
756     * <p>
757     * Also consider using a try-with-resources statement where appropriate.
758     * </p>
759     *
760     * @param serverSocket the ServerSocket to close, may be null or already closed
761     * @since 2.2
762     * @see Throwable#addSuppressed(Throwable)
763     */
764    public static void closeQuietly(final ServerSocket serverSocket) {
765        closeQ(serverSocket);
766    }
767
768    /**
769     * Closes a {@link Socket} unconditionally.
770     * <p>
771     * Equivalent to {@link Socket#close()}, except any exceptions will be ignored.
772     * This is typically used in finally blocks.
773     * </p>
774     * <p>
775     * Example code:
776     * </p>
777     * <pre>
778     *   Socket socket = null;
779     *   try {
780     *       socket = new Socket("http://www.foo.com/", 80);
781     *       // process socket
782     *       socket.close();
783     *   } catch (Exception e) {
784     *       // error handling
785     *   } finally {
786     *       IOUtils.closeQuietly(socket);
787     *   }
788     * </pre>
789     * <p>
790     * Also consider using a try-with-resources statement where appropriate.
791     * </p>
792     *
793     * @param socket the Socket to close, may be null or already closed
794     * @since 2.0
795     * @see Throwable#addSuppressed(Throwable)
796     */
797    public static void closeQuietly(final Socket socket) {
798        closeQ(socket);
799    }
800
801    /**
802     * Closes a stream of {@link Closeable} unconditionally.
803     * <p>
804     * Equivalent calling {@link Closeable#close()} on each element, except any exceptions will be ignored.
805     * </p>
806     *
807     * @param closeables the objects to close, may be null or already closed
808     * @see #closeQuietly(Closeable)
809     * @since 2.12.0
810     */
811    public static void closeQuietly(final Stream<Closeable> closeables) {
812        if (closeables != null) {
813            closeables.forEach(IOUtils::closeQuietly);
814        }
815    }
816
817    /**
818     * Closes an {@link Writer} unconditionally.
819     * <p>
820     * Equivalent to {@link Writer#close()}, except any exceptions will be ignored.
821     * This is typically used in finally blocks.
822     * </p>
823     * <p>
824     * Example code:
825     * </p>
826     * <pre>
827     *   Writer out = null;
828     *   try {
829     *       out = new StringWriter();
830     *       out.write("Hello World");
831     *       out.close(); //close errors are handled
832     *   } catch (Exception e) {
833     *       // error handling
834     *   } finally {
835     *       IOUtils.closeQuietly(out);
836     *   }
837     * </pre>
838     * <p>
839     * Also consider using a try-with-resources statement where appropriate.
840     * </p>
841     *
842     * @param writer the Writer to close, may be null or already closed
843     * @see Throwable#addSuppressed(Throwable)
844     */
845    public static void closeQuietly(final Writer writer) {
846        closeQ(writer);
847    }
848
849    /**
850     * Consumes bytes from a {@link InputStream} and ignores them.
851     * <p>
852     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
853     * </p>
854     *
855     * @param input the {@link InputStream} to read.
856     * @return the number of bytes copied. or {@code 0} if {@code input is null}.
857     * @throws NullPointerException if the InputStream is {@code null}.
858     * @throws IOException if an I/O error occurs.
859     * @since 2.8.0
860     */
861    public static long consume(final InputStream input) throws IOException {
862        return copyLarge(input, NullOutputStream.INSTANCE);
863    }
864
865    /**
866     * Consumes characters from a {@link Reader} and ignores them.
867     * <p>
868     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
869     * </p>
870     *
871     * @param input the {@link Reader} to read.
872     * @return the number of bytes copied. or {@code 0} if {@code input is null}.
873     * @throws NullPointerException if the Reader is {@code null}.
874     * @throws IOException if an I/O error occurs.
875     * @since 2.12.0
876     */
877    public static long consume(final Reader input) throws IOException {
878        return copyLarge(input, NullWriter.INSTANCE);
879    }
880
881    /**
882     * Compares the contents of two Streams to determine if they are equal or
883     * not.
884     * <p>
885     * This method buffers the input internally using
886     * {@link BufferedInputStream} if they are not already buffered.
887     * </p>
888     *
889     * @param input1 the first stream
890     * @param input2 the second stream
891     * @return true if the content of the streams are equal or they both don't
892     * exist, false otherwise
893     * @throws NullPointerException if either input is null
894     * @throws IOException          if an I/O error occurs
895     */
896    public static boolean contentEquals(final InputStream input1, final InputStream input2) throws IOException {
897        // Before making any changes, please test with
898        // org.apache.commons.io.jmh.IOUtilsContentEqualsInputStreamsBenchmark
899        if (input1 == input2) {
900            return true;
901        }
902        if (input1 == null || input2 == null) {
903            return false;
904        }
905
906        // reuse one
907        final byte[] array1 = getScratchByteArray();
908        // allocate another
909        final byte[] array2 = byteArray();
910        int pos1;
911        int pos2;
912        int count1;
913        int count2;
914        while (true) {
915            pos1 = 0;
916            pos2 = 0;
917            for (int index = 0; index < DEFAULT_BUFFER_SIZE; index++) {
918                if (pos1 == index) {
919                    do {
920                        count1 = input1.read(array1, pos1, DEFAULT_BUFFER_SIZE - pos1);
921                    } while (count1 == 0);
922                    if (count1 == EOF) {
923                        return pos2 == index && input2.read() == EOF;
924                    }
925                    pos1 += count1;
926                }
927                if (pos2 == index) {
928                    do {
929                        count2 = input2.read(array2, pos2, DEFAULT_BUFFER_SIZE - pos2);
930                    } while (count2 == 0);
931                    if (count2 == EOF) {
932                        return pos1 == index && input1.read() == EOF;
933                    }
934                    pos2 += count2;
935                }
936                if (array1[index] != array2[index]) {
937                    return false;
938                }
939            }
940        }
941    }
942
943    // TODO Consider making public
944    private static boolean contentEquals(final Iterator<?> iterator1, final Iterator<?> iterator2) {
945        while (iterator1.hasNext()) {
946            if (!iterator2.hasNext()) {
947                return false;
948            }
949            if (!Objects.equals(iterator1.next(), iterator2.next())) {
950                return false;
951            }
952        }
953        return !iterator2.hasNext();
954    }
955
956    /**
957     * Compares the contents of two Readers to determine if they are equal or not.
958     * <p>
959     * This method buffers the input internally using {@link BufferedReader} if they are not already buffered.
960     * </p>
961     *
962     * @param input1 the first reader
963     * @param input2 the second reader
964     * @return true if the content of the readers are equal or they both don't exist, false otherwise
965     * @throws NullPointerException if either input is null
966     * @throws IOException if an I/O error occurs
967     * @since 1.1
968     */
969    public static boolean contentEquals(final Reader input1, final Reader input2) throws IOException {
970        if (input1 == input2) {
971            return true;
972        }
973        if (input1 == null || input2 == null) {
974            return false;
975        }
976
977        // reuse one
978        final char[] array1 = getScratchCharArray();
979        // but allocate another
980        final char[] array2 = charArray();
981        int pos1;
982        int pos2;
983        int count1;
984        int count2;
985        while (true) {
986            pos1 = 0;
987            pos2 = 0;
988            for (int index = 0; index < DEFAULT_BUFFER_SIZE; index++) {
989                if (pos1 == index) {
990                    do {
991                        count1 = input1.read(array1, pos1, DEFAULT_BUFFER_SIZE - pos1);
992                    } while (count1 == 0);
993                    if (count1 == EOF) {
994                        return pos2 == index && input2.read() == EOF;
995                    }
996                    pos1 += count1;
997                }
998                if (pos2 == index) {
999                    do {
1000                        count2 = input2.read(array2, pos2, DEFAULT_BUFFER_SIZE - pos2);
1001                    } while (count2 == 0);
1002                    if (count2 == EOF) {
1003                        return pos1 == index && input1.read() == EOF;
1004                    }
1005                    pos2 += count2;
1006                }
1007                if (array1[index] != array2[index]) {
1008                    return false;
1009                }
1010            }
1011        }
1012    }
1013
1014    // TODO Consider making public
1015    private static boolean contentEquals(final Stream<?> stream1, final Stream<?> stream2) {
1016        if (stream1 == stream2) {
1017            return true;
1018        }
1019        if (stream1 == null || stream2 == null) {
1020            return false;
1021        }
1022        return contentEquals(stream1.iterator(), stream2.iterator());
1023    }
1024
1025    // TODO Consider making public
1026    private static boolean contentEqualsIgnoreEOL(final BufferedReader reader1, final BufferedReader reader2) {
1027        if (reader1 == reader2) {
1028            return true;
1029        }
1030        if (reader1 == null || reader2 == null) {
1031            return false;
1032        }
1033        return contentEquals(reader1.lines(), reader2.lines());
1034    }
1035
1036    /**
1037     * Compares the contents of two Readers to determine if they are equal or
1038     * not, ignoring EOL characters.
1039     * <p>
1040     * This method buffers the input internally using
1041     * {@link BufferedReader} if they are not already buffered.
1042     * </p>
1043     *
1044     * @param reader1 the first reader
1045     * @param reader2 the second reader
1046     * @return true if the content of the readers are equal (ignoring EOL differences),  false otherwise
1047     * @throws NullPointerException if either input is null
1048     * @throws UncheckedIOException if an I/O error occurs
1049     * @since 2.2
1050     */
1051    @SuppressWarnings("resource")
1052    public static boolean contentEqualsIgnoreEOL(final Reader reader1, final Reader reader2) throws UncheckedIOException {
1053        if (reader1 == reader2) {
1054            return true;
1055        }
1056        if (reader1 == null || reader2 == null) {
1057            return false;
1058        }
1059        return contentEqualsIgnoreEOL(toBufferedReader(reader1), toBufferedReader(reader2));
1060    }
1061
1062    /**
1063     * Copies bytes from an {@link InputStream} to an {@link OutputStream}.
1064     * <p>
1065     * This method buffers the input internally, so there is no need to use a {@link BufferedInputStream}.
1066     * </p>
1067     * <p>
1068     * Large streams (over 2GB) will return a bytes copied value of {@code -1} after the copy has completed since
1069     * the correct number of bytes cannot be returned as an int. For large streams use the
1070     * {@link #copyLarge(InputStream, OutputStream)} method.
1071     * </p>
1072     *
1073     * @param inputStream the {@link InputStream} to read.
1074     * @param outputStream the {@link OutputStream} to write.
1075     * @return the number of bytes copied, or -1 if greater than {@link Integer#MAX_VALUE}.
1076     * @throws NullPointerException if the InputStream is {@code null}.
1077     * @throws NullPointerException if the OutputStream is {@code null}.
1078     * @throws IOException if an I/O error occurs.
1079     * @since 1.1
1080     */
1081    public static int copy(final InputStream inputStream, final OutputStream outputStream) throws IOException {
1082        final long count = copyLarge(inputStream, outputStream);
1083        return count > Integer.MAX_VALUE ? EOF : (int) count;
1084    }
1085
1086    /**
1087     * Copies bytes from an {@link InputStream} to an {@link OutputStream} using an internal buffer of the
1088     * given size.
1089     * <p>
1090     * This method buffers the input internally, so there is no need to use a {@link BufferedInputStream}.
1091     * </p>
1092     *
1093     * @param inputStream the {@link InputStream} to read.
1094     * @param outputStream the {@link OutputStream} to write to
1095     * @param bufferSize the bufferSize used to copy from the input to the output
1096     * @return the number of bytes copied.
1097     * @throws NullPointerException if the InputStream is {@code null}.
1098     * @throws NullPointerException if the OutputStream is {@code null}.
1099     * @throws IOException if an I/O error occurs.
1100     * @since 2.5
1101     */
1102    public static long copy(final InputStream inputStream, final OutputStream outputStream, final int bufferSize)
1103            throws IOException {
1104        return copyLarge(inputStream, outputStream, IOUtils.byteArray(bufferSize));
1105    }
1106
1107    /**
1108     * Copies bytes from an {@link InputStream} to chars on a
1109     * {@link Writer} using the default character encoding of the platform.
1110     * <p>
1111     * This method buffers the input internally, so there is no need to use a
1112     * {@link BufferedInputStream}.
1113     * </p>
1114     * <p>
1115     * This method uses {@link InputStreamReader}.
1116     * </p>
1117     *
1118     * @param input the {@link InputStream} to read
1119     * @param writer the {@link Writer} to write to
1120     * @throws NullPointerException if the input or output is null
1121     * @throws IOException          if an I/O error occurs
1122     * @since 1.1
1123     * @deprecated 2.5 use {@link #copy(InputStream, Writer, Charset)} instead
1124     */
1125    @Deprecated
1126    public static void copy(final InputStream input, final Writer writer)
1127            throws IOException {
1128        copy(input, writer, Charset.defaultCharset());
1129    }
1130
1131    /**
1132     * Copies bytes from an {@link InputStream} to chars on a
1133     * {@link Writer} using the specified character encoding.
1134     * <p>
1135     * This method buffers the input internally, so there is no need to use a
1136     * {@link BufferedInputStream}.
1137     * </p>
1138     * <p>
1139     * This method uses {@link InputStreamReader}.
1140     * </p>
1141     *
1142     * @param input the {@link InputStream} to read
1143     * @param writer the {@link Writer} to write to
1144     * @param inputCharset the charset to use for the input stream, null means platform default
1145     * @throws NullPointerException if the input or output is null
1146     * @throws IOException          if an I/O error occurs
1147     * @since 2.3
1148     */
1149    public static void copy(final InputStream input, final Writer writer, final Charset inputCharset)
1150            throws IOException {
1151        final InputStreamReader reader = new InputStreamReader(input, Charsets.toCharset(inputCharset));
1152        copy(reader, writer);
1153    }
1154
1155    /**
1156     * Copies bytes from an {@link InputStream} to chars on a
1157     * {@link Writer} using the specified character encoding.
1158     * <p>
1159     * This method buffers the input internally, so there is no need to use a
1160     * {@link BufferedInputStream}.
1161     * </p>
1162     * <p>
1163     * Character encoding names can be found at
1164     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
1165     * </p>
1166     * <p>
1167     * This method uses {@link InputStreamReader}.
1168     * </p>
1169     *
1170     * @param input the {@link InputStream} to read
1171     * @param writer the {@link Writer} to write to
1172     * @param inputCharsetName the name of the requested charset for the InputStream, null means platform default
1173     * @throws NullPointerException                         if the input or output is null
1174     * @throws IOException                                  if an I/O error occurs
1175     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
1176     *                                                      .UnsupportedEncodingException} in version 2.2 if the
1177     *                                                      encoding is not supported.
1178     * @since 1.1
1179     */
1180    public static void copy(final InputStream input, final Writer writer, final String inputCharsetName)
1181            throws IOException {
1182        copy(input, writer, Charsets.toCharset(inputCharsetName));
1183    }
1184
1185    /**
1186     * Copies bytes from a {@link java.io.ByteArrayOutputStream} to a {@link QueueInputStream}.
1187     * <p>
1188     * Unlike using JDK {@link java.io.PipedInputStream} and {@link java.io.PipedOutputStream} for this, this
1189     * solution works safely in a single thread environment.
1190     * </p>
1191     * <p>
1192     * Example usage:
1193     * </p>
1194     *
1195     * <pre>
1196     * ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
1197     * outputStream.writeBytes("hello world".getBytes(StandardCharsets.UTF_8));
1198     *
1199     * InputStream inputStream = IOUtils.copy(outputStream);
1200     * </pre>
1201     *
1202     * @param outputStream the {@link java.io.ByteArrayOutputStream} to read.
1203     * @return the {@link QueueInputStream} filled with the content of the outputStream.
1204     * @throws NullPointerException if the {@link java.io.ByteArrayOutputStream} is {@code null}.
1205     * @throws IOException if an I/O error occurs.
1206     * @since 2.12
1207     */
1208    @SuppressWarnings("resource") // streams are closed by the caller.
1209    public static QueueInputStream copy(final java.io.ByteArrayOutputStream outputStream) throws IOException {
1210        Objects.requireNonNull(outputStream, "outputStream");
1211        final QueueInputStream in = new QueueInputStream();
1212        outputStream.writeTo(in.newQueueOutputStream());
1213        return in;
1214    }
1215
1216    /**
1217     * Copies chars from a {@link Reader} to a {@link Appendable}.
1218     * <p>
1219     * This method buffers the input internally, so there is no need to use a
1220     * {@link BufferedReader}.
1221     * </p>
1222     * <p>
1223     * Large streams (over 2GB) will return a chars copied value of
1224     * {@code -1} after the copy has completed since the correct
1225     * number of chars cannot be returned as an int. For large streams
1226     * use the {@link #copyLarge(Reader, Writer)} method.
1227     * </p>
1228     *
1229     * @param reader the {@link Reader} to read
1230     * @param output the {@link Appendable} to write to
1231     * @return the number of characters copied, or -1 if &gt; Integer.MAX_VALUE
1232     * @throws NullPointerException if the input or output is null
1233     * @throws IOException          if an I/O error occurs
1234     * @since 2.7
1235     */
1236    public static long copy(final Reader reader, final Appendable output) throws IOException {
1237        return copy(reader, output, CharBuffer.allocate(DEFAULT_BUFFER_SIZE));
1238    }
1239
1240    /**
1241     * Copies chars from a {@link Reader} to an {@link Appendable}.
1242     * <p>
1243     * This method uses the provided buffer, so there is no need to use a
1244     * {@link BufferedReader}.
1245     * </p>
1246     *
1247     * @param reader the {@link Reader} to read
1248     * @param output the {@link Appendable} to write to
1249     * @param buffer the buffer to be used for the copy
1250     * @return the number of characters copied
1251     * @throws NullPointerException if the input or output is null
1252     * @throws IOException          if an I/O error occurs
1253     * @since 2.7
1254     */
1255    public static long copy(final Reader reader, final Appendable output, final CharBuffer buffer) throws IOException {
1256        long count = 0;
1257        int n;
1258        while (EOF != (n = reader.read(buffer))) {
1259            buffer.flip();
1260            output.append(buffer, 0, n);
1261            count += n;
1262        }
1263        return count;
1264    }
1265
1266    /**
1267     * Copies chars from a {@link Reader} to bytes on an
1268     * {@link OutputStream} using the default character encoding of the
1269     * platform, and calling flush.
1270     * <p>
1271     * This method buffers the input internally, so there is no need to use a
1272     * {@link BufferedReader}.
1273     * </p>
1274     * <p>
1275     * Due to the implementation of OutputStreamWriter, this method performs a
1276     * flush.
1277     * </p>
1278     * <p>
1279     * This method uses {@link OutputStreamWriter}.
1280     * </p>
1281     *
1282     * @param reader the {@link Reader} to read
1283     * @param output the {@link OutputStream} to write to
1284     * @throws NullPointerException if the input or output is null
1285     * @throws IOException          if an I/O error occurs
1286     * @since 1.1
1287     * @deprecated 2.5 use {@link #copy(Reader, OutputStream, Charset)} instead
1288     */
1289    @Deprecated
1290    public static void copy(final Reader reader, final OutputStream output)
1291            throws IOException {
1292        copy(reader, output, Charset.defaultCharset());
1293    }
1294
1295    /**
1296     * Copies chars from a {@link Reader} to bytes on an
1297     * {@link OutputStream} using the specified character encoding, and
1298     * calling flush.
1299     * <p>
1300     * This method buffers the input internally, so there is no need to use a
1301     * {@link BufferedReader}.
1302     * </p>
1303     * <p>
1304     * Due to the implementation of OutputStreamWriter, this method performs a
1305     * flush.
1306     * </p>
1307     * <p>
1308     * This method uses {@link OutputStreamWriter}.
1309     * </p>
1310     *
1311     * @param reader the {@link Reader} to read
1312     * @param output the {@link OutputStream} to write to
1313     * @param outputCharset the charset to use for the OutputStream, null means platform default
1314     * @throws NullPointerException if the input or output is null
1315     * @throws IOException          if an I/O error occurs
1316     * @since 2.3
1317     */
1318    public static void copy(final Reader reader, final OutputStream output, final Charset outputCharset)
1319            throws IOException {
1320        final OutputStreamWriter writer = new OutputStreamWriter(output, Charsets.toCharset(outputCharset));
1321        copy(reader, writer);
1322        // XXX Unless anyone is planning on rewriting OutputStreamWriter,
1323        // we have to flush here.
1324        writer.flush();
1325    }
1326
1327    /**
1328     * Copies chars from a {@link Reader} to bytes on an
1329     * {@link OutputStream} using the specified character encoding, and
1330     * calling flush.
1331     * <p>
1332     * This method buffers the input internally, so there is no need to use a
1333     * {@link BufferedReader}.
1334     * </p>
1335     * <p>
1336     * Character encoding names can be found at
1337     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
1338     * </p>
1339     * <p>
1340     * Due to the implementation of OutputStreamWriter, this method performs a
1341     * flush.
1342     * </p>
1343     * <p>
1344     * This method uses {@link OutputStreamWriter}.
1345     * </p>
1346     *
1347     * @param reader the {@link Reader} to read
1348     * @param output the {@link OutputStream} to write to
1349     * @param outputCharsetName the name of the requested charset for the OutputStream, null means platform default
1350     * @throws NullPointerException                         if the input or output is null
1351     * @throws IOException                                  if an I/O error occurs
1352     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
1353     *                                                      .UnsupportedEncodingException} in version 2.2 if the
1354     *                                                      encoding is not supported.
1355     * @since 1.1
1356     */
1357    public static void copy(final Reader reader, final OutputStream output, final String outputCharsetName)
1358            throws IOException {
1359        copy(reader, output, Charsets.toCharset(outputCharsetName));
1360    }
1361
1362    /**
1363     * Copies chars from a {@link Reader} to a {@link Writer}.
1364     * <p>
1365     * This method buffers the input internally, so there is no need to use a
1366     * {@link BufferedReader}.
1367     * </p>
1368     * <p>
1369     * Large streams (over 2GB) will return a chars copied value of
1370     * {@code -1} after the copy has completed since the correct
1371     * number of chars cannot be returned as an int. For large streams
1372     * use the {@link #copyLarge(Reader, Writer)} method.
1373     * </p>
1374     *
1375     * @param reader the {@link Reader} to read.
1376     * @param writer the {@link Writer} to write.
1377     * @return the number of characters copied, or -1 if &gt; Integer.MAX_VALUE
1378     * @throws NullPointerException if the input or output is null
1379     * @throws IOException          if an I/O error occurs
1380     * @since 1.1
1381     */
1382    public static int copy(final Reader reader, final Writer writer) throws IOException {
1383        final long count = copyLarge(reader, writer);
1384        if (count > Integer.MAX_VALUE) {
1385            return EOF;
1386        }
1387        return (int) count;
1388    }
1389
1390    /**
1391     * Copies bytes from a {@link URL} to an {@link OutputStream}.
1392     * <p>
1393     * This method buffers the input internally, so there is no need to use a {@link BufferedInputStream}.
1394     * </p>
1395     * <p>
1396     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
1397     * </p>
1398     *
1399     * @param url the {@link URL} to read.
1400     * @param file the {@link OutputStream} to write.
1401     * @return the number of bytes copied.
1402     * @throws NullPointerException if the URL is {@code null}.
1403     * @throws NullPointerException if the OutputStream is {@code null}.
1404     * @throws IOException if an I/O error occurs.
1405     * @since 2.9.0
1406     */
1407    public static long copy(final URL url, final File file) throws IOException {
1408        try (OutputStream outputStream = Files.newOutputStream(Objects.requireNonNull(file, "file").toPath())) {
1409            return copy(url, outputStream);
1410        }
1411    }
1412
1413    /**
1414     * Copies bytes from a {@link URL} to an {@link OutputStream}.
1415     * <p>
1416     * This method buffers the input internally, so there is no need to use a {@link BufferedInputStream}.
1417     * </p>
1418     * <p>
1419     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
1420     * </p>
1421     *
1422     * @param url the {@link URL} to read.
1423     * @param outputStream the {@link OutputStream} to write.
1424     * @return the number of bytes copied.
1425     * @throws NullPointerException if the URL is {@code null}.
1426     * @throws NullPointerException if the OutputStream is {@code null}.
1427     * @throws IOException if an I/O error occurs.
1428     * @since 2.9.0
1429     */
1430    public static long copy(final URL url, final OutputStream outputStream) throws IOException {
1431        try (InputStream inputStream = Objects.requireNonNull(url, "url").openStream()) {
1432            return copyLarge(inputStream, outputStream);
1433        }
1434    }
1435
1436    /**
1437     * Copies bytes from a large (over 2GB) {@link InputStream} to an
1438     * {@link OutputStream}.
1439     * <p>
1440     * This method buffers the input internally, so there is no need to use a
1441     * {@link BufferedInputStream}.
1442     * </p>
1443     * <p>
1444     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
1445     * </p>
1446     *
1447     * @param inputStream the {@link InputStream} to read.
1448     * @param outputStream the {@link OutputStream} to write.
1449     * @return the number of bytes copied.
1450     * @throws NullPointerException if the InputStream is {@code null}.
1451     * @throws NullPointerException if the OutputStream is {@code null}.
1452     * @throws IOException if an I/O error occurs.
1453     * @since 1.3
1454     */
1455    public static long copyLarge(final InputStream inputStream, final OutputStream outputStream)
1456            throws IOException {
1457        return copy(inputStream, outputStream, DEFAULT_BUFFER_SIZE);
1458    }
1459
1460    /**
1461     * Copies bytes from a large (over 2GB) {@link InputStream} to an
1462     * {@link OutputStream}.
1463     * <p>
1464     * This method uses the provided buffer, so there is no need to use a
1465     * {@link BufferedInputStream}.
1466     * </p>
1467     *
1468     * @param inputStream the {@link InputStream} to read.
1469     * @param outputStream the {@link OutputStream} to write.
1470     * @param buffer the buffer to use for the copy
1471     * @return the number of bytes copied.
1472     * @throws NullPointerException if the InputStream is {@code null}.
1473     * @throws NullPointerException if the OutputStream is {@code null}.
1474     * @throws IOException if an I/O error occurs.
1475     * @since 2.2
1476     */
1477    @SuppressWarnings("resource") // streams are closed by the caller.
1478    public static long copyLarge(final InputStream inputStream, final OutputStream outputStream, final byte[] buffer)
1479        throws IOException {
1480        Objects.requireNonNull(inputStream, "inputStream");
1481        Objects.requireNonNull(outputStream, "outputStream");
1482        long count = 0;
1483        int n;
1484        while (EOF != (n = inputStream.read(buffer))) {
1485            outputStream.write(buffer, 0, n);
1486            count += n;
1487        }
1488        return count;
1489    }
1490
1491    /**
1492     * Copies some or all bytes from a large (over 2GB) {@link InputStream} to an
1493     * {@link OutputStream}, optionally skipping input bytes.
1494     * <p>
1495     * This method buffers the input internally, so there is no need to use a
1496     * {@link BufferedInputStream}.
1497     * </p>
1498     * <p>
1499     * Note that the implementation uses {@link #skip(InputStream, long)}.
1500     * This means that the method may be considerably less efficient than using the actual skip implementation,
1501     * this is done to guarantee that the correct number of characters are skipped.
1502     * </p>
1503     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
1504     *
1505     * @param input the {@link InputStream} to read
1506     * @param output the {@link OutputStream} to write to
1507     * @param inputOffset : number of bytes to skip from input before copying
1508     * -ve values are ignored
1509     * @param length : number of bytes to copy. -ve means all
1510     * @return the number of bytes copied
1511     * @throws NullPointerException if the input or output is null
1512     * @throws IOException          if an I/O error occurs
1513     * @since 2.2
1514     */
1515    public static long copyLarge(final InputStream input, final OutputStream output, final long inputOffset,
1516                                 final long length) throws IOException {
1517        return copyLarge(input, output, inputOffset, length, getScratchByteArray());
1518    }
1519
1520    /**
1521     * Copies some or all bytes from a large (over 2GB) {@link InputStream} to an
1522     * {@link OutputStream}, optionally skipping input bytes.
1523     * <p>
1524     * This method uses the provided buffer, so there is no need to use a
1525     * {@link BufferedInputStream}.
1526     * </p>
1527     * <p>
1528     * Note that the implementation uses {@link #skip(InputStream, long)}.
1529     * This means that the method may be considerably less efficient than using the actual skip implementation,
1530     * this is done to guarantee that the correct number of characters are skipped.
1531     * </p>
1532     *
1533     * @param input the {@link InputStream} to read
1534     * @param output the {@link OutputStream} to write to
1535     * @param inputOffset : number of bytes to skip from input before copying
1536     * -ve values are ignored
1537     * @param length : number of bytes to copy. -ve means all
1538     * @param buffer the buffer to use for the copy
1539     * @return the number of bytes copied
1540     * @throws NullPointerException if the input or output is null
1541     * @throws IOException          if an I/O error occurs
1542     * @since 2.2
1543     */
1544    public static long copyLarge(final InputStream input, final OutputStream output,
1545                                 final long inputOffset, final long length, final byte[] buffer) throws IOException {
1546        if (inputOffset > 0) {
1547            skipFully(input, inputOffset);
1548        }
1549        if (length == 0) {
1550            return 0;
1551        }
1552        final int bufferLength = buffer.length;
1553        int bytesToRead = bufferLength;
1554        if (length > 0 && length < bufferLength) {
1555            bytesToRead = (int) length;
1556        }
1557        int read;
1558        long totalRead = 0;
1559        while (bytesToRead > 0 && EOF != (read = input.read(buffer, 0, bytesToRead))) {
1560            output.write(buffer, 0, read);
1561            totalRead += read;
1562            if (length > 0) { // only adjust length if not reading to the end
1563                // Note the cast must work because buffer.length is an integer
1564                bytesToRead = (int) Math.min(length - totalRead, bufferLength);
1565            }
1566        }
1567        return totalRead;
1568    }
1569
1570    /**
1571     * Copies chars from a large (over 2GB) {@link Reader} to a {@link Writer}.
1572     * <p>
1573     * This method buffers the input internally, so there is no need to use a
1574     * {@link BufferedReader}.
1575     * </p>
1576     * <p>
1577     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
1578     * </p>
1579     *
1580     * @param reader the {@link Reader} to source.
1581     * @param writer the {@link Writer} to target.
1582     * @return the number of characters copied
1583     * @throws NullPointerException if the input or output is null
1584     * @throws IOException          if an I/O error occurs
1585     * @since 1.3
1586     */
1587    public static long copyLarge(final Reader reader, final Writer writer) throws IOException {
1588        return copyLarge(reader, writer, getScratchCharArray());
1589    }
1590
1591    /**
1592     * Copies chars from a large (over 2GB) {@link Reader} to a {@link Writer}.
1593     * <p>
1594     * This method uses the provided buffer, so there is no need to use a
1595     * {@link BufferedReader}.
1596     * </p>
1597     *
1598     * @param reader the {@link Reader} to source.
1599     * @param writer the {@link Writer} to target.
1600     * @param buffer the buffer to be used for the copy
1601     * @return the number of characters copied
1602     * @throws NullPointerException if the input or output is null
1603     * @throws IOException          if an I/O error occurs
1604     * @since 2.2
1605     */
1606    public static long copyLarge(final Reader reader, final Writer writer, final char[] buffer) throws IOException {
1607        long count = 0;
1608        int n;
1609        while (EOF != (n = reader.read(buffer))) {
1610            writer.write(buffer, 0, n);
1611            count += n;
1612        }
1613        return count;
1614    }
1615
1616    /**
1617     * Copies some or all chars from a large (over 2GB) {@link InputStream} to an
1618     * {@link OutputStream}, optionally skipping input chars.
1619     * <p>
1620     * This method buffers the input internally, so there is no need to use a
1621     * {@link BufferedReader}.
1622     * </p>
1623     * <p>
1624     * The buffer size is given by {@link #DEFAULT_BUFFER_SIZE}.
1625     * </p>
1626     *
1627     * @param reader the {@link Reader} to read
1628     * @param writer the {@link Writer} to write to
1629     * @param inputOffset : number of chars to skip from input before copying
1630     * -ve values are ignored
1631     * @param length : number of chars to copy. -ve means all
1632     * @return the number of chars copied
1633     * @throws NullPointerException if the input or output is null
1634     * @throws IOException          if an I/O error occurs
1635     * @since 2.2
1636     */
1637    public static long copyLarge(final Reader reader, final Writer writer, final long inputOffset, final long length)
1638            throws IOException {
1639        return copyLarge(reader, writer, inputOffset, length, getScratchCharArray());
1640    }
1641
1642    /**
1643     * Copies some or all chars from a large (over 2GB) {@link InputStream} to an
1644     * {@link OutputStream}, optionally skipping input chars.
1645     * <p>
1646     * This method uses the provided buffer, so there is no need to use a
1647     * {@link BufferedReader}.
1648     * </p>
1649     *
1650     * @param reader the {@link Reader} to read
1651     * @param writer the {@link Writer} to write to
1652     * @param inputOffset : number of chars to skip from input before copying
1653     * -ve values are ignored
1654     * @param length : number of chars to copy. -ve means all
1655     * @param buffer the buffer to be used for the copy
1656     * @return the number of chars copied
1657     * @throws NullPointerException if the input or output is null
1658     * @throws IOException          if an I/O error occurs
1659     * @since 2.2
1660     */
1661    public static long copyLarge(final Reader reader, final Writer writer, final long inputOffset, final long length,
1662                                 final char[] buffer)
1663            throws IOException {
1664        if (inputOffset > 0) {
1665            skipFully(reader, inputOffset);
1666        }
1667        if (length == 0) {
1668            return 0;
1669        }
1670        int bytesToRead = buffer.length;
1671        if (length > 0 && length < buffer.length) {
1672            bytesToRead = (int) length;
1673        }
1674        int read;
1675        long totalRead = 0;
1676        while (bytesToRead > 0 && EOF != (read = reader.read(buffer, 0, bytesToRead))) {
1677            writer.write(buffer, 0, read);
1678            totalRead += read;
1679            if (length > 0) { // only adjust length if not reading to the end
1680                // Note the cast must work because buffer.length is an integer
1681                bytesToRead = (int) Math.min(length - totalRead, buffer.length);
1682            }
1683        }
1684        return totalRead;
1685    }
1686
1687    /**
1688     * Fills the given array with 0s.
1689     *
1690     * @param arr The array to fill.
1691     * @return The given array.
1692     */
1693    private static byte[] fill0(final byte[] arr) {
1694        Arrays.fill(arr, (byte) 0);
1695        return arr;
1696    }
1697
1698    /**
1699     * Fills the given array with 0s.
1700     *
1701     * @param arr The array to fill.
1702     * @return The given array.
1703     */
1704    private static char[] fill0(final char[] arr) {
1705        Arrays.fill(arr, (char) 0);
1706        return arr;
1707    }
1708
1709    /**
1710     * Gets the internal byte array buffer, intended for both reading and writing.
1711     *
1712     * @return the internal byte array buffer, intended for both reading and writing.
1713     */
1714    static byte[] getScratchByteArray() {
1715        return fill0(SCRATCH_BYTE_BUFFER_RW.get());
1716    }
1717
1718    /**
1719     * Gets the internal byte array intended for write only operations.
1720     *
1721     * @return the internal byte array intended for write only operations.
1722     */
1723    static byte[] getScratchByteArrayWriteOnly() {
1724        return fill0(SCRATCH_BYTE_BUFFER_WO);
1725    }
1726
1727    /**
1728     * Gets the char byte array buffer, intended for both reading and writing.
1729     *
1730     * @return the char byte array buffer, intended for both reading and writing.
1731     */
1732    static char[] getScratchCharArray() {
1733        return fill0(SCRATCH_CHAR_BUFFER_RW.get());
1734    }
1735
1736    /**
1737     * Gets the internal char array intended for write only operations.
1738     *
1739     * @return the internal char array intended for write only operations.
1740     */
1741    static char[] getScratchCharArrayWriteOnly() {
1742        return fill0(SCRATCH_CHAR_BUFFER_WO);
1743    }
1744
1745    /**
1746     * Returns the length of the given array in a null-safe manner.
1747     *
1748     * @param array an array or null
1749     * @return the array length -- or 0 if the given array is null.
1750     * @since 2.7
1751     */
1752    public static int length(final byte[] array) {
1753        return array == null ? 0 : array.length;
1754    }
1755
1756    /**
1757     * Returns the length of the given array in a null-safe manner.
1758     *
1759     * @param array an array or null
1760     * @return the array length -- or 0 if the given array is null.
1761     * @since 2.7
1762     */
1763    public static int length(final char[] array) {
1764        return array == null ? 0 : array.length;
1765    }
1766
1767    /**
1768     * Returns the length of the given CharSequence in a null-safe manner.
1769     *
1770     * @param csq a CharSequence or null
1771     * @return the CharSequence length -- or 0 if the given CharSequence is null.
1772     * @since 2.7
1773     */
1774    public static int length(final CharSequence csq) {
1775        return csq == null ? 0 : csq.length();
1776    }
1777
1778    /**
1779     * Returns the length of the given array in a null-safe manner.
1780     *
1781     * @param array an array or null
1782     * @return the array length -- or 0 if the given array is null.
1783     * @since 2.7
1784     */
1785    public static int length(final Object[] array) {
1786        return array == null ? 0 : array.length;
1787    }
1788
1789    /**
1790     * Returns an Iterator for the lines in an {@link InputStream}, using
1791     * the character encoding specified (or default encoding if null).
1792     * <p>
1793     * {@link LineIterator} holds a reference to the open
1794     * {@link InputStream} specified here. When you have finished with
1795     * the iterator you should close the stream to free internal resources.
1796     * This can be done by using a try-with-resources block, closing the stream directly, or by calling
1797     * {@link LineIterator#close()}.
1798     * </p>
1799     * <p>
1800     * The recommended usage pattern is:
1801     * </p>
1802     * <pre>
1803     * try {
1804     *   LineIterator it = IOUtils.lineIterator(stream, charset);
1805     *   while (it.hasNext()) {
1806     *     String line = it.nextLine();
1807     *     /// do something with line
1808     *   }
1809     * } finally {
1810     *   IOUtils.closeQuietly(stream);
1811     * }
1812     * </pre>
1813     *
1814     * @param input the {@link InputStream} to read, not null
1815     * @param charset the charset to use, null means platform default
1816     * @return an Iterator of the lines in the reader, never null
1817     * @throws IllegalArgumentException if the input is null
1818     * @since 2.3
1819     */
1820    public static LineIterator lineIterator(final InputStream input, final Charset charset) {
1821        return new LineIterator(new InputStreamReader(input, Charsets.toCharset(charset)));
1822    }
1823
1824    /**
1825     * Returns an Iterator for the lines in an {@link InputStream}, using
1826     * the character encoding specified (or default encoding if null).
1827     * <p>
1828     * {@link LineIterator} holds a reference to the open
1829     * {@link InputStream} specified here. When you have finished with
1830     * the iterator you should close the stream to free internal resources.
1831     * This can be done by using a try-with-resources block, closing the stream directly, or by calling
1832     * {@link LineIterator#close()}.
1833     * </p>
1834     * <p>
1835     * The recommended usage pattern is:
1836     * </p>
1837     * <pre>
1838     * try {
1839     *   LineIterator it = IOUtils.lineIterator(stream, StandardCharsets.UTF_8.name());
1840     *   while (it.hasNext()) {
1841     *     String line = it.nextLine();
1842     *     /// do something with line
1843     *   }
1844     * } finally {
1845     *   IOUtils.closeQuietly(stream);
1846     * }
1847     * </pre>
1848     *
1849     * @param input the {@link InputStream} to read, not null
1850     * @param charsetName the encoding to use, null means platform default
1851     * @return an Iterator of the lines in the reader, never null
1852     * @throws IllegalArgumentException                     if the input is null
1853     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
1854     *                                                      .UnsupportedEncodingException} in version 2.2 if the
1855     *                                                      encoding is not supported.
1856     * @since 1.2
1857     */
1858    public static LineIterator lineIterator(final InputStream input, final String charsetName) {
1859        return lineIterator(input, Charsets.toCharset(charsetName));
1860    }
1861
1862    /**
1863     * Returns an Iterator for the lines in a {@link Reader}.
1864     * <p>
1865     * {@link LineIterator} holds a reference to the open
1866     * {@link Reader} specified here. When you have finished with the
1867     * iterator you should close the reader to free internal resources.
1868     * This can be done by using a try-with-resources block, closing the reader directly, or by calling
1869     * {@link LineIterator#close()}.
1870     * </p>
1871     * <p>
1872     * The recommended usage pattern is:
1873     * </p>
1874     * <pre>
1875     * try {
1876     *   LineIterator it = IOUtils.lineIterator(reader);
1877     *   while (it.hasNext()) {
1878     *     String line = it.nextLine();
1879     *     /// do something with line
1880     *   }
1881     * } finally {
1882     *   IOUtils.closeQuietly(reader);
1883     * }
1884     * </pre>
1885     *
1886     * @param reader the {@link Reader} to read, not null
1887     * @return an Iterator of the lines in the reader, never null
1888     * @throws IllegalArgumentException if the reader is null
1889     * @since 1.2
1890     */
1891    public static LineIterator lineIterator(final Reader reader) {
1892        return new LineIterator(reader);
1893    }
1894
1895    /**
1896     * Reads bytes from an input stream.
1897     * This implementation guarantees that it will read as many bytes
1898     * as possible before giving up; this may not always be the case for
1899     * subclasses of {@link InputStream}.
1900     *
1901     * @param input where to read input from
1902     * @param buffer destination
1903     * @return actual length read; may be less than requested if EOF was reached
1904     * @throws IOException if a read error occurs
1905     * @since 2.2
1906     */
1907    public static int read(final InputStream input, final byte[] buffer) throws IOException {
1908        return read(input, buffer, 0, buffer.length);
1909    }
1910
1911    /**
1912     * Reads bytes from an input stream.
1913     * This implementation guarantees that it will read as many bytes
1914     * as possible before giving up; this may not always be the case for
1915     * subclasses of {@link InputStream}.
1916     *
1917     * @param input where to read input from
1918     * @param buffer destination
1919     * @param offset initial offset into buffer
1920     * @param length length to read, must be &gt;= 0
1921     * @return actual length read; may be less than requested if EOF was reached
1922     * @throws IllegalArgumentException if length is negative
1923     * @throws IOException              if a read error occurs
1924     * @since 2.2
1925     */
1926    public static int read(final InputStream input, final byte[] buffer, final int offset, final int length)
1927            throws IOException {
1928        if (length < 0) {
1929            throw new IllegalArgumentException("Length must not be negative: " + length);
1930        }
1931        int remaining = length;
1932        while (remaining > 0) {
1933            final int location = length - remaining;
1934            final int count = input.read(buffer, offset + location, remaining);
1935            if (EOF == count) { // EOF
1936                break;
1937            }
1938            remaining -= count;
1939        }
1940        return length - remaining;
1941    }
1942
1943    /**
1944     * Reads bytes from a ReadableByteChannel.
1945     * <p>
1946     * This implementation guarantees that it will read as many bytes
1947     * as possible before giving up; this may not always be the case for
1948     * subclasses of {@link ReadableByteChannel}.
1949     * </p>
1950     *
1951     * @param input the byte channel to read
1952     * @param buffer byte buffer destination
1953     * @return the actual length read; may be less than requested if EOF was reached
1954     * @throws IOException if a read error occurs
1955     * @since 2.5
1956     */
1957    public static int read(final ReadableByteChannel input, final ByteBuffer buffer) throws IOException {
1958        final int length = buffer.remaining();
1959        while (buffer.remaining() > 0) {
1960            final int count = input.read(buffer);
1961            if (EOF == count) { // EOF
1962                break;
1963            }
1964        }
1965        return length - buffer.remaining();
1966    }
1967
1968    /**
1969     * Reads characters from an input character stream.
1970     * This implementation guarantees that it will read as many characters
1971     * as possible before giving up; this may not always be the case for
1972     * subclasses of {@link Reader}.
1973     *
1974     * @param reader where to read input from
1975     * @param buffer destination
1976     * @return actual length read; may be less than requested if EOF was reached
1977     * @throws IOException if a read error occurs
1978     * @since 2.2
1979     */
1980    public static int read(final Reader reader, final char[] buffer) throws IOException {
1981        return read(reader, buffer, 0, buffer.length);
1982    }
1983
1984    /**
1985     * Reads characters from an input character stream.
1986     * This implementation guarantees that it will read as many characters
1987     * as possible before giving up; this may not always be the case for
1988     * subclasses of {@link Reader}.
1989     *
1990     * @param reader where to read input from
1991     * @param buffer destination
1992     * @param offset initial offset into buffer
1993     * @param length length to read, must be &gt;= 0
1994     * @return actual length read; may be less than requested if EOF was reached
1995     * @throws IllegalArgumentException if length is negative
1996     * @throws IOException              if a read error occurs
1997     * @since 2.2
1998     */
1999    public static int read(final Reader reader, final char[] buffer, final int offset, final int length)
2000            throws IOException {
2001        if (length < 0) {
2002            throw new IllegalArgumentException("Length must not be negative: " + length);
2003        }
2004        int remaining = length;
2005        while (remaining > 0) {
2006            final int location = length - remaining;
2007            final int count = reader.read(buffer, offset + location, remaining);
2008            if (EOF == count) { // EOF
2009                break;
2010            }
2011            remaining -= count;
2012        }
2013        return length - remaining;
2014    }
2015
2016    /**
2017     * Reads the requested number of bytes or fail if there are not enough left.
2018     * <p>
2019     * This allows for the possibility that {@link InputStream#read(byte[], int, int)} may
2020     * not read as many bytes as requested (most likely because of reaching EOF).
2021     * </p>
2022     *
2023     * @param input where to read input from
2024     * @param buffer destination
2025     *
2026     * @throws IOException              if there is a problem reading the file
2027     * @throws IllegalArgumentException if length is negative
2028     * @throws EOFException             if the number of bytes read was incorrect
2029     * @since 2.2
2030     */
2031    public static void readFully(final InputStream input, final byte[] buffer) throws IOException {
2032        readFully(input, buffer, 0, buffer.length);
2033    }
2034
2035    /**
2036     * Reads the requested number of bytes or fail if there are not enough left.
2037     * <p>
2038     * This allows for the possibility that {@link InputStream#read(byte[], int, int)} may
2039     * not read as many bytes as requested (most likely because of reaching EOF).
2040     * </p>
2041     *
2042     * @param input where to read input from
2043     * @param buffer destination
2044     * @param offset initial offset into buffer
2045     * @param length length to read, must be &gt;= 0
2046     *
2047     * @throws IOException              if there is a problem reading the file
2048     * @throws IllegalArgumentException if length is negative
2049     * @throws EOFException             if the number of bytes read was incorrect
2050     * @since 2.2
2051     */
2052    public static void readFully(final InputStream input, final byte[] buffer, final int offset, final int length)
2053            throws IOException {
2054        final int actual = read(input, buffer, offset, length);
2055        if (actual != length) {
2056            throw new EOFException("Length to read: " + length + " actual: " + actual);
2057        }
2058    }
2059
2060    /**
2061     * Reads the requested number of bytes or fail if there are not enough left.
2062     * <p>
2063     * This allows for the possibility that {@link InputStream#read(byte[], int, int)} may
2064     * not read as many bytes as requested (most likely because of reaching EOF).
2065     * </p>
2066     *
2067     * @param input where to read input from
2068     * @param length length to read, must be &gt;= 0
2069     * @return the bytes read from input
2070     * @throws IOException              if there is a problem reading the file
2071     * @throws IllegalArgumentException if length is negative
2072     * @throws EOFException             if the number of bytes read was incorrect
2073     * @since 2.5
2074     */
2075    public static byte[] readFully(final InputStream input, final int length) throws IOException {
2076        final byte[] buffer = byteArray(length);
2077        readFully(input, buffer, 0, buffer.length);
2078        return buffer;
2079    }
2080
2081    /**
2082     * Reads the requested number of bytes or fail if there are not enough left.
2083     * <p>
2084     * This allows for the possibility that {@link ReadableByteChannel#read(ByteBuffer)} may
2085     * not read as many bytes as requested (most likely because of reaching EOF).
2086     * </p>
2087     *
2088     * @param input the byte channel to read
2089     * @param buffer byte buffer destination
2090     * @throws IOException  if there is a problem reading the file
2091     * @throws EOFException if the number of bytes read was incorrect
2092     * @since 2.5
2093     */
2094    public static void readFully(final ReadableByteChannel input, final ByteBuffer buffer) throws IOException {
2095        final int expected = buffer.remaining();
2096        final int actual = read(input, buffer);
2097        if (actual != expected) {
2098            throw new EOFException("Length to read: " + expected + " actual: " + actual);
2099        }
2100    }
2101
2102    /**
2103     * Reads the requested number of characters or fail if there are not enough left.
2104     * <p>
2105     * This allows for the possibility that {@link Reader#read(char[], int, int)} may
2106     * not read as many characters as requested (most likely because of reaching EOF).
2107     * </p>
2108     *
2109     * @param reader where to read input from
2110     * @param buffer destination
2111     * @throws IOException              if there is a problem reading the file
2112     * @throws IllegalArgumentException if length is negative
2113     * @throws EOFException             if the number of characters read was incorrect
2114     * @since 2.2
2115     */
2116    public static void readFully(final Reader reader, final char[] buffer) throws IOException {
2117        readFully(reader, buffer, 0, buffer.length);
2118    }
2119
2120    /**
2121     * Reads the requested number of characters or fail if there are not enough left.
2122     * <p>
2123     * This allows for the possibility that {@link Reader#read(char[], int, int)} may
2124     * not read as many characters as requested (most likely because of reaching EOF).
2125     * </p>
2126     *
2127     * @param reader where to read input from
2128     * @param buffer destination
2129     * @param offset initial offset into buffer
2130     * @param length length to read, must be &gt;= 0
2131     * @throws IOException              if there is a problem reading the file
2132     * @throws IllegalArgumentException if length is negative
2133     * @throws EOFException             if the number of characters read was incorrect
2134     * @since 2.2
2135     */
2136    public static void readFully(final Reader reader, final char[] buffer, final int offset, final int length)
2137            throws IOException {
2138        final int actual = read(reader, buffer, offset, length);
2139        if (actual != length) {
2140            throw new EOFException("Length to read: " + length + " actual: " + actual);
2141        }
2142    }
2143
2144    /**
2145     * Gets the contents of an {@link InputStream} as a list of Strings,
2146     * one entry per line, using the default character encoding of the platform.
2147     * <p>
2148     * This method buffers the input internally, so there is no need to use a
2149     * {@link BufferedInputStream}.
2150     * </p>
2151     *
2152     * @param input the {@link InputStream} to read, not null
2153     * @return the list of Strings, never null
2154     * @throws NullPointerException if the input is null
2155     * @throws UncheckedIOException if an I/O error occurs
2156     * @since 1.1
2157     * @deprecated 2.5 use {@link #readLines(InputStream, Charset)} instead
2158     */
2159    @Deprecated
2160    public static List<String> readLines(final InputStream input) throws UncheckedIOException {
2161        return readLines(input, Charset.defaultCharset());
2162    }
2163
2164    /**
2165     * Gets the contents of an {@link InputStream} as a list of Strings,
2166     * one entry per line, using the specified character encoding.
2167     * <p>
2168     * This method buffers the input internally, so there is no need to use a
2169     * {@link BufferedInputStream}.
2170     * </p>
2171     *
2172     * @param input the {@link InputStream} to read, not null
2173     * @param charset the charset to use, null means platform default
2174     * @return the list of Strings, never null
2175     * @throws NullPointerException if the input is null
2176     * @throws UncheckedIOException if an I/O error occurs
2177     * @since 2.3
2178     */
2179    public static List<String> readLines(final InputStream input, final Charset charset) throws UncheckedIOException {
2180        return readLines(new InputStreamReader(input, Charsets.toCharset(charset)));
2181    }
2182
2183    /**
2184     * Gets the contents of an {@link InputStream} as a list of Strings,
2185     * one entry per line, using the specified character encoding.
2186     * <p>
2187     * Character encoding names can be found at
2188     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
2189     * </p>
2190     * <p>
2191     * This method buffers the input internally, so there is no need to use a
2192     * {@link BufferedInputStream}.
2193     * </p>
2194     *
2195     * @param input the {@link InputStream} to read, not null
2196     * @param charsetName the name of the requested charset, null means platform default
2197     * @return the list of Strings, never null
2198     * @throws NullPointerException                         if the input is null
2199     * @throws UncheckedIOException                         if an I/O error occurs
2200     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
2201     *                                                      .UnsupportedEncodingException} in version 2.2 if the
2202     *                                                      encoding is not supported.
2203     * @since 1.1
2204     */
2205    public static List<String> readLines(final InputStream input, final String charsetName) throws UncheckedIOException {
2206        return readLines(input, Charsets.toCharset(charsetName));
2207    }
2208
2209    /**
2210     * Gets the contents of a {@link Reader} as a list of Strings,
2211     * one entry per line.
2212     * <p>
2213     * This method buffers the input internally, so there is no need to use a
2214     * {@link BufferedReader}.
2215     * </p>
2216     *
2217     * @param reader the {@link Reader} to read, not null
2218     * @return the list of Strings, never null
2219     * @throws NullPointerException if the input is null
2220     * @throws UncheckedIOException if an I/O error occurs
2221     * @since 1.1
2222     */
2223    @SuppressWarnings("resource") // reader wraps input and is the responsibility of the caller.
2224    public static List<String> readLines(final Reader reader) throws UncheckedIOException {
2225        return toBufferedReader(reader).lines().collect(Collectors.toList());
2226    }
2227
2228    /**
2229     * Gets the contents of a resource as a byte array.
2230     * <p>
2231     * Delegates to {@link #resourceToByteArray(String, ClassLoader) resourceToByteArray(String, null)}.
2232     * </p>
2233     *
2234     * @param name The resource name.
2235     * @return the requested byte array
2236     * @throws IOException if an I/O error occurs or the resource is not found.
2237     * @see #resourceToByteArray(String, ClassLoader)
2238     * @since 2.6
2239     */
2240    public static byte[] resourceToByteArray(final String name) throws IOException {
2241        return resourceToByteArray(name, null);
2242    }
2243
2244    /**
2245     * Gets the contents of a resource as a byte array.
2246     * <p>
2247     * Delegates to {@link #resourceToURL(String, ClassLoader)}.
2248     * </p>
2249     *
2250     * @param name The resource name.
2251     * @param classLoader the class loader that the resolution of the resource is delegated to
2252     * @return the requested byte array
2253     * @throws IOException if an I/O error occurs or the resource is not found.
2254     * @see #resourceToURL(String, ClassLoader)
2255     * @since 2.6
2256     */
2257    public static byte[] resourceToByteArray(final String name, final ClassLoader classLoader) throws IOException {
2258        return toByteArray(resourceToURL(name, classLoader));
2259    }
2260
2261    /**
2262     * Gets the contents of a resource as a String using the specified character encoding.
2263     * <p>
2264     * Delegates to {@link #resourceToString(String, Charset, ClassLoader) resourceToString(String, Charset, null)}.
2265     * </p>
2266     *
2267     * @param name The resource name.
2268     * @param charset the charset to use, null means platform default
2269     * @return the requested String
2270     * @throws IOException if an I/O error occurs or the resource is not found.
2271     * @see #resourceToString(String, Charset, ClassLoader)
2272     * @since 2.6
2273     */
2274    public static String resourceToString(final String name, final Charset charset) throws IOException {
2275        return resourceToString(name, charset, null);
2276    }
2277
2278    /**
2279     * Gets the contents of a resource as a String using the specified character encoding.
2280     * <p>
2281     * Delegates to {@link #resourceToURL(String, ClassLoader)}.
2282     * </p>
2283     *
2284     * @param name The resource name.
2285     * @param charset the Charset to use, null means platform default
2286     * @param classLoader the class loader that the resolution of the resource is delegated to
2287     * @return the requested String
2288     * @throws IOException if an I/O error occurs.
2289     * @see #resourceToURL(String, ClassLoader)
2290     * @since 2.6
2291     */
2292    public static String resourceToString(final String name, final Charset charset, final ClassLoader classLoader) throws IOException {
2293        return toString(resourceToURL(name, classLoader), charset);
2294    }
2295
2296    /**
2297     * Gets a URL pointing to the given resource.
2298     * <p>
2299     * Delegates to {@link #resourceToURL(String, ClassLoader) resourceToURL(String, null)}.
2300     * </p>
2301     *
2302     * @param name The resource name.
2303     * @return A URL object for reading the resource.
2304     * @throws IOException if the resource is not found.
2305     * @since 2.6
2306     */
2307    public static URL resourceToURL(final String name) throws IOException {
2308        return resourceToURL(name, null);
2309    }
2310
2311    /**
2312     * Gets a URL pointing to the given resource.
2313     * <p>
2314     * If the {@code classLoader} is not null, call {@link ClassLoader#getResource(String)}, otherwise call
2315     * {@link Class#getResource(String) IOUtils.class.getResource(name)}.
2316     * </p>
2317     *
2318     * @param name The resource name.
2319     * @param classLoader Delegate to this class loader if not null
2320     * @return A URL object for reading the resource.
2321     * @throws IOException if the resource is not found.
2322     * @since 2.6
2323     */
2324    public static URL resourceToURL(final String name, final ClassLoader classLoader) throws IOException {
2325        // What about the thread context class loader?
2326        // What about the system class loader?
2327        final URL resource = classLoader == null ? IOUtils.class.getResource(name) : classLoader.getResource(name);
2328        if (resource == null) {
2329            throw new IOException("Resource not found: " + name);
2330        }
2331        return resource;
2332    }
2333
2334    /**
2335     * Skips bytes from an input byte stream.
2336     * This implementation guarantees that it will read as many bytes
2337     * as possible before giving up; this may not always be the case for
2338     * skip() implementations in subclasses of {@link InputStream}.
2339     * <p>
2340     * Note that the implementation uses {@link InputStream#read(byte[], int, int)} rather
2341     * than delegating to {@link InputStream#skip(long)}.
2342     * This means that the method may be considerably less efficient than using the actual skip implementation,
2343     * this is done to guarantee that the correct number of bytes are skipped.
2344     * </p>
2345     *
2346     * @param input byte stream to skip
2347     * @param toSkip number of bytes to skip.
2348     * @return number of bytes actually skipped.
2349     * @throws IOException              if there is a problem reading the file
2350     * @throws IllegalArgumentException if toSkip is negative
2351     * @see InputStream#skip(long)
2352     * @see <a href="https://issues.apache.org/jira/browse/IO-203">IO-203 - Add skipFully() method for InputStreams</a>
2353     * @since 2.0
2354     */
2355    public static long skip(final InputStream input, final long toSkip) throws IOException {
2356        if (toSkip < 0) {
2357            throw new IllegalArgumentException("Skip count must be non-negative, actual: " + toSkip);
2358        }
2359        //
2360        // No need to synchronize access to SCRATCH_BYTE_BUFFER_WO: We don't care if the buffer is written multiple
2361        // times or in parallel since the data is ignored. We reuse the same buffer, if the buffer size were variable or read-write,
2362        // we would need to synch or use a thread local to ensure some other thread safety.
2363        //
2364        long remain = toSkip;
2365        while (remain > 0) {
2366            // See https://issues.apache.org/jira/browse/IO-203 for why we use read() rather than delegating to skip()
2367            final byte[] byteArray = getScratchByteArrayWriteOnly();
2368            final long n = input.read(byteArray, 0, (int) Math.min(remain, byteArray.length));
2369            if (n < 0) { // EOF
2370                break;
2371            }
2372            remain -= n;
2373        }
2374        return toSkip - remain;
2375    }
2376
2377    /**
2378     * Skips bytes from a ReadableByteChannel.
2379     * This implementation guarantees that it will read as many bytes
2380     * as possible before giving up.
2381     *
2382     * @param input ReadableByteChannel to skip
2383     * @param toSkip number of bytes to skip.
2384     * @return number of bytes actually skipped.
2385     * @throws IOException              if there is a problem reading the ReadableByteChannel
2386     * @throws IllegalArgumentException if toSkip is negative
2387     * @since 2.5
2388     */
2389    public static long skip(final ReadableByteChannel input, final long toSkip) throws IOException {
2390        if (toSkip < 0) {
2391            throw new IllegalArgumentException("Skip count must be non-negative, actual: " + toSkip);
2392        }
2393        final ByteBuffer skipByteBuffer = ByteBuffer.allocate((int) Math.min(toSkip, DEFAULT_BUFFER_SIZE));
2394        long remain = toSkip;
2395        while (remain > 0) {
2396            skipByteBuffer.position(0);
2397            skipByteBuffer.limit((int) Math.min(remain, DEFAULT_BUFFER_SIZE));
2398            final int n = input.read(skipByteBuffer);
2399            if (n == EOF) {
2400                break;
2401            }
2402            remain -= n;
2403        }
2404        return toSkip - remain;
2405    }
2406
2407    /**
2408     * Skips characters from an input character stream.
2409     * This implementation guarantees that it will read as many characters
2410     * as possible before giving up; this may not always be the case for
2411     * skip() implementations in subclasses of {@link Reader}.
2412     * <p>
2413     * Note that the implementation uses {@link Reader#read(char[], int, int)} rather
2414     * than delegating to {@link Reader#skip(long)}.
2415     * This means that the method may be considerably less efficient than using the actual skip implementation,
2416     * this is done to guarantee that the correct number of characters are skipped.
2417     * </p>
2418     *
2419     * @param reader character stream to skip
2420     * @param toSkip number of characters to skip.
2421     * @return number of characters actually skipped.
2422     * @throws IOException              if there is a problem reading the file
2423     * @throws IllegalArgumentException if toSkip is negative
2424     * @see Reader#skip(long)
2425     * @see <a href="https://issues.apache.org/jira/browse/IO-203">IO-203 - Add skipFully() method for InputStreams</a>
2426     * @since 2.0
2427     */
2428    public static long skip(final Reader reader, final long toSkip) throws IOException {
2429        if (toSkip < 0) {
2430            throw new IllegalArgumentException("Skip count must be non-negative, actual: " + toSkip);
2431        }
2432        long remain = toSkip;
2433        while (remain > 0) {
2434            // See https://issues.apache.org/jira/browse/IO-203 for why we use read() rather than delegating to skip()
2435            final char[] charArray = getScratchCharArrayWriteOnly();
2436            final long n = reader.read(charArray, 0, (int) Math.min(remain, charArray.length));
2437            if (n < 0) { // EOF
2438                break;
2439            }
2440            remain -= n;
2441        }
2442        return toSkip - remain;
2443    }
2444
2445    /**
2446     * Skips the requested number of bytes or fail if there are not enough left.
2447     * <p>
2448     * This allows for the possibility that {@link InputStream#skip(long)} may
2449     * not skip as many bytes as requested (most likely because of reaching EOF).
2450     * </p>
2451     * <p>
2452     * Note that the implementation uses {@link #skip(InputStream, long)}.
2453     * This means that the method may be considerably less efficient than using the actual skip implementation,
2454     * this is done to guarantee that the correct number of characters are skipped.
2455     * </p>
2456     *
2457     * @param input stream to skip
2458     * @param toSkip the number of bytes to skip
2459     * @throws IOException              if there is a problem reading the file
2460     * @throws IllegalArgumentException if toSkip is negative
2461     * @throws EOFException             if the number of bytes skipped was incorrect
2462     * @see InputStream#skip(long)
2463     * @since 2.0
2464     */
2465    public static void skipFully(final InputStream input, final long toSkip) throws IOException {
2466        if (toSkip < 0) {
2467            throw new IllegalArgumentException("Bytes to skip must not be negative: " + toSkip);
2468        }
2469        final long skipped = skip(input, toSkip);
2470        if (skipped != toSkip) {
2471            throw new EOFException("Bytes to skip: " + toSkip + " actual: " + skipped);
2472        }
2473    }
2474
2475    /**
2476     * Skips the requested number of bytes or fail if there are not enough left.
2477     *
2478     * @param input ReadableByteChannel to skip
2479     * @param toSkip the number of bytes to skip
2480     * @throws IOException              if there is a problem reading the ReadableByteChannel
2481     * @throws IllegalArgumentException if toSkip is negative
2482     * @throws EOFException             if the number of bytes skipped was incorrect
2483     * @since 2.5
2484     */
2485    public static void skipFully(final ReadableByteChannel input, final long toSkip) throws IOException {
2486        if (toSkip < 0) {
2487            throw new IllegalArgumentException("Bytes to skip must not be negative: " + toSkip);
2488        }
2489        final long skipped = skip(input, toSkip);
2490        if (skipped != toSkip) {
2491            throw new EOFException("Bytes to skip: " + toSkip + " actual: " + skipped);
2492        }
2493    }
2494
2495    /**
2496     * Skips the requested number of characters or fail if there are not enough left.
2497     * <p>
2498     * This allows for the possibility that {@link Reader#skip(long)} may
2499     * not skip as many characters as requested (most likely because of reaching EOF).
2500     * </p>
2501     * <p>
2502     * Note that the implementation uses {@link #skip(Reader, long)}.
2503     * This means that the method may be considerably less efficient than using the actual skip implementation,
2504     * this is done to guarantee that the correct number of characters are skipped.
2505     * </p>
2506     *
2507     * @param reader stream to skip
2508     * @param toSkip the number of characters to skip
2509     * @throws IOException              if there is a problem reading the file
2510     * @throws IllegalArgumentException if toSkip is negative
2511     * @throws EOFException             if the number of characters skipped was incorrect
2512     * @see Reader#skip(long)
2513     * @since 2.0
2514     */
2515    public static void skipFully(final Reader reader, final long toSkip) throws IOException {
2516        final long skipped = skip(reader, toSkip);
2517        if (skipped != toSkip) {
2518            throw new EOFException("Chars to skip: " + toSkip + " actual: " + skipped);
2519        }
2520    }
2521
2522    /**
2523     * Fetches entire contents of an {@link InputStream} and represent
2524     * same data as result InputStream.
2525     * <p>
2526     * This method is useful where,
2527     * </p>
2528     * <ul>
2529     * <li>Source InputStream is slow.</li>
2530     * <li>It has network resources associated, so we cannot keep it open for
2531     * long time.</li>
2532     * <li>It has network timeout associated.</li>
2533     * </ul>
2534     * <p>
2535     * It can be used in favor of {@link #toByteArray(InputStream)}, since it
2536     * avoids unnecessary allocation and copy of byte[].<br>
2537     * This method buffers the input internally, so there is no need to use a
2538     * {@link BufferedInputStream}.
2539     * </p>
2540     *
2541     * @param input Stream to be fully buffered.
2542     * @return A fully buffered stream.
2543     * @throws IOException if an I/O error occurs.
2544     * @since 2.0
2545     */
2546    public static InputStream toBufferedInputStream(final InputStream input) throws IOException {
2547        return ByteArrayOutputStream.toBufferedInputStream(input);
2548    }
2549
2550    /**
2551     * Fetches entire contents of an {@link InputStream} and represent
2552     * same data as result InputStream.
2553     * <p>
2554     * This method is useful where,
2555     * </p>
2556     * <ul>
2557     * <li>Source InputStream is slow.</li>
2558     * <li>It has network resources associated, so we cannot keep it open for
2559     * long time.</li>
2560     * <li>It has network timeout associated.</li>
2561     * </ul>
2562     * <p>
2563     * It can be used in favor of {@link #toByteArray(InputStream)}, since it
2564     * avoids unnecessary allocation and copy of byte[].<br>
2565     * This method buffers the input internally, so there is no need to use a
2566     * {@link BufferedInputStream}.
2567     * </p>
2568     *
2569     * @param input Stream to be fully buffered.
2570     * @param size the initial buffer size
2571     * @return A fully buffered stream.
2572     * @throws IOException if an I/O error occurs.
2573     * @since 2.5
2574     */
2575    public static InputStream toBufferedInputStream(final InputStream input, final int size) throws IOException {
2576        return ByteArrayOutputStream.toBufferedInputStream(input, size);
2577    }
2578
2579    /**
2580     * Returns the given reader if it is a {@link BufferedReader}, otherwise creates a BufferedReader from the given
2581     * reader.
2582     *
2583     * @param reader the reader to wrap or return (not null)
2584     * @return the given reader or a new {@link BufferedReader} for the given reader
2585     * @throws NullPointerException if the input parameter is null
2586     * @see #buffer(Reader)
2587     * @since 2.2
2588     */
2589    public static BufferedReader toBufferedReader(final Reader reader) {
2590        return reader instanceof BufferedReader ? (BufferedReader) reader : new BufferedReader(reader);
2591    }
2592
2593    /**
2594     * Returns the given reader if it is a {@link BufferedReader}, otherwise creates a BufferedReader from the given
2595     * reader.
2596     *
2597     * @param reader the reader to wrap or return (not null)
2598     * @param size the buffer size, if a new BufferedReader is created.
2599     * @return the given reader or a new {@link BufferedReader} for the given reader
2600     * @throws NullPointerException if the input parameter is null
2601     * @see #buffer(Reader)
2602     * @since 2.5
2603     */
2604    public static BufferedReader toBufferedReader(final Reader reader, final int size) {
2605        return reader instanceof BufferedReader ? (BufferedReader) reader : new BufferedReader(reader, size);
2606    }
2607
2608    /**
2609     * Gets the contents of an {@link InputStream} as a {@code byte[]}.
2610     * <p>
2611     * This method buffers the input internally, so there is no need to use a
2612     * {@link BufferedInputStream}.
2613     * </p>
2614     *
2615     * @param inputStream the {@link InputStream} to read.
2616     * @return the requested byte array.
2617     * @throws NullPointerException if the InputStream is {@code null}.
2618     * @throws IOException if an I/O error occurs or reading more than {@link Integer#MAX_VALUE} occurs.
2619     */
2620    public static byte[] toByteArray(final InputStream inputStream) throws IOException {
2621        // We use a ThresholdingOutputStream to avoid reading AND writing more than Integer.MAX_VALUE.
2622        try (UnsynchronizedByteArrayOutputStream ubaOutput = UnsynchronizedByteArrayOutputStream.builder().get();
2623            ThresholdingOutputStream thresholdOutput = new ThresholdingOutputStream(Integer.MAX_VALUE, os -> {
2624                throw new IllegalArgumentException(String.format("Cannot read more than %,d into a byte array", Integer.MAX_VALUE));
2625            }, os -> ubaOutput)) {
2626            copy(inputStream, thresholdOutput);
2627            return ubaOutput.toByteArray();
2628        }
2629    }
2630
2631    /**
2632     * Gets the contents of an {@link InputStream} as a {@code byte[]}. Use this method instead of
2633     * {@link #toByteArray(InputStream)} when {@link InputStream} size is known.
2634     *
2635     * @param input the {@link InputStream} to read.
2636     * @param size the size of {@link InputStream} to read, where 0 &lt; {@code size} &lt;= length of input stream.
2637     * @return byte [] of length {@code size}.
2638     * @throws IOException if an I/O error occurs or {@link InputStream} length is smaller than parameter {@code size}.
2639     * @throws IllegalArgumentException if {@code size} is less than zero.
2640     * @since 2.1
2641     */
2642    public static byte[] toByteArray(final InputStream input, final int size) throws IOException {
2643
2644        if (size < 0) {
2645            throw new IllegalArgumentException("Size must be equal or greater than zero: " + size);
2646        }
2647
2648        if (size == 0) {
2649            return EMPTY_BYTE_ARRAY;
2650        }
2651
2652        final byte[] data = byteArray(size);
2653        int offset = 0;
2654        int read;
2655
2656        while (offset < size && (read = input.read(data, offset, size - offset)) != EOF) {
2657            offset += read;
2658        }
2659
2660        if (offset != size) {
2661            throw new IOException("Unexpected read size, current: " + offset + ", expected: " + size);
2662        }
2663
2664        return data;
2665    }
2666
2667    /**
2668     * Gets contents of an {@link InputStream} as a {@code byte[]}.
2669     * Use this method instead of {@link #toByteArray(InputStream)}
2670     * when {@link InputStream} size is known.
2671     * <b>NOTE:</b> the method checks that the length can safely be cast to an int without truncation
2672     * before using {@link IOUtils#toByteArray(InputStream, int)} to read into the byte array.
2673     * (Arrays can have no more than Integer.MAX_VALUE entries anyway)
2674     *
2675     * @param input the {@link InputStream} to read
2676     * @param size the size of {@link InputStream} to read, where 0 &lt; {@code size} &lt;= min(Integer.MAX_VALUE, length of input stream).
2677     * @return byte [] the requested byte array, of length {@code size}
2678     * @throws IOException              if an I/O error occurs or {@link InputStream} length is less than {@code size}
2679     * @throws IllegalArgumentException if size is less than zero or size is greater than Integer.MAX_VALUE
2680     * @see IOUtils#toByteArray(InputStream, int)
2681     * @since 2.1
2682     */
2683    public static byte[] toByteArray(final InputStream input, final long size) throws IOException {
2684        if (size > Integer.MAX_VALUE) {
2685            throw new IllegalArgumentException("Size cannot be greater than Integer max value: " + size);
2686        }
2687        return toByteArray(input, (int) size);
2688    }
2689
2690    /**
2691     * Gets the contents of a {@link Reader} as a {@code byte[]}
2692     * using the default character encoding of the platform.
2693     * <p>
2694     * This method buffers the input internally, so there is no need to use a
2695     * {@link BufferedReader}.
2696     * </p>
2697     *
2698     * @param reader the {@link Reader} to read
2699     * @return the requested byte array
2700     * @throws NullPointerException if the input is null
2701     * @throws IOException          if an I/O error occurs
2702     * @deprecated 2.5 use {@link #toByteArray(Reader, Charset)} instead
2703     */
2704    @Deprecated
2705    public static byte[] toByteArray(final Reader reader) throws IOException {
2706        return toByteArray(reader, Charset.defaultCharset());
2707    }
2708
2709    /**
2710     * Gets the contents of a {@link Reader} as a {@code byte[]}
2711     * using the specified character encoding.
2712     * <p>
2713     * This method buffers the input internally, so there is no need to use a
2714     * {@link BufferedReader}.
2715     * </p>
2716     *
2717     * @param reader the {@link Reader} to read
2718     * @param charset the charset to use, null means platform default
2719     * @return the requested byte array
2720     * @throws NullPointerException if the input is null
2721     * @throws IOException          if an I/O error occurs
2722     * @since 2.3
2723     */
2724    public static byte[] toByteArray(final Reader reader, final Charset charset) throws IOException {
2725        try (ByteArrayOutputStream output = new ByteArrayOutputStream()) {
2726            copy(reader, output, charset);
2727            return output.toByteArray();
2728        }
2729    }
2730
2731    /**
2732     * Gets the contents of a {@link Reader} as a {@code byte[]}
2733     * using the specified character encoding.
2734     * <p>
2735     * Character encoding names can be found at
2736     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
2737     * </p>
2738     * <p>
2739     * This method buffers the input internally, so there is no need to use a
2740     * {@link BufferedReader}.
2741     * </p>
2742     *
2743     * @param reader the {@link Reader} to read
2744     * @param charsetName the name of the requested charset, null means platform default
2745     * @return the requested byte array
2746     * @throws NullPointerException                         if the input is null
2747     * @throws IOException                                  if an I/O error occurs
2748     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
2749     *                                                      .UnsupportedEncodingException} in version 2.2 if the
2750     *                                                      encoding is not supported.
2751     * @since 1.1
2752     */
2753    public static byte[] toByteArray(final Reader reader, final String charsetName) throws IOException {
2754        return toByteArray(reader, Charsets.toCharset(charsetName));
2755    }
2756
2757    /**
2758     * Gets the contents of a {@link String} as a {@code byte[]}
2759     * using the default character encoding of the platform.
2760     * <p>
2761     * This is the same as {@link String#getBytes()}.
2762     * </p>
2763     *
2764     * @param input the {@link String} to convert
2765     * @return the requested byte array
2766     * @throws NullPointerException if the input is null
2767     * @deprecated 2.5 Use {@link String#getBytes()} instead
2768     */
2769    @Deprecated
2770    public static byte[] toByteArray(final String input) {
2771        // make explicit the use of the default charset
2772        return input.getBytes(Charset.defaultCharset());
2773    }
2774
2775    /**
2776     * Gets the contents of a {@link URI} as a {@code byte[]}.
2777     *
2778     * @param uri the {@link URI} to read
2779     * @return the requested byte array
2780     * @throws NullPointerException if the uri is null
2781     * @throws IOException          if an I/O exception occurs
2782     * @since 2.4
2783     */
2784    public static byte[] toByteArray(final URI uri) throws IOException {
2785        return toByteArray(uri.toURL());
2786    }
2787
2788    /**
2789     * Gets the contents of a {@link URL} as a {@code byte[]}.
2790     *
2791     * @param url the {@link URL} to read
2792     * @return the requested byte array
2793     * @throws NullPointerException if the input is null
2794     * @throws IOException          if an I/O exception occurs
2795     * @since 2.4
2796     */
2797    public static byte[] toByteArray(final URL url) throws IOException {
2798        try (CloseableURLConnection urlConnection = CloseableURLConnection.open(url)) {
2799            return toByteArray(urlConnection);
2800        }
2801    }
2802
2803    /**
2804     * Gets the contents of a {@link URLConnection} as a {@code byte[]}.
2805     *
2806     * @param urlConnection the {@link URLConnection} to read.
2807     * @return the requested byte array.
2808     * @throws NullPointerException if the urlConn is null.
2809     * @throws IOException if an I/O exception occurs.
2810     * @since 2.4
2811     */
2812    public static byte[] toByteArray(final URLConnection urlConnection) throws IOException {
2813        try (InputStream inputStream = urlConnection.getInputStream()) {
2814            return toByteArray(inputStream);
2815        }
2816    }
2817
2818    /**
2819     * Gets the contents of an {@link InputStream} as a character array
2820     * using the default character encoding of the platform.
2821     * <p>
2822     * This method buffers the input internally, so there is no need to use a
2823     * {@link BufferedInputStream}.
2824     * </p>
2825     *
2826     * @param inputStream the {@link InputStream} to read
2827     * @return the requested character array
2828     * @throws NullPointerException if the input is null
2829     * @throws IOException          if an I/O error occurs
2830     * @since 1.1
2831     * @deprecated 2.5 use {@link #toCharArray(InputStream, Charset)} instead
2832     */
2833    @Deprecated
2834    public static char[] toCharArray(final InputStream inputStream) throws IOException {
2835        return toCharArray(inputStream, Charset.defaultCharset());
2836    }
2837
2838    /**
2839     * Gets the contents of an {@link InputStream} as a character array
2840     * using the specified character encoding.
2841     * <p>
2842     * This method buffers the input internally, so there is no need to use a
2843     * {@link BufferedInputStream}.
2844     * </p>
2845     *
2846     * @param inputStream the {@link InputStream} to read
2847     * @param charset the charset to use, null means platform default
2848     * @return the requested character array
2849     * @throws NullPointerException if the input is null
2850     * @throws IOException          if an I/O error occurs
2851     * @since 2.3
2852     */
2853    public static char[] toCharArray(final InputStream inputStream, final Charset charset)
2854            throws IOException {
2855        final CharArrayWriter writer = new CharArrayWriter();
2856        copy(inputStream, writer, charset);
2857        return writer.toCharArray();
2858    }
2859
2860    /**
2861     * Gets the contents of an {@link InputStream} as a character array
2862     * using the specified character encoding.
2863     * <p>
2864     * Character encoding names can be found at
2865     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
2866     * </p>
2867     * <p>
2868     * This method buffers the input internally, so there is no need to use a
2869     * {@link BufferedInputStream}.
2870     * </p>
2871     *
2872     * @param inputStream the {@link InputStream} to read
2873     * @param charsetName the name of the requested charset, null means platform default
2874     * @return the requested character array
2875     * @throws NullPointerException                         if the input is null
2876     * @throws IOException                                  if an I/O error occurs
2877     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
2878     *                                                      .UnsupportedEncodingException} in version 2.2 if the
2879     *                                                      encoding is not supported.
2880     * @since 1.1
2881     */
2882    public static char[] toCharArray(final InputStream inputStream, final String charsetName) throws IOException {
2883        return toCharArray(inputStream, Charsets.toCharset(charsetName));
2884    }
2885
2886    /**
2887     * Gets the contents of a {@link Reader} as a character array.
2888     * <p>
2889     * This method buffers the input internally, so there is no need to use a
2890     * {@link BufferedReader}.
2891     * </p>
2892     *
2893     * @param reader the {@link Reader} to read
2894     * @return the requested character array
2895     * @throws NullPointerException if the input is null
2896     * @throws IOException          if an I/O error occurs
2897     * @since 1.1
2898     */
2899    public static char[] toCharArray(final Reader reader) throws IOException {
2900        final CharArrayWriter sw = new CharArrayWriter();
2901        copy(reader, sw);
2902        return sw.toCharArray();
2903    }
2904
2905    /**
2906     * Converts the specified CharSequence to an input stream, encoded as bytes
2907     * using the default character encoding of the platform.
2908     *
2909     * @param input the CharSequence to convert
2910     * @return an input stream
2911     * @since 2.0
2912     * @deprecated 2.5 use {@link #toInputStream(CharSequence, Charset)} instead
2913     */
2914    @Deprecated
2915    public static InputStream toInputStream(final CharSequence input) {
2916        return toInputStream(input, Charset.defaultCharset());
2917    }
2918
2919    /**
2920     * Converts the specified CharSequence to an input stream, encoded as bytes
2921     * using the specified character encoding.
2922     *
2923     * @param input the CharSequence to convert
2924     * @param charset the charset to use, null means platform default
2925     * @return an input stream
2926     * @since 2.3
2927     */
2928    public static InputStream toInputStream(final CharSequence input, final Charset charset) {
2929        return toInputStream(input.toString(), charset);
2930    }
2931
2932    /**
2933     * Converts the specified CharSequence to an input stream, encoded as bytes
2934     * using the specified character encoding.
2935     * <p>
2936     * Character encoding names can be found at
2937     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
2938     * </p>
2939     *
2940     * @param input the CharSequence to convert
2941     * @param charsetName the name of the requested charset, null means platform default
2942     * @return an input stream
2943     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
2944     *                                                      .UnsupportedEncodingException} in version 2.2 if the
2945     *                                                      encoding is not supported.
2946     * @since 2.0
2947     */
2948    public static InputStream toInputStream(final CharSequence input, final String charsetName) {
2949        return toInputStream(input, Charsets.toCharset(charsetName));
2950    }
2951
2952    /**
2953     * Converts the specified string to an input stream, encoded as bytes
2954     * using the default character encoding of the platform.
2955     *
2956     * @param input the string to convert
2957     * @return an input stream
2958     * @since 1.1
2959     * @deprecated 2.5 use {@link #toInputStream(String, Charset)} instead
2960     */
2961    @Deprecated
2962    public static InputStream toInputStream(final String input) {
2963        return toInputStream(input, Charset.defaultCharset());
2964    }
2965
2966    /**
2967     * Converts the specified string to an input stream, encoded as bytes
2968     * using the specified character encoding.
2969     *
2970     * @param input the string to convert
2971     * @param charset the charset to use, null means platform default
2972     * @return an input stream
2973     * @since 2.3
2974     */
2975    public static InputStream toInputStream(final String input, final Charset charset) {
2976        return new ByteArrayInputStream(input.getBytes(Charsets.toCharset(charset)));
2977    }
2978
2979    /**
2980     * Converts the specified string to an input stream, encoded as bytes
2981     * using the specified character encoding.
2982     * <p>
2983     * Character encoding names can be found at
2984     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
2985     * </p>
2986     *
2987     * @param input the string to convert
2988     * @param charsetName the name of the requested charset, null means platform default
2989     * @return an input stream
2990     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
2991     *                                                      .UnsupportedEncodingException} in version 2.2 if the
2992     *                                                      encoding is not supported.
2993     * @since 1.1
2994     */
2995    public static InputStream toInputStream(final String input, final String charsetName) {
2996        return new ByteArrayInputStream(input.getBytes(Charsets.toCharset(charsetName)));
2997    }
2998
2999    /**
3000     * Gets the contents of a {@code byte[]} as a String
3001     * using the default character encoding of the platform.
3002     *
3003     * @param input the byte array to read
3004     * @return the requested String
3005     * @throws NullPointerException if the input is null
3006     * @deprecated 2.5 Use {@link String#String(byte[])} instead
3007     */
3008    @Deprecated
3009    public static String toString(final byte[] input) {
3010        // make explicit the use of the default charset
3011        return new String(input, Charset.defaultCharset());
3012    }
3013
3014    /**
3015     * Gets the contents of a {@code byte[]} as a String
3016     * using the specified character encoding.
3017     * <p>
3018     * Character encoding names can be found at
3019     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3020     * </p>
3021     *
3022     * @param input the byte array to read
3023     * @param charsetName the name of the requested charset, null means platform default
3024     * @return the requested String
3025     * @throws NullPointerException if the input is null
3026     */
3027    public static String toString(final byte[] input, final String charsetName) {
3028        return new String(input, Charsets.toCharset(charsetName));
3029    }
3030
3031    /**
3032     * Gets the contents of an {@link InputStream} as a String
3033     * using the default character encoding of the platform.
3034     * <p>
3035     * This method buffers the input internally, so there is no need to use a
3036     * {@link BufferedInputStream}.
3037     * </p>
3038     *
3039     * @param input the {@link InputStream} to read
3040     * @return the requested String
3041     * @throws NullPointerException if the input is null
3042     * @throws IOException          if an I/O error occurs
3043     * @deprecated 2.5 use {@link #toString(InputStream, Charset)} instead
3044     */
3045    @Deprecated
3046    public static String toString(final InputStream input) throws IOException {
3047        return toString(input, Charset.defaultCharset());
3048    }
3049
3050    /**
3051     * Gets the contents of an {@link InputStream} as a String
3052     * using the specified character encoding.
3053     * <p>
3054     * This method buffers the input internally, so there is no need to use a
3055     * {@link BufferedInputStream}.
3056     * </p>
3057     *
3058     * @param input the {@link InputStream} to read
3059     * @param charset the charset to use, null means platform default
3060     * @return the requested String
3061     * @throws NullPointerException if the input is null
3062     * @throws IOException          if an I/O error occurs
3063     * @since 2.3
3064     */
3065    public static String toString(final InputStream input, final Charset charset) throws IOException {
3066        try (StringBuilderWriter sw = new StringBuilderWriter()) {
3067            copy(input, sw, charset);
3068            return sw.toString();
3069        }
3070    }
3071
3072    /**
3073     * Gets the contents of an {@link InputStream} as a String
3074     * using the specified character encoding.
3075     * <p>
3076     * Character encoding names can be found at
3077     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3078     * </p>
3079     * <p>
3080     * This method buffers the input internally, so there is no need to use a
3081     * {@link BufferedInputStream}.
3082     * </p>
3083     *
3084     * @param input the {@link InputStream} to read
3085     * @param charsetName the name of the requested charset, null means platform default
3086     * @return the requested String
3087     * @throws NullPointerException                         if the input is null
3088     * @throws IOException                                  if an I/O error occurs
3089     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3090     *                                                      .UnsupportedEncodingException} in version 2.2 if the
3091     *                                                      encoding is not supported.
3092     */
3093    public static String toString(final InputStream input, final String charsetName)
3094            throws IOException {
3095        return toString(input, Charsets.toCharset(charsetName));
3096    }
3097
3098    /**
3099     * Gets the contents of an {@link InputStream} from a supplier as a String
3100     * using the specified character encoding.
3101     * <p>
3102     * This method buffers the input internally, so there is no need to use a
3103     * {@link BufferedInputStream}.
3104     * </p>
3105     *
3106     * @param input supplies the {@link InputStream} to read
3107     * @param charset the charset to use, null means platform default
3108     * @return the requested String
3109     * @throws NullPointerException if the input is null
3110     * @throws IOException          if an I/O error occurs
3111     * @since 2.12.0
3112     */
3113    public static String toString(final IOSupplier<InputStream> input, final Charset charset) throws IOException {
3114        return toString(input, charset, () -> {
3115            throw new NullPointerException("input");
3116        });
3117    }
3118
3119    /**
3120     * Gets the contents of an {@link InputStream} from a supplier as a String
3121     * using the specified character encoding.
3122     * <p>
3123     * This method buffers the input internally, so there is no need to use a
3124     * {@link BufferedInputStream}.
3125     * </p>
3126     *
3127     * @param input supplies the {@link InputStream} to read
3128     * @param charset the charset to use, null means platform default
3129     * @param defaultString the default return value if the supplier or its value is null.
3130     * @return the requested String
3131     * @throws NullPointerException if the input is null
3132     * @throws IOException          if an I/O error occurs
3133     * @since 2.12.0
3134     */
3135    public static String toString(final IOSupplier<InputStream> input, final Charset charset, final IOSupplier<String> defaultString) throws IOException {
3136        if (input == null) {
3137            return defaultString.get();
3138        }
3139        try (InputStream inputStream = input.get()) {
3140            return inputStream != null ? toString(inputStream, charset) : defaultString.get();
3141        }
3142    }
3143
3144    /**
3145     * Gets the contents of a {@link Reader} as a String.
3146     * <p>
3147     * This method buffers the input internally, so there is no need to use a
3148     * {@link BufferedReader}.
3149     * </p>
3150     *
3151     * @param reader the {@link Reader} to read
3152     * @return the requested String
3153     * @throws NullPointerException if the input is null
3154     * @throws IOException          if an I/O error occurs
3155     */
3156    public static String toString(final Reader reader) throws IOException {
3157        try (StringBuilderWriter sw = new StringBuilderWriter()) {
3158            copy(reader, sw);
3159            return sw.toString();
3160        }
3161    }
3162
3163    /**
3164     * Gets the contents at the given URI.
3165     *
3166     * @param uri The URI source.
3167     * @return The contents of the URL as a String.
3168     * @throws IOException if an I/O exception occurs.
3169     * @since 2.1
3170     * @deprecated 2.5 use {@link #toString(URI, Charset)} instead
3171     */
3172    @Deprecated
3173    public static String toString(final URI uri) throws IOException {
3174        return toString(uri, Charset.defaultCharset());
3175    }
3176
3177    /**
3178     * Gets the contents at the given URI.
3179     *
3180     * @param uri The URI source.
3181     * @param encoding The encoding name for the URL contents.
3182     * @return The contents of the URL as a String.
3183     * @throws IOException if an I/O exception occurs.
3184     * @since 2.3.
3185     */
3186    public static String toString(final URI uri, final Charset encoding) throws IOException {
3187        return toString(uri.toURL(), Charsets.toCharset(encoding));
3188    }
3189
3190    /**
3191     * Gets the contents at the given URI.
3192     *
3193     * @param uri The URI source.
3194     * @param charsetName The encoding name for the URL contents.
3195     * @return The contents of the URL as a String.
3196     * @throws IOException                                  if an I/O exception occurs.
3197     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3198     *                                                      .UnsupportedEncodingException} in version 2.2 if the
3199     *                                                      encoding is not supported.
3200     * @since 2.1
3201     */
3202    public static String toString(final URI uri, final String charsetName) throws IOException {
3203        return toString(uri, Charsets.toCharset(charsetName));
3204    }
3205
3206    /**
3207     * Gets the contents at the given URL.
3208     *
3209     * @param url The URL source.
3210     * @return The contents of the URL as a String.
3211     * @throws IOException if an I/O exception occurs.
3212     * @since 2.1
3213     * @deprecated 2.5 use {@link #toString(URL, Charset)} instead
3214     */
3215    @Deprecated
3216    public static String toString(final URL url) throws IOException {
3217        return toString(url, Charset.defaultCharset());
3218    }
3219
3220    /**
3221     * Gets the contents at the given URL.
3222     *
3223     * @param url The URL source.
3224     * @param encoding The encoding name for the URL contents.
3225     * @return The contents of the URL as a String.
3226     * @throws IOException if an I/O exception occurs.
3227     * @since 2.3
3228     */
3229    public static String toString(final URL url, final Charset encoding) throws IOException {
3230        return toString(url::openStream, encoding);
3231    }
3232
3233    /**
3234     * Gets the contents at the given URL.
3235     *
3236     * @param url The URL source.
3237     * @param charsetName The encoding name for the URL contents.
3238     * @return The contents of the URL as a String.
3239     * @throws IOException                                  if an I/O exception occurs.
3240     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3241     *                                                      .UnsupportedEncodingException} in version 2.2 if the
3242     *                                                      encoding is not supported.
3243     * @since 2.1
3244     */
3245    public static String toString(final URL url, final String charsetName) throws IOException {
3246        return toString(url, Charsets.toCharset(charsetName));
3247    }
3248
3249    /**
3250     * Writes bytes from a {@code byte[]} to an {@link OutputStream}.
3251     *
3252     * @param data the byte array to write, do not modify during output,
3253     * null ignored
3254     * @param output the {@link OutputStream} to write to
3255     * @throws NullPointerException if output is null
3256     * @throws IOException          if an I/O error occurs
3257     * @since 1.1
3258     */
3259    public static void write(final byte[] data, final OutputStream output)
3260            throws IOException {
3261        if (data != null) {
3262            output.write(data);
3263        }
3264    }
3265
3266    /**
3267     * Writes bytes from a {@code byte[]} to chars on a {@link Writer}
3268     * using the default character encoding of the platform.
3269     * <p>
3270     * This method uses {@link String#String(byte[])}.
3271     * </p>
3272     *
3273     * @param data the byte array to write, do not modify during output,
3274     * null ignored
3275     * @param writer the {@link Writer} to write to
3276     * @throws NullPointerException if output is null
3277     * @throws IOException          if an I/O error occurs
3278     * @since 1.1
3279     * @deprecated 2.5 use {@link #write(byte[], Writer, Charset)} instead
3280     */
3281    @Deprecated
3282    public static void write(final byte[] data, final Writer writer) throws IOException {
3283        write(data, writer, Charset.defaultCharset());
3284    }
3285
3286    /**
3287     * Writes bytes from a {@code byte[]} to chars on a {@link Writer}
3288     * using the specified character encoding.
3289     * <p>
3290     * This method uses {@link String#String(byte[], String)}.
3291     * </p>
3292     *
3293     * @param data the byte array to write, do not modify during output,
3294     * null ignored
3295     * @param writer the {@link Writer} to write to
3296     * @param charset the charset to use, null means platform default
3297     * @throws NullPointerException if output is null
3298     * @throws IOException          if an I/O error occurs
3299     * @since 2.3
3300     */
3301    public static void write(final byte[] data, final Writer writer, final Charset charset) throws IOException {
3302        if (data != null) {
3303            writer.write(new String(data, Charsets.toCharset(charset)));
3304        }
3305    }
3306
3307    /**
3308     * Writes bytes from a {@code byte[]} to chars on a {@link Writer}
3309     * using the specified character encoding.
3310     * <p>
3311     * Character encoding names can be found at
3312     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3313     * </p>
3314     * <p>
3315     * This method uses {@link String#String(byte[], String)}.
3316     * </p>
3317     *
3318     * @param data the byte array to write, do not modify during output,
3319     * null ignored
3320     * @param writer the {@link Writer} to write to
3321     * @param charsetName the name of the requested charset, null means platform default
3322     * @throws NullPointerException                         if output is null
3323     * @throws IOException                                  if an I/O error occurs
3324     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3325     *                                                      .UnsupportedEncodingException} in version 2.2 if the
3326     *                                                      encoding is not supported.
3327     * @since 1.1
3328     */
3329    public static void write(final byte[] data, final Writer writer, final String charsetName) throws IOException {
3330        write(data, writer, Charsets.toCharset(charsetName));
3331    }
3332
3333    /**
3334     * Writes chars from a {@code char[]} to bytes on an
3335     * {@link OutputStream}.
3336     * <p>
3337     * This method uses {@link String#String(char[])} and
3338     * {@link String#getBytes()}.
3339     * </p>
3340     *
3341     * @param data the char array to write, do not modify during output,
3342     * null ignored
3343     * @param output the {@link OutputStream} to write to
3344     * @throws NullPointerException if output is null
3345     * @throws IOException          if an I/O error occurs
3346     * @since 1.1
3347     * @deprecated 2.5 use {@link #write(char[], OutputStream, Charset)} instead
3348     */
3349    @Deprecated
3350    public static void write(final char[] data, final OutputStream output)
3351            throws IOException {
3352        write(data, output, Charset.defaultCharset());
3353    }
3354
3355    /**
3356     * Writes chars from a {@code char[]} to bytes on an
3357     * {@link OutputStream} using the specified character encoding.
3358     * <p>
3359     * This method uses {@link String#String(char[])} and
3360     * {@link String#getBytes(String)}.
3361     * </p>
3362     *
3363     * @param data the char array to write, do not modify during output,
3364     * null ignored
3365     * @param output the {@link OutputStream} to write to
3366     * @param charset the charset to use, null means platform default
3367     * @throws NullPointerException if output is null
3368     * @throws IOException          if an I/O error occurs
3369     * @since 2.3
3370     */
3371    public static void write(final char[] data, final OutputStream output, final Charset charset) throws IOException {
3372        if (data != null) {
3373            write(new String(data), output, charset);
3374        }
3375    }
3376
3377    /**
3378     * Writes chars from a {@code char[]} to bytes on an
3379     * {@link OutputStream} using the specified character encoding.
3380     * <p>
3381     * Character encoding names can be found at
3382     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3383     * </p>
3384     * <p>
3385     * This method uses {@link String#String(char[])} and
3386     * {@link String#getBytes(String)}.
3387     * </p>
3388     *
3389     * @param data the char array to write, do not modify during output,
3390     * null ignored
3391     * @param output the {@link OutputStream} to write to
3392     * @param charsetName the name of the requested charset, null means platform default
3393     * @throws NullPointerException                         if output is null
3394     * @throws IOException                                  if an I/O error occurs
3395     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3396     * .UnsupportedEncodingException} in version 2.2 if the encoding is not supported.
3397     * @since 1.1
3398     */
3399    public static void write(final char[] data, final OutputStream output, final String charsetName)
3400            throws IOException {
3401        write(data, output, Charsets.toCharset(charsetName));
3402    }
3403
3404    /**
3405     * Writes chars from a {@code char[]} to a {@link Writer}
3406     *
3407     * @param data the char array to write, do not modify during output,
3408     * null ignored
3409     * @param writer the {@link Writer} to write to
3410     * @throws NullPointerException if output is null
3411     * @throws IOException          if an I/O error occurs
3412     * @since 1.1
3413     */
3414    public static void write(final char[] data, final Writer writer) throws IOException {
3415        if (data != null) {
3416            writer.write(data);
3417        }
3418    }
3419
3420    /**
3421     * Writes chars from a {@link CharSequence} to bytes on an
3422     * {@link OutputStream} using the default character encoding of the
3423     * platform.
3424     * <p>
3425     * This method uses {@link String#getBytes()}.
3426     * </p>
3427     *
3428     * @param data the {@link CharSequence} to write, null ignored
3429     * @param output the {@link OutputStream} to write to
3430     * @throws NullPointerException if output is null
3431     * @throws IOException          if an I/O error occurs
3432     * @since 2.0
3433     * @deprecated 2.5 use {@link #write(CharSequence, OutputStream, Charset)} instead
3434     */
3435    @Deprecated
3436    public static void write(final CharSequence data, final OutputStream output)
3437            throws IOException {
3438        write(data, output, Charset.defaultCharset());
3439    }
3440
3441    /**
3442     * Writes chars from a {@link CharSequence} to bytes on an
3443     * {@link OutputStream} using the specified character encoding.
3444     * <p>
3445     * This method uses {@link String#getBytes(String)}.
3446     * </p>
3447     *
3448     * @param data the {@link CharSequence} to write, null ignored
3449     * @param output the {@link OutputStream} to write to
3450     * @param charset the charset to use, null means platform default
3451     * @throws NullPointerException if output is null
3452     * @throws IOException          if an I/O error occurs
3453     * @since 2.3
3454     */
3455    public static void write(final CharSequence data, final OutputStream output, final Charset charset)
3456            throws IOException {
3457        if (data != null) {
3458            write(data.toString(), output, charset);
3459        }
3460    }
3461
3462    /**
3463     * Writes chars from a {@link CharSequence} to bytes on an
3464     * {@link OutputStream} using the specified character encoding.
3465     * <p>
3466     * Character encoding names can be found at
3467     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3468     * </p>
3469     * <p>
3470     * This method uses {@link String#getBytes(String)}.
3471     * </p>
3472     *
3473     * @param data the {@link CharSequence} to write, null ignored
3474     * @param output the {@link OutputStream} to write to
3475     * @param charsetName the name of the requested charset, null means platform default
3476     * @throws NullPointerException        if output is null
3477     * @throws IOException                 if an I/O error occurs
3478     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3479     * .UnsupportedEncodingException} in version 2.2 if the encoding is not supported.
3480     * @since 2.0
3481     */
3482    public static void write(final CharSequence data, final OutputStream output, final String charsetName)
3483            throws IOException {
3484        write(data, output, Charsets.toCharset(charsetName));
3485    }
3486
3487
3488    /**
3489     * Writes chars from a {@link CharSequence} to a {@link Writer}.
3490     *
3491     * @param data the {@link CharSequence} to write, null ignored
3492     * @param writer the {@link Writer} to write to
3493     * @throws NullPointerException if output is null
3494     * @throws IOException          if an I/O error occurs
3495     * @since 2.0
3496     */
3497    public static void write(final CharSequence data, final Writer writer) throws IOException {
3498        if (data != null) {
3499            write(data.toString(), writer);
3500        }
3501    }
3502
3503    /**
3504     * Writes chars from a {@link String} to bytes on an
3505     * {@link OutputStream} using the default character encoding of the
3506     * platform.
3507     * <p>
3508     * This method uses {@link String#getBytes()}.
3509     * </p>
3510     *
3511     * @param data the {@link String} to write, null ignored
3512     * @param output the {@link OutputStream} to write to
3513     * @throws NullPointerException if output is null
3514     * @throws IOException          if an I/O error occurs
3515     * @since 1.1
3516     * @deprecated 2.5 use {@link #write(String, OutputStream, Charset)} instead
3517     */
3518    @Deprecated
3519    public static void write(final String data, final OutputStream output)
3520            throws IOException {
3521        write(data, output, Charset.defaultCharset());
3522    }
3523
3524    /**
3525     * Writes chars from a {@link String} to bytes on an
3526     * {@link OutputStream} using the specified character encoding.
3527     * <p>
3528     * This method uses {@link String#getBytes(String)}.
3529     * </p>
3530     *
3531     * @param data the {@link String} to write, null ignored
3532     * @param output the {@link OutputStream} to write to
3533     * @param charset the charset to use, null means platform default
3534     * @throws NullPointerException if output is null
3535     * @throws IOException          if an I/O error occurs
3536     * @since 2.3
3537     */
3538    @SuppressWarnings("resource")
3539    public static void write(final String data, final OutputStream output, final Charset charset) throws IOException {
3540        if (data != null) {
3541            // Use Charset#encode(String), since calling String#getBytes(Charset) might result in
3542            // NegativeArraySizeException or OutOfMemoryError.
3543            // The underlying OutputStream should not be closed, so the channel is not closed.
3544            Channels.newChannel(output).write(Charsets.toCharset(charset).encode(data));
3545        }
3546    }
3547
3548    /**
3549     * Writes chars from a {@link String} to bytes on an
3550     * {@link OutputStream} using the specified character encoding.
3551     * <p>
3552     * Character encoding names can be found at
3553     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3554     * </p>
3555     * <p>
3556     * This method uses {@link String#getBytes(String)}.
3557     * </p>
3558     *
3559     * @param data the {@link String} to write, null ignored
3560     * @param output the {@link OutputStream} to write to
3561     * @param charsetName the name of the requested charset, null means platform default
3562     * @throws NullPointerException        if output is null
3563     * @throws IOException                 if an I/O error occurs
3564     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3565     * .UnsupportedEncodingException} in version 2.2 if the encoding is not supported.
3566     * @since 1.1
3567     */
3568    public static void write(final String data, final OutputStream output, final String charsetName)
3569            throws IOException {
3570        write(data, output, Charsets.toCharset(charsetName));
3571    }
3572
3573    /**
3574     * Writes chars from a {@link String} to a {@link Writer}.
3575     *
3576     * @param data the {@link String} to write, null ignored
3577     * @param writer the {@link Writer} to write to
3578     * @throws NullPointerException if output is null
3579     * @throws IOException          if an I/O error occurs
3580     * @since 1.1
3581     */
3582    public static void write(final String data, final Writer writer) throws IOException {
3583        if (data != null) {
3584            writer.write(data);
3585        }
3586    }
3587
3588    /**
3589     * Writes chars from a {@link StringBuffer} to bytes on an
3590     * {@link OutputStream} using the default character encoding of the
3591     * platform.
3592     * <p>
3593     * This method uses {@link String#getBytes()}.
3594     * </p>
3595     *
3596     * @param data the {@link StringBuffer} to write, null ignored
3597     * @param output the {@link OutputStream} to write to
3598     * @throws NullPointerException if output is null
3599     * @throws IOException          if an I/O error occurs
3600     * @since 1.1
3601     * @deprecated Use {@link #write(CharSequence, OutputStream)}
3602     */
3603    @Deprecated
3604    public static void write(final StringBuffer data, final OutputStream output) //NOSONAR
3605            throws IOException {
3606        write(data, output, (String) null);
3607    }
3608
3609    /**
3610     * Writes chars from a {@link StringBuffer} to bytes on an
3611     * {@link OutputStream} using the specified character encoding.
3612     * <p>
3613     * Character encoding names can be found at
3614     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3615     * </p>
3616     * <p>
3617     * This method uses {@link String#getBytes(String)}.
3618     * </p>
3619     *
3620     * @param data the {@link StringBuffer} to write, null ignored
3621     * @param output the {@link OutputStream} to write to
3622     * @param charsetName the name of the requested charset, null means platform default
3623     * @throws NullPointerException        if output is null
3624     * @throws IOException                 if an I/O error occurs
3625     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3626     * .UnsupportedEncodingException} in version 2.2 if the encoding is not supported.
3627     * @since 1.1
3628     * @deprecated Use {@link #write(CharSequence, OutputStream, String)}.
3629     */
3630    @Deprecated
3631    public static void write(final StringBuffer data, final OutputStream output, final String charsetName) //NOSONAR
3632        throws IOException {
3633        if (data != null) {
3634            write(data.toString(), output, Charsets.toCharset(charsetName));
3635        }
3636    }
3637
3638    /**
3639     * Writes chars from a {@link StringBuffer} to a {@link Writer}.
3640     *
3641     * @param data the {@link StringBuffer} to write, null ignored
3642     * @param writer the {@link Writer} to write to
3643     * @throws NullPointerException if output is null
3644     * @throws IOException          if an I/O error occurs
3645     * @since 1.1
3646     * @deprecated Use {@link #write(CharSequence, Writer)}
3647     */
3648    @Deprecated
3649    public static void write(final StringBuffer data, final Writer writer) //NOSONAR
3650            throws IOException {
3651        if (data != null) {
3652            writer.write(data.toString());
3653        }
3654    }
3655
3656    /**
3657     * Writes bytes from a {@code byte[]} to an {@link OutputStream} using chunked writes.
3658     * This is intended for writing very large byte arrays which might otherwise cause excessive
3659     * memory usage if the native code has to allocate a copy.
3660     *
3661     * @param data the byte array to write, do not modify during output,
3662     * null ignored
3663     * @param output the {@link OutputStream} to write to
3664     * @throws NullPointerException if output is null
3665     * @throws IOException          if an I/O error occurs
3666     * @since 2.5
3667     */
3668    public static void writeChunked(final byte[] data, final OutputStream output)
3669            throws IOException {
3670        if (data != null) {
3671            int bytes = data.length;
3672            int offset = 0;
3673            while (bytes > 0) {
3674                final int chunk = Math.min(bytes, DEFAULT_BUFFER_SIZE);
3675                output.write(data, offset, chunk);
3676                bytes -= chunk;
3677                offset += chunk;
3678            }
3679        }
3680    }
3681
3682    /**
3683     * Writes chars from a {@code char[]} to a {@link Writer} using chunked writes.
3684     * This is intended for writing very large byte arrays which might otherwise cause excessive
3685     * memory usage if the native code has to allocate a copy.
3686     *
3687     * @param data the char array to write, do not modify during output,
3688     * null ignored
3689     * @param writer the {@link Writer} to write to
3690     * @throws NullPointerException if output is null
3691     * @throws IOException          if an I/O error occurs
3692     * @since 2.5
3693     */
3694    public static void writeChunked(final char[] data, final Writer writer) throws IOException {
3695        if (data != null) {
3696            int bytes = data.length;
3697            int offset = 0;
3698            while (bytes > 0) {
3699                final int chunk = Math.min(bytes, DEFAULT_BUFFER_SIZE);
3700                writer.write(data, offset, chunk);
3701                bytes -= chunk;
3702                offset += chunk;
3703            }
3704        }
3705    }
3706
3707    /**
3708     * Writes the {@link #toString()} value of each item in a collection to
3709     * an {@link OutputStream} line by line, using the default character
3710     * encoding of the platform and the specified line ending.
3711     *
3712     * @param lines the lines to write, null entries produce blank lines
3713     * @param lineEnding the line separator to use, null is system default
3714     * @param output the {@link OutputStream} to write to, not null, not closed
3715     * @throws NullPointerException if the output is null
3716     * @throws IOException          if an I/O error occurs
3717     * @since 1.1
3718     * @deprecated 2.5 use {@link #writeLines(Collection, String, OutputStream, Charset)} instead
3719     */
3720    @Deprecated
3721    public static void writeLines(final Collection<?> lines, final String lineEnding,
3722                                  final OutputStream output) throws IOException {
3723        writeLines(lines, lineEnding, output, Charset.defaultCharset());
3724    }
3725
3726    /**
3727     * Writes the {@link #toString()} value of each item in a collection to
3728     * an {@link OutputStream} line by line, using the specified character
3729     * encoding and the specified line ending.
3730     *
3731     * @param lines the lines to write, null entries produce blank lines
3732     * @param lineEnding the line separator to use, null is system default
3733     * @param output the {@link OutputStream} to write to, not null, not closed
3734     * @param charset the charset to use, null means platform default
3735     * @throws NullPointerException if the output is null
3736     * @throws IOException          if an I/O error occurs
3737     * @since 2.3
3738     */
3739    public static void writeLines(final Collection<?> lines, String lineEnding, final OutputStream output,
3740                                  final Charset charset) throws IOException {
3741        if (lines == null) {
3742            return;
3743        }
3744        if (lineEnding == null) {
3745            lineEnding = System.lineSeparator();
3746        }
3747        final Charset cs = Charsets.toCharset(charset);
3748        final byte[] eolBytes = lineEnding.getBytes(cs);
3749        for (final Object line : lines) {
3750            if (line != null) {
3751                write(line.toString(), output, cs);
3752            }
3753            output.write(eolBytes);
3754        }
3755    }
3756
3757    /**
3758     * Writes the {@link #toString()} value of each item in a collection to
3759     * an {@link OutputStream} line by line, using the specified character
3760     * encoding and the specified line ending.
3761     * <p>
3762     * Character encoding names can be found at
3763     * <a href="http://www.iana.org/assignments/character-sets">IANA</a>.
3764     * </p>
3765     *
3766     * @param lines the lines to write, null entries produce blank lines
3767     * @param lineEnding the line separator to use, null is system default
3768     * @param output the {@link OutputStream} to write to, not null, not closed
3769     * @param charsetName the name of the requested charset, null means platform default
3770     * @throws NullPointerException                         if the output is null
3771     * @throws IOException                                  if an I/O error occurs
3772     * @throws java.nio.charset.UnsupportedCharsetException thrown instead of {@link java.io
3773     *                                                      .UnsupportedEncodingException} in version 2.2 if the
3774     *                                                      encoding is not supported.
3775     * @since 1.1
3776     */
3777    public static void writeLines(final Collection<?> lines, final String lineEnding,
3778                                  final OutputStream output, final String charsetName) throws IOException {
3779        writeLines(lines, lineEnding, output, Charsets.toCharset(charsetName));
3780    }
3781
3782    /**
3783     * Writes the {@link #toString()} value of each item in a collection to
3784     * a {@link Writer} line by line, using the specified line ending.
3785     *
3786     * @param lines the lines to write, null entries produce blank lines
3787     * @param lineEnding the line separator to use, null is system default
3788     * @param writer the {@link Writer} to write to, not null, not closed
3789     * @throws NullPointerException if the input is null
3790     * @throws IOException          if an I/O error occurs
3791     * @since 1.1
3792     */
3793    public static void writeLines(final Collection<?> lines, String lineEnding,
3794                                  final Writer writer) throws IOException {
3795        if (lines == null) {
3796            return;
3797        }
3798        if (lineEnding == null) {
3799            lineEnding = System.lineSeparator();
3800        }
3801        for (final Object line : lines) {
3802            if (line != null) {
3803                writer.write(line.toString());
3804            }
3805            writer.write(lineEnding);
3806        }
3807    }
3808
3809    /**
3810     * Returns the given Appendable if it is already a {@link Writer}, otherwise creates a Writer wrapper around the
3811     * given Appendable.
3812     *
3813     * @param appendable the Appendable to wrap or return (not null)
3814     * @return  the given Appendable or a Writer wrapper around the given Appendable
3815     * @throws NullPointerException if the input parameter is null
3816     * @since 2.7
3817     */
3818    public static Writer writer(final Appendable appendable) {
3819        Objects.requireNonNull(appendable, "appendable");
3820        if (appendable instanceof Writer) {
3821            return (Writer) appendable;
3822        }
3823        if (appendable instanceof StringBuilder) {
3824            return new StringBuilderWriter((StringBuilder) appendable);
3825        }
3826        return new AppendableWriter<>(appendable);
3827    }
3828
3829    /**
3830     * Instances should NOT be constructed in standard programming.
3831     * @deprecated Will be private in 3.0.
3832     */
3833    @Deprecated
3834    public IOUtils() { //NOSONAR
3835    }
3836
3837}