001/* 002 * HA-JDBC: High-Availability JDBC 003 * Copyright (C) 2012 Paul Ferraro 004 * 005 * This program is free software: you can redistribute it and/or modify 006 * it under the terms of the GNU Lesser General Public License as published by 007 * the Free Software Foundation, either version 3 of the License, or 008 * (at your option) any later version. 009 * 010 * This program is distributed in the hope that it will be useful, 011 * but WITHOUT ANY WARRANTY; without even the implied warranty of 012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 013 * GNU Lesser General Public License for more details. 014 * 015 * You should have received a copy of the GNU Lesser General Public License 016 * along with this program. If not, see <http://www.gnu.org/licenses/>. 017 */ 018package net.sf.hajdbc.sql; 019 020import java.io.BufferedReader; 021import java.io.File; 022import java.io.FileInputStream; 023import java.io.FileOutputStream; 024import java.io.FileReader; 025import java.io.FileWriter; 026import java.io.IOException; 027import java.io.InputStream; 028import java.io.Reader; 029import java.io.Writer; 030import java.nio.ByteBuffer; 031import java.nio.CharBuffer; 032import java.nio.channels.Channels; 033import java.nio.channels.FileChannel; 034import java.nio.channels.ReadableByteChannel; 035import java.sql.SQLException; 036import java.util.LinkedList; 037import java.util.List; 038 039import net.sf.hajdbc.ExceptionFactory; 040import net.sf.hajdbc.util.Files; 041import net.sf.hajdbc.util.Resources; 042 043/** 044 * @author Paul Ferraro 045 * @since 1.0 046 */ 047public class FileSupportImpl<E extends Exception> implements FileSupport<E> 048{ 049 private static final String TEMP_FILE_SUFFIX = ".lob"; 050 private static final int BUFFER_SIZE = 8192; 051 052 private final List<File> files = new LinkedList<File>(); 053 private final ExceptionFactory<E> exceptionFactory; 054 055 public FileSupportImpl(ExceptionFactory<E> exceptionFactory) 056 { 057 this.exceptionFactory = exceptionFactory; 058 } 059 060 /** 061 * @see net.sf.hajdbc.sql.FileSupport#createFile(java.io.InputStream) 062 */ 063 @Override 064 public File createFile(InputStream inputStream) throws E 065 { 066 try 067 { 068 File file = this.createTempFile(); 069 FileOutputStream output = new FileOutputStream(file); 070 try 071 { 072 FileChannel fileChannel = output.getChannel(); 073 ReadableByteChannel inputChannel = Channels.newChannel(inputStream); 074 075 ByteBuffer buffer = ByteBuffer.allocate(BUFFER_SIZE); 076 077 while (inputChannel.read(buffer) > 0) 078 { 079 buffer.flip(); 080 fileChannel.write(buffer); 081 buffer.compact(); 082 } 083 084 return file; 085 } 086 finally 087 { 088 Resources.close(output); 089 } 090 } 091 catch (IOException e) 092 { 093 throw this.exceptionFactory.createException(e); 094 } 095 } 096 097 /** 098 * @see net.sf.hajdbc.sql.FileSupport#createFile(java.io.Reader) 099 */ 100 @Override 101 public File createFile(Reader reader) throws E 102 { 103 try 104 { 105 File file = this.createTempFile(); 106 Writer writer = new FileWriter(file); 107 try 108 { 109 CharBuffer buffer = CharBuffer.allocate(BUFFER_SIZE); 110 111 while (reader.read(buffer) > 0) 112 { 113 buffer.flip(); 114 writer.append(buffer); 115 buffer.clear(); 116 } 117 118 return file; 119 } 120 finally 121 { 122 Resources.close(writer); 123 } 124 } 125 catch (IOException e) 126 { 127 throw this.exceptionFactory.createException(e); 128 } 129 } 130 131 /** 132 * @see net.sf.hajdbc.sql.FileSupport#getReader(java.io.File) 133 */ 134 @Override 135 public Reader getReader(File file) throws E 136 { 137 try 138 { 139 return new BufferedReader(new FileReader(file), BUFFER_SIZE); 140 } 141 catch (IOException e) 142 { 143 throw this.exceptionFactory.createException(e); 144 } 145 } 146 147 /** 148 * @see net.sf.hajdbc.sql.FileSupport#getInputStream(java.io.File) 149 */ 150 @Override 151 public InputStream getInputStream(File file) throws E 152 { 153 try 154 { 155 return Channels.newInputStream(new FileInputStream(file).getChannel()); 156 } 157 catch (IOException e) 158 { 159 throw this.exceptionFactory.createException(e); 160 } 161 } 162 163 /** 164 * Creates a temp file and stores a reference to it so that it can be deleted later. 165 * @return a temp file 166 * @throws SQLException if an IO error occurs 167 */ 168 private File createTempFile() throws IOException 169 { 170 File file = Files.createTempFile(TEMP_FILE_SUFFIX); 171 172 this.files.add(file); 173 174 return file; 175 } 176 177 /** 178 * @see net.sf.hajdbc.sql.FileSupport#close() 179 */ 180 @Override 181 public void close() 182 { 183 for (File file: this.files) 184 { 185 if (!file.delete()) 186 { 187 file.deleteOnExit(); 188 } 189 } 190 this.files.clear(); 191 } 192 193 /** 194 * @see java.lang.Object#finalize() 195 */ 196 @Override 197 protected void finalize() throws Throwable 198 { 199 this.close(); 200 201 super.finalize(); 202 } 203}