La
MokaByte Tag Library
I tag che compongono la library permettono essenzialmente
di svolgere le seguenti operazioni:
-
Gestione di un sistema di template JSP: tramite alcuni semplici
tag è possibile definire un template JSP all'interno
del quale sono poi definite alcune zone. Le zone vengono
poi popolate tramite altri tag. Questo sistema (molto semplice
ma flessibile) è il punto di forza di tutta la library.
Data la sua estrema semplicità offre numerosi vantaggi
rispetto alla concorrenza, probabilmente più potente
ma anche un più macchinosa.
- Iterazione
su liste: questo tag consente di scorrere iterativamente
un elenco di elementi e di impaginarli in HTML. La lista
degli articoli trovati dopo una ricerca, gli articoli aggiunti
al carrello della spesa sono due semplici esempi di liste
di elementi che possono essere implementati tramite questo
tag. Il tag può essere considerato come una specie
di ciclo for che consente l'iterazione su elementi passati
dallo strato di business logic.
- Inclusione
condizionale di pezzi di HTML o di pagine esterne: molte
volte può essere necessario includere pezzi di HTML
o pagine esterne in funzione di alcune condizioni logiche
(vero,falso). Ad esempio se un utente sta procedendo al
pagamento di un acquisto ed ha scelto di pagare con carta
di credito potrebbe essere necessario visualizzare informazioni
circa determinati aspetti legati alla sicurezza. Tali messaggi
non verranno visualizzati per coloro che scelgono il pagamento
con contrassegno.
- Paginazione:
se una lista di elementi è troppo lunga per essere
visualizzata in una singola pagina, allora è necessario
effettuare una paginazione. Come accade comunemente in tutti
i motori di ricerca in fondo alla pagina che mostra i risultati
della ricerca appare una tabellina con la quale è
possibile andare a visualizzare le pagine successive. Il
tag in questione è al momento in fase di rifacimento
essendo piuttosto scomodo da usare. Lavora in combinazione
con il tag iterate.
- Menu
condizionali: questo tag è in fase di realizzazione
e rappresenta una evoluzione del tag di inclusione condizionale.
Esso mostra alcune voci in base ad alcune regole logiche
(es. la voce di menu "logout" appare solo se l'utente
si è già loggato) e permette di specificare
il ruolo utente da associare a determinate voci di menu
(solo se un utente si è loggiato con ruolo utente
= "administrator" potrà visualizzare un
menu riservato)
- Navigazione:
in questa categoria sono inseriti alcuni tag utili per la
navigazione web, come ad esempio il tag back(permette di
andare indietro nella history della applicazione in un punto
preciso) o jumpto che consente di inviare l'utente ad un
url particolare fra quelli che ha percorso in precedenza.
Per il momento questi tag non verranno affrontati perché
sono ancora in fase di completamento.
Per
poter utilizzare i tag elencati brevemente qui sopra si deve
specificare che si stanno utilizzando dei custom tag facenti
parte della MBTL: la specifica JSP dice che tale informazione
può essere specificata tramite il tag <taglib>.
Ad esempio nel caso di MBTL si deve inserire la riga
<%@
taglib uri='mbtl' prefix='mbtl' %>
in
ogni pagina JSP della applicazione. L'attributo prefix specifica
il prefisso che sarà utilizzato per tutti i tag della
pagina. Ad esempio in una pagina JSP che non usa tag custom
ma solo quelli definiti dalla JSP API, il prefix è
jsp, e difatti in una comune pagina JSP si è abituati
a incontrare cose del tipo
<jsp:include
.>
L'attributo
uri invece specifica la locazione del file di definizione
della libreria. Si può in questo caso specificare un
URL assoluto, oppure uno relativo (come nel caso in esame).
Citando direttamente il paragrafo del Manuale Pratico di Java
(vedi [MPJ]) edito da MokaByte, ecco la definizione di tale
attributo
"[
]
L'attributo uri specifica la posizione del TLD associato alla
Custom Tag Library, mentre l'attributo prefix comunica al
motore JSP il prefisso con il quale si desidera fare riferimento
ai tag della Custom Tag Library nella pagina corrente. Si
noti che il prefisso associato a una CTL non rappresenta una
proprietà della tag library stessa, ma può essere
liberamente scelto dall'autore della pagina JSP. Dal momento
che ciò può rendere il codice confuso e difficilmente
comprensibile, si consiglia di scegliere e utilizzare i prefissi
delle CTL in maniera logica e coerente, attenendosi alla relativa
documentazione. Uno standard comunemente accettato consiste
nell'utilizzare prefissi chiari e significativi, facendo possibilmente
uso al loro interno del nome della propria azienda o organizzazione
- in maniera sostanzialmente analoga a quanto avviene per
i package Java - al fine di evitare possibili conflitti nella
nomenclatura delle Custom Tag Library.
Vale qui la pena di notare come i prefissi jsp:, jspx:, java:,
javax:, servlet:, sun: e sunw: siano da considerarsi riservati
e non possano venire assegnati a tag library di terze parti."
Per
altre informazioni ed approfondimenti relativi a come si realizzano
tag library, a come si installano in una web application ed
a come si usano, si possono trovare nel capitolo su JSP del
Manuale Pratico di Java (vedi [MPJ]).
Gestione
dei template
Questo tag permette di gestire un sistema di template per
le pagine JSP della applicazione. Il meccanismo si basa su
due parti: nel file di template si specificano le sezioni
che dovranno definire le parti del template stesso tramite
il tag <mbtl:define> come mostrato nel seguente codice
relativo ad un semplicissimo template JSP
<html>
<head>
<title>Untitled Document</title>
<meta http-equiv="Content-Type" content="text/html;
charset=iso-8859-1">
</head>
<body
bgcolor="#FFFFFF" text="#000000">
<table width="700" border="1" cellspacing="0"
cellpadding="0" align="center">
<tr>
<td>
<div align="center">
<mbtl:define section="title" printable="true">
</mbtl:define>
</div>
</td>
</tr>
<tr>
<td>
<div align="center">
<mbtl:define section="body" printable="true">
</mbtl:define>
</div>
</td>
</tr>
<tr>
<td>
<div align="center">
<mbtl:define section="footer" printable="false">
</mbtl:define>
</div>
</td>
</tr>
</table>
</body>
</html>
L'attributo
section permette di specificare il nome della sezione che
si vuole definire, mentre printable=true|false consente di
specificare se si dovrà riempire la zona con del testo
da inserire direttamente come HTML oppure se dovrà
essere inserita una risorsa esterna.
Per capire meglio il funzionamento del template è utile
passare a vedere il funzionamento del tag template
In
ogni pagina JSP che voglia usare il template definito dovrà
usare il tag <mbtl:template> per indicare quale template
debba essere usato, ed il tag <mbtl:insert> per riempire
le varie parti del template header, title, menu, body, footer..).
Supponendo che il template visto in precedenza si chiami template.jsp,
una pagina che utilizzi tale template potrebbe essere così
definita:
<%@
taglib uri='mbtl' prefix='mbtl' %>
< !-- si specifica quale template JSP si deve usare -->
<mbtl:template name='pageTemplate' content='template.jsp'>
<
!-- si inserisce il titolo della pagina tramite la definizione
di testo direttamente nel template-->
<mbtl:insert section='pagetitle' printable='true'>
Una pagina di prova di uso dei template
</mbtl:insert>
<
!-- si inserisce il corpo della pagina tramite la definizione
di testo direttamente nel template-->
<mbtl:insert section='body' printable='true'>
Questa pagina usa un template per la composizione grafica
</mbtl:insert>
<
!-- si inserisce il footer tramite l'inclusione di una pagina
JSP esterna -->
<mbtl:insert section='footer' element='footer.jsp'/>
</mbtl:template>
Da notare che il tag <mbtl:insert> accetta come parametro
l'attributo section con il quale si specifica la porzione
del template che si desidera popolare, e l'attributo printable
che accetta i valori "true|false": nel primo caso
verrà inserito del testo direttamente nel template.
Se invece si usa printable=false, dovrà essere specificato
il nome del file JSP (o HTML) da usare per riempire la porzione
indicata, tramite l'attributo element.
Si
noti il differente uso del tag <mbtl:insert> usato per
inserire del testo direttamente nella pagina, oppure per inserire
un file JSP come mostrato nella sezione footer.
Iterazione
Il tag iterate permette di eseguire un ciclo for all'interno
di una pagina JSP, funzione che tipicamente è utilizzabile
per creare pezzi di HTML in modo ricorsivo sulla base di n
elementi appartenenti ad una lista. Nella applicazione di
esempio allegata, viene realizzato un semplice ciclo di iterazione
con lo scopo di creare una tabella HTML che mostra alcuni
libri di una ipotetica vetrina online.
Il tag iterate si definisce in questo modo
<mbtl:iterate
type="com.mokabyte.testmvc.shop.BookItem" list="<%=
itemsManager.getBookList()%>" name="item">
<!-- iterazione -->
</mbtl:iterate>
All'attributo
list viene assegnata una lista di oggetti confezionati all'interno
di un oggetto LinkedList: in questo caso la lista proviene
dal metodo getBookList() del bean com.mokabyte.testmvc.beans.ItemsManagerBean
il quale svolge la funzione di semplice gestore di serie di
oggetti. Il tipo (classe Java) degli elementi contenuti all'interno
della lista deve essere specificato con l'attributo type:
in questo caso ogni elemento della lista è un BookItem,
oggetto creato ad hoc e presente nella applicazione. Tramite
name si specifica il nome che verrà assegnato ad ogni
oggetto della lista.
Il risultato finale è
<table
width="100%" border="0" >
<!-- Stampa la prima riga con le intestazioni delle colonne
-->
<TR>
<TD><font face="Arial,Helvetica" size=-1><b>Titolo</b></font></TD>
<TD><font face="Arial,Helvetica" size=-1><b>Autore</b></font></TD>
<TD><font face="Arial,Helvetica" size=-1><b>Casa
Editrice</b></font> </TD>
</TR>
<!--
Stampa le altre righe una per ogni libro appartenente alla
lista -->
<mbtl:iterate type="com.mokabyte.testmvc.shop.BookItem"
list="<%= itemsManager.getBookList()%>"
name="item">
<TR>
<TD><font face="Arial,Helvetica"><font
size=-1><%= item.getTitle() %></font></font></TD>
<TD><font face="Arial,Helvetica"><font
size=-1><%= item.getAuthor() %></font></font></TD>
<TD><font face="Arial,Helvetica"><font
size=-1><%= item.getPublisher() %></font></font></TD>
</TR>
</mbtl:iterate>
</table>
Il servlet engine inserirà tante volte il testo inserito
fra i due tag <mbtl:iterate> e </mbtl:iterate>
quanti sono gli elementi appartenenti alla lista.
All'interno della coppia <mbtl:iterate></mbtl:iterate>
si potranno utilizzare i libri della lista per stampare ad
esempio una tabella, dato che ad ogni iterazione l'elemento
item è istanziato con un elemento differente della
lista.
Come sia caricata la lista con i libri è un dettaglio
che non interessa in questo contesto: potrebbe essere stata
caricata da un database oppure creata in un qualsiasi altro
modo. In questo caso la lista viene semplicemente istanziata
all'interno del costruttore del bean ItemsManagerBean:
public
ItemsManagerBean() {
// crea 8 oggetti BookItem
BookItem book1 = new BookItem("Manuale Pratico di Java
- Prima Edizione","aa.vv.","MokaByte Ed.");
BookItem book2 = new BookItem("Manuale Pratico di Java
- Seconda Edizione vol. 1","aa.vv.","MokaByte
Ed.");
BookItem book3 = new BookItem("Manuale Pratico di Java
- Seconda Edizione vol. 2","aa.vv.", "MokaByte
Ed.");
BookItem book4 = new BookItem("UML ed ingegneria del
software","Luca Vetti Tagliati","MokaByte
Ed.");
BookItem book5 = new BookItem("Da Visual Basic a Java","Massimiliano
Bigatti","MokaByte Ed.");
BookItem book6 = new BookItem("Applicazioni J2EE","Giovanni
Puliti","MokaByte Ed.");
BookItem book7 = new BookItem("Java Micro Edition","Pierluigi
Grassi","MokaByte Ed.");
BookItem book8 = new BookItem("Java per esempi","P.Grassi-
G.Puliti","MokaByte Ed.");
// li aggiunge alla lista dei libri
bookList.add(book1);
bookList.add(book2);
bookList.add(book3);
bookList.add(book4);
bookList.add(book5);
bookList.add(book6);
bookList.add(book7);
bookList.add(book8);
}
Conditional
include
Questo semplice tag permette di inserire del testo HTML in
maniera condizionale a seconda che una determinata condizione
sia rispettata. Ad esempio in una pagina si potrebbe scrivere
<!--
ricava un libro dal manger della applicazione -->
<%
BookItem book = ItemsManagerBean.findBookById("3233-233-455");
%>
<!-stampa
l'intestazione della tabella -->
<table width="100%" border="0" >
<!-- Stampa la prima riga con le intestazioni delle colonne
-->
<TR>
<TD><font face="Arial,Helvetica" size=-1><b>Titolo</b></font></TD>
<TD><font face="Arial,Helvetica" size=-1><b>Autore</b></font></TD>
<TD><font face="Arial,Helvetica" size=-1><b>Casa
Editrice</b></font> </TD>
</TR>
<!-- stampa la riga con la visualizzazione dei dati del
libro solo se è diverso da nullo -->
<mbtl:ConditionalInclude condition="<%=!(book ==
null)%>" printable='true'>
<TR>
<TD><font face="Arial,Helvetica"><font
size=-1><%= item.getTitle() %></font></font></TD>
<TD><font face="Arial,Helvetica"><font
size=-1><%= item.getAuthor() %></font></font></TD>
<TD><font face="Arial,Helvetica"><font
size=-1><%= item.getPublisher() %></font></font></TD>
</TR>
</mbtl:ConditionalInclude>
</table>
I messaggi di errore e gestione delle eccezioni
Il tag <mbtl:messages> consente di visualizzare i messaggi
di errore e/o di avvertimento che si sono verificati durante
l'esecuzione di una particolare azione.
Ad esempio nella applicazione di esempio è stato inserito
un link che causa l'esecuzione di FakeAction (letteralmente
azione-falsa) un'azione che volutamente genera una eccezione.
Ecco l'implementazione di FakeAction
public
class FakeAction extends ActionImpl {
// il metodo perform in questo caso genera volutamente
una eccezione
public Routing perform(HttpServlet httpServlet,
HttpServletRequest
httpServletRequest,
HttpServletResponse httpServletResponse)
throws
ActionException {
throw new ActionException("Un
errore generato appositamente per mostrare il
funzionamento
della gestione degli errori in
MokaPackages");
}
}
La azione viene eseguita dal controller (ActionServlet) il
quale intercetta tutte le eccezioni che si generano all'interno
delle azioni: per ogni eccezioni viene creato un oggetto Message
ed aggiunto alla sessione.
Il tag <mbtl:messages> impagina iterando in un HTML
molto semplice i messaggi trovati in sessione (nell'attributo
messages).
Una limitazione attuale del tag è che l'HTML utilizzato
per elencare tutti i messaggi di errore viene prodotto direttamente
all'interno del tag, per cui non è possibile modificare
la struttura (una lista puntata creata con il tag HTML <ul>).
Una possibile evoluzione di questo tag dovrebbe prevedere
la possibilità di parametrizzare l'HTML da usare per
la impaginazione dei messaggi.
Prossimamente
I prossimi passi nella evoluzione di MBTL prevedono l'aggiunta
di ulteriori tag, l'ampliamento delle funzionalità
di quelli esistenti ed una maggiore flessibilità come
ad esempio la possibilità di internazionalizzare alcune
parti.
Il progetto Open Source dovrebbe evolvere grazie al supporto
del gruppo di lavoro che si sta costituendo in questo momento.
Bibliografia
[MPJ] Manuale Pratico di Java - www.mokabyte.it/manualejava2
[MVC] "MokaShop il negozio online di MokaByte: Progettare
applicazioni J2EE multicanale. I parte: il modello MVC, la
View ed il Controller" - di Giovanni Puliti, MokaByte
60 Febbraio 2002 - http://www.mokabyte.it/2002/02/devj2ee_1.htm
|