KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > opencms > loader > CmsResourceManager


1 /*
2  * File : $Source: /usr/local/cvs/opencms/src/org/opencms/loader/CmsResourceManager.java,v $
3  * Date : $Date: 2006/09/22 15:17:03 $
4  * Version: $Revision: 1.37 $
5  *
6  * This library is part of OpenCms -
7  * the Open Source Content Mananagement System
8  *
9  * Copyright (c) 2005 Alkacon Software GmbH (http://www.alkacon.com)
10  *
11  * This library is free software; you can redistribute it and/or
12  * modify it under the terms of the GNU Lesser General Public
13  * License as published by the Free Software Foundation; either
14  * version 2.1 of the License, or (at your option) any later version.
15  *
16  * This library is distributed in the hope that it will be useful,
17  * but WITHOUT ANY WARRANTY; without even the implied warranty of
18  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19  * Lesser General Public License for more details.
20  *
21  * For further information about Alkacon Software GmbH, please see the
22  * company website: http://www.alkacon.com
23  *
24  * For further information about OpenCms, please see the
25  * project website: http://www.opencms.org
26  *
27  * You should have received a copy of the GNU Lesser General Public
28  * License along with this library; if not, write to the Free Software
29  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
30  */

31
32 package org.opencms.loader;
33
34 import org.opencms.configuration.CmsConfigurationException;
35 import org.opencms.configuration.CmsVfsConfiguration;
36 import org.opencms.file.CmsObject;
37 import org.opencms.file.CmsResource;
38 import org.opencms.file.CmsResourceFilter;
39 import org.opencms.file.collectors.I_CmsResourceCollector;
40 import org.opencms.file.types.CmsResourceTypePlain;
41 import org.opencms.file.types.I_CmsResourceType;
42 import org.opencms.main.CmsException;
43 import org.opencms.main.CmsLog;
44 import org.opencms.main.OpenCms;
45 import org.opencms.module.CmsModule;
46 import org.opencms.module.CmsModuleManager;
47 import org.opencms.security.CmsRole;
48 import org.opencms.security.CmsRoleViolationException;
49 import org.opencms.util.CmsResourceTranslator;
50 import org.opencms.util.CmsStringUtil;
51
52 import java.io.IOException JavaDoc;
53 import java.util.ArrayList JavaDoc;
54 import java.util.Collections JavaDoc;
55 import java.util.HashMap JavaDoc;
56 import java.util.Iterator JavaDoc;
57 import java.util.List JavaDoc;
58 import java.util.Locale JavaDoc;
59 import java.util.Map JavaDoc;
60 import java.util.Properties JavaDoc;
61
62 import javax.servlet.ServletException JavaDoc;
63 import javax.servlet.ServletRequest JavaDoc;
64 import javax.servlet.ServletResponse JavaDoc;
65 import javax.servlet.http.HttpServletRequest JavaDoc;
66 import javax.servlet.http.HttpServletResponse JavaDoc;
67
68 import org.apache.commons.logging.Log;
69
70 /**
71  * Collects all available resource loaders, resource types and resource collectors at startup and provides
72  * methods to access them during OpenCms runtime.<p>
73  *
74  * @author Alexander Kandzior
75  *
76  * @version $Revision: 1.37 $
77  *
78  * @since 6.0.0
79  */

