KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > sun > enterprise > deployment > archivist > ApplicationArchivist


1 /*
2  * The contents of this file are subject to the terms
3  * of the Common Development and Distribution License
4  * (the License). You may not use this file except in
5  * compliance with the License.
6  *
7  * You can obtain a copy of the license at
8  * https://glassfish.dev.java.net/public/CDDLv1.0.html or
9  * glassfish/bootstrap/legal/CDDLv1.0.txt.
10  * See the License for the specific language governing
11  * permissions and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL
14  * Header Notice in each file and include the License file
15  * at glassfish/bootstrap/legal/CDDLv1.0.txt.
16  * If applicable, add the following below the CDDL Header,
17  * with the fields enclosed by brackets [] replaced by
18  * you own identifying information:
19  * "Portions Copyrighted [year] [name of copyright owner]"
20  *
21  * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
22  */

23
24 package com.sun.enterprise.deployment.archivist;
25
26 import javax.xml.parsers.SAXParser JavaDoc;
27 import org.xml.sax.SAXParseException JavaDoc;
28 import org.xml.sax.SAXException JavaDoc;
29 import org.xml.sax.InputSource JavaDoc;
30
31 import java.io.*;
32 import java.util.*;
33 import java.util.jar.*;
34 import java.util.zip.ZipEntry JavaDoc;
35
36 import java.util.logging.Logger JavaDoc;
37 import java.util.logging.Level JavaDoc;
38
39 import javax.enterprise.deploy.shared.ModuleType JavaDoc;
40
41 import com.sun.enterprise.deployment.deploy.shared.AbstractArchive;
42 import com.sun.enterprise.deployment.deploy.shared.FileArchive;
43 import com.sun.enterprise.deployment.deploy.shared.InputJarArchive;
44 import com.sun.enterprise.deployment.deploy.shared.Archive;
45 import com.sun.enterprise.deployment.io.*;
46 import com.sun.enterprise.deployment.io.runtime.ApplicationRuntimeDDFile;
47 import com.sun.enterprise.deployment.node.ApplicationNode;
48 import com.sun.enterprise.deployment.util.ApplicationValidator;
49 import com.sun.enterprise.deployment.util.ApplicationVisitor;
50 import com.sun.enterprise.deployment.util.DOLUtils;
51 import com.sun.enterprise.deployment.util.ModuleDescriptor;
52 import com.sun.enterprise.deployment.*;
53 import com.sun.enterprise.deployment.xml.ConnectorTagNames;
54 import com.sun.enterprise.util.LocalStringManagerImpl;
55 import com.sun.enterprise.util.io.FileUtils;
56 import com.sun.enterprise.util.shared.ArchivistUtils;
57
58 /**
59  * This class is responsible for handling application archive files
60  *
61  * @author Jerome Dochez
62  * @version
63  */

