d9e4e8e3c06107cd326d15126189f7d02138c293
[mir.git] / source / mir / misc / HTMLTemplateProcessor.java
1 /*
2  * put your module comment here
3  */
4
5
6 package mir.misc;
7
8 import  java.lang.*;
9 import  java.util.*;
10 import  java.io.*;
11 import  java.net.*;
12 import  freemarker.template.*;
13 import  mir.entity.*;
14 import  mir.storage.*;
15 import javax.servlet.http.*;
16 import org.apache.struts.util.MessageResources;
17
18
19 /**
20  * Hilfsklasse zum Mergen von Template und Daten
21  */
22 public final class HTMLTemplateProcessor {
23
24   public static String                templateDir;
25   private static FileTemplateCache    templateCache;
26   private static Logfile              theLog;
27   private static String               docRoot;
28   private static String               actionRoot;
29   private static String               productionHost;
30   private static String               audioHost;
31   private static String               videoHost;
32   private static String               imageHost;
33   private static String               imagePath;
34   private static String               openAction;
35   private static String               defEncoding;
36   private static String               generateFO;
37   private static String               generatePDF;
38   protected static String producerDocRoot =
39                 MirConfig.getProp("Producer.DocRoot");
40   protected static String producerStorageRoot =
41                 MirConfig.getProp("Producer.StorageRoot");
42
43   //
44   // init
45
46     static {
47     /** @todo either in the above block or here :) //rk */
48     templateDir = MirConfig.getPropWithHome("HTMLTemplateProcessor.Dir");
49     templateCache = new FileTemplateCache(templateDir);
50     templateCache.setLoadingPolicy(templateCache.LOAD_ON_DEMAND);
51     // gone in freemarker 1.7.1
52     // templateCache.startAutoUpdate();
53     theLog = Logfile.getInstance(MirConfig.getPropWithHome("HTMLTemplateProcessor.Logfile"));
54     docRoot = MirConfig.getProp("RootUri");
55     //the quick hack is back in effect as it was more broken than ever before
56     // -mh
57     // sorry: nadir back in town, i have to debug the mirbase.jar in the
58     // nadir evironment. from my point of coding, this needs an urgent
59     // fixxx.
60     // yeah, from my point too - tob.
61           //actionRoot = docRoot + "/servlet/" + MirConfig.getProp("ServletName");
62     //actionRoot = docRoot + "/servlet/NadirAktuell";
63
64     actionRoot = docRoot + "/servlet/Mir";
65
66     defEncoding = MirConfig.getProp("Mir.DefaultEncoding");
67     openAction = MirConfig.getProp("Producer.OpenAction");
68     productionHost = MirConfig.getProp("Producer.ProductionHost");
69     videoHost = MirConfig.getProp("Producer.Video.Host");
70     audioHost = MirConfig.getProp("Producer.Audio.Host");
71     imageHost = MirConfig.getProp("Producer.Image.Host");
72     imagePath = MirConfig.getProp("Producer.Image.Path");
73     producerDocRoot = MirConfig.getProp("Producer.DocRoot");
74     producerStorageRoot = MirConfig.getProp("Producer.StorageRoot");
75     generateFO = MirConfig.getProp("GenerateFO");
76     generatePDF = MirConfig.getProp("GeneratePDF");
77   }
78
79   /**
80    * empty private constructor, to avoid instantiation
81    */
82   private HTMLTemplateProcessor () { }
83
84
85   // process-methods to merge different datastructures
86   // with freemarker templates
87
88
89   /**
90    * Wandelt <code>anEntity</code> in freemarker-Struktur um, mischt die Daten mit
91    * Template <code>templateFilename</code> und gibt das Ergebnis an den PrintWriter
92    * <code>out</code>
93    *
94    * @param templateFilename
95    * @param anEntity
96    * @param out
97    * @exception HTMLParseException
98    */
99
100     public static void process(String templateFilename, Entity anEntity, PrintWriter out)
101       throws HTMLParseException {
102         if (anEntity == null)  throw new HTMLParseException("entity is empty!");
103         else process(templateFilename, anEntity, out);
104     }
105
106
107   /**
108    * Wandelt Liste mit Entities <code>entList</code> in freemarker-Struktur um, mischt die Daten mit
109    * Template <code>templateFilename</code> und gibt das Ergebnis an den PrintWriter
110    * <code>out</code>
111    *
112    * @param templateFilename
113    * @param entList
114    * @param out
115    * @exception HTMLParseException
116    */
117   public static void process(HttpServletResponse res,String templateFilename,
118                                                                                                                  EntityList entList, PrintWriter out, Locale locale)
119     throws HTMLParseException {
120     process(res, templateFilename, entList, (String)null, (TemplateModelRoot)null, out, locale);
121   }
122
123   /**
124    * Wandelt Entitylist in freemarker-Struktur um, fügt <code>additionalModel</code>
125    * unter dem Namen <code>additionalModelName</code> ein und mischt die Daten mit
126    * Template <code>templateFilename</code> und gibt das Ergebnis an den PrintWriter
127    * <code>out</code>
128    *
129    * @param templateFilename
130    * @param entList
131    * @param additionalModelName
132    * @param additionalModel
133    * @param out
134    * @exception HTMLParseException
135    */
136     public static void process(HttpServletResponse res,String templateFilename,
137                                                                                                                          EntityList entList, String additionalModelName,
138                                TemplateModelRoot additionalModel, PrintWriter out,
139                                                                                                                          Locale locale)
140       throws HTMLParseException {
141
142       SimpleHash modelRoot = new SimpleHash();
143
144       if (entList == null) {
145          process(null,templateFilename, modelRoot, out, locale);
146       } else {
147         try {
148           modelRoot = makeSimpleHashWithEntitylistInfos(entList);
149
150           // Quickhack um mal ein Popup mit reinzunhemen ..
151           if (additionalModelName != null && additionalModel != null)
152               modelRoot.put(additionalModelName, additionalModel);
153
154           process(res,templateFilename, modelRoot, out, locale);
155         } catch (StorageObjectException e) {
156           throw new HTMLParseException(e.toString());
157         }
158       }
159     }
160
161   /**
162    * Wandelt HashMap <code>mergeData</code> in freemarker-Struktur und mischt diese mit
163    * Template <code>templateFilename</code> und gibt das Ergebnis an den PrintWriter
164    * <code>out</code>
165    *
166    * @param templateFilename
167    * @param mergeData - a HashMap with mergeData to be converted in SimpleHash
168    * @param out
169    * @exception HTMLParseException
170    */
171     public static void process(HttpServletResponse res,String templateFilename,
172                                                                                                                          HashMap mergeData, PrintWriter out, Locale locale)
173       throws HTMLParseException {
174       process(res,templateFilename, makeSimpleHash(mergeData), out, locale);
175     }
176
177   /**
178    * Gibt Template <code>templateFilename</code> an den PrintWriter
179    * <code>out</code>
180    *
181    * @param templateFilename
182    * @param mergeData
183    * @param out
184    * @exception HTMLParseException
185    */
186     public static void process(String templateFilename, PrintWriter out,
187                                                                                                                          Locale locale)
188       throws HTMLParseException {
189       process(null,templateFilename, (TemplateModelRoot)null, out, locale);
190     }
191
192
193         /**
194    * Mischt die freemarker-Struktur <code>tmr</code> mit
195    * Template <code>templateFilename</code> und gibt das Ergebnis an den PrintWriter
196    * <code>out</code>
197    *
198    * @param templateFilename
199    * @param mergeData
200    * @param out
201    * @exception HTMLParseException
202    */
203         public static void process(HttpServletResponse res,String templateFilename,
204                                                                                                                  TemplateModelRoot tmr, PrintWriter out, Locale locale)
205         throws HTMLParseException {
206                 process(res,templateFilename,tmr,null,out,locale);
207
208         }
209
210   /**
211    * Mischt die freemarker-Struktur <code>tmr</code> mit
212    * Template <code>templateFilename</code> und gibt das Ergebnis an den PrintWriter
213    * <code>out</code>
214    *
215    * @param templateFilename
216    * @param mergeData
217    * @param out
218    * @exception HTMLParseException
219    */
220         public static void process(HttpServletResponse res,String templateFilename,
221                                                                                                                  TemplateModelRoot tmr, TemplateModelRoot extra,
222                                                                                                                  PrintWriter out, Locale locale)
223                 throws HTMLParseException {
224                 if (out==null) throw new HTMLParseException("no outputstream");
225                 Template tmpl = getTemplateFor(templateFilename);
226                 if (tmpl == null) throw new HTMLParseException("no template: " + templateFilename);
227                 if (tmr==null) tmr = new SimpleHash();
228
229                 /** @todo  what is this for? (rk) */
230                 String session="";
231                 if (res!=null) {
232                         session=res.encodeURL("");
233                 }
234
235     // @todo wouldn't it be so much easier to just pass the whole damn config
236     // Hash here from Mirconfig... ??????? than we could access arbitrary config
237     // values in the templates. -mh
238                 // put standard configuration into tempalteRootmodel
239                 SimpleHash configHash = new SimpleHash();
240                 configHash.put("defEncoding", new SimpleScalar(defEncoding));
241                 configHash.put("producerDocRoot", new SimpleScalar(producerDocRoot));
242                 configHash.put("storageRoot", new SimpleScalar(producerStorageRoot));
243     configHash.put("productionHost", new SimpleScalar(productionHost));
244                 configHash.put("openAction", new SimpleScalar(openAction));
245                 configHash.put("actionRootLogin",new SimpleScalar(actionRoot));
246                 configHash.put("docRoot", new SimpleScalar(docRoot));
247                 configHash.put("now", new SimpleScalar(StringUtil.date2readableDateTime(new GregorianCalendar())));
248                 configHash.put("actionRoot", new SimpleScalar(actionRoot+session));
249                 configHash.put("videoHost", new SimpleScalar(videoHost));
250                 configHash.put("audioHost", new SimpleScalar(audioHost));
251                 configHash.put("imageHost", new SimpleScalar(imageHost));
252                 configHash.put("imagePath", new SimpleScalar(imagePath));
253                 configHash.put("mirVersion", new SimpleScalar(MirConfig.getProp("Mir.Version")));
254                 // this conform to updated freemarker syntax
255                 configHash.put("compressWhitespace", new freemarker.template.utility.CompressWhitespace() );
256                 configHash.put("generateFO", new SimpleScalar(generateFO));
257                 configHash.put("generatePDF", new SimpleScalar(generatePDF));
258
259                 SimpleHash outPutHash = new SimpleHash();
260
261                 if(extra!=null){
262                         outPutHash.put("extra",extra);
263                         try{
264                         while(((SimpleList)extra).hasNext()){
265                                 theLog.printDebugInfo(((SimpleList)extra).next().toString());
266                         }
267                         }catch(Exception e){}
268                 }
269                 outPutHash.put("data",tmr);
270                 outPutHash.put("config", configHash);
271
272                 MessageResources messages = MessageResources.getMessageResources("bundles.admin");
273                 outPutHash.put("lang", new MessageMethodModel(locale, messages) );
274
275                 tmpl.process(outPutHash,out);
276         }
277
278
279   /**
280    *   Converts Entity-List to SimpleList of SimpleHashes.
281    *   @param aList ist eine Liste von Entity
282    *   @return eine freemarker.template.SimpleList von SimpleHashes.
283    *
284    *    @deprecated EntityLists comply with TemplateListModel now.
285    */
286   public static SimpleList makeSimpleList(EntityList aList) throws StorageObjectException
287   {
288     theLog.printWarning("## using deprecated makeSimpleList(entityList) - a waste of resources");
289     SimpleList  simpleList = new SimpleList();
290     if (aList != null) {
291       for(int i=0;i<aList.size();i++) {
292         simpleList.add(aList.elementAt(i));
293       }
294     }
295     return simpleList;
296   }
297
298   /**
299    *  Konvertiert ein EntityList in ein freemarker.template.SimpleHash-Modell. Im Hash
300    *  sind die einzelnen Entities ueber ihre id zu erreichen.
301    *  @param aList ist die EntityList
302    *  @return SimpleHash mit den entsprechenden freemarker Daten
303    *
304    */
305   public static SimpleHash makeSimpleHash(EntityList aList) throws StorageObjectException
306   {
307     SimpleHash      simpleHash = new SimpleHash();
308     Entity          currentEntity;
309
310     if (aList != null) {
311       for (int i=0;i<aList.size();i++) {
312          currentEntity = (Entity)aList.elementAt(i);
313          simpleHash.put(currentEntity.getId(), currentEntity);
314       }
315     }
316     return simpleHash;
317   }
318
319   /**
320    *  Konvertiert ein Entity in ein freemarker.template.SimpleHash-Modell
321    *  @param entity ist die Entity
322    *  @return SimpleHash mit den entsprechenden freemarker Daten
323    *
324    *  @deprecated This method is deprecated and will be deleted in the next
325    *  release. Entity interfaces freemarker.template.TemplateHashModel now
326    *  and can be used in the same way as SimpleHash. It is not necessary any
327    *  more to make a SimpleHash from an Entity
328    */
329   public static SimpleHash makeSimpleHash(Entity entity) {
330     if (entity != null) {
331       theLog.printWarning("## using deprecated makeSimpleHash(entity) - a waste of resources");
332       return makeSimpleHash(entity.getValues());
333     }
334     else
335       return null;
336   }
337
338   /**
339    *  Konvertiert ein Hashtable mit den keys und values als String
340    *  in ein freemarker.template.SimpleHash-Modell
341    *  @param mergeData der HashMap mit den String / String Daten
342    *  @return SimpleHash mit den entsprechenden freemarker Daten
343    *
344    */
345   public static SimpleHash makeSimpleHash(HashMap mergeData)
346   {
347     SimpleHash modelRoot = new SimpleHash();
348     String aField;
349     if (mergeData != null) {
350       Set set = mergeData.keySet();
351       Iterator it =  set.iterator();
352       for (int i=0; i<set.size();i++)  {
353         aField = (String)it.next();
354         modelRoot.put(aField, (String)mergeData.get(aField));
355       }
356     }
357     return modelRoot;
358   }
359
360
361   /**
362    * Converts EntityList in SimpleHash and adds additional information
363    * to the returned SimpleHash
364    *
365    * @param entList
366    * @return SimpleHash returns SimpleHash with the converted EntityList plus
367    *        additional Data about the list.
368    * @exception StorageObjectException
369    */
370
371   public static SimpleHash makeSimpleHashWithEntitylistInfos(EntityList entList) throws StorageObjectException {
372     SimpleHash modelRoot = new SimpleHash();
373     if (entList!=null) {
374       modelRoot.put("contentlist", entList);
375       modelRoot.put("count", new SimpleScalar((new Integer(entList.getCount())).toString()));
376       if (entList.getWhere()!=null) {
377         modelRoot.put("where", new SimpleScalar(entList.getWhere()));
378         modelRoot.put("where_encoded", new SimpleScalar(URLEncoder.encode(entList.getWhere())));
379       }
380       if(entList.getOrder()!=null) {
381         modelRoot.put("order", new SimpleScalar(entList.getOrder()));
382         modelRoot.put("order_encoded", new SimpleScalar(URLEncoder.encode(entList.getOrder())));
383       }
384       modelRoot.put("from", new SimpleScalar((new Integer(entList.getFrom())).toString()));
385       modelRoot.put("to", new SimpleScalar((new Integer(entList.getTo())).toString()));
386
387       if (entList.hasNextBatch())
388         modelRoot.put("next", new SimpleScalar((new Integer(entList.getNextBatch())).toString()));
389       if (entList.hasPrevBatch())
390         modelRoot.put("prev", new SimpleScalar((new Integer(entList.getPrevBatch())).toString()));
391     }
392     return modelRoot;
393   }
394
395   /**
396    * Private methods to get template from a templateFilename
397    * @param templateFilename
398    * @return Template
399    * @exception HTMLParseException
400    */
401   private static Template getTemplateFor(String templateFilename) throws HTMLParseException
402   {
403     Template returnTemplate = null;
404     if (templateFilename!=null)
405       returnTemplate = (Template)templateCache.getItem(templateFilename,"template");
406
407
408     if (returnTemplate==null) {
409       theLog.printError("CACHE (ERR): Unknown template: " + templateFilename);
410       throw new HTMLParseException("Templatefile: "+ templateFilename + " not found.");
411     }
412
413     return returnTemplate;
414   }
415
416   public static void stopAutoUpdate(){
417     templateCache.stopAutoUpdate();
418     templateCache=null;
419   }
420
421 }