View Javadoc

1   /*
2    * JaspertReports JSF Plugin Copyright (C) 2011 A. Alonso Dominguez
3    *
4    * This library is free software; you can redistribute it and/or modify it
5    * under the terms of the GNU Lesser General Public License as published by
6    * the Free Software Foundation; either version 2.1 of the License, or (at
7    * your option) any later version. This library is distributed in the hope
8    * that it will be useful, but WITHOUT ANY WARRANTY; without even the implied
9    * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
10   *
11   * See the GNU Lesser General Public License for more details. You should have
12   * received a copy of the GNU Lesser General Public License along with this
13   * library; if not, write to the Free Software Foundation, Inc., 59 Temple
14   * Place, Suite 330, Boston, MA 02111-1307 USA A.
15   *
16   * Alonso Dominguez
17   * alonsoft@users.sf.net
18   */
19  package net.sf.jasperreports.jsf.context;
20  
21  import static net.sf.jasperreports.jsf.util.ComponentUtil.getStringAttribute;
22  
23  import java.util.Collection;
24  import java.util.Collections;
25  import java.util.HashMap;
26  import java.util.Map;
27  
28  import javax.faces.component.UIComponent;
29  import javax.faces.context.FacesContext;
30  
31  import net.sf.jasperreports.jsf.component.UIReport;
32  import net.sf.jasperreports.jsf.component.UISource;
33  import net.sf.jasperreports.jsf.convert.ReportConverter;
34  import net.sf.jasperreports.jsf.convert.SourceConverter;
35  import net.sf.jasperreports.jsf.engine.Exporter;
36  import net.sf.jasperreports.jsf.engine.ExporterException;
37  import net.sf.jasperreports.jsf.engine.Filler;
38  import net.sf.jasperreports.jsf.engine.converters.ReportConverterBase;
39  import net.sf.jasperreports.jsf.engine.converters.SourceConverterBase;
40  import net.sf.jasperreports.jsf.engine.fill.DefaultFiller;
41  import net.sf.jasperreports.jsf.resource.DefaultResourceResolver;
42  import net.sf.jasperreports.jsf.resource.Resource;
43  import net.sf.jasperreports.jsf.resource.ResourceResolver;
44  import net.sf.jasperreports.jsf.resource.UnresolvedResourceException;
45  import net.sf.jasperreports.jsf.util.Services;
46  
47  /**
48   * Default implementation for the <tt>JRFacesContext</tt> abstract class.
49   *
50   * @author A. Alonso Dominguez
51   */
52  final class DefaultJRFacesContext extends JRFacesContext {
53  
54      /** Default filler instance. */
55      private static final Filler DEFAULT_FILLER = new DefaultFiller();
56  
57      /** Default resource resolved instance. */
58      private static final ResourceResolver DEFAULT_RESOURCE_RESOLVER =
59              new DefaultResourceResolver();
60  
61      /** Plugin external context helper. */
62      private ExternalContextHelper externalContext = null;
63  
64      /** Source converter map. */
65      private final Map<String, SourceConverter> sourceConverterMap;
66      private final Map<String, ReportConverter> reportConverterMap;
67      /** Exporter map. */
68      private final Map<String, Exporter> exporterMap;
69      /** MIME type to exporter format map. */
70      private final Map<ContentType, String> contentTypeMap;
71      /** Current fillter instance. */
72      private final Filler filler;
73      /** Current resource resolver instance. */
74      private final ResourceResolver resourceResolver;
75  
76      /**
77       * Default constructor.
78       */
79      protected DefaultJRFacesContext() {
80          sourceConverterMap = Services.map(SourceConverter.class);
81          reportConverterMap = Services.map(ReportConverter.class);
82  
83          exporterMap = Services.map(Exporter.class);
84          contentTypeMap = new HashMap<ContentType, String>();
85          for (Map.Entry<String, Exporter> entry : exporterMap.entrySet()) {
86          	for (ContentType ct : entry.getValue().getContentTypes()) {
87          		contentTypeMap.put(ct, entry.getKey());
88          	}
89          }
90          
91          filler = Services.chain(Filler.class, DEFAULT_FILLER);
92          resourceResolver = Services.chain(
93                  ResourceResolver.class, DEFAULT_RESOURCE_RESOLVER);
94      }
95  
96      /**
97       * Collection of available source types.
98       *
99       * @return collection of available source types.
100      */
101     @Override
102 	public Collection<String> getAvailableSourceTypes() {
103         return Collections.unmodifiableSet(sourceConverterMap.keySet());
104     }
105 
106     /**
107      * Collection of availbale export formats.
108      *
109      * @return collection of available export formats.
110      */
111     @Override
112 	public Collection<String> getAvailableExportFormats() {
113         return Collections.unmodifiableSet(exporterMap.keySet());
114     }
115 
116     @Override
117 	public Collection<ContentType> getSupportedContentTypes() {
118 		return Collections.unmodifiableSet(contentTypeMap.keySet());
119 	}
120 
121 	/**
122      * Obtains the external context helper instance.
123      *
124      * @param context current faces' context.
125      * @return the external context helper.
126      */
127     @Override
128     public ExternalContextHelper getExternalContextHelper(
129             final FacesContext context) {
130         if (externalContext == null) {
131             externalContext = ExternalContextHelper.newInstance(
132                     context.getExternalContext());
133         }
134         return externalContext;
135     }
136 
137     /**
138      * Instantiates a source converter appropiate for the given component.
139      *
140      * @param context current faces' context.
141      * @param component the component which is asking the source converter.
142      * @return a source converter instance.
143      */
144     @Override
145     public SourceConverter createSourceConverter(
146             final FacesContext context,
147             final UIComponent component) {
148         SourceConverter converter = null;
149         if (component instanceof UISource) {
150             String type = getStringAttribute(component, "type", null);
151             if (type != null) {
152                 converter = sourceConverterMap.get(type);
153             }
154         }
155 
156         if (converter == null) {
157             converter = new SourceConverterBase();
158         }
159 
160         return converter;
161     }
162 
163     public ReportConverter createReportConverter(final FacesContext context,
164             final UIReport component) {
165         ReportConverter converter = null;
166 
167         Object aValue = component.getValue();
168 
169         String valueStr;
170         if (aValue instanceof String) {
171             valueStr = (String) aValue;
172             String type = valueStr.substring(
173                     valueStr.lastIndexOf("."));
174             if (type != null && type.length() > 0) {
175                 converter = reportConverterMap.get(type);
176             }
177         }
178 
179         if (converter == null) {
180             converter = new ReportConverterBase();
181         }
182 
183         return converter;
184     }
185 
186     /**
187      * Creates a new resource instance.
188      *
189      * @param context current faces' context.
190      * @param component a report component.
191      * @param name resource name.
192      * @return a resource instance.
193      */
194     @Override
195     public Resource createResource(final FacesContext context,
196             final UIComponent component, final String name) {
197         Resource resource = resourceResolver.resolveResource(
198                 context, component, name);
199         if (resource == null) {
200             throw new UnresolvedResourceException(name);
201         }
202         return resource;
203     }
204 
205     /**
206      * Obtains the report's filler instance.
207      *
208      * @param context current faces' context.
209      * @param component the report component.
210      * @return a filler instance.
211      */
212     @Override
213     public Filler getFiller(final FacesContext context,
214             final UIReport component) {
215         return filler;
216     }
217 
218     /**
219      * Obtains the report's exporter instance.
220      *
221      * @param context current faces' context.
222      * @param component the report component
223      * @return an exporter instance.
224      */
225     @Override
226     public Exporter getExporter(final FacesContext context,
227             final UIReport component) {
228         String format = getStringAttribute(component, "format", null);
229         if (format != null) {
230             Exporter exporter;
231             if (ContentType.isContentType(format)) {
232             	ContentType ct = new ContentType(format);
233             	format = contentTypeMap.get(ct);
234             	if (format == null) {
235             		throw new UnsupportedContentTypeException(ct);
236             	}
237             }
238             exporter = exporterMap.get(format);
239             
240             if (exporter == null) {
241                 throw new ExporterNotFoundException(format);
242             }
243             
244             return exporter;
245         } else {
246             throw new ExporterException(
247                     "No exporting functionality available for component: "
248                     + component.getClientId(context));
249         }
250     }
251 
252 }