64 public class ApplicationArchivist extends Archivist {
65     
66     /**
67      * The application archivist handles J2EE Application archive file
68      */

69     Application application = null;
70     
71     /**
72      * The DeploymentDescriptorFile handlers we are delegating for XML i/o
73      */

74     DeploymentDescriptorFile standardDD = new ApplicationDeploymentDescriptorFile();
75     
76     /** resources... */
77     private static LocalStringManagerImpl localStrings =
78         new LocalStringManagerImpl(ApplicationArchivist.class);
79     
80     /** Creates new ApplicationArchivist */
81     public ApplicationArchivist() {
82         handleRuntimeInfo = true;
83     }
84     
85     /**
86      * @return the module type handled by this archivist
87      * as defined in the application DTD
88      *
89      */

90     public ModuleType JavaDoc getModuleType() {
91         return ModuleType.EAR;
92     }
93     
94     /**
95      * Set the DOL descriptor for this Archivist, used by super classes
96      */

97     public void setDescriptor(Descriptor descriptor) {
98         if (descriptor instanceof Application) {
99             application = (Application) descriptor;
100         } else {
101             throw new RuntimeException JavaDoc("Error setting descriptor in " + this);
102         }
103     }
104             
105     /**
106      * writes the content of an archive to a JarFile
107      *
108      * @param the descriptors to use for writing
109      * @param the output stream to write to
110      */

111     protected void writeContents(AbstractArchive in, AbstractArchive out) throws IOException {
112         
113         Vector filesToSkip = new Vector();
114         
115         if(DOLUtils.getDefaultLogger().isLoggable(Level.FINE)) {
116         DOLUtils.getDefaultLogger().fine("Write " + out.getArchiveUri() + " with " + this);
117     }
118          
119         // any files already written to the output should never be rewritten
120
for (Enumeration alreadyWritten = out.entries(); alreadyWritten.hasMoreElements();) {
121             String JavaDoc elementName = (String JavaDoc) alreadyWritten.nextElement();
122             filesToSkip.add(elementName);
123         }
124                 
125         // write this application .ear file contents...
126
for (Iterator modules = application.getModules();modules.hasNext();) {
127             ModuleDescriptor aModule = (ModuleDescriptor) modules.next();
128             Archivist subArchivist = getPluggableArchivists().getArchivistForType(aModule.getModuleType());
129             subArchivist.initializeContext(this);
130             subArchivist.setModuleDescriptor(aModule);
131             if(DOLUtils.getDefaultLogger().isLoggable(Level.FINE)) {
132                 DOLUtils.getDefaultLogger().info("Write " + aModule.getArchiveUri() + " with " + subArchivist);
133             }
134             
135             if (aModule.getAlternateDescriptor()!=null) {
136                 // no need to rewrite the original bundle since
137
// the deployment descriptors are saved at the application level
138
// so I don't put it in the list of files to be skipped and it will
139
// be copied as a library.
140

141                 // but I need to save the deployment descriptor for this bundle
142
OutputStream os = out.putNextEntry(aModule.getAlternateDescriptor());
143                 subArchivist.writeStandardDeploymentDescriptors(os);
144                 out.closeEntry();
145         
146         // now write runtime descriptors
147
if (isHandlingRuntimeInfo()) {
148                     os = out.putNextEntry("sun-" + aModule.getAlternateDescriptor());
149                     subArchivist.writeRuntimeDeploymentDescriptors(os);
150                     out.closeEntry();
151                 }
152                 
153             } else {
154                 // Create a new jar file inside the application .ear
155
AbstractArchive internalJar = out.getEmbeddedArchive(aModule.getArchiveUri());
156                 
157                 // we need to copy the old archive to a temp file so
158
// the save method can copy its original contents from
159
InputStream is = in.getEntry(aModule.getArchiveUri());
160                 File tmpFile=null;
161                 try {
162                     if (in.supportsElementsOverwriting()) {
163                         subArchivist.setArchiveUri(internalJar.getArchiveUri());
164                     } else {
165                         tmpFile = getTempFile(path);
166                         BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(tmpFile));
167                         ArchivistUtils.copy(is, bos);
168                         
169                         // configure archivist
170
subArchivist.setArchiveUri(tmpFile.getAbsolutePath());
171                     }
172                     subArchivist.writeContents(internalJar);
173                     out.closeEntry(internalJar);
174                     
175                 } catch(IOException ioe) {
176                     throw ioe;
177                 } finally {
178                     if (tmpFile!=null)
179                         tmpFile.delete();
180                 }
181                 
182                 // no need to copy the bundle from the original jar file
183
filesToSkip.add(aModule.getArchiveUri());
184             }
185         }
186         
187         // now write the old contents and new descriptors
188
super.writeContents(in, out, filesToSkip);
189     }
190     
191     /**
192      * @return the descriptor associated with the archivist
193      */

194     public Descriptor getDescriptor() {
195         return application;
196     }
197
198     /**
199      * @return a default BundleDescriptor for this archivist
200      */

201     public Descriptor getDefaultBundleDescriptor() {
202         Application appDesc = new Application();
203         return appDesc;
204     }
205     
206     /**
207      * open a new application archive file, read all the deployment descriptors
208      *
209      * @param path the file path for the J2EE Application archive
210      */

211     public RootDeploymentDescriptor open(AbstractArchive appArchive)
212         throws IOException, SAXParseException JavaDoc {
213         
214         setManifest(appArchive.getManifest());
215         
216         // read the standard deployment descriptors
217
Descriptor appDesc = readStandardDeploymentDescriptor(appArchive);
218         setDescriptor(appDesc);
219
220         // Now that we have parsed the standard DD, let's read all the
221
// PersistenceUnits defined in the ear level.
222
readPersistenceDeploymentDescriptors(appArchive, getDescriptor());
223
224         // read the modules deployment descriptors
225
if (!readModulesDescriptors((Application) appDesc, appArchive))
226             return null;
227         
228         // now read the runtime deployment descriptors
229
super.readRuntimeDeploymentDescriptor(appArchive, appDesc);
230
231         // validate...
232
if (classLoader!=null && isHandlingRuntimeInfo()) {
233             validate(null);
234         }
235         
236         return (RootDeploymentDescriptor) appDesc;
237     }
238     
239     /**
240      * read the modules deployment descriptor from this application object using
241      * the passed archive
242      * @param application containing the list of modules.
243      * @param appArchive containing the sub modules files.
244      * @return true if everything went fine
245      */

