Java consente di gestire le connessioni via TCP/IP utilizzando due oggetti:
Socket
e ServerSocket
che si trovano nel pacchetto
java.net
Una volta avvenuta la connessione sarà possibile ottenere degli flussi di byte in ingresso e in uscita che possono essere utilizzati esattamente come si fa con i file, da questi sarà possibile ottenere degli Writer o Read per scrivere o leggere carattere ecc...
Socket
Questa è la classe che rappresenta uno dei due "capi" della connessione via TCP/IP. È possibile creare oggetti di questa classe direttamente oppure ottenerli in risposta ad una richiesta di connessione.
Quali parametri servono per avere una connessione TCP/IP verso un server?
portanon basta nome servernon basta nome del server e porta IP e portapuò andare ma non è necessario avere l'ip...La classe Socket ha un costruttore che ci permette di collegarci ad un server
scrivendo semplicemente una istruzione del tipo
Socket s = new Socket("snoopy.quercia.org",876)
in cui il primo parametro è
il nome del server e il secondo è la porta.
Una volta creato l'oggetto è possibile ottenere il canale di uscita
usando il metodo getOutputStream()
(ritorna un OutputStream, cioè
un oggetto ingrado di inviare byte) e poi usando questo si può costruire un OutputStreamWriter
per inviare caratteri.
In maniera analoga si può avere il canale di ingresso
utilizzando getInputStream()
che ritorna un InputStream da cui di nuovo
si può costruire un InputStreamReader.
Gli OutputStream utilizzano dei buffer per la gestione dei dati. Inviare un byte alla volta (o scriverlo su disco) è una operazione in generale poco sensata: per questo motivo gli stream accumulano una certa (non dichiarano la dimensione) quantità di dati e poi la inviano sulla rete o al disco poco cambia.
Potrebbere però succedere che ci serva di inviare una piccola quantità di dati e possiamo
forzare il meccanismo: sia l'oggetto OutputStream che l'OutputStreamWriter hanno un metodo
flush()
che forza l'invio dei dati (o detto in altri termini chiede di svuotare i buffer).
Un frammento di programma come quello qui sotto serve ad inviare una semplice stringa di testo al server:
Socket connessione = new Socket("snoopy.quercia.org",876); OutputStream flussoByte = connessione.getOutputStream(); OutputStreamWriter flussoCaratteri = new OutputStreamWriter(flussoByte); flussoCaratteri.write("saluti!\n"); // non uso flush() perché chiudo lo stream flussoCaratteri.close(); flussoByte.close(); connessione.close();
ServerSocket
Questa classe è in grado di bloccare l'esecuzione del programma attendendo che qualcuno si connetta via TCP/IP, una volta avvenuta la connessione quesllo che si ottiene è di nuovo un oggetto Socket da cui è possibile ottenere dei flussi in ingresso/uscita.
ServerSocket ss = new ServerSocket(7777) // il metodo accept serve per mettersi in ascolto Socket s = ss.accept(); // da questo punto posso usare il socket come in un client
considerando il frammento di programma precedente cosa succede se dopo il primo client se ne connette un secondo?
avrà un erroregiusto, non c'è più nessuno in ascolto crea un altro Socketpurtroppo no, non c'è più nessuno in ascolto