Title: Tecnologies web
1Tecnologies web
- Una visió global de les tecnologies i
arquitectures que hi ha darrera de les
aplicacions web, especialment les basades en Java
2Les tecnologies web engloben
- Els dissenyadors gràfics, que seran experts en
- HTML, CSS, usabilitat
- Els programadors, que hauran de conèixer
- PHP, ASP, JSP
- Els analistes o arquitectes, que hauran de
dominar - J2EE, Frameworks, webservices
- La gent de sistemes a qui li preocuparà
- Seguretat, escalabilitat
- En aquest seminari, intentarem parlar una mica de
totes aquestes àrees de coneixement.
3Índex
- Tecnologies de client del HTML a AJAX.
- Conceptes bàsics d'aplicacions web.
- Les arquitectures basades en Java (de JSP a JEE)
- El mon dels frameworks Spring, Struts,
Hibernate... - Seguretat en aplicacions web
- Elements d'una infrastructura web.
- Últim dia
- Casos pràctics sobre aplicacions web a la FIB
4Les tecnologies del client.Del HTML a AJAX
5De què parlarem?
- CSS
- DOM
- Javascript
- AJAX
- Altres tecnologies per aplicacions riques
6Els estàndards W3C
- És un organisme que es dedica a promoure els
estàndards al web, dissenyant especificacions i
eines - Tenen una oficina a Espanya http//www.w3c.es/
- No només HTML, sino molts altres temes
relacionats amb el web - Accés universal (iniciativa WAI)
- Web semàntica (RDF)
- Multimedia (SVG, SMIL)
- Web services (SOAP,WSDL)
- ...
- http//www.w3c.es/divulgacion/guiasbreves/
7CSS
- Fulls d'estil, que es poden tenir un un fitxer a
part del HTML o entre els tags ltstylegtlt/stylegt - Defineixen atributs de visualització de
- Els tags HTML normals i corrents
- Classes que podem associar a una part del text
- ltspan classtitolgtAixo es un titollt/spangt
- Elements amb un identificador únic
- ltspan idmenu1gtPrimer menult/spangt
- Separar la presentació del contingut, faciliten
la coherència - Permet tenir un HTML molt mes senzill i
estructurat
8Tipus de propietats que hi ha a CSS
- Podem jugar amb
- Marges
- Mides
- Posicions en pantalla
- Tipus de lletra
- Imatges i colors de fons
- Visualització o no dun element
- Aplicar uns estils depenent de la plataforma
- Fer que un menu es vegi en pantalla i no a
limprimir - Fer que un disseny s'adapti a una PDA
9El mon ideal HTML valid CSS
- Idealment, tots els webs haurien de tenir HTML
vàlid - El CSS hauria de proporcionar tota la presentació
- Exemple de fins on podem arribar
- http//www.csszengarden.com
- Realment el que normalment tenim es...
- HTML que es veu be, però que no es 100 vàlid
- Format incorporat dintre del HTML (taules)
- Webs totalment correctes que es veuen malament en
algun navegador per diferències en implementació
10Un exemple de problemes de CSS
- ltstylegt .postit width 200px / amplada de
200 px /padding 25px / deixem un marge de
25 px /background yellow -
- lt/stylegt
- ltdiv class"postit"gt
- ltpgtAixo amb explorer medeix 200 pixels i amb
Mozilla, 250.lt/pgt - ltpgtEl "padding" s'afegeix de formes
diferents.lt/pgt - lt/divgt
- Diferents navegadors representen CSS diferent
11El problema de CSS
12Treballant amb CSS
- Web developer extension
- Validadors de HTML
- Edició de CSS on the fly
- Firebug
- Inspecció delements i els seus estils
- Fitxa de les propietats
- http//www.ilovejackdaniels.com/cheat-sheets/css-c
heat-sheet/ - Treballar amb CSS es dur. S'ha de provar amb tots
els navegadors i tot i així d'han de recorrer a
"hacks" per que les coses quedin com volem
13Lestructura de la pàgina i el DOM
- Document Object Model model d'objectes de la
pàgina que exposa el navegador als llenguatges de
script. - API que ens permet accedir al que esta mostrant
el navegador o manipular el seu comportament - DOM Javascript? NO.
- Javascript ens permet accedir a la pàgina
mostrada i al navegador utilitzant el DOM - Accedint al DOM podem veure i manipular les
propietats definides a través de CSS - Podem accedir a elements qualsevol de la pàgina
si els identifiquem amb un ID únic al HTML
14El DOM ha existit des de sempre...
- ltscriptgt
- function comprova()
- if (document.forms0.elements0.value"")
- alert("Escriu un titol!")
-
- return false // evita que enviem les dades
-
- lt/scriptgt
- ...
- ltform name"pelicula" onSubmit"comprova()"gt
- ltinput type"text" type"titol" gt
- ltinput type"submit" value"OK"gt
- lt/formgt
15L'evolució del DOM simple
- El DOM simple permetia accedir només a
- Valor de camps de formularis
- Frames i finestres
- Extensions propietaries i incompatibles
- Netscape 4 layers (document.layers)
- Explorer array all, amb els elements de la
pàgina - Ens obligava a fer 2 versions de les pàgines!
- Últimes versions de navegadors
- Implementació estàndard del DOM versió 2
- document.getElementById() per accedir als elements
16Exemple àrea desplegable amb DOM
- ltscriptgt
- function desplegar(id)
- valordocument.getElementById(id).style.display
- if (valor!"block") valor"block" else
valor"none" - document.getElementById(id).style.displayvalor
-
- lt/scriptgt
- ltstylegt
- .desplegable displaynone
- lt/stylegt
- ...
- ltdivgtlta hrefjavascriptdesplegar('op1')"gtDespleg
arlt/agtlt/divgt - ltdiv class"desplegable" id"op1"gt
- Aquest text apareixerà i desapareixeràlt/divgt
17Javascript DOM
- Obrim la porta a manipular la pàgina un cop
carregada - Funcions per accedir i manipular larbre,
normalment a partir del seu ID - nodegetElementById(x)
- node.appendChildren(node2)
- node.parentElement
- Podem mostrar, amagar, moure elements de la
pàgina i crear interfaces molt mes agradables i
usables. - Hem destar preparats per patir diferències entre
navegadors - Hi ha llibreries que ens permeten abstrure'ns
18Un exemple tiddlywiki
- Representa tot el que es pot arribar a fer
- http//www.tiddlywiki.org
- Hi podem veure...
- Creació de nous nodes a larbre HTML
- Efectes de visualització
- Programació avançada en Javascript
- Accés a objectes interns del navegador per
guardar - I a sobre... pot ser útil!
19La revolució AJAX
- AJAXAsynchronous JavaScriptXML
- Treballar des del navegador comunicant-se amb el
servidor pero sense necessitat de recarregar les
pàgines - Ús extensiu de lobjecte XMLHttpRequest
- Permet fer peticions HTTP des de Javascript
- Executa codi JavaScript en resposta a la crida
- Manipulem el DOM de la pàgina
- Resultat pàgines interactives amb 0 recarregues
- Problemes
- depenem molt del navegador
- dificultat de desenvolupament
20Fluxe dexecució de AJAX
- Tenim un objecte AJAX
- Creem una instancia i li diem
- URL a la que connecta
- Funció de callback
- En rebre la resposta, executem el callback
(assincronament) - El callback rep XML, HTML, JSON...
- Variant fem que periodicament es vagin
actualitzant les dades (per exemple per veure
actualitzacions de mail)
21Un exemple Google Maps
- Parteix el mapa en rajoles, casdascuna amb una
URL fixa per posició i nivell de zoom - Mateixa tecnologia dels jocs 2D (tiles)
- Quan volem marcar una posició al mapa, hi coloca
un indicador amb un PNG amb transparencies - Quan fem un recorregut, genera un PNG amb la ruta
i la posiciona - Fa les cerques carregant-les en un iframe
- retorna XML i per JS el parseja i coloca sobre el
mapa - genera també la llista de resultats
- No HTTPRequest, així podem fer back
- Ens proporciona una API que utilitza AJAX
22Més exemples
- GMail
- només demana la pàgina sencera al principi
- Demana via xmlhttprequest fragments de Javascript
- Via DOM, modifica la pàgina amb la informacio del
JavaScript - Pàgina personalitzada de Google
- eyeOS
- sistema operatiu al navegador
- Un dels creadors era fiber
- Flickr, ta-da list, Basecamp...
- Parcialment a filmaffinity (al votar), a
atrapalo (buscar vols)...
23Què no és AJAX?
- AJAX és un nom que ha funcionat tan bé que
saplica a coses que no tenen res a veure. - AJAX no es només Javascript
- Si no hi ha interacció amb el servidor, no es
AJAX - AJAX no es només XMLHTTPRequest
- Es poden simular recàrregues amb un frame ocult.
- http//developer.apple.com/internet/webcontent/ifr
ame.html - Parlem amb propietat, que per algo som enginyers!
24Conclusions AJAX
- AJAX es útil per
- Tenir interfícies més dinàmiques
- Pantalles en la que les recàrregues molesten
- Aconseguir efectes propis daplicacions
descriptori (autocompletar...) - Però en canvi no es correcte per
- Llistats url que hem de poder passar a la gent
- Quan el botó de tornar enrere té sentit
- En resum quan NO estem programant una aplicació
25Javascript avançat
- Amb la manipulació del DOM i AJAX, Javascript
demostra que serveix per mes que validar
formularis i fer rollovers - Necessitem capacitats més avançades per fer que
poguem realment programar aplicacions en
Javascript. - Crear objectes i classes
- Passar com a paràmetres estructures complexes
- Crear callbacks en resposta a events
- Facilitar lus de AJAX
- Accedir facilment al DOM
- Algunes daquestes capacitats depenen del
navegador i es fa necessari una llibreria que ens
abstregui
26JSON. Tipus complexes en Javascript
- Javascript Object Notation
- Es una forma en que podem declarar un objecte en
Javascript i que també serveix com a notació per
dades estructurades - aulaTecnologies web,
- professors
- nomJaume,cognomMoral,
- nomDaniel,cognomGolobart
-
- Permet simular passar paràmetres a una funció
per nom o pasar estructures complexes - Molt utilitzat en llibreries, per simplificar les
API. - Similar a XML en el que permet expressar, pero
més llegible per les persones
27La llibreria Prototype
- Molt bon dissenyada i base daltres llibreries
- Proporciona una capa per programar més còmodament
- Funció equivalent a document.getElementById()
- (element)
- Gestió dincompatibilitats. executa fins que
funcioni algo - Try.these
- funcio1(),
- funcio2()
-
- Registrar handlers pels events.
- Event.observe(element_id,click,callback,false)
28Llibreria Prototype (2)
- Objecte AJAX
- var myAjax new Ajax.Updater(
- 'element_a_actualitzar',
- 'http//servidor/url',
- method 'get', parameters'pnosque'
- )
- Ajuda en la sintaxi per declarar classes
- MevaClasse Class.create()
- MevaClasse.prototype
- initialize function(el)
- this.el el
- ,
- ...
mnew MevaClasse(el)
29Llibreria script.aculo.us
- Llibreria construida sobre Prototype
- Efectes i animacions (no AJAX) de forma molt
senzilla - Drag drop
- Per AJAX
- Autocompletar
- Edició in place com el tiddlywiki
- Lligar el drag and drop
- Molt senzilla dutilitzar
- Effect.BlindDown('id_of_element', duration3)
- Ajax.InPlaceEditor('editme', '/demoajaxreturn.php
') - Paradoxalment té un web tremendament mal dissenyat
30Altres llibreries útils
- Yahoo User Interface library (YUI)
- http//developer.yahoo.com/yui/
- Similar a script.aculo.us
- Molt ben documentada
- Google Web Toolkit (GWT)
- http//code.google.com/webtoolkit/
- Orientada únicament a AJAX
- Es una llibreria Java que genera el Javascript
- Parteix de la base que no hem de programar
Javascript - JQuery
- http//jquery.com/
31i el Flash? Millor FLEX
- Supera a HTML Javascript amb temes relacionats
amb gràfics vectorials, pero no en temes
d'interfaces d'usuari - Encara que es pugui generar d'altres formes, el
normal es fer-ho a partir del Flash Editor.
Incomode (per programadors) - La solució FLEX 2
- Framework basat en Flash per aplicacions "riques"
- Llenguatge per generar interfícies MXML(similar a
HTML) ActionScript (similar a Javascript)
sense problemes de navegador! - Permet accedir a dades remotes per HTTP
- SDK gratuit, un compilador que genera fitxers
.swf - Es pot integrar a Eclipse
32Altres tecnologies per les RIA (Rich Internet
Applications)
- OpenLaszlo
- Framework OpenSource que genera HTMLJavascript o
Fitxers Flash (SWF) a partir de LZX - Silverlight
- Es l'alternativa a Flex de Microsoft.
- XAML per definir l'interface programació en
algun llenguatge de la família .NET - Adobe AIR
- Permet crear aplicacions multiplataforma
d'escriptori com si fossin aplicacions web. Poden
estar basades en HTMLJavascript o en FLEX - Els oblidats Java Applets / Controls ActiveX
33Conclusions
- Una pàgina web no es una pàgina immutable i
estàtica - La seva extructura s'exposa via DOM
- Es pot manipular i canviar la visualització
- Pot respondre a events Javascript
- Pot demanar informació a un servidor via AJAX
- Pero
- Hem de tenir en compte diferències entre
navegadors - Hem de recorrer a llibreries per facilitar la
programació - Hi ha alternatives a la idea de HTML Javascript
que poden evitar aquesta complexitat.
34Conceptes bàsics d'aplicacions web.
35De què parlarem?
- La interacció bàsica amb aplicacions web
- Pas de paràmetres
- Sessions
- Cookies
- Proteccions / seguretat
- Connexions a BD
36Interacció bàsica amb aplicacions web
- Com pot comunicar-se una pàgina web amb el
servidor? Utilitzant el protocol HTTP - Seguint un link
- Demana al servidor una certa URL, que pot ser una
pàgina generada pel servidor i el navegador la
carrega. - Enviant un formulari
- Li enviem les dades que acabem d'omplir
- Amb una petició tipus AJAX
- El navegador fa una petició "en background" i
sense recarregar la pàgina - Veurem quins elements intervenen en aquesta
comunicació
37Pas de paràmetres
- Les aplicacions web permeten el pas de paràmetres
de 2 formes GET i POST - GET
- S'afegeixen els paràmetres a la URL
- POST
- S'envien com una segona part de la petició
- Aquesta informació es posa al formulari que envia
els paràmetres. - Hi ha una tercera forma que ens permet enviar
fitxer complets al servidor (fer uploads).
S'envia codificat en MIME - Els parametres son strings. Qualsevol tipus
complex requereix un tractament dels que
s'encarrega la plataforma escollida
38Sessions
- Cada petició HTTP és independent de les altres.
Problema quan volem desenvolupar aplicacions. - El protocol no proporciona cap mètode per saber
des del servidor quines peticions ens arriben del
mateix client, no incorpora el concepte de
sessió. - Tècniques per aconseguir tenir estat
- Cookies amb un identificador de sessió
- Paràmetre ID_SESSIO
- Altres possibles tècniques
- Adreça IP. No sempre funciona.
39Mites sobre la falta destat
- Jo treballo amb IIS i el servidor ja suporta
- sessions, sense necessitar cookies
- Per què hem de passar un identificador de
sessió? - Encara que desactivem les cookies el PHP
- ja té una variable amb la sessió.
- Aquestes frases ens mostren que no sha entès el
significat de sense estat. Espero no sentir-les
de vosaltres - Si volem sessions, el navegador sempre ha
denviar alguna dada en les seves peticions per
identificar-se. El servidor no fa miracles
40Cookies
- Les cookies permeten guardar al client petites
quantitats dinformació i després tornar-les a
enviar cap al servidor. - Un servidor ens pot enviar una cookie quan
demanem qualsevol fitxer, afegint una capçalera
de lestil... - Set-Cookie foobar path/ expires Mon,
21-Feb-2005 134600 GMT - Quan fem una altra petició al mateix servidor,
enviem aquesta informació en una capçalera extra - Cookie foobar
- Les cookies no les demana el servidor les envia
automàticament el navegador com si fos un
paràmetre
41Cookies de sessio
- Les cookies que no tenen data de caducitat duren
fins que es tanca el navegador. Son cookies de
sessió - Les plataformes de desenvolupament web més
conegudes (JSP, ASP, PHP) utilitzen cookies per
mantenir la sessió - La primera vegada que ens connectem al web, ens
donen un identificador aleatori, que anirem
enviant mentre no tanquem el navegador - El servidor es guardarà valors associats a aquest
identificador (una mena de taula de hash) - Cookies habituals
- JSESSIONID, PHPSESSID, ASPSESSIONID
42Eines per treballar amb cookies
- Si estem desenvolupant una aplicació web i les
coses no acaben de funcionar, pot ser interessant
veure que esta passan amb les cookies - Live http headers
- Permet veure les capçaleres HTTP que s'estan
passant entre el client i el servidor. Entre
elles, les cookies - Add'n'edit cookie
- Permet manipular les cookies que tenim i canviar
el valor - Exemple Bústia
43Paràmetre ID_SESSIO
- És un substitut de les cookies, amb exactament la
mateixa idea de la cookie de sessió, però passat
explícitament com un paràmetre o una part de la
URL - És més difícil d'implementar, perquè les nostres
aplicacions l'han de passar explícitament a
qualsevol petició que es faci al servidor,
reescrivint les URL a les pàgines. - Podem perdre la sessió si fem una petició al
servidor sense lidentificador (per exemple, una
pàgina estàtica) - No es guarda cap informació el id_sessió només
serà vàlid fins que tanquem el navegador - Funciona sempre, ja que no depenem d'una
funcionalitat que pot estar desactivada.
44Perquè no podem utilitzar la IP?
- Si necessitem un identificador per identificar el
client perquè no utilitzem ladreça IP origen? - Cas 1 tenim una màquina multiusuari amb
diferents usuaris accedint a la vegada a
internet. Tots ells serien tractats com la
mateixa persona. - Cas 2 Hi ha una màquina intermitja que fa de
proxy. Automàticament, totes les peticions que
fem tenen com a origen la IP del proxy
45Perquè ens pot servir la sessió?
- Saber que una sèrie de peticions ha vingut del
mateix usuari, sense haver de confiar en la IP - Guardar temporalment al servidor informació de
lusuari - Carret de la compra
- Guardar-se el fet que ja hem introduit un
username i password valids i estem autentificats. - Permet guardar valors que han destar disponibles
en altres pàgines i sense haver denviar més
cookies - Exemple idioma triat
46Quan acaben les sessions?
- En sistemes orientats a connexió, la sessió acaba
quan tallem la connexió. En web no existeix aixo - 3 possibilitats
- Tanquem el navegador. Sesborra la cookie pero no
la informació que teníem al servidor - Caduca. Els servidors es configuren perque la
informació de la sessió caduqui passats uns
minuts dinactivitat - Invalidem la sessio. Anem a una pàgina que
esborra la informació de la sessió - Una sessió no invalidada ni caducada és
perfectament vàlida al servidor. Si tenim el seu
identificador, la podem robar
47Seguretat declarativa
- És afegir autentificació i autorització dels
usuaris en una aplicació sense haver de tocar el
codi - autentificació és el fet de saber que una
persona es qui diu ser (normalment, en base a un
usuari i password) - 2 grans formes
- HTTP Basic authentication (amb un popup)
- Basada en forms i sessions
- autorització és el fet de permetre o no a un
usuari laccés a un cert recurs (normalment, en
base als rols daquest usuari) - Per exemple, JSP permet fer-ho al fitxer web.xml,
PHP a la configuració del servidor Apache
48Accés a bases de dades
- Generar pàgines dinàmiques normalment implica
treballar amb alguna bases de dades - En una aplicació no web, podem connectar una
vegada al principi de l'aplicació i desconnectar
al final. - En una aplicació web, no tenim clar quan ens
desconnectem, així que no podem mantenir una
connexió oberta "per sempre" - Obrir i tancar connexions continuament cada
vegada que hem d'accedir a la BD té un cost - Solució pool de connexions
- Tenim una sèrie de connexions obertes
- Agafem una quan la necessitem i la tornem al pool
- Permet aprofitar millor els recursos
49Conclusions
- Programem amb el que programem, hem de tenir molt
clars una sèrie de conceptes - Els diferents tipus de pas de paràmetres
- Els problemes que ens poden portar les sessions
- El fet de no tenir estat i els problemes que
implica - La millor forma de plantejar la seguretat d'una
aplicació és de forma declarativa. - Els problemes que poden representar els accessos
a les bases de dades - La plataforma que escollim per programar
probablement ja ens aïllarà d'aquests conceptes,
però és bo saber-los.
50Les arquitectures basades en Java (de JSP a JEE)
51De què parlarem
- Java com a llenguatge per fer aplicacions web
- Servlets
- JSP
- El concepte d'aplicació web
- L'especificació JEE
- Els servidors JEE
52Java un llenguatge buscant el seu lloc
- Java va sorgir fa ja més de 10 anys
- Primera utilitat petits programes que s'executen
al navegador (amb el plugin de Java) els Applets - A la època, la única forma d'afegir més
interactivitat - Complexitat per tenir el plugin correcte
- Actualment quasi no s'utilitzen (millor Flash o
similars) - Segon intent Java per aplicacions d'escriptori
- No gaire èxit. Aplicacions massa pesades
- Tercer intent Java al servidor
- Al no tenir interfície d'usuari, funcionava
millor - Aplicacions web
53Servlets
- Framework per generar pàgines web des de classes
Java - Tenim accés a la petició, la resposta, la sessió
i a paràmetres daplicació - Anem escrivint la pàgina des del programa,
generant el codi HTML per programa. (Sí, es molt
lleig!) - Necessitem un contenidor de servlets, bàsicament
es un programa Java que carrega els Servlets i
els executa en resposta a la nostra petició - El servidor més conegut es Apache Tomcat
- Servidor de referència (quan surt una nova
especificació, es qui l'implementa)
54Exemple de Servlet (1)
- import java.io.
- import java.sql.
- import javax.servlet.
- import javax.servlet.http.
- public class ServletConsulta extends HttpServlet
- public void doGet(HttpServletRequest request,
HttpServletResponse response) - throws IOException, ServletException
-
- response.setContentType("text/html")
- PrintWriter out response.getWriter()
55Exemple de Servlet (2)
- out.println("ltHTMLgt")
- out.println("ltBODYgt")
- out.println("ltTABLE border1gt")
-
- try
- Class.forName("sun.jdbc.odbc.JdbcOdbcDriver")
- Connection conn
- DriverManager.getConnection("jdbcodbcautho
rs") - Statement stmtconn.createStatement()
- ResultSet rset
- stmt.executeQuery("SELECT FROM AUTHORS")
- int colsrset.getMetaData().getColumnCount()
56Exemple de Servlet (3)
- while(rset.next())
- out.println("ltTRgt")
- for (int i1iltcolsi)
- out.println("ltTDgt"rset.getString(i)"lt/TDgt"
) -
- out.println("lt/TRgt")
-
- out.println("lt/BODYgt")
- out.println("lt/HTMLgt")
- rset.close()stmt.close()conn.close()
- catch (Exception e)
- out.println(e.toString())
-
-
57JSP
- JSP permet tenir pàgines HTML amb codi Java que
s'executa abans de tornar-la cap al client. - Permet cridar altres classes Java, on hi haurà el
gruix del codi. Les JSP fan de vista, amb un
mínim de codi. Per exemple... - ltjspuseBean id"cart" scope"session
class"session.Carts /gt - lt/jspuseBeangt
- No sinterpreta el codi cada vegada. La primera
invocació fa que es compili la pàgina i es
converteixi en un servlet.
58Exemple amb JSP (1)
- lt_at_ page language"java" import"java.sql." gt
- ltHTMLgt
- ltBODYgt
- lt
- Class.forName("sun.jdbc.odbc.JdbcOdbcDriver")
- Connection conn
- DriverManager.getConnection("jdbcodbcauthors")
- Statement stmtconn.createStatement()
- ResultSet rset
- stmt.executeQuery("SELECT From authors")
- int colsrset.getMetaData().getColumnCount()
- gt
-
59Exemple amb JSP (2)
- ltTABLE border 1gt
- lt while(rset.next()) gt
- ltTRgt
- lt for (int i1iltcolsi) gt
- ltTDgt lt rset.getString(i) gt lt/TDgt
- lt gt
- lt/TRgt
- lt gt
- lt/TABLEgt
- lt rset.close()
- stmt.close()
- conn.close() gt
- lt/BODYgt
- lt/HTMLgt
60La idea de Tag Libs
- JSP permet declarar nous tags per posar a les
notres pàgines i associar-los a codi java - Podem aconseguir una molt més gran separació
entre presentació i codi idea de JSP sense codi
Java - Per una llista de Tag Libs ja programats...
- http//jakarta.apache.org/taglibs/
- Hi ha una llibreria estàndar (JSTL), que permet
no haver de recorrer a Java dintre de JSP per
moltes coses. - Iteradors, condicionals...
- Nou lleguatge per expressions expression
language - Ben utilitzada, converteix un JSP en una
plantilla
61Exemple de pàgina amb Tag Libs
- ltsqldriver var"dataSource"
- driver"sun.jdbc.odbc.JdbcOdbcDriver
url"jdbcodbcauthors"gt - ltsqlquery var"authors" dataSource"dataSource"gt
- SELECT FROM Authors
- lt/sqlquerygt
- lttablegt
- ltcforEach var"row" items"authors.rows"gt
- lttrgt
- lttdgtrow.Au_IDlt/tdgt
- lttdgtrow.Authorlt/tdgt
- lttdgtrow.YearBornlt/tdgt
- lttdgt
- lt/cforEachgt
- lt/tablegt
62Aplicacions JSP/Servlet Web applicacions
- Concepte daplicació, no només pàgines
independents. - Separarem en una estructura de directoris...
- Pàgines estàtiques i JSP
- Classes Java que sexecuten com a servlets
- Classes Java dutilitats (JavaBeans) o Taglibs
- Configurarem laplicació al fitxer web.xml
- Paràmetres dinicialització
- Mapejos de URL a servlets
- Usuaris, grups i autoritzacions
- Recursos externs que necessitem (p.e.
DataSources) - Empaquetarem tot aixo en un fitxer .WAR (Web
Application Archive)
63Llibreries que ens poden ser útils
- Java té moltissimes llibreries, moltes d'elles
útils per web - log4j
- Sistema de logs configurable
- Per posar xivatos i treure'ls fàcilment
- Velocity, Freemaker
- Sistema de plantilles en Java
- Per si no ens agraden les JSP
- HttpClient
- Per poder connectar-nos a altres servidors web
- iText
- Generar PDF
64Conclusions sobre Servlets/JSP
- Bona idea d'aplicació web en que posem en un sol
paquet - Aplicació
- Fitxers de configuració
- Sha convertit en un estàndard amb molta
acceptació, especialment al mon empresarial - Suport per fer aplicacions estructurades
- Llibreries de qualsevol cosa busqueu abans de
desenvolupar! - Per donar suport a necessitats mes avançades
sobretot en el mon empresarial es va crear
l'especificació JEE (abans coneguda com a J2EE)
65Un canvi de filosofia
- Fins ara ens hem plantejat el desenvolupament de
contingut dinàmic des del punt de vista web - Quan ens estem plantejant una aplicació més gran,
per exemple, un sistema de banca on-line, hem de
pensar duna altra forma
66Model general daplicacions de 3 capes
BD
67Arquitectura JEE
- Arquitectura completa daplicacions de n-capes
basat en la plataforma Java - Idea principal aplicacions a la capa intermitja,
accessibles a través navegadors web o altres
tipus de client - Components per la lògica de negoci
- Capa de presentació
- JEE és un Model de programació
- Com hem de desenvolupar les aplicacions?
- JEE és una Plataforma
- Què necessitem per executar-les?
68Elements del Model dAplicació
- Model de components
- EJB (Enterprise Java Beans)
- Capa de presentació
- Servlets /JSP
- Protocol per comunicar components remots
- RMI / IIOP
- Accés a bases de dades o altres fonts
dinformació - JDBC (Bases de dades relacionals)
- JNDI (Serveis de directori)
- JavaMail (Correu electrònic)
- JTA (Transaccions)
69Esquema de larquitectura
70Què és un EJB?
- Són components de laplicació que sexecuten a la
capa intermitja i que executen la lògica de
negoci. El que us expliquen com capa de domini - Han dexecutar-se en un servidor de EJB, que els
hi proporcionarà serveis transaccionals,
persistència, alta disponibilitat... - Ha passat per unes especificacions molt complexes
que han fet que no sutilitzessin gaire. - Lespecificació actual (EJB 3.0) es basa en les
anotacions de Java 5.0 per configurar-les. - _at_Stateful, _at_Stateless
- _at_Remote
71Exemple. Botiga de llibres
72Servidors JEE
- Per poder executar una aplicació que utilitzi
EJB, necessitem un servidor que sigui "JEE
compliant" - Hi ha una gran quantitat d'aquests servidors que
basen el seu negoci en els serveis
d'assessorament i consultoria - A l'estar dirigits bàsicament a empreses es
centren en temes d'alta disponibilitat. - Jboss, líder dintre dels Open Source
- Glassfish de Sun Microsystems, ara en Open Source
- Oracle Application Server
- BEA Weblogic
- IBM Websphere
- ...
73Conclusions d'arquitectures Java
- Java ha trobat un lloc com a plataforma pel
desenvolupament d'aplicacions empresarials - JEE són actualment 23 especificacions diferents
que ha de complir qualsevol servidor per ser "JEE
compliant" - Una aplicació JEE teòricament es pot executar en
qualsevol d'aquests servidors "sense canvis" - És necessaria tota aquesta complexitat?
Normalment, no - Un servidor com Tomcat (no totalment JEE ni de
lluny) pot executar la majoria d'aplicacions Java
que necessitem - Per exemple, el Racó
74Frameworks i altres llibreries daplicacions web
75Frameworks
- Que és exactament un framework?
- Struts
- Spring i com lligar-lo amb Struts
- Hibernate
- L'arquitectura completa
- El nouvingut Ruby on rails
- Mantra daquesta lliçó
- Tothom es troba els mateixos problemes
- Hi ha gent que sap mes que nosaltres que els ha
resolt - No reinventem la roda
76Framework ltgt plataforma ltgt llibreria
- Una plataforma normalment implica una decisió de
- Hardware
- Servidors
- Llenguatge de programació
- Una llibreria normalment sutilitza per
solucionar un problema concret - En canvi un framework...
- Un framework, es un conjunt de llibreries per
una determinada plataforma que condicionen
totalment la forma en que ens plantegem,
organitzem i desenvolupem una aplicació(definici
ó pròpia)
77Perquè un framework?
- En un primer moment
- Són excessivament restrictius
- Les coses passen i no sabem perque
- Amb el temps
- No hem de pensar desde zero. Programar es
converteix en omplir forats - Facilitem el manteniment. Qualsevol persona que
conegui el framework triat podrà modificar
fàcilment la nostra aplicació - En general es bo utilitzar un framework quan
veiem que la nostra aplicació pot ser complexa o
altres persones lhauran de mantenir - El problema es quin framework triar?
78JEE es un framework?
- Presentació amb JSP / Servlets
- Model implementat amb EJB
- Interacció amb la base de dades feta pel
contenidor - Aixo condiciona totalment com ha de ser la nostra
aplicació, per tant JEE es un framework - Podem pensar en JEE només com un conjunt de
llibreries que podem fer servir o no - Podem triar no fer servir EJB
- Podem decidir fer nosaltres la persistència amb
BD - En resum, podem decidir passar del framework de
JEE
79Frameworks i llibreries per JEE que s'han imposat
- Struts
- Capa de presentació
- Permet estructurar les aplicacions segons el
patró MVC - Spring
- Ens permet estructurar la capa de domini
- Es basa en el patró Dependency injection
- Hibernate
- No es pot considerar propiament un framework,
sino un mapejador d'objectes a bases de dades
relacionals - Els veurem un a un per veure que ens poden oferir
i entendre com colaboren per formar una gran
plataforma
80L'aplicació d'exemple
- Farem un petit gestor de tasques
- Una tasca tindrà un nom i una prioritat
- Hi ha haurà una pantalla de llistar les tasques
- Podrem editar-les, esborrar-les i crear-ne de
noves - Una paraula d'advertència. És necessari utilitzar
3 frameworks per una aplicació tan tonta? - La resposta es NO
- En aquest cas ho estem fent per mostrar les idees
claus d'aquests 3 frameworks. - No hem de fer aplicacions "overengineered". El
codi que menys falla es aquell que no existeix.
81Forçant MVC Struts
- Struts és un framework que ens permet forçar les
nostres aplicacions a utilitzar MVC - Proporciona un servlet controlador configurable
amb un fitxer XML amb les accions a executar per
cada una de les URL de l'aplicació (les classes
Actions) - Tenim uns objectes (els ActionForms) que permeten
accedir desde les Actions als valors entrats als
formularis de les nostres pàgines. - Les Actions actuen sobre les classes Java que
formen el model, que son les que realment fan la
feina - A les vistes, ens proporciona tags que ens ajuden
a visualitzar les dades dels formularis o
obtingudes per les Actions
82Exemple form nova tasca
- lthtmlform action"/guardarTasca"gt
- lthtmlhidden property"id" /gt
- Nom lthtmltext property"nom"/gt
- ltbrgt
- Prioritat lthtmltext property"prioritat"/gt
- lthtmlsubmit value"Guardar"/gt
- lt/htmlformgt
- Taglibs pels elements del form (nom, propietat,
id) que es mapegen amb les propietats de
l'ActionForm - Fem referència a URL declarades al
struts-config.xml
83El ActionForm associat a aquest formulari
- ltform-bean name"tascaForm"
type"org.apache.struts.action.DynaActionForm"gt - ltform-property name"id"
type"java.lang.Integer" initial"-1" /gt - ltform-property name"nom"
type"java.lang.String" /gt - ltform-property name"prioritat"
type"java.lang.Integer" initial"1" /gt - lt/form-beangt
- Descrivim les propietats del form
- Podem fer la classe per programa o declarar-la al
struts-config.xml (es aquest cas)
84Una Action al struts-config.xml
- ltaction path"/guardarTasca"
- type"presentacio.GuardarTascaAction"
- name"tascaForm"
- scope"request"gt
- ltforward name"success" path"/llistaTasque
s.do" - redirect"true"/gt
- ltforward name"error" path"/errorTasca.jsp
"/gt - lt/actiongt
- Per cada acció de la nostra aplicació tenim
- què s'executa (en aquest cas el
GuardarTascaAction) - quins paràmetres li arriben (estaran al
tascaForm) - vistes on podem anar després de executar-la
85La Action GuardarTascaAction
- public class GuardarTascaAction extends Action
- public ActionForward execute(
- ActionMapping mapping, ActionForm form,
- HttpServletRequest request,
HttpServletResponse response) - throws Exception
- DynaActionForm f(DynaActionForm)form
- try
- // Crear una tasca i guardar-la obtenint les
dades de - // f.get("nom") i f.get("prioritat")
- return mapping.findForward("success")
- Catch (Exception e)
- return mapping.findForward("error")
-
-
-
86Exemple de Action i Vista lligades
- La Action obté una llista de tasques
- ...
- Tasca tasques gt.llistar()
- request.setAttribute("tasques",tasques)
- return mapping.findForward("success")
- La vista visualitza les dades colocades per la
Action - ...
- ltcforEach var"tasca" items"tasques"gt
- lttrgt
- lttdgttasca.idlt/tdgt
- lttdgttasca.nomlt/tdgt
- lttdgttasca.prioritatlt/tdgt
- lt/cforEachgt
87Flux d'una aplicació struts
- Demanem una URL struts (normalment acaba en .do)
- Totes aquestes URL van a parar al servlet
controlador - Empaquetem els paràmetres (si n'hi ha) en la
classe de tipus ActionForm especificada. - Mirem al fitxer XML quina classe hem d'executar
per la URL que ens han demant - Executem el mètode execute() de la ActionClass
que toqui passant-li el ActionForm amb els
paràmetres - La Action retorna quina vista ha de mostrar i
posa les dades necessaries a l'entorn. - La vista es construeix consultant les dades que
la Action li proporciona
88Flux d'una aplicació struts
89Més sobre struts
- D'entrada sembla complicat
- En una aplicació gran, ajuda molt a la
organització. - No ens obliga a utilitzar tecnologies concretes
- domini o persistència com volguem
- Les vistes, no necessàriament JSP
- Que mes permet?
- Sistematitzar les validacions. Podem fer que el
ActionForm validi els valors entrats, per
programa o per configuració - Plugin Tiles. Idea de jspinclude
- Internacionalització dels missatges (fitxer
properties)
90Conclusions sobre Struts
- Struts es un dels primers frameworks MVC que va
sortir per Java - Permet automatitzar processos que poden donar
lloc a errors com per exemple les validacions - Ordena el nostre codi
- Les Actions no tenen res de codi de presentació
- El pas de paràmetres cap a les accions queda
especificat a través de les propietats dels
objectes Form - Les vistes no "executen" res, només mostren
- El nostre struts-config.xml mostra el flux de
l'aplicació (el podriem dibuixar com un diagrama
d'estats)
91Spring
- Es un framework de frameworks, pero en aquest cas
ens centrarem en el contenidor lleuger - Serveix per organizar millor la nostra capa de
domini - Programació basada en interfaces
- Èmfasi en el baix acoblament de les classes
- Exemple l'aplicació de les tasques
- Tindrem la classe "Tasca"
- Necessitarem un GestorTasques, que serà una
façana de tot el nostre sistema - El GestorTasques utilitzarà un TascaDAO per
guardar les tasques. Per ara, en tindrem un de
prova
92Capa de domini de laplicació dexemple
Tasca
TascaDAO ltltinterfacegtgt
GestorTasques
ProvesTascaDAO
JDBCTascaDAO
DataSource
93Si no utilitzem Spring...
- Qui crea el gestorTasques? Es crea en cada
petició? - Podem utilitzar el patró Singleton
- Si el gestorSoci utilitza un objecte de tipus
DAO, li especifiquem quin es per programa? - Si, es clar. Com a molt podriem tenir un fitxer
de propietats si volem que es pugui canviar - Com li diem la base de dades al DAO?
- Utilitzarà JNDI per anar-la a buscar o bé la
configurarem en un fitxer de propietats també
94Si utilitzem Spring...
- Spring ens permetrà
- Llegir un fitxer de configuració on li diem els
objectes que formen el nostre sistema - Si una classe depèn de una altra, farem aquesta
dependència explícita al fitxer. A nivell de
programació, tindrem un setter daquesta
propietat. - Spring fa de muntador de laplicació
- Es basa en Inversion of Control o principi de
Hollywood, - "No ens truquis, dona'ns el número i et truquem
nosaltres" - No creis els objectes. Deixa un "set" i te
l'assignarà Spring
95Què hauríem dafegir a les nostres classes?
- El nostre DAO necessita un Datasource? Li afegim
- DataSource setDataSource (Datasource ds)
- this.dsds
-
- El nostre GestorTasques necessita un TascaDAO?
- TascaDAO setTascaDAO (TascaDAO dao)
- this.daodao
-
- Fixem-nos que TascaDAO es un interface. Aixo
permet canviar facilment la implementació que
utilitzarà el GestorTasques tocant la
configuració de Spring.
96Fitxer de configuració Spring (proves)
- ltbeansgt
- ltbean id"gestorTasques" class"exemple.GestorTasq
ues"gt - ltproperty name"tascaDAO"gt
- ltref bean"provesTascaDAO"/gt
- lt/propertygt
- lt/beangt
- ltbean id"provesTascaDAO" class"exemple.ProvesTas
caDAO"gt - ltproperty name"tasques"gt
- ltlistgt
- ltbean class"exemple.Tasca"gt
- ltproperty name"id" value"1"/gt
- ltproperty name"nom" value"Acabar
transparencies"/gt - ltproperty name"prioritat" value"1"/gt
- lt/beangt ...
- lt/listgt
- lt/propertygt
- lt/beangt
- lt/beansgt
97Fitxer de configuració real
- ltbeansgt
- ltbean id"mysqlDataSource" destroy-method"close"gt
- ltproperty name"driverClassName"
value"com.mysql.jdbc.Driver" /gt - ltproperty name"url" value"jdbcmysql//localhos
t3306/aules" /gt - ltproperty name"username" value"aules" /gt
- lt/beangt
- ltbean id"gestorTasques" class"exemple.GestorTasq
ues"gt - ltproperty name"tascaDAO"gt
- ltref bean"JDBCTascaDAO"/gt
- lt/propertygt
- lt/beangt
- ltbean id"JDBCTascaDAO" class"exemple.JDBCTascaDA
O"gt - ltproperty name"dataSource"gt
- ltref bean"mysqlDataSource"/gt
- lt/propertygt
- lt/beangt
- lt/beansgt
98Què fa Spring amb aixo?
- El contenidor (que s'anomena ApplicationContext)
només es crearà una vegada, quan sinicialitzi
laplicació, que pot ser web o no - ApplicationContext ctx new
- ClassPathXmlApplicationContext("applicationContext
.xml") - En el moment en que inicialitzem el contenidor...
- Spring parsejarà el fitxer i crearà les
instàncies - Cridarà els setters de les propietats per
passar-li els paràmetres especificats - A través del contenidor, podrem accedir a les
instàncies creades - ctx.getBean("gestorTasques"))
99Què mes ens permet Spring?
- Permet fer referències per tipus
- exemple crear un DataSource i passar-lo a totes
les classes que en necessitin un - Spring JDBC
- Exepcions amb sentit
- Ens podem oblidar dobrir i tancar connexions
- Spring MVC
- Similar a struts, però integrat al contenidor.
- AOP (Aspect Oriented Programming)
- Permet configurar codi a executar quan cridem un
mètode dun bean obtingut de Spring.
Interceptors. - Serveix per marcar transaccions
100Conclusions sobre Spring
- Es un framework poc habitual no ens condiciona
massa la forma de programar, només ens estructura - Un cop entès el concepte de Inversion of Control
i utilitzat de forma bàsica, no es gens complicat - Les nostres classes no son conscients de que
lestem utilitzant. Fins i tot podriem arribar a
canviar-lo o prescindir dun framework de la capa
de domini - Únic punt negatiu els fitxers de configuració
son horribles.
101Hibernate
- Intenta solucionar letern problema de la
persistència - Per un costat tenim la nostra aplicació amb
objectes - Per laltre, una BD relacional (mysql, Oracle)
- Com les casem? hibernate
- Hibernate es un mapejador Objecte-Relacional. No
és un framework tal i com lhem definit. - Fitxer XML amb
- els mapejos propietats lt-gt columnes
- relacions entre elles
- Ofereix una capa de persistència pels objectes
- A la vegada, ofereix una forma de consultar-los
- Igual que SQL, pero amb els objectes
102Hibernate exemple de guardar un objecte
- // ...
- Configuration cfg new Configuration()
- .addClass(Product.class)
- .addClass(Order.class)
- .addClass(OrderItem.class)
- // ...
- Order order new Order()
- order.addProduct(milk, 3)
- order.addProduct(coffee, 5)
- // ...
- sess sf.openSession()
- Transaction t sess.beginTransaction()
- sess.save(order)
- t.commit()
- sess.close()
103Hibernate exemple de consulta
- // ...
- String query "select o from o "
- "in class test.hibernate.Order "
- "where o.priceTotal gt priceTotalLower "
- "and o.priceTotal lt priceTotalUpper"
- // ...
- Query q sess.createQuery(query)
- q.setDouble("priceTotalLower",
- Double.parseDouble(args0))
- q.setDouble("priceTotalUpper",
- Double.parseDouble(args1))
- List list q.list()
- // ...
- sess.close()
- // ...
104Relacions
- Implementa relacions entre classes
- Exemple equips i jugadors
- lthibernate-mappinggt
- ltclass name"example.Team" table"teams"gt
- ltid name"id" column"team_id" type"long"
unsaved-value"null"gt - ltgenerator class"hilo"/gt
- lt/idgt
- ltproperty name"name" column"team_name"
type"string" - length"15" not-null"true"/gt
- ltproperty name"city" column"city"
type"string" length"15" - not-null"true"/gt
- ltset name"players" cascade"all"
inverse"true" lazy"true"gt - ltkey column"team_id"/gt
- ltone-to-many class"example.Player"/gt
- lt/setgt
- lt/classgt
- lt/hibernate-mappinggt
105Com soluciona les relacions?
- A partir daquest fitxer, genera lesquelet de la
classe - Bidireccional
- Des del jugador, podem accedir a lequip
(getTeam) - Des de lequip podem accedir al jugadors
(getPlayers) - Ens torna un Set (conjunt) de resultats
- Lazy
- Quan carreguem un jugador, no carrega els
jugadors - Quan volem els jugadors, saccedeix a BD
- No podem tancar la sessió
- Cascade
- Mateix sentit que a bases de dades
106Hibernate a l'exemple de les tasques
- Farem un DAO utilitzant Hibernate
- Li passarem la configuració amb Spring
- Mapejarem la taula "tasques"
- lthibernate-mappinggt
- ltclass name"exemple.Tasca" table"TASQUES"gt
- ltid name"id" column"ID"gt
- ltgenerator class"increment"/gt
- lt/idgt
- ltproperty name"nom" column"NOM"/gt
- ltproperty name"prioritat"
column"PRIORITAT"/gt - lt/classgt
- lt/hibernate-mappinggt
107Conclusions sobre Hibernate
- Hibernate posa una capa important respecte a
executar SQL contra una base de dades - Pot tenir mètodes de cache que acceleren les
nostres consultes i optimitzar la velocitat - Pot generar un SQL molt més costós que el que
podriem generar nosaltres mateixos directament - En general, Hibernate requereix uns coneixements
importants de la plataforma per treure el màxim
rendiment - Consell particular Si no us espanta el SQL,
utilitzeu JDBCTemplate. No es tan sofisticat,
pero dona més sensació de control.
108Resumint l'exemple
- Amb Struts hem fet la capa de presentació
- pantalles amb JSP
- Controlador amb les "Action"
- Amb Spring hem organitzat la capa de domini
- Creació i configuració dels gestors
- Configuració general de l'aplicació
- Amb Hibernate hem accedit a la BD
- Hem accedit a una base de dades relacional sense
abandonar la orientació a objectes - Hem utilitzat les 3 tecnologies conjuntament
sense interferències entre elles
109Relació entre Struts i Spring
- Plugin de struts al fitxer struts-config.xml
- ltplug-in className"org.springframework.web.strut
s.ContextLoaderPlugIn"gt - ltset-property property"contextConfigLocation"
- value"/WEB-INF/applicationContext.xml"/gtlt
/plug-ingt - Canviem les ActionClass per ActionSupport
- public class EditarTascaAction extends
ActionSupport - public ActionForward execute(...) throws
Exception - ApplicationContext ctx getWebApplicationContext
() - GestorTasques gt (GestorTasques)(ctx.getBean(
"gestorTasques"))
110Cap on anem?
- Struts 2
- Evolució de Struts, amb alguns canvis importants
- Ha agafat idees de Spring
- Anotacions
- Novetat de Java 1.5
- Permet fer comentaris que després es puguin
llegir, es a dir, afegir informació a les
classes, mètodes i propietats - Permet estalviar-nos alguns fitxers de
configuració - Exemples columnes de BD a que equivalen
propietats
111Necessitem eines!
- xDoclet
- Generador automàtic de fitxers a partir de
meta-informacio als fitxers Java - Es com un JavaDoc , les anotacions ho han
copiat - Eclipse plugins adequats
- Entorn de desenvolupament extensible
- Desenvolupar amb el plugin adequat pot suposar
que una tecnologia sigui o no usable. - ANT i Maven
- Entorns per compilar, similar al Make
- Junit
- Framework per proves unitaries.
112Conclusions de frameworks
- Utilitzar Spring, Struts i Hibernate es complex
- La corba d'aprenentatge es important
- Costa dominar-los al 100
- Canviem programació per configuració de fitxers
XML - Tenim més codi del que voldríem, tot i que tenim
eines que ens ajuden a generar-lo - Tot es dolent? No
- Ens obliguen a fer la nostra aplicació més
ordenada - Importants per la mantenibilitat
- Existexen frameworks centrats en simplificar? SI
113Ruby on Rails
- Ruby és un llenguatge de programació (poc
conegut) - Rails és un framework per programar aplicacions
web - Diferència
- No fa servir fitxers XML i molt poca configuració
- Intenta reduir el codi al màxim
- Es publicita amb videos tipus teletienda
- Voleu provar?
- http//instantrails.rubyforge.org/wiki/wiki.pl
- Llibre Agile Web Development with Rails
114L'exemple de les tasques (I)
- Pas 1 crear laplicació
- rails tasques
- Pas 2 configurar la BD
- Tocar el fitxer config/database.yml (no XML!)
- Pas 3 crear la taula i la base de dades al mysql
- create table tasks(id int auto_increment primary
key, nom char(50), prioritat integer(1)) - Pas 4 programar el model
- No hem de crear ni configurar res
- ruby script/generate model task
115Lexemple de les tasques (II)
- Pas 5 crear el controlador i les vistes
- ruby script/generate controller task
- i editar el fitxer que esta a app\controllers
- Class TaskController lt ApplicationController
- scaffold task
- end
- Pas 6 executar el servidor
- ruby script/server
- Pas 7 provar l'aplicació
- http//localhost3000/task
116Conclusions sobre rails
- Aire fresc en el mon dels frameworks
- Convention over configuration
- Suposarem que les coses es diuen duna certa
forma - Guanyem coherència i estalviem errors
- Substitueix XML per un format mes senzill
- Mapeig totalment transparent objecte/relacional
- URL amb sentit (edit, new...)
- Podem posar en marxa un prototip en un temps
mínim - Però...
- Convencions innecessàries basades en langlès
(plurals i noms de columnes) - Ruby es un llenguatge desconegut i aixo fa por