246     public boolean readModulesDescriptors(Application app, AbstractArchive appArchive)
247         throws IOException, SAXParseException JavaDoc {
248         
249         for (Iterator modules = app.getModules();modules.hasNext();) {
250             ModuleDescriptor aModule = (ModuleDescriptor) modules.next();
251             if(DOLUtils.getDefaultLogger().isLoggable(Level.FINE)) {
252                 DOLUtils.getDefaultLogger().fine("Opening sub-module " + aModule);
253             }
254             Descriptor descriptor = null;
255             Archivist newArchivist = getPluggableArchivists().getArchivistForType(aModule.getModuleType());
256             newArchivist.initializeContext(this);
257             newArchivist.setRuntimeXMLValidation(this.getRuntimeXMLValidation());
258             newArchivist.setRuntimeXMLValidationLevel(
259                 this.getRuntimeXMLValidationLevel());
260
261             AbstractArchive embeddedArchive = appArchive.getEmbeddedArchive(aModule.getArchiveUri());
262             if (aModule.getAlternateDescriptor()!=null) {
263                 // the module use alternate deployement descriptor, ignore the
264
// DDs in the archive.
265
InputStream is = appArchive.getEntry(aModule.getAlternateDescriptor());
266                 DeploymentDescriptorFile ddFile = newArchivist.getStandardDDFile();
267                 ddFile.setXMLValidation(newArchivist.getXMLValidation());
268                 ddFile.setXMLValidationLevel(newArchivist.getXMLValidationLevel());
269                 if (appArchive.getArchiveUri()!=null) {
270                     ddFile.setErrorReportingString(appArchive.getArchiveUri());
271                 }
272
273                 descriptor = ddFile.read(is);
274                 is.close();
275                 newArchivist.readWebServicesDescriptor(embeddedArchive, descriptor);
276                 newArchivist.readPersistenceDeploymentDescriptors(embeddedArchive, descriptor);
277                 newArchivist.postStandardDDsRead((RootDeploymentDescriptor) descriptor, embeddedArchive);
278                 newArchivist.readAnnotations(embeddedArchive, (BundleDescriptor)descriptor);
279                 newArchivist.postAnnotationProcess((BundleDescriptor)descriptor, embeddedArchive);
280                 newArchivist.postOpen((RootDeploymentDescriptor) descriptor, embeddedArchive);
281                 // now reads the runtime deployment descriptor...
282
if (isHandlingRuntimeInfo()) {
283                     is = appArchive.getEntry("sun-" + aModule.getAlternateDescriptor());
284                     if (is!=null) {
285                         DeploymentDescriptorFile confDD =
286                             newArchivist.getConfigurationDDFile();
287                         confDD.setXMLValidation(
288                             newArchivist.getRuntimeXMLValidation());
289                         confDD.setXMLValidationLevel(
290                             newArchivist.getRuntimeXMLValidationLevel());
291                         if (appArchive.getArchiveUri()!=null) {
292                             confDD.setErrorReportingString(
293                                 appArchive.getArchiveUri());
294                         }
295
296                         confDD.read(descriptor, is);
297                         is.close();
298                         newArchivist.postRuntimeDDsRead((RootDeploymentDescriptor)descriptor, embeddedArchive);
299                     } else {
300                         if (embeddedArchive!=null) {
301                             newArchivist.readRuntimeDeploymentDescriptor(embeddedArchive,descriptor);
302                         }
303                     }
304                 }
305             } else {
306                 // open the subarchive to get the deployment descriptor...
307
if (embeddedArchive!=null) {
308                     descriptor = newArchivist.open(embeddedArchive);
309                 } else {
310                     DOLUtils.getDefaultLogger().info(localStrings.getLocalString(
311                         "enterprise.deployment.cannotfindmodule",
312                         "Cannot find module {0} in application bundle",
313                         new Object JavaDoc[] {aModule.getArchiveUri()}));
314                     return false;
315                 }
316             }
317             if (embeddedArchive!=null) {
318                 embeddedArchive.close();
319             }
320             if (descriptor != null && descriptor instanceof BundleDescriptor) {
321                 aModule.setDescriptor((BundleDescriptor) descriptor);
322                 ((BundleDescriptor) descriptor).setApplication(app);
323                 aModule.setManifest(newArchivist.getManifest());
324             } else {
325                 // display a message only if we had a handle on the sub archive
326
if (embeddedArchive!=null) {
327                     DOLUtils.getDefaultLogger().info(localStrings.getLocalString(
328                         "enterprise.deployment.cannotreadDDs",
329                         "Cannot read the Deployment Descriptors for module {0}",
330                         new Object JavaDoc[] {aModule.getArchiveUri()}));
331                 }
332                 return false;
333             }
334         }
335         return true;
336     }
337     
338     /**
339      * Read the runtime deployment descriptors (can contained in one or
340      * many file) set the corresponding information in the passed descriptor.
341      * By default, the runtime deployment descriptors are all contained in
342      * the xml file characterized with the path returned by
343      * @see getRuntimeDeploymentDescriptorPath
344      *
345      * @param the initialized deployment descriptor
346      */

