001    package railo.commons.io;
002    
003    import java.io.BufferedInputStream;
004    import java.io.BufferedOutputStream;
005    import java.io.BufferedReader;
006    import java.io.BufferedWriter;
007    import java.io.ByteArrayInputStream;
008    import java.io.ByteArrayOutputStream;
009    import java.io.Closeable;
010    import java.io.File;
011    import java.io.FileOutputStream;
012    import java.io.IOException;
013    import java.io.InputStream;
014    import java.io.InputStreamReader;
015    import java.io.OutputStream;
016    import java.io.OutputStreamWriter;
017    import java.io.PrintStream;
018    import java.io.Reader;
019    import java.io.StringWriter;
020    import java.io.UnsupportedEncodingException;
021    import java.io.Writer;
022    import java.lang.reflect.Method;
023    import java.util.LinkedList;
024    import java.util.zip.ZipFile;
025    
026    import javax.mail.Transport;
027    
028    import net.sf.jmimemagic.Magic;
029    import railo.commons.io.res.Resource;
030    import railo.commons.net.URLEncoder;
031    import railo.runtime.exp.PageException;
032    
033    import com.lowagie.text.Document;
034    
035    /**
036     * I/O Util 
037     */
038    public final class IOUtil {
039    
040        /**
041         * copy a inputstream to a outputstream
042         * @param in 
043         * @param out
044         * @param closeIS 
045         * @param closeOS 
046         * @throws IOException
047         */
048        public static final void copy(InputStream in, OutputStream out, boolean closeIS, boolean closeOS) throws IOException {
049            try {
050                copy(in,out,0xffff);
051            }
052            finally {
053                if(closeIS)closeEL(in);
054                if(closeOS)closeEL(out);
055            }
056        }
057        
058        /**
059         * copy a inputstream to a outputstream
060         * @param in 
061         * @param out
062         * @param closeIS 
063         * @param closeOS 
064         * @throws IOException
065         */
066        public static final void merge(InputStream in1, InputStream in2, OutputStream out, boolean closeIS1, boolean closeIS2, boolean closeOS) throws IOException {
067            try {
068                merge(in1,in2,out,0xffff);
069            }
070            finally {
071                if(closeIS1)closeEL(in1);
072                if(closeIS2)closeEL(in2);
073                if(closeOS)closeEL(out);
074            }
075        }
076        
077        /**
078         * copy a inputstream to a outputstream
079         * @param in 
080         * @param out
081         * @param closeIS 
082         * @param closeOS 
083         * @throws IOException
084         */
085        public static final void copy(OutputStream out, InputStream in,boolean closeIS, boolean closeOS) throws IOException {
086            copy(in,out,closeIS,closeOS);
087        }
088        
089            /**
090             * copy a input resource to a output resource
091         * @param in
092             * @param out
093             * @throws IOException
094             */
095            public static void copy(Resource in, Resource out) throws IOException {
096                    in.copyTo(out, false);
097            }
098            
099            public static void merge(Resource in1, Resource in2, Resource out) throws IOException {
100                    InputStream is1=null;
101                    InputStream is2=null;
102                    OutputStream os=null;
103                    try {
104                            is1=toBufferedInputStream(in1.getInputStream());
105                            is2=toBufferedInputStream(in2.getInputStream());
106                            os=toBufferedOutputStream(out.getOutputStream());
107                    }
108                    catch(IOException ioe) {
109                            IOUtil.closeEL(is1);
110                            IOUtil.closeEL(is2);
111                            IOUtil.closeEL(os);
112                            throw ioe;
113                    }
114                    merge(is1,is2,os,true,true,true);
115            }
116    
117            /**
118             * copy a input resource to a output resource
119         * @param in
120             * @param out
121             * @throws IOException
122             */
123            public static void copy(InputStream is, Resource out, boolean closeIS) throws IOException {
124                    OutputStream os=null;
125                    try {
126                            os=toBufferedOutputStream(out.getOutputStream());
127                    }
128                    catch(IOException ioe) {
129                            IOUtil.closeEL(os);
130                            throw ioe;
131                    }
132                    copy(is,os,closeIS,true);
133            }
134        
135            /**
136             * copy a input resource to a output resource
137         * @param in
138             * @param out
139             * @throws IOException
140             */
141            public static void copy(Resource in, OutputStream os, boolean closeOS) throws IOException {
142                    InputStream is=null;
143                    try {
144                            is=toBufferedInputStream(in.getInputStream());
145                    }
146                    catch(IOException ioe) {
147                            IOUtil.closeEL(is);
148                            throw ioe;
149                    }
150                    copy(is,os,true,closeOS);
151            }
152        
153        public static final void copy(InputStream in, OutputStream out, int offset, int length) throws IOException {
154            copy(in, out, offset, length,0xffff);
155        }
156        
157    
158        public static final void copy(InputStream in, OutputStream out, long offset, long length) throws IOException {
159            int len;
160            byte[] buffer;
161            int block=0xffff;
162            
163            // first offset to start
164            if(offset>0) {
165                    while(true) {
166                    if(block>offset)block=(int)offset;
167                    buffer = new byte[block];
168                    len = in.read(buffer);
169                    if(len==-1) throw new IOException("reading offset is bigger than input itself");
170                    //dnos.write(buffer, 0, len);
171                    offset-=len;
172                    if(offset<=0) break;
173                }
174            }
175            
176            // write part
177            if(length<0) {
178                    copy(in, out,block);
179                    return;
180            }
181            
182            while(true) {
183                    if(block>length)block=(int) length;
184                    buffer = new byte[block];
185                    len = in.read(buffer);
186                    if(len==-1) break;
187                    out.write(buffer, 0, len);
188                    length-=len;
189                    if(length<=0) break;
190            }
191        }
192        
193        public static final void copy(InputStream in, OutputStream out, int offset, int length, int blockSize) throws IOException {
194    
195            int len;
196            byte[] buffer;
197            int block;//0xffff;
198            
199            // first offset to start
200            if(offset>0) {
201                    block = blockSize;//0xffff;
202                    while(true) {
203                    if(block>offset)block=offset;
204                    buffer = new byte[block];
205                    len = in.read(buffer);
206                    if(len==-1) throw new IOException("reading offset is bigger than input itself");
207                    //dnos.write(buffer, 0, len);
208                    offset-=len;
209                    if(offset<=0) break;
210                }
211            }
212            
213            // write part
214            if(length<0) {
215                    copy(in, out,blockSize);
216                    return;
217            }
218            block = blockSize;//0xffff;
219            while(true) {
220                    if(block>length)block=length;
221                    buffer = new byte[block];
222                    len = in.read(buffer);
223                    if(len==-1) break;
224                    out.write(buffer, 0, len);
225                    length-=len;
226                    if(length<=0) break;
227            }
228            
229        }
230    
231            /**
232         * copy a inputstream to a outputstream
233         * @param in 
234         * @param out
235         * @param blockSize 
236         * @throws IOException
237         */
238        private static final void copy(InputStream in, OutputStream out, int blockSize) throws IOException {
239            byte[] buffer = new byte[blockSize];
240            int len;
241            while((len = in.read(buffer)) !=-1) {
242              out.write(buffer, 0, len);
243            }
244        }
245        
246        private static final void merge(InputStream in1, InputStream in2, OutputStream out, int blockSize) throws IOException {
247            copy(in1, out,blockSize);
248            copy(in2, out,blockSize);
249        }
250        
251        /**
252         * copy a reader to a writer
253         * @param r 
254         * @param w 
255         * @throws IOException
256         */
257        private static final void copy(Reader r, Writer w) throws IOException {
258            copy(r,w,0xffff);
259        }
260        
261        /**
262         * copy a reader to a writer
263         * @param reader 
264         * @param writer 
265         * @param closeReader 
266         * @param closeWriter 
267         * @throws IOException
268         */
269        public static final void copy(Reader reader, Writer writer, boolean closeReader, boolean closeWriter) throws IOException {
270            try {
271                copy(reader,writer,0xffff);
272            }
273            finally {
274                if(closeReader)closeEL(reader);
275                if(closeWriter)closeEL(writer);
276            }
277        }
278        
279        /**
280         * copy a reader to a writer
281         * @param r 
282         * @param w 
283         * @param blockSize 
284         * @throws IOException
285         */
286        private static final void copy(Reader r, Writer w, int blockSize) throws IOException {
287            char[] buffer = new char[blockSize];
288            int len;
289    
290            while((len = r.read(buffer)) !=-1)
291              w.write(buffer, 0, len);
292        }
293        
294        /** 
295         * copy content of in file to out File 
296         * @param in input 
297         * @param out output 
298         * @throws IOException 
299         */ 
300        public void copy(File in,File out) throws IOException {
301            InputStream is=null;
302            OutputStream os=null;
303                    try {
304                            is = new BufferedFileInputStream(in);
305                            os = new BufferedFileOutputStream(out);
306                    } 
307                    catch (IOException ioe) {
308                            closeEL(is,os);
309                            throw ioe;
310                    }
311            copy(is,os,true,true); 
312        } 
313    
314        
315        
316        
317    
318        /**
319         * close inputstream without a Exception
320         * @param is 
321         * @param os 
322         */
323         public static void closeEL(InputStream is, OutputStream os) {
324              closeEL(is);
325              closeEL(os);
326          }
327         
328        /**
329         * close inputstream without a Exception
330         * @param is 
331         */
332         public static void closeEL(InputStream is) {
333             try {
334                     if(is!=null)is.close();
335             } 
336             //catch (AlwaysThrow at) {throw at;}
337             catch (Throwable t) {}
338         }
339         
340         public static void closeEL(ZipFile zip) {
341             try {
342                     if(zip!=null)zip.close();
343             } 
344             //catch (AlwaysThrow at) {throw at;}
345             catch (Throwable t) {}
346         }
347         
348         /**
349          * close outputstream without a Exception
350          * @param os 
351          */
352         public static void closeEL(OutputStream os) {
353               try {
354                   if(os!=null)os.close();
355             } 
356             //catch (AlwaysThrow at) {throw at;}
357             catch (Throwable e) {}
358           }
359         
360         /**
361          * close Reader without a Exception
362          * @param r 
363          */
364         public static void closeEL(Reader r) {
365               try {
366                   if(r!=null)r.close();
367             } 
368             //catch (AlwaysThrow at) {throw at;}
369             catch (Throwable e) {}
370           }
371    
372         
373         /**
374          * close Closeable without a Exception
375          * @param r 
376          */
377         public static void closeEL(Closeable c ) {
378               try {
379                   if(c!=null)c.close();
380             } 
381             //catch (AlwaysThrow at) {throw at;}
382             catch (Throwable e) {}
383           }
384         
385         /**
386          * close Writer without a Exception
387          * @param w 
388          */
389         public static void closeEL(Writer w) {
390             try {
391                   if(w!=null)w.close();
392             } 
393             //catch (AlwaysThrow at) {throw at;}
394             catch (Throwable e) {}
395         }
396         
397         /**
398          * close Writer without a Exception
399          * @param w 
400          */
401         public static void closeEL(Transport t) {
402               try {
403                   if(t!=null && t.isConnected())t.close();
404             } 
405             catch (Throwable e) {}
406         }
407         
408         
409         public static void closeEL(Document doc) {
410               try {
411                   if(doc!=null)doc.close();
412             } 
413             catch (Throwable e) {}
414         }
415         
416         
417         
418         /**
419         * call close method from any Object with a close method.
420         * @param obj
421         */
422         public static void closeEL(Object obj) {
423             if(obj instanceof InputStream)         IOUtil.closeEL((InputStream)obj);
424             else if(obj instanceof OutputStream)   IOUtil.closeEL((OutputStream)obj);
425             else if(obj instanceof Writer)         IOUtil.closeEL((Writer)obj);
426             else if(obj instanceof Reader)         IOUtil.closeEL((Reader)obj);
427             else if(obj instanceof Closeable)         IOUtil.closeEL((Closeable)obj);
428             else if(obj instanceof ZipFile)        IOUtil.closeEL((ZipFile)obj);
429             else {
430                 try {
431                     Method method = obj.getClass().getMethod("close",new Class[0]);
432                     method.invoke(obj,new Object[0]);
433                 } 
434                 catch (Throwable e) {}
435             }
436         }
437    
438            public static Reader getReader(Resource res, String charset) throws IOException {
439                    /*
440                    00 00 FE FF     UTF-32, big-endian
441                    FF FE 00 00     UTF-32, little-endian
442                    */
443                    
444                    
445                    InputStream is=null;
446                    try {
447                            is = res.getInputStream();
448                            boolean markSupported=is.markSupported();
449                    if(markSupported) is.mark(4);
450                    int first = is.read();
451                    int second = is.read();
452                    // FE FF        UTF-16, big-endian
453                    if (first == 0xFE && second == 0xFF)    {
454                            return _getReader(is, "UTF-16BE");
455                    }
456                    // FF FE        UTF-16, little-endian
457                    if (first == 0xFF && second == 0xFE)    {
458                            return _getReader(is, "UTF-16LE");
459                    }
460                    
461                    int third=is.read();
462                    // EF BB BF     UTF-8
463                    if (first == 0xEF && second == 0xBB && third == 0xBF)    {
464                            //is.reset();
465                                    return _getReader(is, "utf-8");
466                    }
467                            /*
468                    int forth=is.read();
469                    // 00 00 FE FF          UTF-32, big-endian
470                    if (first == 0x00 && second == 0x00 && third == 0xFE  && forth == 0xFF)    {
471                            is.reset();
472                                    return _getReader(is, "utf-32");
473                    }
474                    // FF FE 00 00  UTF-32, little-endian
475                    if (first == 0xFF && second == 0xFE && third == 0x00  && forth == 0x00)    {
476                            is.reset();
477                                    return _getReader(is, "utf-32");
478                    }*/
479                    
480                    if(markSupported) {
481                            is.reset();
482                            return _getReader(is,charset);
483                    }
484                    }
485                    catch(IOException ioe) {
486                            IOUtil.closeEL(is);
487                            throw ioe;
488                    }
489                    
490            // when mark not supported return new reader
491            closeEL(is);
492            is=null;
493                    try {
494                            is=res.getInputStream();
495                    }
496                    catch(IOException ioe) {
497                            closeEL(is);
498                            throw ioe;
499                    }
500            return _getReader(is, charset);             
501       }
502            
503    
504     public static Reader getReader(InputStream is, String charset) throws IOException {
505                    
506                    boolean markSupported=is.markSupported();
507            if(!markSupported) return _getReader(is, charset);
508            
509            if(markSupported) is.mark(4);
510            
511            int first = is.read();
512            int second = is.read();
513            // FE FF        UTF-16, big-endian
514            if (first == 0xFE && second == 0xFF)    {
515                    //is.reset();
516                            return _getReader(is, "utf-16BE");
517            }
518            // FF FE        UTF-16, little-endian
519            if (first == 0xFF && second == 0xFE)    {
520                    //is.reset();
521                            return _getReader(is, "UTF-16LE");
522            }
523            
524            int third=is.read();
525            // EF BB BF     UTF-8
526            if (first == 0xEF && second == 0xBB && third == 0xBF)    {
527                            //is.reset();
528                            //print.err("reset");
529                    return _getReader(is, "utf-8");
530            }
531    
532            /*int forth=is.read();
533            // 00 00 FE FF          UTF-32, big-endian
534            if (first == 0x00 && second == 0x00 && third == 0xFE  && forth == 0xFF)    {
535                    is.reset();
536                            return _getReader(is, "utf-32");
537            }
538            // FF FE 00 00  UTF-32, little-endian
539            if (first == 0xFF && second == 0xFE && third == 0x00  && forth == 0x00)    {
540                    is.reset();
541                            return _getReader(is, "utf-32");
542            }*/
543            
544            
545            
546            
547                    /*if(markSupported) is.mark(3);
548                    if (is.read() == 0xEF && is.read() == 0xBB && is.read() == 0xBF)    {
549                            return _getReader(is, "utf-8");
550            }*/
551                    is.reset();
552            return _getReader(is,charset);       
553       }
554            
555            
556         
557         /* *
558          * returns a Reader for the given File and charset (Automaticly check BOM Files)
559          * @param file
560          * @param charset
561          * @return Reader
562          * @throws IOException
563          * /
564         public static Reader getReader(File file, String charset) throws IOException {
565            InputStream is=null;
566                    try {
567                            is=new FileInputStream(file);
568                    }
569                    catch(IOException ioe) {
570                            closeEL(is);
571                            throw ioe;
572                    }
573            return _getReader(is, charset);
574        }*/
575         
576         /**
577          * returns a Reader for the given InputStream
578          * @param is
579          * @param charset
580          * @return Reader
581          * @throws IOException
582          */
583         private static Reader _getReader(InputStream is, String charset) throws IOException {
584             if(charset==null) charset=SystemUtil.getCharset();
585             return new BufferedReader(new InputStreamReader(is,charset.trim()));
586         }
587    
588        /**
589         * reads string data from a InputStream
590         * @param is
591         * @param charset 
592         * @return string from inputstream
593        * @throws IOException 
594        */
595         public static String toString(InputStream is, String charset) throws IOException {
596             return toString(getReader(is,charset));
597         }
598         
599         public static String toString(byte[] barr, String charset) throws IOException {
600             return toString(getReader(new ByteArrayInputStream(barr),charset));
601         }
602    
603       /**
604        * reads String data from a Reader
605        * @param reader
606        * @return readed string
607        * @throws IOException
608        */
609       public static String toString(Reader reader) throws IOException {
610           StringWriter sw=new StringWriter(512);
611           copy(toBufferedReader(reader),sw);
612           sw.close();
613           return sw.toString();
614       }
615    
616       /**
617        * reads String data from a Reader
618        * @param reader
619        * @return readed string
620        * @throws IOException
621        */
622       public static String toString(Reader reader,boolean buffered) throws IOException {
623           StringWriter sw=new StringWriter(512);
624           if(buffered)copy(toBufferedReader(reader),sw);
625           else copy(reader,sw);
626           sw.close();
627           return sw.toString();
628       }
629    
630       /**
631        * reads String data from File
632         * @param file 
633         * @param charset 
634         * @return readed string
635        * @throws IOException
636        * /
637       public static String toString(File file, String charset) throws IOException {
638           Reader r = null;
639           try {
640               r=getReader(file,charset);
641               String str = toString(r);
642               return str;
643           }
644           finally {
645               closeEL(r);
646           }
647       }*/
648    
649       /**
650        * reads String data from File
651         * @param file 
652         * @param charset 
653         * @return readed string
654        * @throws IOException
655        */
656       public static String toString(Resource file, String charset) throws IOException {
657           Reader r = null;
658           try {
659               r = getReader(file,charset);
660               String str = toString(r);
661               return str;
662           }
663           finally {
664               closeEL(r);
665           }
666       }
667    
668        /**
669         * @param reader Reader to get content from it
670         * @return returns the content of the file as String Array (Line by Line)
671         * @throws IOException
672         */
673        public static String[] toStringArray(Reader reader) throws IOException {
674            if(reader==null)return new String[0];
675            BufferedReader br = new BufferedReader(reader); 
676            LinkedList<String> list=new LinkedList<String>();
677            
678            String line;
679            while((line=br.readLine())!=null)   {
680                list.add(line);
681            }
682            br.close();
683            String[] content=new String[list.size()];
684            int count=0;
685            while(!list.isEmpty()) {
686                content[count++]=list.removeFirst();
687            }
688            return content;
689        }
690    
691        /**
692         * writes a String to a object
693         * @param file 
694         * @param string String to write to file
695         * @param charset
696         * @param append  append to cuuretn data or overwrite existing data
697         * @throws IOException
698         */
699        public static void write(File file, String string, String charset, boolean append) throws IOException {
700            if(charset==null) {
701                charset=SystemUtil.getCharset();
702            }
703                    
704            
705            OutputStreamWriter writer=null;
706            try {
707                writer=new OutputStreamWriter(new BufferedFileOutputStream(file,append),charset);
708                writer.write(string);
709                
710            }
711            finally {
712                closeEL(writer);
713            }
714        }
715        
716        public static void write(Resource res, String string, String charset, boolean append) throws IOException {
717            if(charset==null) {
718                charset=SystemUtil.getCharset();
719            }
720                    
721            
722            Writer writer=null;
723            try {
724                writer=IOUtil.getWriter(res, charset,append);
725                writer.write(string);
726            }
727            finally {
728                closeEL(writer);
729            }
730        }
731        
732    
733        public static void write(Resource res, byte[] barr) throws IOException {
734            ByteArrayInputStream bais = new ByteArrayInputStream(barr);
735            OutputStream os=IOUtil.toBufferedOutputStream(res.getOutputStream());
736            IOUtil.copy(bais, os, true, true);
737        }
738        
739        /**
740         * @param file 
741         * @return returns the Content of the file as byte array
742         * @throws IOException
743         */
744        public static byte[] toBytes(File file) throws IOException {
745            BufferedFileInputStream bfis = null;
746            try {
747                    bfis = new BufferedFileInputStream(file);
748                byte[] barr = toBytes(bfis);
749                return barr;
750            }
751            finally {
752                closeEL(bfis);
753            }
754        }
755        
756        /**
757         * @param res 
758         * @return returns the Content of the file as byte array
759         * @throws IOException
760         */
761        public static byte[] toBytes(Resource res) throws IOException {
762            BufferedInputStream bfis = null;
763            try {
764                    bfis = toBufferedInputStream(res.getInputStream());
765                byte[] barr = toBytes(bfis);
766                return barr;
767            }
768            finally {
769                closeEL(bfis);
770            }
771        }
772    
773        public static BufferedInputStream toBufferedInputStream(InputStream is) {
774                    if(is instanceof BufferedInputStream) return (BufferedInputStream) is;
775                    return new BufferedInputStream(is);
776            }
777        
778        public static BufferedOutputStream toBufferedOutputStream(OutputStream os) {
779                    if(os instanceof BufferedOutputStream) return (BufferedOutputStream) os;
780                    return new BufferedOutputStream(os);
781            }
782        
783        public static BufferedReader toBufferedReader(Reader r) {
784                    if(r instanceof BufferedReader) return (BufferedReader) r;
785                    return new BufferedReader(r);
786            }
787        
788        public static BufferedReader getBufferedReader(Resource res,String charset) throws IOException {
789                    return toBufferedReader(getReader(res, charset));
790            }
791        
792        public static BufferedWriter toBufferedWriter(Writer w) {
793                    if(w instanceof BufferedWriter) return (BufferedWriter) w;
794                    return new BufferedWriter(w);
795            }
796    
797            /**
798         * @param is 
799         * @return returns the Content of the file as byte array
800         * @throws IOException
801         */
802        public static byte[] toBytes(InputStream is) throws IOException {
803           return toBytes(is,false);
804        }
805        
806    
807        public static byte[] toBytes(InputStream is, boolean closeStream) throws IOException {
808            ByteArrayOutputStream baos = new ByteArrayOutputStream();
809            copy(is,baos,closeStream,true);
810            return baos.toByteArray();
811        }
812    
813        public static byte[] toBytesMax(InputStream is, int max) throws IOException {
814            ByteArrayOutputStream baos = new ByteArrayOutputStream();
815            copy(is,baos,0,max);
816            return baos.toByteArray();
817        }
818    
819        /**
820         * flush OutputStream without a Exception
821         * @param os
822         */
823        public static void flushEL(OutputStream os) {
824            try {
825                if(os!=null)os.flush();
826            } catch (Exception e) {}
827        }
828    
829        /**
830         * flush OutputStream without a Exception
831         * @param os
832         */
833        public static void flushEL(Writer w) {
834            try {
835                if(w!=null)w.flush();
836            } catch (Exception e) {}
837        }
838        
839        /**
840         * check if given encoding is ok
841         * @param encoding
842         * @throws PageException 
843         */
844        public static void checkEncoding(String encoding) throws IOException {
845                    try {
846                            URLEncoder.encode("", encoding);
847                    } catch (UnsupportedEncodingException e) {
848                            throw new IOException("invalid encoding ["+encoding+"]");
849                    }
850            }
851        
852    
853        /**
854         * return the mime type of a file, dont check extension
855         * @param barr
856         * @param defaultValue 
857         * @return mime type of the file
858         */
859        public static String getMymeType(byte[] barr, String defaultValue) {
860            PrintStream out = System.out;
861            try {
862                    System.setOut(new PrintStream(DevNullOutputStream.DEV_NULL_OUTPUT_STREAM));
863                return Magic.getMagicMatch(barr).getMimeType();
864            }
865            catch (Exception e) {
866                return defaultValue;
867            }
868            finally {
869                    System.setOut(out);
870            }
871        }
872        
873    
874        public static String getMymeType(File file, String defaultValue) {
875            PrintStream out = System.out;
876            try {
877                    System.setOut(new PrintStream(DevNullOutputStream.DEV_NULL_OUTPUT_STREAM));
878                return Magic.getMagicMatch(file,false).getMimeType();
879            }
880            catch (Exception e) {
881                return defaultValue;
882            }
883            finally {
884                    System.setOut(out);
885            }
886        }
887        
888        /**
889         * return the mime type of a file, dont check extension
890         * @param barr
891         * @param defaultValue 
892         * @return mime type of the file
893         */
894        public static String getMymeType(InputStream is, String defaultValue) {
895            try {
896                            return getMymeType(IOUtil.toBytesMax(is,1000), defaultValue);
897                    } catch (IOException e) {
898                            return defaultValue;
899                    }
900        }
901        
902        /**
903         * return the mime type of a file, dont check extension
904         * @param barr
905         * @param defaultValue 
906         * @return mime type of the file
907         */
908        public static String getMymeType(Resource res, String defaultValue) {
909            if(res instanceof File)
910                    return getMymeType((File)res, defaultValue);
911            InputStream is = null;
912            try {
913                    is = res.getInputStream();
914                            return getMymeType(IOUtil.toBytesMax(is,1000), defaultValue);
915                    } 
916            catch (IOException e) {
917                            return defaultValue;
918                    }
919                    finally {
920                            closeEL(is);
921                    }
922        }
923        
924            public static Writer getWriter(Resource res, String charset) throws IOException {
925                    OutputStream os=null;
926                    try {
927                            os=res.getOutputStream();
928                    }
929                    catch(IOException ioe) {
930                            closeEL(os);
931                            throw ioe;
932                    }
933                    return getWriter(os, charset);
934             
935            }
936        
937            public static Writer getWriter(Resource res, String charset, boolean append) throws IOException {
938                    OutputStream os=null;
939                    try {
940                            os=res.getOutputStream(append);
941                    }
942                    catch(IOException ioe) {
943                            closeEL(os);
944                            throw ioe;
945                    }
946                    return getWriter(os, charset);
947            }
948        
949        /**
950         * returns a Reader for the given File and charset (Automaticly check BOM Files)
951         * @param file
952         * @param charset
953         * @return Reader
954         * @throws IOException
955         */
956        public static Writer getWriter(File file, String charset) throws IOException {
957            OutputStream os=null;
958                    try {
959                            os=new FileOutputStream(file);
960                    }
961                    catch(IOException ioe) {
962                            closeEL(os);
963                            throw ioe;
964                    }
965                    return getWriter(os, charset);
966       }
967        
968        /**
969         * returns a Reader for the given File and charset (Automaticly check BOM Files)
970         * @param file
971         * @param charset
972         * @return Reader
973         * @throws IOException
974         */
975        public static Writer getWriter(File file, String charset, boolean append) throws IOException {
976            OutputStream os=null;
977                    try {
978                            os=new FileOutputStream(file,append);
979                    }
980                    catch(IOException ioe) {
981                            closeEL(os);
982                            throw ioe;
983                    }
984                    return getWriter(os, charset);
985       }
986         
987    
988        /**
989         * returns a Reader for the given InputStream
990         * @param is
991         * @param charset
992         * @return Reader
993         * @throws IOException
994         */
995        public static Writer getWriter(OutputStream os, String charset) throws IOException {
996             if(charset==null) charset=SystemUtil.getCharset();
997            return new BufferedWriter(new OutputStreamWriter(os,charset.trim()));
998        }
999    
1000            public static String read(Reader reader, int size) throws IOException {
1001                    return read(reader, new char[size]);
1002            }
1003            
1004            public static String read(Reader reader,char[] carr) throws IOException {
1005                    int rst = reader.read(carr);
1006                    if(rst==-1)return null;
1007                    return new String(carr,0,rst);
1008            }
1009    }