/
index.xml
476 lines (451 loc) · 17.3 KB
/
index.xml
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
<?xml version="1.0" encoding="UTF-8"?>
<book version="5.0" xmlns="http://docbook.org/ns/docbook" xml:id="springfaces-reference"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xi="http://www.w3.org/2001/XInclude"
xmlns:xlink="http://www.w3.org/1999/xlink"
xsi:schemaLocation="http://docbook.org/ns/docbook http://www.docbook.org/xml/5.0/xsd/docbook.xsd http://www.w3.org/1999/xlink http://www.docbook.org/xml/5.0/xsd/xlink.xsd">
<info>
<title>SpringFaces Reference Guide</title>
<titleabbrev>SpringFaces</titleabbrev>
<productname>SpringFaces</productname>
<releaseinfo>Version 0.0.1</releaseinfo>
<authorgroup>
<author>
<personname>
<firstname>Phillip</firstname>
<surname>Webb</surname>
</personname>
</author>
</authorgroup>
<copyright>
<year>2010-2012</year>
<holder>Phillip Webb</holder>
</copyright>
<legalnotice>
<para>Copies of this document may be made for your own use and for
distribution to others, provided that
you do not charge any fee for such copies and further provided that
each copy contains this Copyright
Notice, whether distributed in print or electronically.
</para>
</legalnotice>
</info>
<toc />
<preface xml:id="preface">
<title>Preface</title>
<para>TODO</para>
</preface>
<chapter>
<title>Getting Started</title>
<para>TODO maven references, jar structure, namespace</para>
</chapter>
<chapter xml:id="core-spring-faces">
<title>JSF Integration</title>
<para>TODO</para>
<sect1 xml:id="converters">
<title>Converters</title>
<para>
JSF converters are used to perform the Object-to-String and String-to-Object
conversion required to render and decode component values. Classically implementations of the
<code>javax.faces.convert.Converter</code> interface are registered in your <code>faces-config.xml</code>
file or marked with the <code>javax.faces.convert.FacesConverter</code> annotation.
</para>
<sect2>
<title>JSF Converters as Spring Beans</title>
<para>
SpringFaces allows JSF converters to be registered as regular Spring beans. All the common Spring
programming idioms (such as dependency injection and AOP) can now be used with JSF converters.
</para>
<para>
By default any Spring Bean that implements the <code>javax.faces.Converter</code> interface will
be registered as a JSF converter using the bean name. The example below shows how a
<code>Converter</code> bean can be referenced from a JSF <code>XHTML</code> page.
</para>
<programlisting language="java">
@Component
public class MyConverterBean implements Converter {
public Object getAsObject(FacesContext context, UIComponent component, String value) {
// ...
}
public String getAsString(FacesContext context, UIComponent component, Object value) {
// ...
}
}</programlisting>
<programlisting language="xml">
<h:inputText ... converter="myConverterBean" /></programlisting>
</sect2>
<sect2 xml:id="converters-for-class">
<title>Registering a converter for a specific Class</title>
<para>
Converters can also be registered such that they are always used for a particular
<code>Class</code>. Using standard JSF annotations this would be achieved using
<code>@FacesConverter(forClass=SpecificClass.class)</code>. With spring beans the
<code>org.springframework.springfaces.bean.ForClass</code> annotation can be used.
</para>
<programlisting language="java">
@Component
@ForClass(SpecificClass.class)
public class MyConverterBean implements Converter {
public Object getAsObject(FacesContext context, UIComponent component, String value) {
// ...
}
public String getAsString(FacesContext context, UIComponent component, Object value) {
SpecificClass v = (SpecificClass) value;
// ...
}
}</programlisting>
<para>
More complex "for class" registrations can also be supported using the
<code>org.springframework.springfaces.bean.ConditionalForClass</code> interface. For example,
using this technique it is possible to register a <code>Converter</code> for all classes with
a given annotation.
</para>
<programlisting language="java">
@Component
public class MyConverterBean implements Converter, ConditionalForClass {
public boolean isForClass(Class<?> targetClass) {
// Some conditional, eg. targetClass has a specific annotation
}
public Object getAsObject(FacesContext context, UIComponent component, String value) {
// ...
}
public String getAsString(FacesContext context, UIComponent component, Object value) {
SpecificClass v = (SpecificClass) value;
// ...
}
}</programlisting>
</sect2>
<sect2>
<title>Support for generics</title>
<para>
Many times a JSF converter will need to cast the incoming object parameter of the
<code>getAsString</code> to a specific type. SpringFaces provides a convenient alternative
variant of the <code>javax.faces.convert.Converter</code> interface that includes a generic type.
The <code>org.springframework.springfaces.convert.Converter</code> class is functionally
equivalent to the standard JSF interface.
</para>
<para>
When using the generic variant of the <code>Converter</code> interface the value attribute of
<code>@ForClass</code> can be omitted as it can be deduced from the generic.
</para>
<programlisting language="java">
@Component
@ForClass
public class MyConverterBean implements Converter<SpecificClass> {
public SpecificClass getAsObject(FacesContext context, UIComponent component, String value) {
// ...
}
public String getAsString(FacesContext context, UIComponent component, SpecificClass value) {
// ...
}
}</programlisting>
</sect2>
<sect2>
<title>Disabling converter support</title>
<para>
JSF converter support can be disabled if necessary when configuring SpringFaces integration.
</para>
<programlisting language="xml">
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:faces="http://www.springframework.org/schema/springfaces"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/springfaces
http://www.springframework.org/schema/springfaces/springfaces.xsd">
<faces:integration converters="false"/>
<beans/></programlisting>
</sect2>
</sect1>
<sect1>
<title>Validators</title>
<para>
JSF <code>Validators</code> can be used to validate user submitted input. Classically
implementations of the <code>javax.faces.validator.Validator</code> interface are
registered in your <code>faces-config.xml</code> file or marked with the
<code>javax.faces.validator.FacesValidator</code> annotation.
</para>
<sect2>
<title>JSF Validators as Spring Beans</title>
<para>
As with the <link linkend="converters"><code>Converter</code></link>
support, SpringFaces allows Spring Beans to be used as JSF <code>Validators</code>.
</para>
<para>
Any Spring Bean that implements the <code>javax.faces.validator.Validator</code> interface
will automatically registered as a JSF validator using the bean name. The example below
shows how a <code>Validator</code> can be referenced from a JSF <code>XHTML</code> page.
</para>
<programlisting language="java">
@Component
public class MyValidatorBean implements Validator {
public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException {
// ...
}
}</programlisting>
<programlisting language="xml" >
<h:inputText ... validator="myValidatorBean" /></programlisting>
</sect2>
<sect2>
<title>Registering a Validator for a specific Class</title>
<para>
The <code>org.springframework.springfaces.bean.ForClass</code> annotation can be used to associate
a <code>Validator</code> with a specific <code>Class</code>. In such cases the validator will be
automatically called for all suitable instances, regardless of any validators specified in the JSF
mark-up.
</para>
<programlisting language="java">
@Component
@ForClass(SpecificClass.class)
public class MyValidatorBean implements Validator {
public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException {
SpecificClass v = (SpecificClass)value;
// ...
}
}</programlisting>
<para>
As with <link linkend="converters-for-class"><code>Converters</code></link> the
<code>org.springframework.springfaces.bean.ConditionalForClass</code> interface can be used if
more complex conditional logic is required.
</para>
</sect2>
<sect2>
<title>Support for generics</title>
<para>
To remove the need to cast the <code>value</code> parameter SpringFaces provides the
alternative <code>org.springframework.springfaces.validator.Validator</code> interface.
This variation works in the same way as the standard JSF interface.
</para>
<para>
When using the generic variant of the <code>Validator</code> interface the value
attribute of <code>@ForClass</code> can be omitted as it can be deduced from the generic.
</para>
<programlisting language="java">
@Component
@ForClass
public class MyValidatorBean implements Validator<SpecificClass> {
public void validate(FacesContext context, UIComponent component, SpecificClass value) throws ValidatorException {
// ...
}
}</programlisting>
</sect2>
<sect2>
<title>Disabling validator support</title>
<para>
JSF validator support can be disabled if necessary when configuring SpringFaces integration.
</para>
<programlisting language="xml">
<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:faces="http://www.springframework.org/schema/springfaces"
xsi:schemaLocation="
http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/springfaces
http://www.springframework.org/schema/springfaces/springfaces.xsd">
<faces:integration validators="false"/>
<beans/></programlisting>
</sect2>
</sect1>
<sect1>
<title>Internationalization and Localization</title>
<para>TODO</para>
<sect2>
<title>Spring MessageSource</title>
<para>
The <code>org.springframework.context.MessageSource</code> interface provides a standard way for
Spring applications to support internationalization. SpringFaces offers support for any
<code>MessageSource</code> using the <code><s:messageSource></code> component.
</para>
<para>
The <code><s:messageSource></code> component has been designed as a drop-in replacement
to the standard <code><f:loadBundle></code> JSF Component. The example below shows
how the component can be used.
</para>
<programlisting language="xml">
<s:messageSource source="#{messageSource}" var="messages"/>
<p>
<h:outputText value="#{messages.hello}"/>
</p></programlisting>
<para>
The source attribute can be any EL expression that resolves to a <code>MessageSource</code> instance.
If the source is not specified the Spring <code>ApplicationContext</code> will be used. The
<code>var</code> attribute is the name of the variable that will be used to access the messages.
</para>
<sect3>
<title>Page IDs</title>
<para>
Unlike standard JSF, the key of the message to load will be built from the ID of the page
being rendered. For example, assuming the page above is from the file
<code>WEB-INF/pages/messages/simple.xhtml</code>, the key used to load the <code>hello</code>
message will be <code>pages.messages.simple.hello</code>.
</para>
<para>
Using these compound keys prevents message key clashes and keeps the page mark-up nice and
concise. You can use the <code>prefix</code> attribute to override this behaviour if you
need to.
</para>
</sect3>
<sect3>
<title>Missing Message Keys</title>
<para>
If you make reference to message in your XHTML that you have forgotten to define you will
either see a warning message (when in development) or an exception will be thrown
(when in production).
</para>
</sect3>
<sect3>
<title>Parameters</title>
<para>
As with standard JSF, your messages and include place-holders for use with
<code><h:outputFormat></code>.
</para>
<programlisting language="text">
pages.message.simple.welcome=Welcome to {1} with {0}</programlisting>
<programlisting language="xml">
<h:outputFormat value="#{messages.welcome}">
<f:param value="Spring"/>
<f:param value="JSF"/>
</h:outputFormat></programlisting>
<para>
The <code><h:outputFormat></code> tag is a little bit verbose, so for convenience,
Spring messages can be used as a <code>Map</code>. This allows you to reference place-holders in a
much more concise way:
</para>
<programlisting language="xml">
<s:messageSource source="#{messageSource}" var="messages"/>
<h:outputText value="#{messages.welcome['Spring']['JSF']}"/></programlisting>
</sect3>
</sect2>
<sect2>
<title>ObjectMessageSource</title>
<para>
Often it is necessary to convert java <code>Objects</code> into localized messages. Common
scenarios here include converting <code>enum</code> values or displaying messages for a
specific type of <code>Exception</code>.
</para>
<para>
Several of the components provided by SpringFaces implicitly support Object-to-Message
conversion. The example below shows how the <code>ExampleObject</code> class can
be mapped to a message using <code><s:messageSource></code>.
</para>
<programlisting language="java">
package org.example;
public class ExampleObject {
}</programlisting>
<programlisting language="xml">
<s:messageSource source="#{messageSource}" var="messages"/>
<h:outputText value="#{messages[exampleInstance]}"/></programlisting>
<sect3>
<title>Object Message Keys</title>
<para>
By default objects are mapped to messages using a key constructed from their fully
qualified class name. The <code>ExampleObject</code> above would resolve using the
key <code>org.example.ExampleObject</code>
</para>
<programlisting language="text">
org.example.ExampleObject=example</programlisting>
<para>
When resolving an <code>Enum</code> object they key also includes the enum value,
for example:
</para>
<programlisting language="java">
package org.example;
public enum ExampleObject {
ONE, //mapped to message key org.example.ExampleObject.ONE
TWO //mapped to message key org.example.ExampleObject.TWO
}
</programlisting>
</sect3>
<sect3>
<title>Message parameters</title>
<para>
Message values can refer to properties of the Object being resolved using the
<code>{name}</code> syntax. For example:
</para>
<programlisting language="java">
package org.example;
public class PersonName {
// ...
public String getFirst() {...}
public String getLast() {...}
}
</programlisting>
<programlisting language="text">
org.example.PersonName=Name is {first} {last}</programlisting>
</sect3>
<sect3>
<title>Custom Object Message Stategies</title>
<para>
Internally the <code>org.springframework.springfaces.message.ObjectMessageSource</code>
interface is used to resolve object messages. If you need to implement a custom object
message strategy you can create your own implementation of this interface and register
it with Spring using the bean name <code>messageSource</code>.
</para>
<para>
The <code>org.springframework.springfaces.message.DefaultObjectMessageSource</code>
class provides a good basis for any custom strategies; override the
<code>resolveCode</code>, <code>resolveMessage</code> or <code>resolveToString</code>
methods.
</para>
</sect3>
</sect2>
</sect1>
<sect1>
<title>Pagination</title>
<para>TODO</para>
</sect1>
<sect1>
<title>Select Items</title>
<para>TODO</para>
</sect1>
<sect1>
<title>Templating</title>
<para>TODO</para>
<!--
- decorate all
- component info
-->
</sect1>
<sect1>
<title>Exception Handlers</title>
<para>TODO</para>
<!-- Custom EH, Object Messages -->
</sect1>
<sect1>
<title>Expression Language</title>
<para>TODO</para>
<!--
SPEL Support
EL Base Classes
-->
</sect1>
<sect1>
<title>Utilities</title>
<para>TODO</para>
<!--
- FacesUtils
- FacesVendor
-->
</sect1>
</chapter>
<chapter>
<title>JSF with Spring MVC</title>
<para>TODO</para>
<!--
Reaching beans
- Spring beans
- MVC model
Implicit Variables
Navigation
- implicit
- to @RequestMappings
- With ReverseDataBinder
- programatic
Converters
- @FacesConverterId
-->
</chapter>
</book>