347     public void readRuntimeDeploymentDescriptor(AbstractArchive archive, Descriptor descriptor)
348         throws IOException, SAXParseException JavaDoc {
349         
350         if (descriptor instanceof Application) {
351             Application application = (Application) descriptor;
352             
353             // each modules first...
354
for (Iterator itr=application.getModules();itr.hasNext();) {
355                 ModuleDescriptor md = (ModuleDescriptor) itr.next();
356                 Archivist archivist = getPluggableArchivists().getArchivistForType(md.getModuleType());
357                 archivist.initializeContext(this);
358                 archivist.setRuntimeXMLValidation(
359                     this.getRuntimeXMLValidation());
360                 archivist.setRuntimeXMLValidationLevel(
361                     this.getRuntimeXMLValidationLevel());
362                 InputStream is = null;
363                 
364                 if (md.getAlternateDescriptor()!=null) {
365                     // we are using alternate deployment descriptors
366
is = archive.getEntry("sun-" + md.getAlternateDescriptor());
367                     if (is!=null) {
368                         DeploymentDescriptorFile confDD =
369                             archivist.getConfigurationDDFile();
370                         confDD.setXMLValidation(
371                             archivist.getRuntimeXMLValidation());
372                         confDD.setXMLValidationLevel(
373                             archivist.getRuntimeXMLValidationLevel());
374                         if (archive.getArchiveUri()!=null) {
375                             confDD.setErrorReportingString(
376                                 archive.getArchiveUri());
377                         }
378                         confDD.read(md.getDescriptor(), is);
379                         is.close();
380                     }
381                 }
382                 // if is variable is null, it means that we are either
383
// not using alternate deployment descriptors or we could
384
// not find the appropriate sun-???.xml alternate DD.
385
if (is==null) {
386                     AbstractArchive subArchive = archive.getEmbeddedArchive(md.getArchiveUri());
387                     archivist.readRuntimeDeploymentDescriptor(subArchive, md.getDescriptor());
388                 }
389             }
390         }
391         // for the application
392
super.readRuntimeDeploymentDescriptor(archive, descriptor);
393     }
394
395     /**
396      * Read the runtime deployment descriptors (can contained in one or
397      * many file) from a deployment plan archive, set the corresponding
398      * information in the passed descriptor.
399      */

400     public void readRuntimeDDFromDeploymentPlan(
401             AbstractArchive planArchive, Descriptor descriptor)
402         throws IOException, SAXParseException JavaDoc {
403
404         if (planArchive == null) {
405             return;
406         }
407
408         // list of entries in the deployment plan
409
Vector dpEntries = new Vector();
410         for (Enumeration e = planArchive.entries(); e.hasMoreElements();) {
411             dpEntries.add(e.nextElement());
412         }
413
414         if (descriptor instanceof Application) {
415             Application application = (Application) descriptor;
416             
417             //runtime deployment descriptor for the sub modules
418
for (Iterator itr = application.getModules(); itr.hasNext();) {
419                 ModuleDescriptor moduleDesc = (ModuleDescriptor) itr.next();
420                 Archivist subArchivist = ArchivistFactory.getArchivistForType(moduleDesc.getModuleType());
421                 String JavaDoc archiveUri = moduleDesc.getArchiveUri();
422                 String JavaDoc runtimeDDPath = subArchivist.getRuntimeDeploymentDescriptorPath();
423
424                 if (runtimeDDPath!=null) {
425                     String JavaDoc mangledName;
426                     // the runtime deployment descriptor from the deployment file
427
mangledName = archiveUri + "."
428                         + runtimeDDPath.substring(runtimeDDPath.lastIndexOf('/')+1);
429                     DOLUtils.getDefaultLogger().fine("mangledName is " + mangledName);
430
431                     if (dpEntries.contains(mangledName)) {
432                         subArchivist.readRuntimeDDFromDeploymentPlan(
433                             mangledName, planArchive, moduleDesc.getDescriptor());
434                     }
435                 }
436             }
437         }
438
439         //for sun-application.xml
440
super.readRuntimeDDFromDeploymentPlan(planArchive, descriptor);
441     }
442     
443     /**
444      * validates the DOL Objects associated with this archivist, usually
445      * it requires that a class loader being set on this archivist or passed
446      * as a parameter
447      */

448     public void validate(ClassLoader JavaDoc aClassLoader) {
449         ClassLoader JavaDoc cl = aClassLoader;
450         if (cl==null) {
451             cl = classLoader;
452         }
453         if (cl==null) {
454             return;
455         }
456     application.setClassLoader(cl);
457         application.visit((ApplicationVisitor) new ApplicationValidator());
458         
459     }
460     
461     /**
462      * add a new module to this archivist
463      *
464      * @param path for the new module to be added
465      * @param set of library jars for this module
466      * @param external deployment descriptor to use instead of the
467      * the ones in the jar file.
468      */

469     public ModuleDescriptor addArchive(String JavaDoc archivePath, Set libraryJars, String JavaDoc externalDD)
470         throws SAXParseException JavaDoc, IOException {
471         
472         AbstractArchive newArchive = abstractArchiveFactory.openArchive(archivePath);
473         return addArchive(newArchive, libraryJars, externalDD);
474     }
475     
476     /**
477      * add a new module to this archivist
478      *
479      * @param AbstractArchive for the new module to be added
480      * @param set of library jars for this module
481      * @param external deployment descriptor to use instead of the
482      * the ones in the jar file.
483      */

