Uploaded by Angelo Carmine De Bartolo

JDBC Java

advertisement
JDBC: Database con Java.
E’ necessario utilizzare il Driver JDBC scaricando ed installando il Connector del DBMS (es: MariaDB
Connector, oppure MySQL Connector).
Una volta che la Libreria JAR “mariadb-java-client-2.5.4.jar” risulta nelle nostre dipendenze Maven possiamo
iniziare a lavorare sui DB.
Per inserirla nelle Dipendenze SENZA SCARICARE NULLA, per un progetto Maven bisogna inserire nel file
“pom.xml” la seguente dipendenza:
<dependency>
<groupId>org.mariadb.jdbc</groupId>
<artifactId>mariadb-java-client</artifactId>
<version>2.5.4</version>
</dependency>
All’interno del tags <dependencies>.
Primo Passo: richiedere una connessione.
La stringa di connessione si costruisce:
final
final
final
final
final
final
String DBUrl = "localhost";
String DBPort = "3306";
String DBName = "libretto";
String DBUser = "root";
String DBPass = "";
String url = "jdbc:mysql://" + DBUrl + ":" + DBPort + "/"
+ DBName + "?user=" + DBUser + "&password=" + DBPass;
Secondo Passo: eseguire delle istruzioni.
Si crea uno Statement (istruzione) per richiedere una Query (richiesta), diciamo che lo Statement si carica
della Query da eseguire, attenderà i risultati e poi ci restituirà un ResultSet in uscita.
Il ResultSet è un tipo particolare in Java, è un CURSORE che punta ad una riga del risultato ed avrà metodi
per scorrere il cursore e metodi per leggere i dati nel cursore.
Quando si esegue una Query il ResultSet non punta alla prima riga del risultato ma bensì alla riga precedente.
Mentre l’ultima posizione ammessa è quella DOPO l’ultimo record / tupla, quindi ad esempio in caso di un
RS di 3 righe avrà 5 posizioni (-1, Riga1, Riga2, Riga3, +1). Riusciamo a capire se non siamo alla fine usando il
metodo next() che restituisce TRUE se c’è ancora una riga altrimenti se siamo arrivati alla riga +1 restituisce
falso.
Terzo Passo: gestione dei dati.
La gestione ed il recupero dei dati avviene con il cursore RS che va chiuso dopo l’utilizzo
ResultSet rs = st.executeQuery(sql);
while (rs.next()) {
System.out.println(rs.getString("nome") + " - " + rs.getInt("punti"));
}
rs.close();
Se invece so già che il risultato è composto da una sola riga per posizionare il cursore sulla prima riga uso il
metodo first() che restituisce il resultSet della prima riga (es: SELECT COUNT restituisce una sola riga contente
un numero).
Anche la connessione al DB va chiusa dopo l’utilizzo.
Metodi Alternativi per eseguire le Query.
Esistono altri metodi al posto di ExcecuteQuery, come ad esempio
-ExecuteUpdate(sql) usata per INSERT, DELETE E UPDATE, restituisce il numero di righe interessate (1 se è
andato bene, 0 se è andato male);
-Execute(sql), più generico, serve per le query che non restituiscono un ResultSet;
Metodi SICURI per eseguire una Query.
Al fine di evitare una SQL Injection si usa un PreparedStatement inserendo poi gli attributi.
String prepSql = "INSERT INTO voti (nome, punti) VALUES ( ?, ?);";
PreparedStatement prepStat = conn.prepareStatement(prepSql);
prepStat.setString(1, "Geometria");
prepStat.setInt(2, 25);
prepStat.executeUpdate();
DAO PATTERN (Data Access Object).
Serve per disaccoppiare la gestione del DB dal resto dell’applicazione.
E’ composto dalle classi:
-Client, che è la nostra applicazione, ignora i dettagli del DB, ha bisogno solo di gestire dei dati;
-DAO, (es: LibrettoDAO) che è la classe dedicata all’accesso ai dati vero e proprio, ignora il resto dell’app,
conterrà tutti i metodi per interfacciarci con la tabella specifica (es: LibrettoDAO si interfaccia con la tabella
“libretto”, CorsiDAO si interfaccia con la tabella “corsi”, ecc);
PATTERN ORM (Object-Relational Mapping).
In realtà ci sarà una sorta di ponte di comunicazione, sono i DTO (Data Transfer Object), in pratica si afferma
che ogni tabella avrà un oggetto in Java che rappresenta il dato memorizzato, quindi DAO e Model si
scambiano oggetti di questo tipo (di tipo DTO) quindi il DTO dovrebbe stare nel package del Model e non del
DB.
Ad esempio nel caso del Libretto Universitario sarà l’oggetto Voto:
public class LibrettoDAO {
public void creaVoto(Voto v) {
}
public List<Voto> readAllVoto() {
}
public Voto readFromNome(String _nome) {
}
}
La classe DAO non avrà stati (cioè attributi, campi), non avrà dati da memorizzare, metterà a disposizione
solo metodi CRUD ed eventualmente metodi di ricerca.
È conveniente anche creare una classe con un solo metodo statico che restituisce l’oggetto Connection in
modo che settiamo una sola volta i parametri di connessione.
Nel Modello troveremo un metodo che recupera e salva oggetti DTO che gli serviranno per interfacciarsi con
il Controller che poi li visualizzerà sulla View (ad esempio nel Model avremmo un metodo readAllVoto() così
come lo troviamo nella classe DAO).
Il Controller non chiama il DAO, chiama il metodo sul modello che a sua volta chiama il DAO.
PATTERN DAO IN PRATICA.
Nella pratica si crea un PACKAGE “db” o “database” al cui interno creiamo:
1)classe DTO (Data Transfer Object) che sarà l’oggetto registrato (libro, studente, corso, ecc), con i vari
costruttori, i metodi getter/setter, toString, isEqual, HashCode;
2)interfaccia che conterrà i metodi che devono necessariamente scritti (libroDAO, studenteDAO) ad esempio
le operazioni CRUD;
3)classe che contiene i metodi, una classe per ogni tipologia di storage (libroDAOArray, libroDAOsql), al cui
interno ci sarà la struttura dati (array, mappa) che conterrà i dati che verranno realmente gestiti dal software;
public class Book {
private int isbn;
private String title;
private String author;
public Book() {
}
public Book(int isbn, String title, String author) {
this.isbn = isbn;
this.title = title;
this.author = author;
}
// altri metodi GETTER e SETTER, ISEQUAL, HASHCODE, TOSTRING
}
public interface BookDAO {
public
public
public
public
public
List<Book> getAllBooks();
Book getBookByISBN(int _isbn);
void addBook(Book _book);
void delBook(int _isbn);
String strAllBooks();
}
public class BookDAOArray implements BookDAO {
private List<Book> books;
public BookDAOArray() {
// test only
books = new ArrayList<>();
books.add(new Book(9488715, "Elementi di Fisica 1", "AA.VV"));
books.add(new Book(9477604, "Elementi di Fisica 2", "AA.VV"));
books.add(new Book(9466593, "Algebra Lineare", "Merkel"));
}
@Override
public List<Book> getAllBooks() {
List<Book> result = new ArrayList(books);
return result;
}
@Override
public Book getBookByISBN(int _isbn) {
for (Book book : books) {
if ( book.getIsbn() == _isbn ) {
return book;
}
}
return null;
}
}
Download