1 21 22 package org.apache.derby.impl.sql.execute; 23 24 import org.apache.derby.iapi.reference.Property; 25 import org.apache.derby.iapi.util.IdUtil; 26 import org.apache.derby.impl.sql.execute.JarDDL; 27 import org.apache.derby.iapi.services.property.PropertyUtil; 28 import org.apache.derby.iapi.services.loader.ClassFactory; 29 import org.apache.derby.iapi.services.context.ContextService; 30 import org.apache.derby.iapi.services.sanity.SanityManager; 31 import org.apache.derby.iapi.error.StandardException; 32 import org.apache.derby.iapi.sql.conn.LanguageConnectionContext; 33 import org.apache.derby.iapi.sql.dictionary.DataDescriptorGenerator; 34 import org.apache.derby.iapi.sql.dictionary.DataDictionary; 35 import org.apache.derby.iapi.sql.dictionary.FileInfoDescriptor; 36 import org.apache.derby.iapi.sql.dictionary.SchemaDescriptor; 37 38 import org.apache.derby.iapi.sql.depend.DependencyManager; 39 import org.apache.derby.iapi.reference.SQLState; 40 import org.apache.derby.iapi.store.access.FileResource; 41 import org.apache.derby.catalog.UUID; 42 import org.apache.derby.iapi.services.io.FileUtil; 43 import org.apache.derby.io.StorageFile; 44 45 import java.io.IOException ; 46 import java.io.InputStream ; 47 import java.sql.CallableStatement ; 48 import java.sql.Connection ; 49 import java.sql.SQLException ; 50 51 public class JarUtil 52 { 53 public static final String ADD_JAR_DDL = "ADD JAR"; 54 public static final String DROP_JAR_DDL = "DROP JAR"; 55 public static final String REPLACE_JAR_DDL = "REPLACE JAR"; 56 public static final String READ_JAR = "READ JAR"; 57 private UUID id; private String schemaName; 61 private String sqlName; 62 63 private LanguageConnectionContext lcc; 65 private FileResource fr; 66 private DataDictionary dd; 67 private DataDescriptorGenerator ddg; 68 69 public JarUtil(UUID id, String schemaName, String sqlName) 72 throws StandardException 73 { 74 this.id = id; 75 this.schemaName = schemaName; 76 this.sqlName = sqlName; 77 78 lcc = (LanguageConnectionContext) 79 ContextService.getContext(LanguageConnectionContext.CONTEXT_ID); 80 fr = lcc.getTransactionExecute().getFileHandler(); 81 dd = lcc.getDataDictionary(); 82 ddg = dd.getDataDescriptorGenerator(); 83 } 84 85 96 static public long 97 add(UUID id, String schemaName, String sqlName, String externalPath) 98 throws StandardException 99 { 100 JarUtil jutil = new JarUtil(id, schemaName, sqlName); 101 InputStream is = null; 102 103 try { 104 is = FileUtil.getInputStream(externalPath, 0); 105 return jutil.add(is); 106 } catch (java.io.IOException fnfe) { 107 throw StandardException.newException(SQLState.SQLJ_INVALID_JAR, fnfe, externalPath); 108 } 109 finally { 110 try {if (is != null) is.close();} 111 catch (IOException ioe) {} 112 } 113 } 114 115 124 public long add(InputStream is) throws StandardException 125 { 126 dd.startWriting(lcc); 129 FileInfoDescriptor fid = getInfo(); 130 if (fid != null) 131 throw 132 StandardException.newException(SQLState.LANG_OBJECT_ALREADY_EXISTS_IN_OBJECT, 133 fid.getDescriptorType(), sqlName, fid.getSchemaDescriptor().getDescriptorType(), schemaName); 134 135 try { 136 notifyLoader(false); 137 dd.invalidateAllSPSPlans(); 138 long generationId = fr.add(JarDDL.mkExternalName(schemaName, sqlName, fr.getSeparatorChar()),is); 139 140 SchemaDescriptor sd = dd.getSchemaDescriptor(schemaName, null, true); 141 142 fid = ddg.newFileInfoDescriptor(id, sd, 143 sqlName, generationId); 144 dd.addDescriptor(fid, sd, DataDictionary.SYSFILES_CATALOG_NUM, 145 false, lcc.getTransactionExecute()); 146 return generationId; 147 } finally { 148 notifyLoader(true); 149 } 150 } 151 152 163 static public void 164 drop(UUID id, String schemaName, String sqlName,boolean purgeOnCommit) 165 throws StandardException 166 { 167 JarUtil jutil = new JarUtil(id, schemaName,sqlName); 168 jutil.drop(purgeOnCommit); 169 } 170 171 182 public void drop(boolean purgeOnCommit) throws StandardException 183 { 184 dd.startWriting(lcc); 187 FileInfoDescriptor fid = getInfo(); 188 if (fid == null) 189 throw StandardException.newException(SQLState.LANG_FILE_DOES_NOT_EXIST, sqlName,schemaName); 190 191 if (SanityManager.DEBUG) 192 { 193 if (id != null && !fid.getUUID().equals(id)) 194 { 195 SanityManager.THROWASSERT("Drop id mismatch want="+id+ 196 " have "+fid.getUUID()); 197 } 198 } 199 200 String dbcp_s = PropertyUtil.getServiceProperty(lcc.getTransactionExecute(),Property.DATABASE_CLASSPATH); 201 if (dbcp_s != null) 202 { 203 String [][]dbcp= IdUtil.parseDbClassPath(dbcp_s, 204 lcc.getIdentifierCasing() != lcc.ANTI_ANSI_CASING ); 205 boolean found = false; 206 for (int ix=0;ix<dbcp.length;ix++) 212 if (dbcp.length == 2 && 213 dbcp[ix][0].equals(schemaName) && dbcp[ix][1].equals(sqlName)) 214 found = true; 215 if (found) 216 throw StandardException.newException(SQLState.LANG_CANT_DROP_JAR_ON_DB_CLASS_PATH_DURING_EXECUTION, 217 IdUtil.mkQualifiedName(schemaName,sqlName), 218 dbcp_s); 219 } 220 221 try { 222 223 notifyLoader(false); 224 dd.invalidateAllSPSPlans(); 225 DependencyManager dm = dd.getDependencyManager(); 226 dm.invalidateFor(fid, DependencyManager.DROP_JAR, lcc); 227 228 dd.dropFileInfoDescriptor(fid); 229 230 fr.remove(JarDDL.mkExternalName(schemaName, sqlName, fr.getSeparatorChar()), 231 fid.getGenerationId(), true ); 232 } finally { 233 notifyLoader(true); 234 } 235 } 236 237 252 static public long 253 replace(UUID id,String schemaName, String sqlName, 254 String externalPath,boolean purgeOnCommit) 255 throws StandardException 256 { 257 JarUtil jutil = new JarUtil(id,schemaName,sqlName); 258 InputStream is = null; 259 260 261 try { 262 is = FileUtil.getInputStream(externalPath, 0); 263 264 return jutil.replace(is,purgeOnCommit); 265 } catch (java.io.IOException fnfe) { 266 throw StandardException.newException(SQLState.SQLJ_INVALID_JAR, fnfe, externalPath); 267 } 268 finally { 269 try {if (is != null) is.close();} 270 catch (IOException ioe) {} 271 } 272 } 273 274 286 public long replace(InputStream is,boolean purgeOnCommit) throws StandardException 287 { 288 dd.startWriting(lcc); 291 292 FileInfoDescriptor fid = getInfo(); 295 if (fid == null) 296 throw StandardException.newException(SQLState.LANG_FILE_DOES_NOT_EXIST, sqlName,schemaName); 297 298 if (SanityManager.DEBUG) 299 { 300 if (id != null && !fid.getUUID().equals(id)) 301 { 302 SanityManager.THROWASSERT("Replace id mismatch want="+ 303 id+" have "+fid.getUUID()); 304 } 305 } 306 307 try { 308 notifyLoader(false); 310 dd.invalidateAllSPSPlans(); 311 dd.dropFileInfoDescriptor(fid); 312 313 long generationId = 316 fr.replace(JarDDL.mkExternalName(schemaName, sqlName, fr.getSeparatorChar()), 317 fid.getGenerationId(), is, purgeOnCommit); 318 319 FileInfoDescriptor fid2 = 322 ddg.newFileInfoDescriptor(fid.getUUID(),fid.getSchemaDescriptor(), 323 sqlName,generationId); 324 dd.addDescriptor(fid2, fid.getSchemaDescriptor(), 325 DataDictionary.SYSFILES_CATALOG_NUM, false, lcc.getTransactionExecute()); 326 return generationId; 327 328 } finally { 329 330 notifyLoader(true); 332 } 333 } 334 335 344 public static FileInfoDescriptor getInfo(String schemaName, String sqlName, String statementType) 345 throws StandardException 346 { 347 JarUtil jUtil = new JarUtil(null,schemaName,sqlName); 348 return jUtil.getInfo(); 349 } 350 351 355 private FileInfoDescriptor getInfo() 356 throws StandardException 357 { 358 SchemaDescriptor sd = dd.getSchemaDescriptor(schemaName, null, true); 359 return dd.getFileInfoDescriptor(sd,sqlName); 360 } 361 362 public static Object getAsObject(String schemaName, String sqlName) 364 throws StandardException 365 { 366 JarUtil jUtil = new JarUtil(null,schemaName,sqlName); 367 368 FileInfoDescriptor fid = jUtil.getInfo(); 369 if (fid == null) 370 throw StandardException.newException(SQLState.LANG_FILE_DOES_NOT_EXIST, sqlName,schemaName); 371 372 long generationId = fid.getGenerationId(); 373 374 StorageFile f = jUtil.getAsFile(generationId); 375 if (f != null) 376 return f; 377 378 return jUtil.getAsStream(generationId); 379 } 380 381 private StorageFile getAsFile(long generationId) { 382 return fr.getAsFile(JarDDL.mkExternalName(schemaName, sqlName, fr.getSeparatorChar()), generationId); 383 } 384 385 public static InputStream getAsStream(String schemaName, String sqlName, 386 long generationId) throws StandardException { 387 JarUtil jUtil = new JarUtil(null,schemaName,sqlName); 388 389 return jUtil.getAsStream(generationId); 390 } 391 392 private InputStream getAsStream(long generationId) throws StandardException { 393 try { 394 return fr.getAsStream(JarDDL.mkExternalName(schemaName, sqlName, fr.getSeparatorChar()), generationId); 395 } catch (IOException ioe) { 396 throw StandardException.newException(SQLState.LANG_FILE_ERROR, ioe, ioe.toString()); 397 } 398 } 399 400 private void notifyLoader(boolean reload) throws StandardException { 401 ClassFactory cf = lcc.getLanguageConnectionFactory().getClassFactory(); 402 cf.notifyModifyJar(reload); 403 } 404 } 405 | Popular Tags |