484     public ModuleDescriptor addArchive(AbstractArchive newArchive, Set libraryJars, String JavaDoc externalDD)
485         throws SAXParseException JavaDoc, IOException {
486             
487         // let's create a tmp file to store the new application .ear
488
File outputFile=null;
489         ModuleDescriptor newModule = null;
490         try {
491             outputFile = getTempFile(path);
492             AbstractArchive out = abstractArchiveFactory.createArchive(outputFile.getAbsolutePath());
493         
494             // let's create a new module descriptor for this module
495
newModule = getModuleFor(out, newArchive, libraryJars, externalDD);
496             application.addModule(newModule);
497                     
498             // this should take care of writing the sub modules with the right
499
// manifests and deployment descriptors settings...
500
AbstractArchive in = abstractArchiveFactory.openArchive(path);
501             Vector filesToSkip = new Vector();
502             filesToSkip.add(newModule.getArchiveUri());
503             writeContents(in, out, filesToSkip);
504             in.close();
505
506             out.close();
507         
508             // rename the tmp file
509
renameTmp(outputFile.getAbsolutePath(), path);
510             
511         } finally {
512             if (outputFile!=null)
513                 outputFile.delete();
514         }
515         return newModule;
516     }
517     
518     
519     /**
520      * creates a new module descriptor for a J2EE Archive to be added to the current
521      * application archive.
522      *
523      * @param abstract archive for the application archive file
524      * @param the archive file path to be added
525      * @param set of library jars to add to the classpath of this module
526      * @param optional external deployment descriptors
527      *
528      * @return an initialized ModuleDescriptor for the new module
529      */

530     private ModuleDescriptor getModuleFor(AbstractArchive out, AbstractArchive newArchive, Set libraryJars, String JavaDoc externalDD)
531         throws SAXParseException JavaDoc, IOException {
532     
533         // Let's get an archivist for the new archive to be added and delegate
534
Archivist newArchivist = getPluggableArchivists().getArchivistForArchive(newArchive);
535         newArchivist.initializeContext(this);
536         newArchivist.setArchiveUri(newArchive.getArchiveUri());
537         ModuleDescriptor newModule = newArchivist.addToArchive(this, externalDD);
538         newArchivist.prepareForInclusion(out);
539                         
540         // now update the manifest for this archivist... and writes the libray jars
541
// to our application archive...
542
if (libraryJars!=null && !libraryJars.isEmpty()) {
543             StringBuffer JavaDoc classPath = new StringBuffer JavaDoc();
544             for (Iterator e = libraryJars.iterator(); e.hasNext();) {
545                 String JavaDoc libUri = (String JavaDoc) e.next();
546                 File libFile = new File(libUri);
547                 if (libFile.exists()) {
548                     classPath.append(libUri);
549                     classPath.append(' ');
550                     addFileToArchive(out, libFile.getAbsolutePath(), libUri);
551                 } else {
552                     throw new FileNotFoundException("Library file " + libFile.getAbsolutePath() + " not found");
553                 }
554             }
555             Manifest manifest = newArchivist.getManifest();
556             if (manifest==null) {
557                 manifest = new Manifest();
558                 newArchivist.setManifest(manifest);
559             }
560             Attributes atts = manifest.getMainAttributes();
561             atts.putValue(Attributes.Name.CLASS_PATH.toString(), classPath.toString());
562         }
563         
564         // now include the new module in the output archive
565
AbstractArchive newModuleJar = out.getEmbeddedArchive(newModule.getArchiveUri());
566         
567         // write and close
568
newArchivist.writeContents(newModuleJar);
569         out.closeEntry(newModuleJar);
570                 
571         return newModule;
572     }
573     
574     /**
575      * @return the DeploymentDescriptorFile responsible for handling
576      * standard deployment descriptor
577      */

578     public DeploymentDescriptorFile getStandardDDFile() {
579         return standardDD;
580     }
581     
582     /**
583      * @return if exists the DeploymentDescriptorFile responsible for
584      * handling the configuration deployment descriptors
585      */

586     public DeploymentDescriptorFile getConfigurationDDFile() {
587         return new ApplicationRuntimeDDFile();
588     }
589     
590     /**
591      * Perform Optional packages dependencies checking on an archive
592      */

593     public boolean performOptionalPkgDependenciesCheck(AbstractArchive archive) throws IOException {
594         
595         if (!super.performOptionalPkgDependenciesCheck(archive))
596             return false;
597         
598         // now check sub modules
599
if (application==null) {
600             throw new IOException("Application object not set on archivist");
601         }
602         Iterator<ModuleDescriptor> modulesItr = application.getModules();
603         boolean returnValue = true;
604         while(modulesItr.hasNext()) {
605             ModuleDescriptor md = modulesItr.next();
606             AbstractArchive sub = archive.getEmbeddedArchive(md.getArchiveUri());
607             if (sub!=null) {
608                 Archivist subArchivist = getPluggableArchivists().getArchivistForType(md.getModuleType());
609                 if (!subArchivist.performOptionalPkgDependenciesCheck(sub))
610                     returnValue = false;
611             }
612         }
613         return returnValue;
614     }
615         
616     /**
617      * Copy this archivist to a new abstract archive
618      * @param out the new archive to use to copy our contents into
619      */

620     public void copyInto(AbstractArchive source, AbstractArchive target) throws IOException {
621         try {
622             Application a = (Application) readStandardDeploymentDescriptor(source);
623         } catch(SAXParseException JavaDoc spe) {
624             spe.printStackTrace();
625             DOLUtils.getDefaultLogger().log(Level.SEVERE, "enterprise.deployment.backend.fileCopyFailure");
626         }
627     }
628     
629     /**
630      * Copy this archivist to a new abstract archive
631      * @param a the deployment descriptor for an application
632      * @param source the source archive
633      * @param target the target archive
634      */

