In questa guida, JAVA – Applicazioni con SOCKET UDP, realizziamo delle applicazioni di rete a livello di Socket con protocollo UDP in JAVA. Qui in basso e nella sezione download si possono scaricare i sorgenti
Sommario
Introduzione
La programmazione di rete consente a più applicazioni di comunicare tra loro attraverso protocolli standard. In Java, questa comunicazione può avvenire utilizzando socket basati sui principali protocolli di trasporto, tra cui TCP e UDP.
In questo articolo ci concentreremo sul protocollo UDP (User Datagram Protocol) e sulla realizzazione di una semplice applicazione Client–Server in Java. L’obiettivo è comprendere come funziona una comunicazione connectionless e come utilizzare le classi messe a disposizione dal linguaggio per inviare e ricevere dati tramite datagrammi.
📌 Prima di procedere con l’implementazione pratica, è consigliabile aver configurato correttamente l’ambiente di sviluppo. Sul sito è disponibile una guida dedicata alla preparazione dell’ambiente per le applicazioni Java basate su socket:
Il protocollo UDP
UDP è un protocollo di livello di trasporto che si distingue nettamente da TCP per il suo approccio alla comunicazione. A differenza di TCP, UDP non è orientato alla connessione: tra client e server non viene stabilito alcun canale persistente prima dell’invio dei dati.
Quando un’applicazione utilizza UDP, i messaggi vengono inviati sotto forma di datagrammi, ciascuno dei quali è indipendente dagli altri. Non esiste un meccanismo di handshaking iniziale e il protocollo non garantisce che i pacchetti arrivino effettivamente a destinazione né che arrivino nello stesso ordine in cui sono stati inviati.
Questo non significa che UDP sia privo di controlli: viene comunque verificata l’integrità dei dati tramite checksum. Tuttavia, eventuali pacchetti persi o duplicati non vengono gestiti automaticamente dal protocollo.
Proprio grazie a questa semplicità strutturale, UDP risulta estremamente veloce ed efficiente. Per questo motivo viene utilizzato in numerose applicazioni reali, come il servizio DNS, lo streaming multimediale e tutte quelle situazioni in cui la rapidità di trasmissione è più importante dell’affidabilità assoluta.
Comunicazione datagram e modello Client–Server
La comunicazione UDP è spesso definita datagram-based. Ogni messaggio contiene al proprio interno tutte le informazioni necessarie per raggiungere il destinatario, come indirizzo IP e numero di porta. Non esiste quindi uno stato condiviso tra client e server.
In un sistema Client–Server basato su UDP, il client invia una richiesta al server specificando l’indirizzo e la porta di destinazione. Il server, una volta ricevuto il datagramma, elabora il contenuto e invia una risposta utilizzando le informazioni presenti nel pacchetto ricevuto.
Questo modello rende la comunicazione semplice e leggera, ma richiede attenzione nella progettazione dell’applicazione, poiché la gestione di errori, ritrasmissioni o perdita di dati deve essere eventualmente implementata a livello applicativo.
Le classi Java per la comunicazione UDP
Java fornisce un supporto diretto alla comunicazione UDP attraverso il package java.net. Le due classi fondamentali sono DatagramSocket e DatagramPacket.
La classe DatagramSocket rappresenta il socket UDP vero e proprio. Attraverso questa classe è possibile inviare e ricevere pacchetti di dati utilizzando il protocollo UDP. Un socket può essere creato senza specificare una porta, nel caso del client, oppure associato a una porta specifica, come avviene tipicamente nel server.
La classe DatagramPacket, invece, rappresenta il singolo pacchetto di dati che viaggia sulla rete. Al suo interno sono contenuti i dati da trasmettere, l’indirizzo IP del destinatario e il numero di porta. Nel caso della ricezione, il pacchetto consente di recuperare anche l’indirizzo e la porta del mittente.
Realizzazione di un’applicazione Client–Server UDP
Per comprendere concretamente il funzionamento di UDP in Java, realizzeremo una semplice applicazione Client–Server. Il client invierà una stringa di testo al server e il server risponderà restituendo la stessa stringa convertita in maiuscolo.
L’esempio è volutamente semplice, ma consente di osservare tutti i passaggi fondamentali della comunicazione UDP.
Implementazione del Server UDP
Il server UDP ha il compito di restare in ascolto su una porta ben definita, ricevere i messaggi inviati dai client ed elaborare una risposta. In questo esempio, il server utilizza la porta 12345.
Dopo aver creato il DatagramSocket, il server entra in un ciclo continuo in cui attende la ricezione dei pacchetti. Quando un messaggio arriva, il contenuto viene estratto dal datagramma, convertito in maiuscolo e inviato nuovamente al client utilizzando l’indirizzo IP e la porta da cui è partita la richiesta.
Se il messaggio ricevuto è "0", il server termina l’esecuzione e chiude il socket.
Codice del Server (UDPServer.java)
import java.io.*;
import java.net.*;
public class UDPServer {
public static void main(String[] args) {
try {
// Creazione del socket sulla porta 12345
DatagramSocket UDPserver = new DatagramSocket(12345);
DatagramPacket datagrammaRicevuto;
DatagramPacket datagrammaDaInviare;
boolean attivo = true;
byte[] bufferIN = new byte[1024]; // Buffer per ricezione
byte[] bufferOUT; // Buffer per invio
System.out.println("Server avviato...");
while(attivo){
// Definizione del datagramma di ricezione
datagrammaRicevuto = new DatagramPacket(bufferIN, bufferIN.length);
UDPserver.receive(datagrammaRicevuto); // Attesa ricezione pacchetto
// Estrazione del messaggio ricevuto
String ricevuto = new String(datagrammaRicevuto.getData(), 0, datagrammaRicevuto.getLength());
System.out.println("Messaggio ricevuto: " + ricevuto);
// Riconoscimento parametri del client (IP e porta)
InetAddress IPClient = datagrammaRicevuto.getAddress();
int portaClient = datagrammaRicevuto.getPort();
// Preparazione della risposta in maiuscolo
String messaggioOUT = ricevuto.toUpperCase();
bufferOUT = messaggioOUT.getBytes();
datagrammaDaInviare = new DatagramPacket(bufferOUT, bufferOUT.length, IPClient, portaClient);
// Invio del datagramma al client
UDPserver.send(datagrammaDaInviare);
// Se il client digita "0", termina l'esecuzione
if (ricevuto.equals("0")){
System.out.println("Arrivederci...");
attivo = false;
}
}
UDPserver.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Descrizione del codice UDPServer.java
-
Creazione del socket:
- Viene creato un oggetto
DatagramSocketsulla porta 12345. - Si definiscono due buffer per i dati: uno per la ricezione e uno per la trasmissione (entrambi di 1024 byte).
- Viene inizializzata una variabile booleana per gestire il ciclo di esecuzione del server.
- Viene creato un oggetto
-
Attesa e ricezione dati dal Client:
- Il server attende la ricezione di un pacchetto UDP tramite
receive(). - Il messaggio ricevuto viene estratto ed elaborato rimuovendo i caratteri superflui.
- Il server attende la ricezione di un pacchetto UDP tramite
-
Preparazione della risposta:
- Il messaggio ricevuto viene convertito in maiuscolo.
- Il server identifica l’indirizzo IP e la porta del client.
- Viene creato un DatagramPacket contenente la risposta e inviato al client.
-
Gestione dell’uscita:
- Se il client invia
"0", il server termina l’elaborazione, esce dal ciclo e chiude il socket.
- Se il client invia
Implementazione del Client UDP
Il client ha un comportamento più semplice rispetto al server. Dopo aver creato il socket, chiede all’utente di inserire una stringa da tastiera. Il messaggio viene poi inviato al server sotto forma di datagramma.
Successivamente, il client si mette in attesa della risposta. Quando il pacchetto di risposta viene ricevuto, il messaggio viene estratto e visualizzato a schermo. Terminata la comunicazione, il socket viene chiuso.
Codice del Client (UDPClient.java)
import java.io.*;
import java.net.*;
public class UDPClient {
public static void main(String[] args) {
try {
int portaServer = 12345;
InetAddress IPServer = InetAddress.getByName("localhost");
byte[] bufferIN = new byte[1024]; // Buffer per ricezione
byte[] bufferOUT; // Buffer per invio
BufferedReader input = new BufferedReader(new InputStreamReader(System.in));
DatagramSocket clientSocket;
DatagramPacket datagrammaDaInviare;
DatagramPacket datagrammaRicevuto;
// Creazione del socket
clientSocket = new DatagramSocket();
System.out.println("Inserisci una stringa: n");
// Lettura dell'input utente e preparazione buffer di uscita
String messaggioDaInviare = input.readLine();
bufferOUT = messaggioDaInviare.getBytes();
// Creazione del DatagramPacket per l'invio
datagrammaDaInviare = new DatagramPacket(bufferOUT, bufferOUT.length, IPServer, portaServer);
clientSocket.send(datagrammaDaInviare);
// Attesa della risposta dal server
datagrammaRicevuto = new DatagramPacket(bufferIN, bufferIN.length);
clientSocket.receive(datagrammaRicevuto);
String ricevuto = new String(datagrammaRicevuto.getData());
// Elaborazione del messaggio ricevuto
int numCaratteri = datagrammaRicevuto.getLength();
ricevuto = ricevuto.substring(0, numCaratteri);
System.out.println("Messaggio ricevuto dal server: " + ricevuto);
// Chiusura del socket
clientSocket.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
Descrizione del codice UDPClient.java
-
Configurazione della comunicazione:
- Vengono definiti i buffer per la comunicazione (trasmissione e ricezione).
- Si specificano i riferimenti del server (indirizzo IP e porta 12345).
- Viene creato un DatagramSocket per la comunicazione.
-
Invio del messaggio al Server:
- Il client chiede all’utente di inserire un messaggio.
- Il messaggio viene convertito in array di byte e inviato al server tramite un DatagramPacket.
-
Attesa e ricezione della risposta dal Server:
- Il client si mette in attesa della risposta.
- Una volta ricevuto il pacchetto, il messaggio viene estratto e stampato.
-
Chiusura della connessione:
- Dopo aver ricevuto la risposta, il client chiude il socket e termina l’esecuzione.
Esecuzione e test dell’applicazione
Per testare l’applicazione è sufficiente avviare prima il server e successivamente il client, utilizzando Visual Studio Code o un qualsiasi ambiente di sviluppo Java. Inserendo una stringa dal client, il server risponderà restituendo la versione in maiuscolo.
Se il client invia il valore "0", il server terminerà la propria esecuzione.
Nella sezione Download dedicata puoi scaricare i codici sorgente di applicazioni Applicazioni Client / Server con SOCKET UDP

Lascia un commento