Programmazione Java Avanzata Accesso ai Dati Ing. Giuseppe D'Aquì Testi Consigliati ● Eclipse In Action ● Core J2EE Patterns - DAO ● ● [http://java.sun.com/blueprints/corej2eepatterns/Patterns/DataAccessObject.html] JDBC API Documentation ● [http://download.oracle.com/javase/6/docs/technotes/guides/jdbc/] Accesso ai dati ● ● ● ● Ogni applicazione ha bisogno di un sottosistema che si occupi di salvare le informazioni Per motivi di integrità e di gestione, le informazioni non possono stare tutte in RAM In genere si utilizzano dei meccanismi che rendono trasparente allo sviluppatore il modo con cui lo stato interno degli oggetti viene salvato Si parla quindi di “Persistenza” degli oggetti e di “Persistence Layer” Accesso ai dati ● Le modalità di storage, però, variano in modo ampio ● ● ● Database Relazionali Database Non-relazionali (document-based / NoSQL) ● Database Object-Oriented ● Flat Files ● Servizi Vari (LDAP) Inoltre l'implementazione dei singoli accessi può avere le sue complessità Accesso ai dati ● ● ● Ogni API infatti può essere implementata in modi diversi e avere modalità di accesso differenti Inoltre i dati potrebbero non essere presenti fisicamente sulla macchina Per questo nasce la necessità di usare “API universali” che astraggano questa complessità CRUD ● Ogni sistema di persistenza deve fornire almeno quattro funzionalità: ● Create ● Read ● Update ● Delete JDBC ● ● ● ● ● Java DataBase Connectivity È una API che definisce l'accesso ad un database Fornisce metodi per effettuare query ed aggiornare i dati JDBC è orientato ai database relazionali Le classi JDBC sono contenute nel package java.sql and javax.sql JDBC ● ● ● JDBC è una API universale per i Relational DBMS Il linguaggio di interrogazione è SQL ...ma come ben sappiamo spesso ogni produttore di DBMS aggiunge le sue estensioni ad SQL, rendendolo incompatibile JDBC ● JDBC si compone di due parti: ● ● API: l'interfaccia con cui lo sviluppatore accede alle funzionalità Driver: in genere scritto dal produttore del DBMS; lo sviluppatore difficilmente conoscerà il suo funzionamento JDBC JDBC ● Classi fondamentali: ● DriverManager ● Connection ● Statement – ● PreparedStatement ResultSet JDBC: DriverManager ● ● ● DriverManager si occupa di fornire la connessione più adatta ad un DBMS La connessione, infatti, viene creata specificando una stringa detta URL DriverManager astrae la gestione del singolo driver JDBC: DriverManager ● ● ● Ogni JDBC Driver, alla prima inizializzazione, si registra presso DriverManager Chiamando getConnection(), DriverManager cerca tra tutti i driver registrati quello che soddisfa la url specificata Url JDBC: ● jdbc:<driver>:<host_url> – jdbc:mysql://localhost:3306/mydb – jdbc:microsoft:sqlserver://localhost;databasename=my db;user=yourUser;password=yourPwd JDBC: Connection ● ● ● Connection gestisce una connessione al database Permette di creare due tipi di statement: ● Statement: normale query, da eseguire una volta ● PreparedStatement: query parametrizzata È importante chiudere sempre la connessione (con il metodo close() ), perché altrimenti il Garbage Collector non può liberare le risorse JDBC: Statement ● ● In JDBC, uno Statement è un oggetto che permette di inviare una dichiarazione SQL al database Possiede un metodo executeQuery(String) che restituisce un ResultSet (array di risultati) ● stmt.executeQuery(“SELECT * FROM Studenti”); JDBC: PreparedStatement ● I PreparedStatement, invece, hanno dei parametri ● PreparedStatement ps = conn.prepareStatement( "SELECT * FROM STUDENTI WHERE id = ?" ); ● ps.setInt(1, 123456); ● ps.executeQuery(); DAO ● ● ● ● Data Access Object (pattern) È un oggetto che fornisce un'interfaccia astratta ad un database Fa da tramite tra l'applicazione e il Persistence Layer Disaccoppia, quindi, l'applicazione dai dettagli implementativi come il tipo di DBMS, lo schema, ecc. DAO DAO DAO: vantaggi ● ● ● Separazione rigorosa tra due parti importanti di ogni applicazione, che in genere evolvono in parallelo Moduli maggiormente riusabili Integrazione semplice con framework che forniscono questa funzionalità Programmazione Java Avanzata Web Development HTTP ● Protocollo alla base del Web ● Richiesta/Risposta Testuale ● ● ● Stateless: ogni richiesta è indipendente da tutte le altre Pochi metodi di richiesta (GET, POST, altri poco usati) per “incanalare” tutte le funzionalità Completamente in chiaro HTTP Request/Response HTTP ● ● ● Un server, generalmente, si occupa di fornire, a richiesta, il contenuto di file I browser sono in grado di interpretare i file testuali scritti in linguaggio HTML Nella maggior parte dei casi, quindi, la risposta del server sarà contenuto scritto secondo HTML HTTP Request ● Se l'utente scrive la URL: ● ● http://www.unirc.it/index.html Il browser invierà al server la seguente stringa: GET /index.html HTTP/1.1 HOST www.unirc.it User-Agent: Mozilla/5.0 HTTP Request ● Se si possono richiedere solo “nomi di file”, come si può strutturare una applicazione webbased? HTTP Request ● Si può scrivere la URL in modo che contenga dei parametri: ● ● ● Http://www.unirc.it/index.html?var1=9&var2=1 oltre a chiedere la pagina index.html passiamo al server le variabili var1 (pari a 9) e var2 (pari ad 1) Si può usare il metodo POST che permette di inviare parametri nello stesso formato ma non “immersi” nella URL HTTP Response ● ● ● Il server sta in ascolto sulla porta TCP 80 Quando riceve la richiesta, cerca il file con quel nome e ne invia il contenuto al client Fin qui c'è poco di “applicativo”! Web Server ● ● ● I Web Server al giorno d'oggi non sono più semplici “fornitori di HTML” Moduli di estensione, script e server ad-hoc intercettano le richieste e permettono di manipolare l'input tramite linguaggi di programmazione L'output deve essere sempre HTML, ma i file possono essere generati “al volo” e non più essere fisicamente presenti sul server Protocollo Stateless ● La mancanza di “salvataggio dello stato interno” è uno dei più grandi pregi e difetti dell'HTTP ● ● ● Vedi XKCD: [http://www.xkcd.com/869/] Pro: ● Velocità di esecuzione ● Basse richieste di memoria Contro: ● Ogni applicazione ha bisogno di sapere cosa ha fatto l'utente in precedenza Protocollo Stateless: soluzioni ● Una prima soluzione è stato l'uso dei cookie ● ● ● Piccoli file di testo, salvati sul client, che contengono variabili e i loro valori I cookie vengono inviati al server ad ogni request Esempio: se l'utente fornisce username e password, possono essere salvate in un cookie (insieme ad altri dati); ad ogni richiesta i cookie vengono inviati al server e quindi il server legge lo stato dai cookie Cookie: Problematiche ● File di testo non crittografati ● ● File di testo scrivibili da chiunque ● ● Chiunque può leggerli sul pc o durante l'invio, quindi non si possono salvare dati sensibili Lato server, non possiamo fidarci di quello che abbiamo scritto precedentemente nei cookie Insicuri ● Un sito B, sfruttando vulnerabilità, potrebbe avere accesso ai cookie del sito A Variabili di sessione ● ● ● ● Per risolvere il problema dei cookie si usano le variabili di sessione, lato server Variabili salvate sul server Si assegna ad ogni utente un hash (detto Session ID) Se l'utente fornisce l'hash al server, il server lo identifica e può consultare i dati che lo riguardano Variabili di sessione vs. Cookie ● Rimane il problema: come fa il server ad identificare un client come “rappresentante di un utente”? ● ● Se le variabili sono lato server non c'è modo di saperlo Si scrive il Session ID in un cookie ● ● Il Session ID è un hash, è molto difficile indovinarlo Anche se il Session ID viene intercettato, ha una durata limitata nel tempo (una sessione o anche meno) Perché il Web? ● Con tutti questi problemi da risolvere la domanda sorge spontanea ● Perché il Web è ovunque – ● Perché il Web è semplice – ● Quasi 2 miliardi di persone al mondo usano Internet HTML non è un linguaggio di programmazione, ma definisce solo come le informazioni vengono presentate Perché il Web è standard – Esistono organismi come il W3C che si preoccupano di creare degli standard in modo che ognuno abbia la stessa esperienza sul Web, indipendentemente dal browser, dal sistema operativo e dal dispositivo Java e HTTP ● ● Esistono librerie e classi per gestire le richieste/risposte HTTP direttamente in Java Ma gestire le richieste a questo livello molto basso: ● ● ● È dispendioso (è un problema abbastanza indipendente e non ha senso gestirlo volta per volta) È soggetto ad errori Sottrae tempo lavorativo che potrebbe essere dedicato alla business logic Servlet ● ● Le Servlet sono classi Java che rispondono ad HTTP Request Definiscono delle modalità di risposta (ad esempio, in caso di GET o POST) e poi gestiscono in modo automatico il resto ● Per esempio, viene mantenuto lo stato nelle variabili di sessione senza che lo sviluppatore debba preoccuparsi Servlet ● Una Servlet restituisce, in genere, HTML ● ● ● Anche se può restituire XML o altro Una Servlet viene inizializzata dal server, e, a questo punto, gestisce ogni request in un thread a parte Le Servlet sono definite nella libreria di JavaEE