635     public void copyInto(Application a, AbstractArchive source, AbstractArchive target) throws IOException {
636         copyInto(a, source, target, true);
637     }
638     
639     /**
640      * Copy this archivist to a new abstract archive
641      * @param a the deployment descriptor for an application
642      * @param source the source archive
643      * @param target the target archive
644      * @param overwriteManifest if true, the manifest in source archive overwrites the one in target
645      */

646     public void copyInto(Application a, AbstractArchive source,
647                          AbstractArchive target, boolean overwriteManifest)
648         throws IOException {
649         Vector entriesAdded = new Vector();
650         for (Iterator modules = a.getModules();modules.hasNext();) {
651             ModuleDescriptor aModule = (ModuleDescriptor) modules.next();
652             entriesAdded.add(aModule.getArchiveUri());
653             AbstractArchive subSource = source.getEmbeddedArchive(aModule.getArchiveUri());
654             AbstractArchive subTarget = target.getEmbeddedArchive(aModule.getArchiveUri());
655             Archivist newArchivist = getPluggableArchivists().getArchivistForType(aModule.getModuleType());
656             newArchivist.copyInto(subSource, subTarget, overwriteManifest);
657             target.closeEntry(subTarget);
658             String JavaDoc subModulePath = subSource.getArchiveUri();
659             if (subModulePath.startsWith(source.getArchiveUri())) {
660                 subModulePath = subModulePath.substring(source.getArchiveUri().length()+File.separator.length());
661                 for (Enumeration subEntries = subSource.entries();subEntries.hasMoreElements();) {
662                     String JavaDoc anEntry = (String JavaDoc) subEntries.nextElement();
663                     entriesAdded.add(subModulePath + "/" + anEntry);
664                 }
665             }
666             subSource.close();
667         }
668         super.copyInto(source, target, entriesAdded, overwriteManifest);
669     }
670     
671     /**
672      * Open a jar file and return an application object for the modules contained
673      * in the archive. If the archive is a standalone module, this API will
674      * create an empty application and add the standalone module to it
675      *
676      * @param the archive file
677      * @param true to read configuration deployment descriptors
678      * @return the application object
679      */

680     public static Application openArchive(File jarFile)
681         throws IOException, SAXParseException JavaDoc {
682            
683         return openArchive(jarFile, false);
684     }
685     
686     /**
687      * Open a jar file and return an application object for the modules contained
688      * in the archive/directory. If the archive/directory is a standalone module, this API will
689      * create an empty application and add the standalone module to it
690      *
691      * @param archivist to use to open the archive file
692      * @param the archive file
693      * @param true to read configuration deployment descriptors
694      * @return the application object
695      */

696     public static Application openArchive(Archivist archivist, File jarFile, boolean handleRuntimeInfo)
697         throws IOException, SAXParseException JavaDoc{
698             
699         // never read the runtime deployment descriptor before the
700
// module type is found and the application object created
701
AbstractArchive originalArchive = null;
702         if(jarFile.isDirectory())
703         {
704             originalArchive = new FileArchive();
705             ((FileArchive)originalArchive).open(jarFile.getAbsolutePath());
706         }
707         else
708         {
709             originalArchive = new InputJarArchive();
710             ((InputJarArchive)originalArchive).open(jarFile.getAbsolutePath());
711         }
712     Application application = openArchive(archivist, originalArchive, handleRuntimeInfo);
713     originalArchive.close();
714     return application;
715     }
716     
717     /**
718      * Open a jar file and return an application object for the modules contained
719      * in the archive. If the archive is a standalone module, this API will
720      * create an empty application and add the standalone module to it
721      *
722      * @param archivist to use to open the archive file
723      * @param the archive abstraction
724      * @param true to read configuration deployment descriptors
725      * @return the application object
726      */

727
728     public static Application openArchive(Archivist archivist, AbstractArchive in, boolean handleRuntimeInfo)
729             throws IOException, SAXParseException JavaDoc {
730                 
731         return openArchive(in.getArchiveUri(), archivist, in, handleRuntimeInfo);
732     }
733     /**
734      * Open a jar file and return an application object for the modules contained
735      * in the archive. If the archive is a standalone module, this API will
736      * create an empty application and add the standalone module to it
737      *
738      * @param the application moduleID
739      * @param archivist to use to open the archive file
740      * @param the archive abstraction
741      * @param true to read configuration deployment descriptors
742      * @return the application object
743      */