80 public class CmsResourceManager {
81
82     /**
83      * Contains the resource manager data that can be initialized during runtime by a module.<p>
84      */

85     final class CmsResourceManagerConfiguration {
86
87         /** Array with all configured resource types. */
88         protected I_CmsResourceType[] m_resourceTypes;
89
90         /** The mappings of file extensions to resource types. */
91         private Map JavaDoc m_mappings;
92
93         /** A list that contains all initialized resource types. */
94         private List JavaDoc m_resourceTypeList;
95
96         /** A map that contains all initialized resource types mapped to their type name. */
97         private Map JavaDoc m_resourceTypeMap;
98
99         /**
100          * Creates a new resource manager data storage.<p>
101          */

102         protected CmsResourceManagerConfiguration() {
103
104             m_resourceTypes = new I_CmsResourceType[100];
105             m_resourceTypeMap = new HashMap JavaDoc();
106             m_mappings = new HashMap JavaDoc();
107             m_resourceTypeList = new ArrayList JavaDoc();
108         }
109
110         /**
111          * Freezes the current configuration by making all configured data sructures unmodifiable.<p> *
112          */

113         protected void freeze() {
114
115             // freeze the current configuration
116
m_resourceTypeList = Collections.unmodifiableList(m_resourceTypeList);
117             m_resourceTypeMap = Collections.unmodifiableMap(m_resourceTypeMap);
118             m_mappings = Collections.unmodifiableMap(m_mappings);
119         }
120
121         /**
122          * Returns the mappings of file extensions to resource types.<p>
123          *
124          * @return the mappings of file extensions to resource types
125          */

126         protected Map JavaDoc getMappings() {
127
128             return m_mappings;
129         }
130
131         /**
132          * Returns the list that contains all initialized resource types.<p>
133          *
134          * @return the list that contains all initialized resource types
135          */

136         protected List JavaDoc getResourceTypeList() {
137
138             return m_resourceTypeList;
139         }
140
141         /**
142          * Returns the map that contains all initialized resource types mapped to their type name.<p>
143          *
144          * @return the map that contains all initialized resource types mapped to their type name
145          */

146         protected Map JavaDoc getResourceTypeMap() {
147
148             return m_resourceTypeMap;
149         }
150     }
151
152     /** The mimetype <code>"text/html"</code>. */
153     public static final String JavaDoc MIMETYPE_HTML = "text/html";
154
155     /** The mimetype <code>"text/plain"</code>. */
156     public static final String JavaDoc MIMETYPE_TEXT = "text/plain";
157
158     /** The log object for this class. */
159     private static final Log LOG = CmsLog.getLog(CmsResourceManager.class);
160
161     /** The map for all configured collector names, mapped to their collector class. */
162     private Map JavaDoc m_collectorNameMappings;
163
164     /** The list of all currently configured content collector instances. */
165     private List JavaDoc m_collectors;
166
167     /** The current resource manager configuration. */
168     private CmsResourceManagerConfiguration m_configuration;
169
170     /** The list of all configured MIME types. */
171     private List JavaDoc m_configuredMimeTypes;
172
173     /** Filename translator, used only for the creation of new files. */
174     private CmsResourceTranslator m_fileTranslator;
175
176     /** Folder translator, used to translate all accesses to resources. */
177     private CmsResourceTranslator m_folderTranslator;
178
179     /** Indicates if the configuration is finalized (frozen). */
180     private boolean m_frozen;
181
182     /** Contains all loader extensions to the include process. */
183     private List JavaDoc m_includeExtensions;
184
185     /** A list that contains all initialized resource loaders. */
186     private List JavaDoc m_loaderList;
187
188     /** All initialized resource loaders, mapped to their id. */
189     private I_CmsResourceLoader[] m_loaders;
190
191     /** The OpenCms map of configured mime types. */
192     private Map JavaDoc m_mimeTypes;
193
194     /** A list that contains all resource types added from the XML configuration. */
195     private List JavaDoc m_resourceTypesFromXml;
196
197     /**
198      * Creates a new instance for the resource manager,
199      * will be called by the vfs configuration manager.<p>
200      */

201     public CmsResourceManager() {
202
203         if (CmsLog.INIT.isInfoEnabled()) {
204             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_STARTING_LOADER_CONFIG_0));
205         }
206
207         m_resourceTypesFromXml = new ArrayList JavaDoc();
208         m_loaders = new I_CmsResourceLoader[16];
209         m_loaderList = new ArrayList JavaDoc();
210         m_includeExtensions = new ArrayList JavaDoc();
211         m_configuredMimeTypes = new ArrayList JavaDoc();
212     }
213
214     /**
215      * Adds a given content collector class to the type manager.<p>
216      *
217      * @param className the name of the class to add
218      * @param order the order number for this collector
219      *
220      * @return the created content collector instance
221      *
222      * @throws CmsConfigurationException in case the collector could not be properly initialized
223      */

