1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19 package org.apache.myfaces.view.facelets.tag.composite;
20
21 import java.lang.reflect.Method;
22 import java.net.URL;
23 import java.util.regex.Pattern;
24
25 import javax.faces.FacesException;
26 import javax.faces.application.Resource;
27 import javax.faces.application.ResourceHandler;
28 import javax.faces.application.ViewHandler;
29 import javax.faces.context.ExternalContext;
30 import javax.faces.context.FacesContext;
31 import javax.faces.view.facelets.ComponentConfig;
32 import javax.faces.view.facelets.FaceletHandler;
33 import javax.faces.view.facelets.Tag;
34 import javax.faces.view.facelets.TagConfig;
35 import javax.faces.view.facelets.TagHandler;
36
37 import org.apache.myfaces.shared.util.ArrayUtils;
38 import org.apache.myfaces.shared.util.StringUtils;
39 import org.apache.myfaces.shared.util.WebConfigParamUtils;
40 import org.apache.myfaces.view.facelets.tag.TagLibrary;
41
42
43
44
45
46
47
48
49
50 public class CompositeResourceLibrary implements TagLibrary
51 {
52 public final static String NAMESPACE_PREFIX = "http://xmlns.jcp.org/jsf/composite/";
53 public final static String ALIAS_NAMESPACE_PREFIX = "http://java.sun.com/jsf/composite/";
54
55 private final ResourceHandler _resourceHandler;
56 private Pattern _acceptPatterns;
57 private String _extension;
58 private String[] _defaultSuffixesArray;
59 private String _namespacePrefix;
60
61 public CompositeResourceLibrary(FacesContext facesContext, String namespacePrefix)
62 {
63 super();
64 _namespacePrefix = namespacePrefix;
65 _resourceHandler = facesContext.getApplication().getResourceHandler();
66
67 ExternalContext externalContext = FacesContext.getCurrentInstance().getExternalContext();
68
69 _acceptPatterns = loadAcceptPattern(externalContext);
70
71 _extension = loadFaceletExtension(externalContext);
72
73 String defaultSuffixes = WebConfigParamUtils.getStringInitParameter(externalContext,
74 ViewHandler.DEFAULT_SUFFIX_PARAM_NAME, ViewHandler.DEFAULT_SUFFIX );
75
76 _defaultSuffixesArray = StringUtils.splitShortString(defaultSuffixes, ' ');
77
78 boolean faceletsExtensionFound = false;
79 for (String ext : _defaultSuffixesArray)
80 {
81 if (_extension.equals(ext))
82 {
83 faceletsExtensionFound = true;
84 break;
85 }
86 }
87 if (!faceletsExtensionFound)
88 {
89 _defaultSuffixesArray = (String[]) ArrayUtils.concat(_defaultSuffixesArray, new String[]{_extension});
90 }
91 }
92
93
94
95
96
97
98
99
100
101 private Pattern loadAcceptPattern(ExternalContext context)
102 {
103 assert context != null;
104
105 String mappings = context.getInitParameter(ViewHandler.FACELETS_VIEW_MAPPINGS_PARAM_NAME);
106 if (mappings == null)
107 {
108 return null;
109 }
110
111
112 mappings = mappings.trim();
113 if (mappings.length() == 0)
114 {
115 return null;
116 }
117
118 return Pattern.compile(toRegex(mappings));
119 }
120
121 private String loadFaceletExtension(ExternalContext context)
122 {
123 assert context != null;
124
125 String suffix = context.getInitParameter(ViewHandler.FACELETS_SUFFIX_PARAM_NAME);
126 if (suffix == null)
127 {
128 suffix = ViewHandler.DEFAULT_FACELETS_SUFFIX;
129 }
130 else
131 {
132 suffix = suffix.trim();
133 if (suffix.length() == 0)
134 {
135 suffix = ViewHandler.DEFAULT_FACELETS_SUFFIX;
136 }
137 }
138
139 return suffix;
140 }
141
142
143
144
145
146
147
148
149
150 private String toRegex(String mappings)
151 {
152 assert mappings != null;
153
154
155 mappings = mappings.replaceAll("\\s", "");
156
157
158 mappings = mappings.replaceAll("\\.", "\\\\.");
159
160
161 mappings = mappings.replaceAll("\\*", ".*");
162
163
164 mappings = mappings.replaceAll(";", "|");
165
166 return mappings;
167 }
168
169 public boolean handles(String resourceName)
170 {
171 if (resourceName == null)
172 {
173 return false;
174 }
175
176 if (resourceName.endsWith(_extension))
177 {
178
179 return true;
180 }
181
182
183 return _acceptPatterns != null && _acceptPatterns.matcher(resourceName).matches();
184 }
185
186 public boolean containsFunction(String ns, String name)
187 {
188
189 return false;
190 }
191
192 public boolean containsNamespace(String ns)
193 {
194 if (ns != null && ns.startsWith(_namespacePrefix))
195 {
196 if (ns.length() > _namespacePrefix.length())
197 {
198 String libraryName = ns.substring(_namespacePrefix.length());
199 return _resourceHandler.libraryExists(libraryName);
200 }
201 }
202 return false;
203 }
204
205 public boolean containsTagHandler(String ns, String localName)
206 {
207 if (ns != null && ns.startsWith(_namespacePrefix))
208 {
209 if (ns.length() > _namespacePrefix.length())
210 {
211 String libraryName = ns.substring(_namespacePrefix.length());
212
213 for (String defaultSuffix : _defaultSuffixesArray)
214 {
215 String resourceName = localName + defaultSuffix;
216 if (handles(resourceName))
217 {
218 Resource compositeComponentResource =
219 _resourceHandler.createResource(resourceName, libraryName);
220 if (compositeComponentResource != null)
221 {
222 URL url = compositeComponentResource.getURL();
223 return (url != null);
224 }
225 }
226 }
227 }
228 }
229 return false;
230 }
231
232 public Method createFunction(String ns, String name)
233 {
234
235 return null;
236 }
237
238 public TagHandler createTagHandler(String ns, String localName,
239 TagConfig tag) throws FacesException
240 {
241 if (ns != null && ns.startsWith(_namespacePrefix))
242 {
243 if (ns.length() > _namespacePrefix.length())
244 {
245 String libraryName = ns.substring(_namespacePrefix.length());
246 for (String defaultSuffix : _defaultSuffixesArray)
247 {
248 String resourceName = localName + defaultSuffix;
249 if (handles(resourceName))
250 {
251
252
253
254
255
256
257
258
259 Resource compositeComponentResourceWrapped
260 = _resourceHandler.createResource(resourceName, libraryName);
261 if (compositeComponentResourceWrapped != null)
262 {
263 Resource compositeComponentResource
264 = new CompositeResouceWrapper(compositeComponentResourceWrapped);
265 ComponentConfig componentConfig = new ComponentConfigWrapper(tag,
266 "javax.faces.NamingContainer", null);
267
268 return new CompositeComponentResourceTagHandler(componentConfig,
269 compositeComponentResource);
270 }
271 }
272 }
273 }
274 }
275 return null;
276 }
277
278 private static class ComponentConfigWrapper implements ComponentConfig
279 {
280
281 protected final TagConfig parent;
282
283 protected final String componentType;
284
285 protected final String rendererType;
286
287 public ComponentConfigWrapper(TagConfig parent, String componentType,
288 String rendererType)
289 {
290 this.parent = parent;
291 this.componentType = componentType;
292 this.rendererType = rendererType;
293 }
294
295 public String getComponentType()
296 {
297 return this.componentType;
298 }
299
300 public String getRendererType()
301 {
302 return this.rendererType;
303 }
304
305 public FaceletHandler getNextHandler()
306 {
307 return this.parent.getNextHandler();
308 }
309
310 public Tag getTag()
311 {
312 return this.parent.getTag();
313 }
314
315 public String getTagId()
316 {
317 return this.parent.getTagId();
318 }
319 }
320 }