1 2 24 package org.enhydra.tool.archive; 25 26 29 import org.enhydra.tool.common.PathHandle; 31 import org.enhydra.tool.common.FileUtil; 32 import org.enhydra.tool.common.ResUtil; 33 import org.enhydra.tool.archive.Descriptor; 34 import org.enhydra.tool.archive.xml.EarDescriptorHandler; 35 36 import java.io.BufferedInputStream ; 38 import java.io.BufferedOutputStream ; 39 import java.io.ByteArrayInputStream ; 40 import java.io.ByteArrayOutputStream ; 41 import java.io.InputStream ; 42 import java.io.IOException ; 43 import java.io.File ; 44 import java.io.FileInputStream ; 45 import java.io.FileOutputStream ; 46 import java.util.Arrays ; 47 import java.util.ArrayList ; 48 import java.util.Enumeration ; 49 import java.util.ResourceBundle ; 50 import java.util.jar.Attributes ; 51 import java.util.jar.JarFile ; 52 import java.util.jar.JarEntry ; 53 import java.util.jar.JarInputStream ; 54 import java.util.jar.JarOutputStream ; 55 import java.util.jar.Manifest ; 56 57 public class EarBuilder extends JarBuilder { 59 60 private final String APPLICATION_XML = 62 "META-INF/application.xml"; private InputStream [] mergeDescriptors = new InputStream [0]; 64 private PathHandle tmpDir = null; 65 66 public EarBuilder() {} 69 70 public EarPlan getEarPlan() { 71 EarPlan ep = null; 72 73 if (getPlan() instanceof EarPlan) { 74 ep = (EarPlan) getPlan(); 75 } 76 return ep; 77 } 78 79 public File buildArchive() throws ArchiveException { 80 File jar = null; 81 String root = null; 82 File [] files = new File [0]; 83 Descriptor[] dd = new Descriptor[0]; 84 boolean userAppDD = false; 85 86 root = getPlan().getClassRoot(); 87 dd = getPlan().getDescriptors(); 88 files = getPlan().getClassFileArray(); 89 jar = openJarStream(getEarPlan().getArchivePath()); 90 addModules(); 91 addLibraries(); 92 for (int i = 0; i < dd.length; i++) { 93 addDescriptor(dd[i], root, files); 94 if (dd[i].getArchivePath().equalsIgnoreCase(APPLICATION_XML)) { 95 userAppDD = true; 96 } 97 } 98 if (!userAppDD) { 99 addApplicationXML(); 100 } 101 closeJarStream(); 102 cleanTmp(); 103 return jar; 104 } 105 106 protected Manifest buildManifest(Manifest m) { 107 Manifest manifest = super.buildManifest(m); 108 Boolean b = null; 109 String [] eMods = new String [0]; 110 Descriptor[] metaDD = new Descriptor[0]; 111 WebApplication[] webApps = new WebApplication[0]; 112 113 manifest.getMainAttributes().put(new Attributes.Name (APP_NAME), 115 getEarPlan().getAppName()); 116 117 manifest.getMainAttributes().put(new Attributes.Name (APP_DESC), 119 getEarPlan().getDescription()); 120 121 b = new Boolean (getEarPlan().isCopyClient()); 123 manifest.getMainAttributes().put(new Attributes.Name (COPY_CLIENT), 124 b.toString()); 125 126 b = new Boolean (getEarPlan().isAlt()); 128 manifest.getMainAttributes().put(new Attributes.Name (ALT_DD), 129 b.toString()); 130 131 eMods = getEarPlan().getEnterpriseModules(); 133 for (int i = 0; i < eMods.length; i++) { 134 manifest.getMainAttributes().put(new Attributes.Name (ENTERPRISE_MODULE 135 + i), eMods[i]); 136 } 137 138 webApps = getEarPlan().getWebApplications(); 140 for (int i = 0; i < webApps.length; i++) { 141 manifest.getMainAttributes().put(new Attributes.Name (WEBAPP_MODULE 142 + i), webApps[i].getArchive()); 143 manifest.getMainAttributes().put(new Attributes.Name (WEBAPP_CONTEXT 144 + i), webApps[i].getContextRoot()); 145 } 146 147 metaDD = getEarPlan().getDescriptors(); 149 for (int i = 0; i < metaDD.length; i++) { 150 manifest.getMainAttributes().put(new Attributes.Name (APP_META 151 + i), metaDD[i].getPath()); 152 } 153 return manifest; 154 } 155 156 private void addModules() throws ArchiveException { 157 Module[] mods = getEarPlan().getAllModules(); 158 159 if (getEarPlan().isCopyClient()) { 160 mods = copyClients(mods); 161 } 162 for (int i = 0; i < mods.length; i++) { 163 addModule(mods[i]); 164 } 165 } 166 167 private void addLibraries() throws ArchiveException { 168 File [] files = getEarPlan().getLibFileArray(); 169 170 for (int i = 0; i < files.length; i++) { 171 addLibFile(files[i]); 172 } 173 } 174 175 private void extractModules(Module mod) throws ArchiveException { 176 JarFile jar = null; 177 JarEntry entry = null; 178 InputStream stream = null; 179 Enumeration entries = null; 180 ArrayList list = null; 181 182 try { 183 jar = new JarFile (new File (mod.getArchive())); 184 entries = jar.entries(); 185 while (entries.hasMoreElements()) { 186 entry = (JarEntry ) entries.nextElement(); 187 if (isJar(entry.getName())) { 188 getEarPlan().addEnterpriseModule(entry.getName()); 189 stream = jar.getInputStream(entry); 190 createEntry(stream, entry.getName()); 191 stream = jar.getInputStream(entry); 192 extractDD(new JarInputStream (stream), entry.getName()); 193 } else if (isWar(entry.getName())) { 194 getEarPlan().addWebApplication(entry.getName()); 195 stream = jar.getInputStream(entry); 196 createEntry(stream, entry.getName()); 197 stream = jar.getInputStream(entry); 198 extractDD(new JarInputStream (stream), entry.getName()); 199 } 200 } 201 entry = jar.getJarEntry(APPLICATION_XML); 202 list = new ArrayList (Arrays.asList(mergeDescriptors)); 203 list.add(jar.getInputStream(entry)); 204 list.trimToSize(); 205 mergeDescriptors = new InputStream [list.size()]; 206 mergeDescriptors = (InputStream []) list.toArray(mergeDescriptors); 207 list.clear(); 208 } catch (IOException e) { 209 throw new ArchiveException(e, 210 "Unable to extract modules from: " 211 + mod.getName()); 212 } 213 } 214 215 private void extractDD(JarInputStream stream, 216 String jarName) throws ArchiveException { 217 JarEntry entry = null; 218 String dd = new String (); 219 StringBuffer entryPath = new StringBuffer (); 220 ByteArrayOutputStream outStream = null; 221 222 if (isWar(jarName)) { 224 dd = Descriptor.getArchivePath(Descriptor.WEB); 225 } else { 226 dd = Descriptor.getArchivePath(Descriptor.EJB); 227 } 228 entryPath.append(jarName); 229 entryPath.append('/'); 230 entryPath.append(dd); 231 try { 232 entry = stream.getNextJarEntry(); 233 while (entry != null) { 234 if (entry.getName().equalsIgnoreCase(dd)) { 235 byte[] bytes = new byte[0]; 236 237 outStream = new ByteArrayOutputStream (); 238 FileUtil.copy(stream, outStream); 239 bytes = outStream.toByteArray(); 240 outStream.close(); 241 createEntry(new ByteArrayInputStream (bytes), 242 entryPath.toString()); 243 break; 244 } 245 entry = stream.getNextJarEntry(); 246 } 247 stream.close(); 248 } catch (IOException e) { 249 throw new ArchiveException(e, 250 "Unable to extract deployment descriptor from: " 251 + jarName); 252 } 253 } 254 255 private void extractDD(Module mod) throws ArchiveException { 256 JarFile jar = null; 257 JarEntry entry = null; 258 InputStream stream = null; 259 String dd = new String (); 260 StringBuffer entryPath = new StringBuffer (); 261 262 if (isWar(mod.getName())) { 264 dd = Descriptor.getArchivePath(Descriptor.WEB); 265 } else { 266 dd = Descriptor.getArchivePath(Descriptor.EJB); 267 } 268 entryPath.append(mod.getName()); 269 entryPath.append('/'); 270 entryPath.append(dd); 271 try { 272 jar = new JarFile (mod.getArchive()); 273 entry = jar.getJarEntry(dd); 274 stream = jar.getInputStream(entry); 275 createEntry(stream, entryPath.toString()); 276 } catch (NullPointerException e) { 277 throw new ArchiveException(e, 278 "Unable to extract deployment descriptor from: " 279 + mod.getName()); 280 } catch (IOException e) { 281 throw new ArchiveException(e, 282 "Unable to extract deployment descriptor from: " 283 + mod.getName()); 284 } 285 } 286 287 private boolean isWar(String path) { 288 return path.toString().toLowerCase().endsWith(".war"); 289 } 290 291 private boolean isJar(String path) { 292 return path.toString().toLowerCase().endsWith(".jar"); 293 } 294 295 private boolean isEar(String path) { 296 return path.toString().toLowerCase().endsWith(".ear"); 297 } 298 299 private void addModule(Module mod) throws ArchiveException { 300 String entryPath = new String (); 301 302 entryPath = mod.getName(); 304 if (getEarPlan().isAlt()) { 305 if (isWar(entryPath)) { 306 extractDD(mod); 307 } else if (isJar(entryPath)) { 308 extractDD(mod); 309 } else if (isEar(entryPath)) { 310 extractModules(mod); 311 } 312 } 313 if (!isEar(entryPath)) { 314 315 try { 317 createEntry(new File (mod.getArchive()), entryPath); 318 } catch (IOException e) { 319 String exMess = res.getString("EarBuilder_Unable_to"); 320 321 exMess = ResUtil.format(exMess, mod.getName()); 322 throw new ArchiveException(e, exMess); 323 } 324 } 325 } 326 327 private void addLibFile(File source) throws ArchiveException { 328 StringBuffer entryPath = new StringBuffer (); 329 330 entryPath.append("lib"); 332 entryPath.append('/'); 333 entryPath.append(source.getName()); 334 335 try { 337 createEntry(source, entryPath.toString()); 338 } catch (IOException e) { 339 String exMess = res.getString("EarBuilder_Unable_to"); 340 341 exMess = ResUtil.format(exMess, source); 342 throw new ArchiveException(e, exMess); 343 } 344 } 345 346 private void addApplicationXML() throws ArchiveException { 347 EarDescriptorHandler prep = new EarDescriptorHandler(); 348 StringBuffer entryPath = new StringBuffer (); 349 String classRoot = null; 350 String relative = null; 351 352 prep.setAppName(getEarPlan().getAppName()); 353 prep.setDescription(getEarPlan().getDescription()); 354 prep.setAllModules(getEarPlan().getAllModules()); 355 prep.setAlt(getEarPlan().isAlt()); 356 prep.setMergeDescriptors(mergeDescriptors); 357 prep.prep(); 358 entryPath.append(APPLICATION_XML); 359 try { 360 createEntry(prep.getInputStream(), entryPath.toString()); 361 } catch (IOException e) { 362 throw new ArchiveException(e, 363 ResUtil.format(res.getString("EjbBuilder_Unable_to2"), 364 APPLICATION_XML)); 365 } 366 } 367 368 private Module[] copyClients(Module[] mods) { 369 ArrayList list = new ArrayList (); 370 String [] clients = new String [0]; 371 PathHandle ph = null; 372 374 try { 375 tmpDir = getTempDir(); 376 377 for (int i = 0; i < mods.length; i++) { 379 ph = PathHandle.createPathHandle(mods[i].getArchive()); 380 if (ph.isFile() && ph.hasExtension("jar")) { 381 ph = createTempClientPH(ph); 383 if (ph.isFile()) { 386 list.add(ph.getPath()); 387 } 388 } 389 } 390 list.trimToSize(); 391 clients = new String [list.size()]; 392 clients = (String []) list.toArray(clients); 393 list.clear(); 394 if (clients.length > 0) { 395 396 for (int i = 0; i < mods.length; i++) { 398 if (mods[i] instanceof WebApplication) { 399 ph = addClients(mods[i], clients); 400 if (ph.isFile()) { 401 mods[i].setArchive(ph.getPath()); 402 } 403 } 404 } 405 } 406 ph = null; 408 409 for (int i = 0; i < clients.length; i++) { 411 File client = new File (clients[i]); 412 413 clients[i] = null; 414 if (client.isFile()) { 415 sleep(10); 416 client.deleteOnExit(); 417 client.delete(); 418 client = null; 419 } 420 } 421 } catch (IOException e) { 422 e.printStackTrace(System.err); 423 } 424 return mods; 425 } 426 427 private PathHandle addClients(Module mod, 428 String [] clients) throws IOException { 429 Enumeration entries = null; 430 PathHandle ph = null; 431 JarFile source = null; 432 JarOutputStream out = null; 433 File dest = null; 434 Manifest manifest = null; 435 436 ph = PathHandle.createPathHandle(mod.getArchive()); 437 dest = File.createTempFile("tmp", ".kelp", tmpDir.getFile()); 438 source = new JarFile (ph.getFile()); 439 manifest = source.getManifest(); 440 out = new JarOutputStream (new FileOutputStream (dest)); 441 entries = source.entries(); 442 while (entries.hasMoreElements()) { 443 JarEntry entry = null; 444 445 entry = (JarEntry ) entries.nextElement(); 446 out.putNextEntry(entry); 447 FileUtil.copy(source.getInputStream(entry), out); 448 out.flush(); 449 out.closeEntry(); 450 } 451 for (int i = 0; i < clients.length; i++) { 452 JarEntry entry = null; 453 FileInputStream in = null; 454 455 ph = PathHandle.createPathHandle(clients[i]); 456 in = new FileInputStream (ph.getFile()); 457 ph.setExtension("jar"); 458 entry = new JarEntry ("lib/" + ph.getFile().getName()); 459 entry.setTime(System.currentTimeMillis()); 460 out.putNextEntry(entry); 461 FileUtil.copy(in, out); 462 in.close(); 463 out.flush(); 464 out.closeEntry(); 465 in = null; 466 } 467 source.close(); 468 out.flush(); 469 out.close(); 470 return PathHandle.createPathHandle(dest); 471 } 472 473 private PathHandle getTempDir() throws IOException { 474 File tmp = null; 475 476 tmp = File.createTempFile("tmp", ".kelp"); 477 return PathHandle.createPathHandle(tmp.getParentFile()); 478 } 479 480 private PathHandle createTempClientPH(PathHandle ejb) throws IOException { 481 File tmpFile = null; 482 PathHandle ph = null; 483 String tmpName = ejb.getFile().getName(); 484 485 tmpName = tmpName.substring(0, tmpName.indexOf('.')); 486 tmpName = tmpName + "Client"; 487 tmpFile = File.createTempFile(tmpName, ".kelp", tmpDir.getFile()); 488 ph = PathHandle.createPathHandle(tmpFile); 489 tmpFile.delete(); 490 return ph; 491 } 492 493 private void cleanTmp() { 494 PathHandle ph; 495 496 if (tmpDir != null) { 497 sleep(10); 498 File [] files = tmpDir.getFile().listFiles(); 499 500 sleep(10); 501 for (int i = 0; i < files.length; i++) { 502 ph = PathHandle.createPathHandle(files[i]); 503 if (ph.hasExtension("kelp")) { 504 ph.getFile().deleteOnExit(); 505 ph.getFile().delete(); 506 } 507 sleep(10); 508 } 509 sleep(10); 510 tmpDir = null; 511 } 512 } 513 514 private void sleep(int m) { 515 try { 516 Thread.sleep(m); 517 } catch (InterruptedException e) { 518 e.printStackTrace(System.err); 519 } 520 } 521 522 } 523 | Popular Tags |