Ejemplo Socket Server Java Program

How to write a Ejemplo Socket Server Java Program ?


package redessocket;
import java.io.BufferedReader;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.ServerSocket;
import java.net.Socket;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.logging.Level;
import java.util.logging.Logger;

/**
 *
 * @author Lopez, Mariano
 */
public class SocketServer {
     ServerSocket server = null;
     //array de clientes
     ArrayList<SocketInfo> clientes;
     public SocketServer(int port) throws IOException{
         this.server = new ServerSocket(port);
         this. clientes = new ArrayList<>();
     }
    
     public void listen() throws IOException{
         //escuchar comandos por teclado
         escucharComandosServer();
         //si se logro instanciar.. mientras que no este cerrado el socket
        while(server != null && !server.isClosed()){
            Socket clientSocket = null;
            try {
               //escucha de peticiones 
               clientSocket = server.accept();
               if(clientSocket != null){
                   lanzarHilo(clientSocket);
               }
            }catch (IOException e){System.out.println(e.toString());}
        }
     }
     public static void main(String[] args) {
        System.out.println("Socket Server - Redes de datos 2015 - Lopez, Mariano");
        BufferedReader entrada = new BufferedReader(new InputStreamReader(System.in));
         System.out.print("Ingrese el puerto para inicializar el servidor: ");
         try {
             int port = Integer.parseInt(entrada.readLine());
             SocketServer server = new SocketServer(port);
             System.out.println("Inicialización correcta! puerto: "+port+"\nLISTENING");
             server.listen();
         } catch (IOException ex) {
             System.out.println(ex.toString());
         }catch(NumberFormatException fe){
             System.out.println(fe.toString());
         }
    }
    //comandos que se pueden ejecutar solo en el servidor 
    private void escucharComandosServer() throws IOException{
        BufferedReader entradaDesdeUsuario = new BufferedReader(new InputStreamReader(System.in));
        Thread t = new Thread(new Runnable() {
            @Override
            public void run() {
                boolean flag_fin = true;
                while(flag_fin){
                    try {
                        if(entradaDesdeUsuario.ready()){
                            String in =entradaDesdeUsuario.readLine();
                            switch(in){
                                case "exit":
                                    System.out.println("Shooting down...");
                                    KillEmAll();
                                    server.close();
                                    flag_fin=false;
                                    break;
                                case "who":
                                    System.out.println(clientesInfo());
                                    break;
                                default:
                                    System.out.println("Comandos:\nwho\t\tInformación sobre clientes conectados\nexit\t\tFinalizar todas las conexiones y cerrar el socket\n");
                                    break;
                            }
                        }
                    } catch (IOException ex) {
                        Logger.getLogger(SocketServer.class.getName()).log(Level.SEVERE, null, ex);
                    }
                }
            }
        });
       t.start();
    }
    //hilo para atender a cada socket cliente
    private void lanzarHilo(Socket clientSocket){
        SocketInfo socket_info = new SocketInfo(clientSocket);
        clientes.add(socket_info);
        Thread t = new Thread(new Runnable() {
            @Override
            public void run() {
                try {
                    //string para almacenar mensajes del cliente
                    String line;
                    //ip del cliente
                    String ip = clientSocket.getInetAddress().toString();
                    //puerto del cliente
                    int puerto = clientSocket.getPort();
                    System.out.println("Nuevo cliente: "+ip+":"+puerto);
                    //output stream para escritura con el cliente
                    DataOutputStream salidaACliente = new DataOutputStream(clientSocket.getOutputStream());
                    //stream para lectura del cliente
                    DataInputStream in = new DataInputStream(clientSocket.getInputStream());
                    //mientras este conectado
                    while (!clientSocket.isClosed()) {
                        //leer desde el stream del cliente
                        line = readStringUTF(in);
                        System.out.println("\nCliente: "+ip+":"+puerto+"\n"+line);
                        //en la linea 0 esta el comando a ejecutar
                        line = (line.split("\n"))[0];
                        //si el mensaje es exit -> cerrar conexión
                        if(line.equals("exit")){
                            System.out.println("El cliente: "+ip+":"+puerto +" ha solicitado cierre");
                            clientes.remove(socket_info);
                            clientSocket.close();
                            break;
                        }else{
                            //todas las acciones que puede realizar el servidor
                            acciones(line, salidaACliente,socket_info);
                        }
                    }//fin while 
                    //cerrar stream
                    in.close();
                } catch (IOException ex) {
                    System.out.println(ex.toString());
                } 
            }//end run
        });
        t.start();
    }
    //comandos que pueden realizar los clientes
    private void acciones(String in,DataOutputStream salidaACliente,SocketInfo socket_info) throws IOException{
        //historial de solicitudes
        socket_info.addToHistory(in);
        switch(in){
            case "cores":
                respuesta(salidaACliente, 200, "Procesadores disponibles para JVM (cores): " +Runtime.getRuntime().availableProcessors());
                break;
            case "ram -free":
                respuesta(salidaACliente, 200, "Memoria libre para JVM: " + Runtime.getRuntime().freeMemory()+"Bytes");
                break;
            case "ram -total":
                respuesta(salidaACliente, 200, "JVM total de memoria: " +Runtime.getRuntime().totalMemory()+"Bytes");
                break;   
            case "ram -max":
                respuesta(salidaACliente, 200, "Maxima cantidad de RAM que puede llegar a usar la JVM: " +Runtime.getRuntime().maxMemory()+"Bytes");
                break;
             case "so -name":
                respuesta(salidaACliente, 200, "Sistema Operativo: "+System.getProperty("os.name"));
                break;  
            case "history":
                respuesta(salidaACliente, 200, socket_info.getHistory());
                break; 
             case "help":
                 String aux = "Lista de comandos\n"
                         + "cores\t\tProcesadores disponibles para JVM\n"
                         + "ram -free\t\tMemoria libre para JVM\n"
                         + "ram -total\t\tJVM total de memoria\n"
                         + "ram -max\t\tMaxima cantidad de RAM que puede llegar a usar la JVM\n"
                         + "so -name\t\tSistema Operativo\n"
                         + "history\t\tHistorial de comandos\n"
                         + "exit\t\tterminar conexión\n";
                respuesta(salidaACliente, 200, aux);
                break; 
            default:
                respuesta(salidaACliente, 400, "Comando no reconocido");
                break;
                
        }
                            
    }
    //finaliza todas las conexiones existentes ... tambien es el primer disco de Metallica.
    private void KillEmAll() throws IOException{
        for(SocketInfo s:clientes){
            s.getSocket().close();
        }
    }
    //String con información de los clientes online
    private String clientesInfo(){
        String retorno = "Cantidad de clientes online: "+clientes.size()+"\n";
        retorno+="Socket información(IP, puerto remoto y puerto local) \t Fecha de la conexión\n";
        for(SocketInfo s:clientes){retorno+=s.showInfo();}
        return retorno;
    }
    //escribir cabecera + respuesta en el DataOutputStram para el cliente
    private void respuesta(DataOutputStream salidaACliente,int code, String mensaje) throws IOException{
        String estado = "";
        switch(code){
            case 200:
                estado="OK";
                break;
            case 400:
                estado="Bad request";
                break;
            case 500:
                estado="Internal Error";
                break;
                default:
                    estado="OK";
                    break;
        }
        Date fecha = new Date();
        String aux = code+" "+estado+"\nDate: "+fecha+"\nContent-Type: text charset=UTF-8\nContent-Length: "+mensaje.length()+"\n\n"+mensaje+"\n";
        byte[] data=aux.getBytes("UTF-8");
        salidaACliente.writeInt(data.length);
        salidaACliente.write(data);
    }
    private static String readStringUTF(DataInputStream in) throws IOException{
        int length=in.readInt();
        byte[] data=new byte[length];
        in.readFully(data);
        return new String(data,"UTF-8");
    }
    //clase auxiliar para guardar atributos
    private class SocketInfo{
        private Socket socket;
        private Date fecha;
        private String history;
        private DateFormat dateFormat = new SimpleDateFormat("dd/MM/yyyy HH:mm:ss");
        
        public SocketInfo(Socket s){
            this.socket = s;
            this.fecha = new Date();
            this.history="Historial de comandos:\n";
        }
        public void addToHistory(String s){
            this.history+=s+"\t"+dateFormat.format(new Date())+"\n";
        }
        public String getHistory(){
            return this.history+"\n******************************************************************";
        }
        public Socket getSocket(){
            return this.socket;
        }
        public Date getFechaConexion(){
            return this.fecha;
        }
        public String showInfo(){
            return this.getSocket().toString()+"\t"+dateFormat.format(this.getFechaConexion())+"\n"+this.getHistory()+"\n\n";
        }
    }
}


Learn More :

Learn More Multiple Choice Question :