224     public synchronized I_CmsResourceCollector addContentCollector(String JavaDoc className, String JavaDoc order)
225     throws CmsConfigurationException {
226
227         Class JavaDoc classClazz;
228         // init class for content collector
229
try {
230             classClazz = Class.forName(className);
231         } catch (ClassNotFoundException JavaDoc e) {
232             LOG.error(Messages.get().getBundle().key(Messages.LOG_CONTENT_COLLECTOR_CLASS_NOT_FOUND_1, className), e);
233             return null;
234         }
235
236         I_CmsResourceCollector collector;
237         try {
238             collector = (I_CmsResourceCollector)classClazz.newInstance();
239         } catch (InstantiationException JavaDoc e) {
240             throw new CmsConfigurationException(Messages.get().container(
241                 Messages.ERR_INVALID_COLLECTOR_NAME_1,
242                 className));
243         } catch (IllegalAccessException JavaDoc e) {
244             throw new CmsConfigurationException(Messages.get().container(
245                 Messages.ERR_INVALID_COLLECTOR_NAME_1,
246                 className));
247         } catch (ClassCastException JavaDoc e) {
248             throw new CmsConfigurationException(Messages.get().container(
249                 Messages.ERR_INVALID_COLLECTOR_NAME_1,
250                 className));
251         }
252
253         // set the configured order for the collector
254
int ord = 0;
255         try {
256             ord = Integer.valueOf(order).intValue();
257         } catch (NumberFormatException JavaDoc e) {
258             LOG.error(Messages.get().getBundle().key(Messages.LOG_COLLECTOR_BAD_ORDER_NUMBER_1, className), e);
259         }
260         collector.setOrder(ord);
261
262         if (CmsLog.INIT.isInfoEnabled()) {
263             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_ADD_COLLECTOR_CLASS_2, className, order));
264         }
265
266         // extend or init the current list of configured collectors
267
if (m_collectors != null) {
268             m_collectors = new ArrayList JavaDoc(m_collectors);
269             m_collectorNameMappings = new HashMap JavaDoc(m_collectorNameMappings);
270         } else {
271             m_collectors = new ArrayList JavaDoc();
272             m_collectorNameMappings = new HashMap JavaDoc();
273         }
274
275         if (!m_collectors.contains(collector)) {
276             // this is a collector not currently configured
277
m_collectors.add(collector);
278
279             Iterator JavaDoc i = collector.getCollectorNames().iterator();
280             while (i.hasNext()) {
281                 String JavaDoc name = (String JavaDoc)i.next();
282                 if (m_collectorNameMappings.containsKey(name)) {
283                     // this name is already configured, check the order of the collector
284
I_CmsResourceCollector otherCollector = (I_CmsResourceCollector)m_collectorNameMappings.get(name);
285                     if (collector.getOrder() > otherCollector.getOrder()) {
286                         // new collector has a greater order than the old collector in the Map
287
m_collectorNameMappings.put(name, collector);
288                         if (CmsLog.INIT.isInfoEnabled()) {
289                             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_COLLECTOR_REPLACED_1, name));
290                         }
291                     } else {
292                         if (CmsLog.INIT.isInfoEnabled()) {
293                             CmsLog.INIT.info(Messages.get().getBundle().key(
294                                 Messages.INIT_DUPLICATE_COLLECTOR_SKIPPED_1,
295                                 name));
296                         }
297                     }
298                 } else {
299                     m_collectorNameMappings.put(name, collector);
300                     if (CmsLog.INIT.isInfoEnabled()) {
301                         CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_ADD_COLLECTOR_1, name));
302                     }
303                 }
304             }
305         }
306
307         // ensure list is unmodifiable to avoid potential misuse or accidental changes
308
Collections.sort(m_collectors);
309         m_collectors = Collections.unmodifiableList(m_collectors);
310         m_collectorNameMappings = Collections.unmodifiableMap(m_collectorNameMappings);
311
312         // return the created collector instance
313
return collector;
314     }
315
316     /**
317      * Adds a new loader to the internal list of loaded loaders.<p>
318      *
319      * @param loader the loader to add
320      * @throws CmsConfigurationException in case the resource manager configuration is already initialized
321      */

322     public synchronized void addLoader(I_CmsResourceLoader loader) throws CmsConfigurationException {
323
324         // check if new loaders can still be added
325
if (m_frozen) {
326             throw new CmsConfigurationException(Messages.get().container(Messages.ERR_NO_CONFIG_AFTER_STARTUP_0));
327         }
328
329         // add the loader to the internal list of loaders
330
int pos = loader.getLoaderId();
331         if (pos > m_loaders.length) {
332             I_CmsResourceLoader[] buffer = new I_CmsResourceLoader[pos * 2];
333             System.arraycopy(m_loaders, 0, buffer, 0, m_loaders.length);
334             m_loaders = buffer;
335         }
336         m_loaders[pos] = loader;
337         if (loader instanceof I_CmsLoaderIncludeExtension) {
338             // this loader requires special processing during the include process
339
m_includeExtensions.add(loader);
340         }
341         m_loaderList.add(loader);
342         if (CmsLog.INIT.isInfoEnabled()) {
343             CmsLog.INIT.info(Messages.get().getBundle().key(
344                 Messages.INIT_ADD_LOADER_2,
345                 loader.getClass().getName(),
346                 new Integer JavaDoc(pos)));
347         }
348     }
349
350     /**
351      * Adds a new MIME type from the XML configuration to the internal list of MIME types.<p>
352      *
353      * @param extension the MIME type extension
354      * @param type the MIME type description
355      *
356      * @return the created content collector instance
357      *
358      * @throws CmsConfigurationException in case the resource manager configuration is already initialized
359      */

