In other words, you want a GET link instead of a POST link? Use <h:link>
instead of <h:commandLink>
in the source page, and use in the target page <f:viewParam>
to set a bean property based on the request parameter, if necessary along with a Converter
which converts from a String
representing an ISBN number to a conrete Book
instance.
E.g. in Home.xhtml
<h:link outcome="Books.xhtml">
<h:graphicImage name="images/books/s1.jpg" />
<f:param name="isbn" value="25413652" />
</h:link>
and in Books.xhtml
<f:metadata>
<f:viewParam name="isbn" value="#{booksBean.book}" converter="isbnToBookConverter" />
</f:metadata>
with this converter
@FacesConverter("isbnToBookConverter")
public class IsbnToBookConverter {
@Override
public Object getAsString(FacesContext context, UIComponent component, Object modelValue) {
Book book = (Book) modelValue;
return (book != null) ? book.getIsbn() : "";
}
@Override
public Object getAsObject(FacesContext context, UIComponent component, String submittedValue) {
if (submittedValue == null || submittedValue.isEmpty()) {
return null; // Let required="true" or @NotNull handle this condition.
}
String isbn = submittedValue;
Book book = someBookService.getByIsbn(isbn);
return book;
}
}
Thanks to the converter, you don't need any action to set the selected book. In case you needed to perform another action based on the set book, just add a <f:viewAction>
to the <f:metadata>
.
<f:metadata>
<f:viewParam name="isbn" value="#{booksBean.book}" converter="isbnToBookConverter" />
<f:viewAction action="#{booksBean.initializeBasedOnSelectedBook}" />
</f:metadata>
See also:
Unrelated to the concrete problem, note that I also fixed the improper usage of library
attribute of the image component. For the proper usage, head to What is the JSF resource library for and how should it be used? And, you'd better lowercase the XHTML filenames, as URLs are case sensitive and this would fail when an user attempts to type the URL from top of head and wouldn't expect to use capitals ( == bad for UX thus).