744
745     public static Application openArchive(String JavaDoc appName, Archivist archivist, AbstractArchive in, boolean handleRuntimeInfo)
746             throws IOException, SAXParseException JavaDoc {
747         // we are not reading the runtime deployment descriptor now...
748
archivist.setHandleRuntimeInfo(false);
749         
750         Descriptor descriptor = archivist.open(in);
751         Application application;
752         if (descriptor instanceof Application) {
753             application = (Application) descriptor;
754             application.setRegistrationName(appName);
755         } else {
756             BundleDescriptor aBundle = (BundleDescriptor) descriptor;
757             if (aBundle==null) {
758                 logger.log(Level.SEVERE, localStrings.getLocalString(
759                     "enterprise.deployment.cannotreadDDs",
760                     "Cannot read the Deployment Descriptors for module {0}",
761                     new Object JavaDoc[] { in.getArchiveUri() }));
762                 return null;
763             }
764             ModuleDescriptor newModule = archivist.createModuleDescriptor(aBundle);
765             newModule.setArchiveUri(in.getArchiveUri());
766             application = Application.createApplication(appName, newModule);
767         }
768         
769         // now read the runtime deployment descriptor
770
if (handleRuntimeInfo) {
771             // now read the runtime deployment descriptors from the original jar file
772
archivist.setHandleRuntimeInfo(true);
773             archivist.readRuntimeDeploymentDescriptor(in, descriptor);
774         }
775         
776         // validate
777
archivist.validate(null);
778         return application;
779         
780     }
781
782     /**
783      * Open a jar file with the Archivists define by the
784      * pluggable archivists instance and return an application
785      * object for the modules contained in the archive.
786      * If the archive is a standalone module, this API will
787      * create an empty application and add the standalone module to it
788      *
789      * @param the archive file
790      * @param the instance of PluggableArchivists responsible for
791      * instanciating the archivists.
792      * @param true to read configuration deployment descriptors
793      * @return the application object
794      */

795     public static Application openArchive(File jarFile,
796         PluggableArchivists pa, boolean handleRuntimeInfo)
797         throws IOException, SAXParseException JavaDoc {
798             
799         Archivist archivist = pa.getArchivistForArchive(jarFile);
800         return openArchive(archivist, jarFile, handleRuntimeInfo);
801     }
802     
803     /**
804      * Open a jar file with the default Archivists and return an application
805      * object for the modules contained in the archive.
806      * If the archive is a standalone module, this API will
807      * create an empty application and add the standalone module to it
808      *
809      * @param the archive file
810      * @param true to read configuration deployment descriptors
811      * @return the application object
812      */

813     public static Application openArchive(File jarFile, boolean handleRuntimeInfo)
814         throws IOException, SAXParseException JavaDoc {
815             
816         Archivist archivist = ArchivistFactory.getArchivistForArchive(jarFile);
817         return openArchive(archivist, jarFile, handleRuntimeInfo);
818     }
819     
820     /**
821      * @return the application name from an application .ear file
822      * @param the .ear file
823      */

824     static public String JavaDoc getApplicationName(File jarFile) throws IOException {
825
826     if (!jarFile.exists()) {
827         throw new IOException(localStrings.getLocalString(
828         "enterprise.deployment.exceptionjarfiledoesn'texist",
829         "{0} does not exist", new Object JavaDoc[] {jarFile}));
830     }
831         
832         /*
833          *Add finally clause containing explicit close of jar file.
834          */

835     JarFile jar = null;
836     try {
837             jar = new JarFile(jarFile);
838             ApplicationDeploymentDescriptorFile node = new ApplicationDeploymentDescriptorFile();
839             node.setXMLValidation(false);
840             ZipEntry JavaDoc deploymentEntry = jar.getEntry(node.getDeploymentDescriptorPath());
841             if (deploymentEntry != null) {
842                 try {
843                     Application application = (Application) node.read(jar.getInputStream(deploymentEntry));
844                     return application.getDisplayName();
845                 } catch (Exception JavaDoc pe) {
846                     pe.printStackTrace();
847                 }
848             }
849         } finally {
850             if (jar != null) {
851                 jar.close();
852             }
853         }
854         return null;
855     }
856
857     /**
858      * This method will be invoked if and only if the following is true:
859      * 1. directory deployment with neither standard nor runtime DD
860      * 2. JSR88 DeploymentManager.distribute using InputStream with neither
861      * standard nor runtime DD
862      * <p>
863      * Note that we will only venture a guess for case 1. JSR88 deployment
864      * of an application (ear) using InputStream without any deployment
865      * descriptor will NOT be supported at this time.
866      */