360     public CmsMimeType addMimeType(String JavaDoc extension, String JavaDoc type) throws CmsConfigurationException {
361
362         // check if new resource types can still be added
363
if (m_frozen) {
364             throw new CmsConfigurationException(Messages.get().container(Messages.ERR_NO_CONFIG_AFTER_STARTUP_0));
365         }
366
367         CmsMimeType mimeType = new CmsMimeType(extension, type);
368         m_configuredMimeTypes.add(mimeType);
369         return mimeType;
370     }
371
372     /**
373      * Adds a new resource type from the XML configuration to the internal list of loaded resource types.<p>
374      *
375      * Resource types can also be added from a module.<p>
376      *
377      * @param resourceType the resource type to add
378      * @throws CmsConfigurationException in case the resource manager configuration is already initialized
379      */

380     public synchronized void addResourceType(I_CmsResourceType resourceType) throws CmsConfigurationException {
381
382         // check if new resource types can still be added
383
if (m_frozen) {
384             throw new CmsConfigurationException(Messages.get().container(Messages.ERR_NO_CONFIG_AFTER_STARTUP_0));
385         }
386
387         m_resourceTypesFromXml.add(resourceType);
388     }
389
390     /**
391      * Returns the configured content collector with the given name, or <code>null</code> if
392      * no collector with this name is configured.<p>
393      *
394      * @param collectorName the name of the collector to get
395      * @return the configured content collector with the given name
396      */

397     public I_CmsResourceCollector getContentCollector(String JavaDoc collectorName) {
398
399         return (I_CmsResourceCollector)m_collectorNameMappings.get(collectorName);
400     }
401
402     /**
403      * Returns the default resource type for the given resource name, using the
404      * configured resource type file extensions.<p>
405      *
406      * In case the given name does not map to a configured resource type,
407      * {@link CmsResourceTypePlain} is returned.<p>
408      *
409      * This is only required (and should <i>not</i> be used otherwise) when
410      * creating a new resource automatically during file upload or synchronization.
411      * Only in this case, the file type for the new resource is determined using this method.
412      * Otherwise the resource type is <i>always</i> stored as part of the resource,
413      * and is <i>not</i> related to the file name.<p>
414      *
415      * @param resourcename the resource name to look up the resource type for
416      *
417      * @return the default resource type for the given resource name
418      *
419      * @throws CmsException if something goes wrong
420      */

421     public I_CmsResourceType getDefaultTypeForName(String JavaDoc resourcename) throws CmsException {
422
423         String JavaDoc typeName = null;
424         String JavaDoc suffix = null;
425         if (CmsStringUtil.isNotEmpty(resourcename)) {
426             int pos = resourcename.lastIndexOf('.');
427             if (pos >= 0) {
428                 suffix = resourcename.substring(pos);
429                 if (CmsStringUtil.isNotEmpty(suffix)) {
430                     suffix = suffix.toLowerCase();
431                     typeName = (String JavaDoc)m_configuration.getMappings().get(suffix);
432
433                 }
434             }
435         }
436
437         if (typeName == null) {
438             // use default type "plain"
439
typeName = CmsResourceTypePlain.getStaticTypeName();
440         }
441
442         if (CmsLog.INIT.isDebugEnabled()) {
443             CmsLog.INIT.debug(Messages.get().getBundle().key(Messages.INIT_GET_RESTYPE_2, typeName, suffix));
444         }
445         // look up and return the resource type
446
return getResourceType(typeName);
447     }
448
449     /**
450      * Returns the file extensions (suffixes) mappings to resource types.<p>
451      *
452      * @return a Map with all known file extensions as keys and their resource types as values.
453      */

454     public Map JavaDoc getExtensionMapping() {
455
456         return m_configuration.getMappings();
457     }
458
459     /**
460      * Returns the file translator.<p>
461      *
462      * @return the file translator
463      */

464     public CmsResourceTranslator getFileTranslator() {
465
466         return m_fileTranslator;
467     }
468
469     /**
470      * Returns the folder translator.<p>
471      *
472      * @return the folder translator
473      */

474     public CmsResourceTranslator getFolderTranslator() {
475
476         return m_folderTranslator;
477     }
478
479     /**
480      * Returns the loader class instance for a given resource.<p>
481      *
482      * @param resource the resource
483      * @return the appropriate loader class instance
484      * @throws CmsLoaderException if something goes wrong
485      */

486     public I_CmsResourceLoader getLoader(CmsResource resource) throws CmsLoaderException {
487
488         return getLoader(getResourceType(resource.getTypeId()).getLoaderId());
489     }
490
491     /**
492      * Returns the loader class instance for the given loader id.<p>
493      *
494      * @param id the id of the loader to return
495      * @return the loader class instance for the given loader id
496      */

497     public I_CmsResourceLoader getLoader(int id) {
498
499         return m_loaders[id];
500     }
501
502     /**
503      * Returns the (unmodifyable array) list with all initialized resource loaders.<p>
504      *
505      * @return the (unmodifyable array) list with all initialized resource loaders
506      */

