View Javadoc

1   /*
2    * $Source: /usr/cvsroot/melati/melati/src/main/java/org/melati/MelatiConfig.java,v $
3    * $Revision: 1.54 $
4    *
5    * Copyright (C) 2000 Tim Joyce
6    *
7    * Part of Melati (http://melati.org), a framework for the rapid
8    * development of clean, maintainable web applications.
9    *
10   * Melati is free software; Permission is granted to copy, distribute
11   * and/or modify this software under the terms either:
12   *
13   * a) the GNU General Public License as published by the Free Software
14   *    Foundation; either version 2 of the License, or (at your option)
15   *    any later version,
16   *
17   *    or
18   *
19   * b) any version of the Melati Software License, as published
20   *    at http://melati.org
21   *
22   * You should have received a copy of the GNU General Public License and
23   * the Melati Software License along with this program;
24   * if not, write to the Free Software Foundation, Inc.,
25   * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA to obtain the
26   * GNU General Public License and visit http://melati.org to obtain the
27   * Melati Software License.
28   *
29   * Feel free to contact the Developers of Melati (http://melati.org),
30   * if you would like to work out a different arrangement than the options
31   * outlined here.  It is our intention to allow Melati to be used by as
32   * wide an audience as possible.
33   *
34   * This program is distributed in the hope that it will be useful,
35   * but WITHOUT ANY WARRANTY; without even the implied warranty of
36   * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
37   * GNU General Public License for more details.
38   *
39   * Contact details for copyright holder:
40   *
41   *     Tim Joyce <timj At paneris.org>
42   *     http://paneris.org/
43   *     68 Sandbanks Rd, Poole, Dorset. BH14 8BY. UK
44   */
45  
46  package org.melati;
47  
48  import java.io.FileNotFoundException;
49  import java.io.IOException;
50  import java.util.List;
51  import java.util.Properties;
52  import java.util.Vector;
53  
54  import org.melati.login.AccessHandler;
55  import org.melati.poem.PoemLocale;
56  import org.melati.poem.util.EnumUtils;
57  import org.melati.servlet.FormDataAdaptorFactory;
58  import org.melati.template.ClassNameTempletLoader;
59  import org.melati.template.ServletTemplateEngine;
60  import org.melati.template.SimpleDateAdaptor;
61  import org.melati.template.TemplateEngine;
62  import org.melati.template.TempletLoader;
63  import org.melati.template.YMDDateAdaptor;
64  import org.melati.template.YMDHMSTimestampAdaptor;
65  import org.melati.util.ConfigException;
66  import org.melati.util.HttpHeader;
67  import org.melati.util.PropertiesUtils;
68  
69  /**
70   * A MelatiConfig loads and provides access to the configuration parameters for
71   * melati. These are held in <TT>org.melati.MelatiConfig.properties</TT>.
72   */
73  public class MelatiConfig {
74  
75    private Properties configuration = null;
76    /** The properties file name. */
77    private String propertiesName = "org.melati.MelatiConfig";
78  
79    private AccessHandler accessHandler = null;
80    private FormDataAdaptorFactory fdaFactory = null;
81    private TempletLoader templetLoader = null;
82    private TemplateEngine templateEngine = null;
83    private static PoemLocale poemLocale = null;
84    private Vector preferredCharsets = null;
85    private String javascriptLibraryURL = null;
86    private String staticURL = null;
87    private String templatePath = null;
88    private static String loginPageServletClassName = "org.melati.login.Login";
89    private static String logoutPageServletClassName = "org.melati.login.Logout";
90  
91    private static String realPath = null;
92    
93    /**
94     * Allows creation of a <code>MelatiConfig</code> with default config
95     * params.
96     */
97    public MelatiConfig() {
98      try {
99        configuration =
100         PropertiesUtils.fromResource(getClass(), propertiesName + ".properties");
101     }
102     catch (FileNotFoundException e) {
103       configuration = new Properties();
104       // TimJ: i think that if we don't have a properties file, it is pretty fatal
105       // TimP: Naah
106     }
107     catch (IOException e) {
108       throw new ConfigException("The file " + propertiesName + ".properties" +
109                                 " could not be read." +
110                                 " Full Error: " + e.toString());
111     }
112     init(propertiesName);
113   }
114 
115   /**
116    * Allows creation of a <code>MelatiConfig</code> with a specified
117    * properties file.
118    * 
119    * @param propertiesName
120    *        the name of a properties file
121    */
122   public MelatiConfig(String propertiesName) {
123     this.propertiesName = propertiesName;
124     try {
125       configuration =
126         PropertiesUtils.fromResource(getClass(), propertiesName + ".properties");
127     }
128     catch (FileNotFoundException e) {
129       throw new ConfigException("The file " + propertiesName + "properties" +
130                                 " could not be found." +
131                                 " Is it in your CLASSPATH?  Full Error: " +
132                                 e.toString());
133     }
134     catch (IOException e) {
135       throw new ConfigException("The file " + propertiesName + ".properties" +
136                                 " could not be read." +
137                                 " Full Error: " + e.toString());
138     }
139     init(propertiesName);
140   }
141 
142   /**
143    * Comnstructor from a given Properties object.
144    * @param properties the properies object to look in 
145    */
146   public MelatiConfig(Properties properties) {
147     configuration = properties;
148     init(propertiesName);
149   }
150 
151   void init(String propertiesNameIn) {
152     this.propertiesName = propertiesNameIn;
153     String pref = propertiesName + ".";
154     
155     String accessHandlerProp              = pref + "accessHandler";
156     String fdaFactoryProp                 = pref + "formDataAdaptorFactory";
157     String templetLoaderProp              = pref + "templetLoader";
158     String templateEngineProp             = pref + "templateEngine";
159     String templatePathProp               = pref + "templatePath";
160     String javascriptLibraryURLProp       = pref + "javascriptLibraryURL";
161     String staticURLProp                  = pref + "staticURL";
162     String melatiLocaleProp               = pref + "locale";
163     String preferredCharsetsProp          = pref + "preferredCharsets";
164     String loginPageServletClassNameProp  = pref + "loginPageServletClassName";
165     String logoutPageServletClassNameProp = pref + "logoutPageServletClassName";
166 
167     try {
168       setAccessHandler((AccessHandler)PropertiesUtils.
169           instanceOfNamedClass(
170               configuration,
171               accessHandlerProp,
172               "org.melati.login.AccessHandler",
173               "org.melati.login.OpenAccessHandler"));
174 
175       setFdaFactory((FormDataAdaptorFactory)PropertiesUtils.
176           instanceOfNamedClass(
177                        configuration,
178                        fdaFactoryProp,
179                        "org.melati.servlet.FormDataAdaptorFactory",
180                        "org.melati.servlet.MemoryFormDataAdaptorFactory"));
181 
182       String templetLoaderClassName =  (String)configuration.get(templetLoaderProp);
183       if(templetLoaderClassName == null || 
184          templetLoaderClassName.equals("org.melati.template.ClassNameTempletLoader")) {
185         setTempletLoader(ClassNameTempletLoader.getInstance());
186       } else
187         setTempletLoader((TempletLoader)PropertiesUtils.
188           instanceOfNamedClass(
189                           configuration,
190                           templetLoaderProp,
191                           "org.melati.template.TempletLoader",
192                           "org.melati.template.ClassNameTempletLoader"));
193 
194       setTemplateEngine((TemplateEngine)PropertiesUtils.
195           instanceOfNamedClass(
196                            configuration,
197                            templateEngineProp,
198                            "org.melati.template.TemplateEngine",
199                            "org.melati.template.NoTemplateEngine"));
200 
201       String languageTag = PropertiesUtils.getOrDefault(configuration,
202                                                         melatiLocaleProp,
203                                                         "en-gb");
204 
205       setPoemiLocale(PoemLocale.fromLanguageTag(languageTag));
206       if (poemLocale == null)
207           throw new ConfigException(languageTag +
208                               " is not a valid language tag for " +
209                               melatiLocaleProp);
210 
211       // This is a fancy way of splitting, trimming and checking for
212       // errors such as spaces within fields. 
213       // It reflects the fact that the config file format 
214       // is like a quoteless Http header field.
215       setPreferredCharsets(
216         EnumUtils.vectorOf(
217             new HttpHeader(PropertiesUtils.getOrDefault(
218                                configuration,
219                                preferredCharsetsProp,
220                                "ISO-8859-1, UTF-8, UTF-16")).wordIterator()));
221 
222       setJavascriptLibraryURL(PropertiesUtils.getOrDefault(
223               configuration,
224               javascriptLibraryURLProp,
225               "/melati-static/admin/"));
226 
227       setStaticURL(PropertiesUtils.getOrDefault(
228               configuration, 
229               staticURLProp,
230               "/melati-static/"
231               ));
232 
233       setTemplatePath(PropertiesUtils.getOrDefault(configuration,
234           templatePathProp, "."));
235 
236       setLoginPageServletClassName(PropertiesUtils.getOrDefault(configuration,
237           loginPageServletClassNameProp, loginPageServletClassName));
238 
239       setLogoutPageServletClassName(PropertiesUtils.getOrDefault(configuration,
240           logoutPageServletClassNameProp, logoutPageServletClassName));
241     }
242     catch (Exception e) {
243       throw new ConfigException("Melati could not be configured because: " +
244                                 e.toString(), e);
245     }
246 
247   }
248 
249   /**
250    * @return {@link ServletTemplateEngine} in use.
251    */
252   public ServletTemplateEngine getServletTemplateEngine() {
253     return (ServletTemplateEngine)templateEngine;
254   }
255 
256   /**
257    * @return {@link TemplateEngine} in use.
258    */
259   public TemplateEngine getTemplateEngine() {
260     return templateEngine;
261   }
262 
263   /**
264    * Set the {@link TemplateEngine} to use.
265    * 
266    * @param templateEngine
267    *        a {@link TemplateEngine}
268    */
269   public void setTemplateEngine(TemplateEngine templateEngine) {
270     this.templateEngine = templateEngine;
271   }
272 
273   /**
274    * @return the configured {@link AccessHandler}
275    */
276   public AccessHandler getAccessHandler() {
277     return accessHandler;
278   }
279 
280   /**
281    * Set the <code>AccessHandler</code> for use by this Melati.
282    * 
283    * @param accessHandler
284    *        a {@link AccessHandler}
285    */
286   public void setAccessHandler(AccessHandler accessHandler) {
287     this.accessHandler = accessHandler;
288   }
289 
290   /**
291    * @return the configured {@link TempletLoader}
292    */
293   public TempletLoader getTempletLoader() {
294     return templetLoader;
295   }
296 
297   /**
298    * Set the {@link TempletLoader} for use by this Melati.
299    * 
300    * @param templetLoader
301    *        a {@link TempletLoader}
302    */
303   public void setTempletLoader(TempletLoader templetLoader) {
304     this.templetLoader = templetLoader;
305   }
306 
307   /**
308    * @return the configured {@link FormDataAdaptorFactory}
309    */
310   public FormDataAdaptorFactory getFormDataAdaptorFactory() {
311     return fdaFactory;
312   }
313 
314   /**
315    * Set the {@link FormDataAdaptorFactory} for use by this Melati.
316    * 
317    * @param fdaf
318    *        a {@link FormDataAdaptorFactory}
319    */
320   public void setFormDataAdaptorFactory(FormDataAdaptorFactory fdaf) {
321     fdaFactory = fdaf;
322   }
323 
324   /**
325    * @return the location of javascript for this site.
326    */
327   public String getJavascriptLibraryURL() {
328     return javascriptLibraryURL;
329   }
330 
331   /**
332    * Set the <code>JavascriptLibraryURL</code> for use by this Melati.
333    * 
334    * @param url
335    *        a URL to the directory containing the JavaScript for this site
336    */
337   public void setJavascriptLibraryURL(String url) {
338     this.javascriptLibraryURL = url;
339   }
340 
341   /**
342    * Normally set to <code>melati-static</code>.
343    * 
344    * @return the location of static content for this site.
345    */
346   public String getStaticURL() {
347     return staticURL;
348   }
349 
350   /**
351    * Set the <code>StaticURL</code> for use by this Melati.
352    * 
353    * @param url
354    *        a URL to the directory containing the static content
355    */
356   public void setStaticURL(String url) {
357     this.staticURL = url;
358   }
359 
360   /**
361    * @return the location of templates.
362    */
363   public String getTemplatePath() {
364     return templatePath;
365   }
366 
367   /**
368    * @param templatePath
369    *        The templatePath to set.
370    */
371   public void setTemplatePath(String templatePath) {
372     this.templatePath = templatePath;
373   }
374 
375   /**
376    * @return the class name of the logout servlet
377    */
378   public static String getLogoutPageServletClassName() {
379     return logoutPageServletClassName;
380   }
381 
382   /**
383    * @param logoutPageServletClassName
384    *        The logoutPageServletClassName to set.
385    */
386   public static void setLogoutPageServletClassName(
387       String logoutPageServletClassName) {
388     MelatiConfig.logoutPageServletClassName = logoutPageServletClassName;
389   }
390 
391   /**
392    * @return the class name of the login servlet
393    */
394   public static String getLoginPageServletClassName() {
395     return loginPageServletClassName;
396   }
397 
398   /**
399    * @param loginPageServletClassName
400    *        The loginPageServletClassName to set.
401    */
402   public static void setLoginPageServletClassName(
403       String loginPageServletClassName) {
404     MelatiConfig.loginPageServletClassName = loginPageServletClassName;
405   }
406 
407   /**
408    * @return The configured locale, defaults to British English melati locale.
409    */
410   public static PoemLocale getPoemLocale() {
411     return poemLocale;
412   }
413 
414   /**
415    * @param poemLocale
416    *        The PoemLocale to set.
417    */
418   public void setPoemiLocale(PoemLocale poemLocale) {
419     MelatiConfig.poemLocale = poemLocale;
420   }
421 
422 
423   /**
424    * Return the set encodings that the server prefers and supports.
425    * 
426    * @return List of encoding names or aliases.
427    */
428   public List getPreferredCharsets() {
429     return preferredCharsets;
430   }
431 
432   /**
433    * @param preferredCharsets
434    *        The preferredCharsets to set.
435    */
436   public void setPreferredCharsets(Vector preferredCharsets) {
437     this.preferredCharsets = preferredCharsets;
438   }
439 
440   /**
441    * @return Returns the fdaFactory.
442    */
443   public FormDataAdaptorFactory getFdaFactory() {
444     return fdaFactory;
445   }
446 
447   /**
448    * @param fdaFactory
449    *        The fdaFactory to set.
450    */
451   public void setFdaFactory(FormDataAdaptorFactory fdaFactory) {
452     this.fdaFactory = fdaFactory;
453   }
454   
455   //
456   // Non configurable but here to make them available in a template context.
457   //
458   
459   /**
460    * Called from within templets using 
461    * <code>
462    * #set $yearField = $melati.Config.YMDDateAdaptor.yearField($field)
463    * </code>
464    * idiom.
465    * Perhaps this should be elsewhere.
466    * @return the adaptor for rendering dates as drop-downs.
467    */
468   public static YMDDateAdaptor getYMDDateAdaptor() {
469     return YMDDateAdaptor.it;
470   }
471 
472   /**
473    * Called from within templets using 
474    * <code>
475    * #set $secondField = $melati.Config.YMDHMSTimestampAdaptor.secondField($field)
476    * </code>
477    * idiom.
478    * Perhaps this should be elsewhere.
479    * @return the adaptor for rendering timestamps as drop-downs.
480    */
481   public static YMDHMSTimestampAdaptor getYMDHMSTimestampAdaptor() {
482     return YMDHMSTimestampAdaptor.getIt();
483   }
484 
485   /**
486    * Called from within templets.
487    * Perhaps this should be elsewhere.
488    * @return the adaptor for rendering dates as normal.
489    */
490   public static SimpleDateAdaptor getSimpleDateAdaptor() {
491     return SimpleDateAdaptor.it;
492   }
493 
494   /**
495    * @param realPathP the path to set 
496    */
497   public void setRealPath(String realPathP) {
498     realPath = realPathP;
499   }
500   /**
501    * @return the real path, if set null otherwise
502    */
503   public String getRealPath() {
504     if (realPath == null) throw new NullPointerException();
505     return realPath;
506   }
507 
508 }