867     protected boolean postHandles(AbstractArchive abstractArchive)
868             throws IOException {
869
870         // Only try to make a guess if the archive is a directory
871

872         // We will try to conclude if a directory represents an application
873
// by looking at if it contains any Java EE modules.
874
File file = new File(abstractArchive.getArchiveUri());
875         if (file.isDirectory()) {
876             File[] files = file.listFiles();
877             for (File content : files) {
878                 if (content.isDirectory()) {
879                     String JavaDoc dirPath = content.getPath();
880                     if (dirPath.endsWith("_war")
881                         || dirPath.endsWith("_jar")
882                         || dirPath.endsWith("_rar")) {
883                         return true;
884                     }
885                 }
886             }
887         }
888
889         return false;
890     }
891
892     protected String JavaDoc getArchiveExtension() {
893         return APPLICATION_EXTENSION;
894     }
895
896     @Override JavaDoc public void readPersistenceDeploymentDescriptors(
897             AbstractArchive appArchive, Descriptor descriptor) throws IOException, SAXParseException JavaDoc {
898         if(logger.isLoggable(Level.FINE)) {
899             logger.logp(Level.FINE, "ApplicationArchivist",
900                     "readPersistenceDeploymentDescriptors", "archive = {0}",
901                     appArchive.getURI());
902         }
903         Application application = Application.class.cast(descriptor);
904         Map<String JavaDoc, Archive> subArchives = new HashMap<String JavaDoc, Archive>();
905         try{
906             Enumeration entries = appArchive.entries();
907             while(entries.hasMoreElements()){
908                 String JavaDoc entry = String JavaDoc.class.cast(entries.nextElement());
909                 // at ear level only jar files can be root of PU.
910
if (entry.endsWith(".jar")) {
911                     Iterator modules = application.getModules();
912                     boolean belongsToSomeModule = false;
913                     while(modules.hasNext()){
914                         // We need to do the following check because we don't want
915
// to process files like foo_war/WEB-INF/lib/a.jar.
916
// So the following check ensures that
917
// we have found a .jar embedded in ear file which is
918
// neither an appclient jar nor an ejb jar and nor is it
919
// part of a rar or war.
920
String JavaDoc explodedModuleURI = FileUtils.makeFriendlyFileName(
921                                 ModuleDescriptor.class.cast(modules.next()).
922                                 getArchiveUri()) + "/"; // add '/' to indicate its a directory
923
if(entry.startsWith(explodedModuleURI)){
924                             belongsToSomeModule = true;
925                             break; // no need to see if it belongs to some other module
926
}
927                     }
928                     if(!belongsToSomeModule) {
929                         subArchives.put(entry, appArchive.getSubArchive(entry));
930                     }
931                 }
932             }
933             for(Map.Entry<String JavaDoc, Archive> pathToArchiveEntry : subArchives.entrySet()) {
934                 readPersistenceDeploymentDescriptor(pathToArchiveEntry.getValue(), pathToArchiveEntry.getKey(), descriptor);
935             }
936         }finally{
937             for(Archive subArchive : subArchives.values()) {
938                 subArchive.close();
939             }
940         }
941
942     }
943
944     /**
945      * This is a helper method.
946      * This method is needed because we sometimes have to read PU descriptors
947      * from the original app exploded dir as opposed to generated dir
948      * because generated XML do not contain any information about PUs.
949      * This method also handles the case where application object is virtual,
950      * (a virtual application represents a standalone module deployment object).
951      * @param archive from where persistence descriptors will be read from.
952      * @param application the application object whose persistence units
953      * will be read. This method will read all the persistence units
954      * recurssively and register at appropriate level.
955      * @throws IOException
956      * @throws SAXParseException
957      */

958     public static void readPersistenceDeploymentDescriptorsRecursively(
959             AbstractArchive archive, Application application) throws IOException,
960             SAXParseException JavaDoc {
961         if(!application.isVirtual()) {
962             ApplicationArchivist appArchivist = new ApplicationArchivist();
963             appArchivist.readPersistenceDeploymentDescriptors(archive, application);
964             for(Iterator modules = application.getModules(); modules.hasNext();) {
965                 final ModuleDescriptor moduleDescriptor =
966                         ModuleDescriptor.class.cast(modules.next());
967                 Archivist moduleArchivist = ArchivistFactory.
968                         getArchivistForType(moduleDescriptor.getModuleType());
969                 AbstractArchive moduleArchive = archive.getEmbeddedArchive(
970                         moduleDescriptor.getArchiveUri());
971                 try{
972                     moduleArchivist.readPersistenceDeploymentDescriptors(
973                             moduleArchive, moduleDescriptor.getDescriptor());
974                 } finally {
975                     moduleArchive.close();
976                 }
977             }
978         } else {
979             // it's a standalone war/jar/rar etc.
980
final ModuleDescriptor module =
981                     ModuleDescriptor.class.cast(application.getModules().next());
982             Archivist archivist =
983                     ArchivistFactory.getArchivistForType(module.getModuleType());
984             archivist.readPersistenceDeploymentDescriptors(
985                     archive, module.getDescriptor());
986         }
987     }
988
989     // for test purposes
990
public static void main(String JavaDoc args[]) {
991         
992         if (args.length==0) {
993             return;
994         } else {
995             String JavaDoc fileName = args[0];
996             try {
997                 Archivist archivist = ArchivistFactory.getArchivistForArchive(fileName);
998                 archivist.setHandleRuntimeInfo(true);
999                 archivist.setArchiveUri(fileName);
1000        archivist.setXMLValidation(true);
1001        archivist.setXMLValidationLevel("full");
1002                Descriptor descriptor = ApplicationArchivist.openArchive(archivist, new File(fileName), true);
1003                if (args.length >1 && args[1]!=null) {
1004                    archivist.write(args[1]);
1005                }
1006                
1007            } catch(Exception JavaDoc e) {
1008                e.printStackTrace();
1009            }
1010        }
1011    }
1012    
1013}
1014
Popular Tags