507     public List JavaDoc getLoaders() {
508
509         return m_loaderList;
510     }
511
512     /**
513      * Returns the mime type for a specified file name.<p>
514      *
515      * If an encoding parameter that is not <code>null</code> is provided,
516      * the returned mime type is extended with a <code>; charset={encoding}</code> setting.<p>
517      *
518      * If no mime type for the given filename can be determined, the
519      * default <code>{@link #MIMETYPE_HTML}</code> is used.<p>
520      *
521      * @param filename the file name to check the mime type for
522      * @param encoding the default encoding (charset) in case of mime types is of type "text"
523      *
524      * @return the mime type for a specified file
525      */

526     public String JavaDoc getMimeType(String JavaDoc filename, String JavaDoc encoding) {
527
528         return getMimeType(filename, encoding, MIMETYPE_HTML);
529     }
530
531     /**
532      * Returns the mime type for a specified file name.<p>
533      *
534      * If an encoding parameter that is not <code>null</code> is provided,
535      * the returned mime type is extended with a <code>; charset={encoding}</code> setting.<p>
536      *
537      * If no mime type for the given filename can be determined, the
538      * privided default is used.<p>
539      *
540      * @param filename the file name to check the mime type for
541      * @param encoding the default encoding (charset) in case of mime types is of type "text"
542      * @param defaultMimeType the default mime type to use if no matching type for the filename is found
543      *
544      * @return the mime type for a specified file
545      */

546     public String JavaDoc getMimeType(String JavaDoc filename, String JavaDoc encoding, String JavaDoc defaultMimeType) {
547
548         String JavaDoc mimeType = null;
549         int lastDot = filename.lastIndexOf('.');
550         // check the mime type for the file extension
551
if ((lastDot > 0) && (lastDot < (filename.length() - 1))) {
552             mimeType = (String JavaDoc)m_mimeTypes.get(filename.substring(lastDot).toLowerCase(Locale.ENGLISH));
553         }
554         if (mimeType == null) {
555             mimeType = defaultMimeType;
556             if (mimeType == null) {
557                 // no default mime type was provided
558
return null;
559             }
560         }
561         StringBuffer JavaDoc result = new StringBuffer JavaDoc(mimeType);
562         if ((encoding != null) && mimeType.startsWith("text") && (mimeType.indexOf("charset") == -1)) {
563             result.append("; charset=");
564             result.append(encoding);
565         }
566         return result.toString();
567     }
568
569     /**
570      * Returns an unmodifiable List of the configured {@link CmsMimeType} objects.<p>
571      *
572      * @return an unmodifiable List of the configured {@link CmsMimeType} objects
573      */

574     public List JavaDoc getMimeTypes() {
575
576         return m_configuredMimeTypes;
577     }
578
579     /**
580      * Returns an (unmodifiable) list of class names of all currently registered content collectors.<p>
581      *
582      * @return an (unmodifiable) list of class names of all currently registered content collectors
583      */

584     public List JavaDoc getRegisteredContentCollectors() {
585
586         return m_collectors;
587     }
588
589     /**
590      * Returns the initialized resource type instance for the given id.<p>
591      *
592      * @param typeId the id of the resource type to get
593      * @return the initialized resource type instance for the given id
594      * @throws CmsLoaderException if no resource type is available for the given id
595      */

596     public I_CmsResourceType getResourceType(int typeId) throws CmsLoaderException {
597
598         I_CmsResourceType result = null;
599         if (typeId < m_configuration.m_resourceTypes.length) {
600             result = m_configuration.m_resourceTypes[typeId];
601         }
602         if (result == null) {
603             throw new CmsLoaderException(Messages.get().container(
604                 Messages.ERR_UNKNOWN_RESTYPE_ID_REQ_1,
605                 new Integer JavaDoc(typeId)));
606         }
607         return result;
608     }
609
610     /**
611      * Returns the initialized resource type instance for the given resource type name.<p>
612      *
613      * @param typeName the name of the resource type to get
614      * @return the initialized resource type instance for the given name
615      * @throws CmsLoaderException if no resource type is available for the given name
616      */

617     public I_CmsResourceType getResourceType(String JavaDoc typeName) throws CmsLoaderException {
618
619         I_CmsResourceType result = (I_CmsResourceType)m_configuration.getResourceTypeMap().get(typeName);
620         if (result != null) {
621             return result;
622         }
623         throw new CmsLoaderException(Messages.get().container(Messages.ERR_UNKNOWN_RESTYPE_NAME_REQ_1, typeName));
624     }
625
626     /**
627      * Returns the (unmodifyable array) list with all initialized resource types.<p>
628      *
629      * @return the (unmodifyable array) list with all initialized resource types
630      */

631     public List JavaDoc getResourceTypes() {
632
633         // return the list of resource types
634
return m_configuration.getResourceTypeList();
635     }
636
637     /**
638      * Returns a template loader facade for the given file.<p>
639      * @param cms the current cms context
640      * @param resource the requested file
641      * @param templateProperty the property to read for the template
642      *
643      * @return a resource loader facade for the given file
644      * @throws CmsException if something goes wrong
645      */

646     public CmsTemplateLoaderFacade getTemplateLoaderFacade(CmsObject cms, CmsResource resource, String JavaDoc templateProperty)
647     throws CmsException {
648
649         String JavaDoc absolutePath = cms.getSitePath(resource);
650
651         String JavaDoc templateProp = cms.readPropertyObject(absolutePath, templateProperty, true).getValue();
652
653         if (templateProp == null) {
654             // no template property defined, this is a must for facade loaders
655
throw new CmsLoaderException(Messages.get().container(
656                 Messages.ERR_NONDEF_PROP_2,
657                 templateProperty,
658                 absolutePath));
659         }
660
661         CmsResource template = cms.readFile(templateProp, CmsResourceFilter.IGNORE_EXPIRATION);
662         return new CmsTemplateLoaderFacade(getLoader(template), resource, template);
663     }
664
665     /**
666      * @see org.opencms.configuration.I_CmsConfigurationParameterHandler#initConfiguration()
667      */

668     public void initConfiguration() {
669
670         if (CmsLog.INIT.isInfoEnabled()) {
671             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_LOADER_CONFIG_FINISHED_0));
672         }
673
674         m_resourceTypesFromXml = Collections.unmodifiableList(m_resourceTypesFromXml);
675         m_loaderList = Collections.unmodifiableList(m_loaderList);
676         Collections.sort(m_configuredMimeTypes);
677         m_configuredMimeTypes = Collections.unmodifiableList(m_configuredMimeTypes);
678
679         // initalize the resource types
680
initResourceTypes();
681         // initialize the MIME types
682
initMimeTypes();
683     }
684
685     /**
686      * Initializes all additional resource types stored in the modules.<p>
687      *
688      * @param cms an initialized OpenCms user context with "module manager" role permissions
689      *
690      * @throws CmsRoleViolationException in case the provided OpenCms user context did not have "module manager" role permissions
691      */

692     public synchronized void initialize(CmsObject cms) throws CmsRoleViolationException {
693
694         if (OpenCms.getRunLevel() > OpenCms.RUNLEVEL_1_CORE_OBJECT) {
695             // some simple test cases don't require this check
696
cms.checkRole(CmsRole.RESOURCE_TYPE_MANAGER);
697         }
698
699         // initalize the resource types
700
initResourceTypes();
701
702         // call initialize method on all resource types
703
Iterator JavaDoc i = m_configuration.getResourceTypeList().iterator();
704         while (i.hasNext()) {
705             I_CmsResourceType type = (I_CmsResourceType)i.next();
706             type.initialize(cms);
707         }
708
709         if (CmsLog.INIT.isInfoEnabled()) {
710             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_LOADER_CONFIG_FINISHED_0));
711         }
712     }
713
714     /**
715      * Loads the requested resource and writes the contents to the response stream.<p>
716      *
717      * @param req the current http request
718      * @param res the current http response
719      * @param cms the curren cms context
720      * @param resource the requested resource
721      * @throws ServletException if something goes wrong
722      * @throws IOException if something goes wrong
723      * @throws CmsException if something goes wrong
724      */

725     public void loadResource(CmsObject cms, CmsResource resource, HttpServletRequest JavaDoc req, HttpServletResponse JavaDoc res)
726     throws ServletException JavaDoc, IOException JavaDoc, CmsException {
727
728         res.setContentType(getMimeType(resource.getName(), cms.getRequestContext().getEncoding()));
729         I_CmsResourceLoader loader = getLoader(resource);
730         loader.load(cms, resource, req, res);
731     }
732
733     /**
734      * Extension method for handling special, loader depended actions during the include process.<p>
735      *
736      * Note: If you have multiple loaders configured that require include extensions,
737      * all loaders are called in the order they are configured in.<p>
738      *
739      * @param target the target for the include, might be <code>null</code>
740      * @param element the element to select form the target might be <code>null</code>
741      * @param editable the flag to indicate if the target is editable
742      * @param paramMap a map of parameters for the include, can be modified, might be <code>null</code>
743      * @param req the current request
744      * @param res the current response
745      * @throws CmsException in case something goes wrong
746      * @return the modified target URI
747      */

748     public String JavaDoc resolveIncludeExtensions(
749         String JavaDoc target,
750         String JavaDoc element,
751         boolean editable,
752         Map JavaDoc paramMap,
753         ServletRequest JavaDoc req,
754         ServletResponse JavaDoc res) throws CmsException {
755
756         if (m_includeExtensions == null) {
757             return target;
758         }
759         String JavaDoc result = target;
760         for (int i = 0; i < m_includeExtensions.size(); i++) {
761             // offer the element to every include extension
762
I_CmsLoaderIncludeExtension loader = (I_CmsLoaderIncludeExtension)m_includeExtensions.get(i);
763             result = loader.includeExtension(target, element, editable, paramMap, req, res);
764         }
765         return result;
766     }
767
768     /**
769      * Sets the folder and the file translator.<p>
770      *
771      * @param folderTranslator the folder translator to set
772      * @param fileTranslator the file translator to set
773      */

774     public void setTranslators(CmsResourceTranslator folderTranslator, CmsResourceTranslator fileTranslator) {
775
776         m_folderTranslator = folderTranslator;
777         m_fileTranslator = fileTranslator;
778     }
779
780     /**
781      * Shuts down this resource manage instance.<p>
782      *
783      * @throws Exception in case of errors during shutdown
784      */

785     public synchronized void shutDown() throws Exception JavaDoc {
786
787         Iterator JavaDoc it = m_loaderList.iterator();
788         while (it.hasNext()) {
789             // destroy all resource loaders
790
I_CmsResourceLoader loader = (I_CmsResourceLoader)it.next();
791             loader.destroy();
792         }
793
794         m_loaderList = null;
795         m_loaders = null;
796         m_collectorNameMappings = null;
797         m_includeExtensions = null;
798         m_mimeTypes = null;
799         m_configuredMimeTypes = null;
800
801         if (CmsLog.INIT.isInfoEnabled()) {
802             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_SHUTDOWN_1, this.getClass().getName()));
803         }
804     }
805
806     /**
807      * Initialize the MIME types.<p>
808      *
809      * MIME types are configured in the OpenCms <code>opencms-vfs.xml</code> configuration file.<p>
810      *
811      * For legacy reasons, the MIME types are also read from a file <code>"mimetypes.properties"</code>
812      * that must be located in the default <code>"classes"</code> folder of the web application.<p>
813      */

814     private void initMimeTypes() {
815
816         // legacy MIME type initialization: try to read properties file
817
Properties JavaDoc mimeTypes = new Properties JavaDoc();
818         try {
819             // first try: read MIME types from default package
820
mimeTypes.load(getClass().getClassLoader().getResourceAsStream("mimetypes.properties"));
821         } catch (Throwable JavaDoc t) {
822             try {
823                 // second try: read MIME types from loader package (legacy reasons, there are no types by default)
824
mimeTypes.load(getClass().getClassLoader().getResourceAsStream(
825                     "org/opencms/loader/mimetypes.properties"));
826             } catch (Throwable JavaDoc t2) {
827                 if (LOG.isInfoEnabled()) {
828                     LOG.info(Messages.get().getBundle().key(
829                         Messages.LOG_READ_MIMETYPES_FAILED_2,
830                         "mimetypes.properties",
831                         "org/opencms/loader/mimetypes.properties"));
832                 }
833             }
834         }
835
836         // initalize the Map with all available MIME types
837
List JavaDoc combinedMimeTypes = new ArrayList JavaDoc(mimeTypes.size() + m_configuredMimeTypes.size());
838         // first add all MIME types from the configuration
839
combinedMimeTypes.addAll(m_configuredMimeTypes);
840         // now add the MIME types from the properties
841
Iterator JavaDoc i = mimeTypes.entrySet().iterator();
842         while (i.hasNext()) {
843             Map.Entry JavaDoc entry = (Map.Entry JavaDoc)i.next();
844             CmsMimeType mimeType = new CmsMimeType((String JavaDoc)entry.getKey(), (String JavaDoc)entry.getValue(), false);
845             if (!combinedMimeTypes.contains(mimeType)) {
846                 // make sure no MIME types from the XML configuration are overwritten
847
combinedMimeTypes.add(mimeType);
848             }
849         }
850
851         // create a lookup Map for the MIME types
852
m_mimeTypes = new HashMap JavaDoc(mimeTypes.size());
853         Iterator JavaDoc j = combinedMimeTypes.iterator();
854         while (j.hasNext()) {
855             CmsMimeType mimeType = (CmsMimeType)j.next();
856             m_mimeTypes.put(mimeType.getExtension(), mimeType.getType());
857         }
858
859         if (CmsLog.INIT.isInfoEnabled()) {
860             CmsLog.INIT.info(Messages.get().getBundle().key(
861                 Messages.INIT_NUM_MIMETYPES_1,
862                 new Integer JavaDoc(m_mimeTypes.size())));
863         }
864     }
865
866     /**
867      * Adds a new resource type to the internal list of loaded resource types and initializes
868      * options for the resource type.<p>
869      *
870      * @param resourceType the resource type to add
871      * @param configuration the resource configuration
872      */

873     private synchronized void initResourceType(
874         I_CmsResourceType resourceType,
875         CmsResourceManagerConfiguration configuration) {
876
877         // add the loader to the internal list of loaders
878
int pos = resourceType.getTypeId();
879         if (pos > configuration.m_resourceTypes.length) {
880             I_CmsResourceType[] types = new I_CmsResourceType[pos * 2];
881             System.arraycopy(configuration.m_resourceTypes, 0, types, 0, configuration.m_resourceTypes.length);
882             configuration.m_resourceTypes = types;
883         }
884         configuration.m_resourceTypes[pos] = resourceType;
885         configuration.getResourceTypeList().add(resourceType);
886         configuration.getResourceTypeMap().put(resourceType.getTypeName(), resourceType);
887         if (CmsLog.INIT.isInfoEnabled()) {
888             CmsLog.INIT.info(Messages.get().getBundle().key(
889                 Messages.INIT_ADD_RESTYPE_3,
890                 resourceType.getTypeName(),
891                 new Integer JavaDoc(resourceType.getTypeId()),
892                 resourceType.getClass().getName()));
893         }
894
895         // add the mappings
896
List JavaDoc mappings = resourceType.getConfiguredMappings();
897         Iterator JavaDoc i = mappings.iterator();
898         while (i.hasNext()) {
899             String JavaDoc mapping = (String JavaDoc)i.next();
900             // only add this mapping if a mapping with this file extension does not
901
// exist already
902
if (!configuration.getMappings().containsKey(mapping)) {
903                 configuration.getMappings().put(mapping, resourceType.getTypeName());
904                 if (CmsLog.INIT.isInfoEnabled()) {
905                     CmsLog.INIT.info(Messages.get().getBundle().key(
906                         Messages.INIT_MAP_RESTYPE_2,
907                         mapping,
908                         resourceType.getTypeName()));
909                 }
910             }
911         }
912     }
913
914     /**
915      * Initializes member variables required for storing the resource types.<p>
916      */

917     private synchronized void initResourceTypes() {
918
919         if (CmsLog.INIT.isInfoEnabled()) {
920             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_STARTING_LOADER_CONFIG_0));
921         }
922
923         CmsResourceManagerConfiguration newConfiguration = new CmsResourceManagerConfiguration();
924
925         if (CmsLog.INIT.isInfoEnabled()) {
926             CmsLog.INIT.info(Messages.get().getBundle().key(
927                 Messages.INIT_ADD_RESTYPE_FROM_FILE_2,
928                 new Integer JavaDoc(m_resourceTypesFromXml.size()),
929                 CmsVfsConfiguration.DEFAULT_XML_FILE_NAME));
930         }
931
932         // build a new resource type list from the resource types of the XML configuration
933
Iterator JavaDoc i;
934         i = m_resourceTypesFromXml.iterator();
935         while (i.hasNext()) {
936             I_CmsResourceType resourceType = (I_CmsResourceType)i.next();
937             initResourceType(resourceType, newConfiguration);
938         }
939
940         // add all resource types declared in the modules
941
CmsModuleManager moduleManager = OpenCms.getModuleManager();
942         if (moduleManager != null) {
943             i = moduleManager.getModuleNames().iterator();
944             while (i.hasNext()) {
945                 CmsModule module = moduleManager.getModule((String JavaDoc)i.next());
946                 if ((module != null) && (module.getResourceTypes().size() > 0)) {
947                     // module contains resource types
948
if (CmsLog.INIT.isInfoEnabled()) {
949                         CmsLog.INIT.info(Messages.get().getBundle().key(
950                             Messages.INIT_ADD_NUM_RESTYPES_FROM_MOD_2,
951                             new Integer JavaDoc(module.getResourceTypes().size()),
952                             module.getName()));
953                     }
954
955                     Iterator JavaDoc j = module.getResourceTypes().iterator();
956                     while (j.hasNext()) {
957                         I_CmsResourceType resourceType = (I_CmsResourceType)j.next();
958                         initResourceType(resourceType, newConfiguration);
959                     }
960                 }
961             }
962         }
963
964         // freeze the current configuration
965
newConfiguration.freeze();
966         m_configuration = newConfiguration;
967         m_frozen = true;
968
969         if (CmsLog.INIT.isInfoEnabled()) {
970             CmsLog.INIT.info(Messages.get().getBundle().key(Messages.INIT_RESOURCE_TYPE_INITIALIZED_0));
971         }
972     }
973 }
Popular Tags