Prévia do material em texto
Victor Henrique Fernandes Silva Anápolis 29/03/2024 Atividade Avaliativa de Sistemas Distribuídos 1. Implemente em um único projeto os códigos referentes às classes TCPClient.java e TCPServer.java encontradas nas páginas 137 a 138 do livro de referência da Disciplina Sistemas Distribuídos, Coulouris, Sistemas Distribuídos 4ª Edição. R: TCPCliente.java import java.io.*; import java.net.*; public class TCPClient { public static void main(String[] args) { // Verifica se o número de argumentos está correto if (args.length != 2) { System.err.println("Uso: java TCPClient <host do servidor> <mensagem>"); System.exit(1); } // Obtém o nome do host e a mensagem a ser enviada String serverHost = args[0]; String message = args[1]; try ( // Cria o socket para se conectar ao servidor Socket clientSocket = new Socket(serverHost, 6789); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Envia a mensagem para o servidor out.println(message); // Lê a resposta do servidor e a exibe String response = in.readLine(); System.out.println("Resposta do servidor: " + response); } catch (UnknownHostException e) { System.err.println("Host desconhecido: " + serverHost); System.exit(1); } catch (IOException e) { System.err.println("Erro de I/O para o host " + serverHost); System.exit(1); } } } R: TCPServer.java import java.net.*; import java.io.*; public class TCPServer { public static void main(String[] args) { try ( // Cria um socket de servidor para aguardar conexões na porta 6789 ServerSocket serverSocket = new ServerSocket(6789); // Aguarda e aceita uma conexão do cliente Socket clientSocket = serverSocket.accept(); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Lê a mensagem enviada pelo cliente String message = in.readLine(); System.out.println("Mensagem recebida do cliente: " + message); // Processa a mensagem (neste exemplo, apenas converte para maiúsculas) String response = message.toUpperCase(); // Envia a resposta de volta para o cliente out.println(response); } catch (IOException e) { System.err.println("Erro de I/O no servidor"); System.exit(1); } } } 2. Implemente em um único projeto os códigos referentes às classes UDPClient.java, UDPServer.java encontradas nas páginas 134 a 136 do livro de referência da Disciplina Sistemas Distribuídos, Coulouris, Sistemas Distribuídos 4ª Edição. UDPClient.java import java.net.*; import java.io.*; public class UDPClient { public static void main(String args[]) { DatagramSocket socket = null; try { // Verifica se o número de argumentos está correto if (args.length != 2) { System.out.println("Uso: java UDPClient <hostname do servidor> <mensagem>"); return; } // Obtém o hostname do servidor e a mensagem a ser enviada String serverHostname = args[0]; String message = args[1]; // Cria um socket UDP socket = new DatagramSocket(); // Converte a mensagem em um array de bytes byte[] sendData = message.getBytes(); // Obtém o endereço IP do servidor InetAddress serverAddress = InetAddress.getByName(serverHostname); // Cria um pacote com os dados, o endereço e a porta do servidor DatagramPacket sendPacket = new DatagramPacket(sendData, sendData.length, serverAddress, 6789); // Envia o pacote para o servidor socket.send(sendPacket); // Prepara o pacote para receber a resposta do servidor byte[] receiveData = new byte[1024]; DatagramPacket receivePacket = new DatagramPacket(receiveData, receiveData.length); // Recebe a resposta do servidor socket.receive(receivePacket); // Exibe a resposta String response = new String(receivePacket.getData(), 0, receivePacket.getLength()); System.out.println("Resposta do servidor: " + response); } catch (IOException e) { e.printStackTrace(); } finally { // Fecha o socket if (socket != null) { socket.close(); } } } } UDPServer.java import java.net.*; import java.io.*; public class UDPServer { public static void main(String args[]) { DatagramSocket socket = null; try { // Cria um socket UDP na porta 6789 socket = new DatagramSocket(6789); while (true) { // Cria um buffer para armazenar os dados recebidos byte[] receiveData = new byte[1024]; // Prepara um pacote para receber os dados do cliente DatagramPacket receivePacket = new DatagramPacket(receiveData, receiveData.length); // Recebe os dados do cliente socket.receive(receivePacket); // Obtém os dados recebidos e o endereço do cliente String message = new String(receivePacket.getData(), 0, receivePacket.getLength()); InetAddress clientAddress = receivePacket.getAddress(); int clientPort = receivePacket.getPort(); // Exibe a mensagem recebida do cliente System.out.println("Mensagem recebida do cliente " + clientAddress + ":" + clientPort + ": " + message); // Converte a mensagem em maiúsculas String response = message.toUpperCase(); // Converte a resposta em um array de bytes byte[] sendData = response.getBytes(); // Prepara um pacote com a resposta e o endereço do cliente DatagramPacket sendPacket = new DatagramPacket(sendData, sendData.length, clientAddress, clientPort); // Envia a resposta para o cliente socket.send(sendPacket); } } catch (IOException e) { e.printStackTrace(); } finally { // Fecha o socket if (socket != null) { socket.close(); } } } } 3. Altere os códigos da questão 1 anterior, a fim que a classe TCPClient possa enviar uma mensagem à classe TCPServer e obter o retorno processado. A Classe TCPClient deve enviar a temperatura em graus celsius. A Classe TCPServer deve retornar a temperatura em graus fahrenheit. TCPClient.java Import java.io.*; import java.net.*; public class TCPClient { public static void main(String[] args) { // Verifica se o número de argumentos está correto if (args.length != 2) { System.err.println("Uso: java TCPClient <host do servidor> <temperatura em Celsius>"); System.exit(1); } // Obtém o nome do host e a temperatura em Celsius String serverHost = args[0]; double celsius = Double.parseDouble(args[1]); try ( // Cria o socket para se conectar ao servidor Socket clientSocket = new Socket(serverHost, 6789); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(),true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Envia a temperatura em Celsius para o servidor out.println(celsius); // Lê a resposta do servidor (temperatura em Fahrenheit) e a exibe String response = in.readLine(); System.out.println("Temperatura em Fahrenheit: " + response); } catch (UnknownHostException e) { System.err.println("Host desconhecido: " + serverHost); System.exit(1); } catch (IOException e) { System.err.println("Erro de I/O para o host " + serverHost); System.exit(1); } } } TCPServer.java import java.net.*; import java.io.*; public class TCPServer { public static void main(String[] args) { try ( // Cria um socket de servidor para aguardar conexões na porta 6789 ServerSocket serverSocket = new ServerSocket(6789); // Aguarda e aceita uma conexão do cliente Socket clientSocket = serverSocket.accept(); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Lê a temperatura em Celsius enviada pelo cliente double celsius = Double.parseDouble(in.readLine()); // Converte a temperatura de Celsius para Fahrenheit double fahrenheit = celsius * 9/5 + 32; // Envia a temperatura em Fahrenheit de volta para o cliente out.println(fahrenheit); } catch (IOException e) { System.err.println("Erro de I/O no servidor"); System.exit(1); } } } 4. Altere os códigos da questão anterior, a fim que o projeto utilize as classes UDPServer e UDPClient. UDPClient.java import java.net.*; import java.io.*; public class UDPClient { public static void main(String args[]) { DatagramSocket socket = null; try { // Verifica se o número de argumentos está correto if (args.length != 2) { System.out.println("Uso: java UDPClient <hostname do servidor> <temperatura em Celsius>"); return; } // Obtém o hostname do servidor e a temperatura em Celsius String serverHostname = args[0]; double celsius = Double.parseDouble(args[1]); // Cria um socket UDP socket = new DatagramSocket(); // Converte a temperatura em um array de bytes byte[] sendData = String.valueOf(celsius).getBytes(); // Obtém o endereço IP do servidor InetAddress serverAddress = InetAddress.getByName(serverHostname); // Cria um pacote com os dados, o endereço e a porta do servidor DatagramPacket sendPacket = new DatagramPacket(sendData, sendData.length, serverAddress, 6789); // Envia o pacote para o servidor socket.send(sendPacket); // Prepara o pacote para receber a resposta do servidor byte[] receiveData = new byte[1024]; DatagramPacket receivePacket = new DatagramPacket(receiveData, receiveData.length); // Recebe a resposta do servidor socket.receive(receivePacket); // Exibe a resposta String response = new String(receivePacket.getData(), 0, receivePacket.getLength()); System.out.println("Temperatura em Fahrenheit: " + response); } catch (IOException e) { e.printStackTrace(); } finally { // Fecha o socket if (socket != null) { socket.close(); } } } } UDPServer.java import java.net.*; import java.io.*; public class UDPServer { public static void main(String args[]) { DatagramSocket socket = null; try { // Cria um socket UDP na porta 6789 socket = new DatagramSocket(6789); while (true) { // Cria um buffer para armazenar os dados recebidos byte[] receiveData = new byte[1024]; // Prepara um pacote para receber os dados do cliente DatagramPacket receivePacket = new DatagramPacket(receiveData, receiveData.length); // Recebe os dados do cliente socket.receive(receivePacket); // Obtém os dados recebidos e o endereço do cliente double celsius = Double.parseDouble(new String(receivePacket.getData(), 0, receivePacket.getLength())); InetAddress clientAddress = receivePacket.getAddress(); int clientPort = receivePacket.getPort(); // Converte a temperatura de Celsius para Fahrenheit double fahrenheit = celsius * 9/5 + 32; // Converte a resposta em um array de bytes byte[] sendData = String.valueOf(fahrenheit).getBytes(); // Prepara um pacote com a resposta e o endereço do cliente DatagramPacket sendPacket = new DatagramPacket(sendData, sendData.length, clientAddress, clientPort); // Envia a resposta para o cliente socket.send(sendPacket); } } catch (IOException e) { e.printStackTrace(); } finally { // Fecha o socket if (socket != null) { socket.close(); } } } } 5. Altere a questão 1 anterior para que a aplicação TCPClient encripte uma palavra qualquer, transmita na rede para a aplicação TCPServer. A aplicação TCPServer deve mostrar a palavra transmitida encriptada e a palavra original transmitida. O algoritmo de criptografia a ser utilizado é bem simples: cada letra do alfabeto deve pular três posições. Assim a palavra abacaxi, seria cdceczk. Para decreptar, usa-se o algoritmo inverso, ou seja, cada letra deve descer 3 posições. TCPClient.java import java.io.*; import java.net.*; public class TCPClient { public static void main(String[] args) { // Verifica se o número de argumentos está correto if (args.length != 2) { System.err.println("Uso: java TCPClient <host do servidor> <palavra>"); System.exit(1); } // Obtém o nome do host e a palavra a ser criptografada String serverHost = args[0]; String palavra = args[1]; try ( // Cria o socket para se conectar ao servidor Socket clientSocket = new Socket(serverHost, 6789); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Criptografa a palavra String palavraCriptografada = criptografar(palavra); // Envia a palavra criptografada para o servidor out.println(palavraCriptografada); // Lê a resposta do servidor (palavra original e palavra criptografada) e as exibe String response = in.readLine(); System.out.println("Palavra original: " + response.split(":")[0]); System.out.println("Palavra criptografada: " + response.split(":")[1]); } catch (UnknownHostException e) { System.err.println("Host desconhecido: " + serverHost); System.exit(1); } catch (IOException e) { System.err.println("Erro de I/O para o host " + serverHost); System.exit(1); } } // Método para criptografar uma palavra private static String criptografar(String palavra) { StringBuilder sb = new StringBuilder(); for (char c : palavra.toCharArray()) { //Criptografa cada caractere (letra) if (Character.isLetter(c)) { char criptografado = (char) (((c - 'a' + 3) % 26) + 'a'); sb.append(criptografado); } else { // Mantém caracteres não alfabéticos intactos sb.append(c); } } return sb.toString(); } } TCPServer.java import java.net.*; import java.io.*; public class TCPServer { public static void main(String[] args) { try ( // Cria um socket de servidor para aguardar conexões na porta 6789 ServerSocket serverSocket = new ServerSocket(6789); // Aguarda e aceita uma conexão do cliente Socket clientSocket = serverSocket.accept(); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Lê a palavra criptografada enviada pelo cliente String palavraCriptografada = in.readLine(); // Descriptografa a palavra String palavraOriginal = descriptografar(palavraCriptografada); // Envia a palavra original e a palavra criptografada de volta para o cliente out.println(palavraOriginal + ":" + palavraCriptografada); } catch (IOException e) { System.err.println("Erro de I/O no servidor"); System.exit(1); } } // Método para descriptografar uma palavra private static String descriptografar(String palavraCriptografada) { StringBuilder sb = new StringBuilder(); for (char c : palavraCriptografada.toCharArray()) { // Descriptografa cada caractere (letra) if (Character.isLetter(c)) { char descriptografado = (char) (((c - 'a' + 26 - 3) % 26) + 'a'); sb.append(descriptografado); } else { // Mantém caracteres não alfabéticos intactos sb.append(c); } } return sb.toString(); } } 6. Altere a questões 2 anterior para implementar o mesmo algoritmo da questão 5 acima. TCPClient.java import java.io.*; import java.net.*; public class TCPClient { public static void main(String[] args) { // Verifica se o número de argumentos está correto if (args.length != 2) { System.err.println("Uso: java TCPClient <host do servidor> <palavra>"); System.exit(1); } // Obtém o nome do host e a palavra a ser criptografada String serverHost = args[0]; String palavra = args[1]; try ( // Cria o socket para se conectar ao servidor Socket clientSocket = new Socket(serverHost, 6789); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Criptografa a palavra String palavraCriptografada = criptografar(palavra); // Envia a palavra criptografada para o servidor out.println(palavraCriptografada); // Lê e exibe a resposta do servidor (palavra original e palavra criptografada) String response = in.readLine(); System.out.println("Palavra original: " + response.split(":")[0]); System.out.println("Palavra criptografada: " + response.split(":")[1]); } catch (UnknownHostException e) { System.err.println("Host desconhecido: " + serverHost); System.exit(1); } catch (IOException e) { System.err.println("Erro de I/O para o host " + serverHost); System.exit(1); } } // Método para criptografar a palavra private static String criptografar(String palavra) { StringBuilder sb = new StringBuilder(); for (char c : palavra.toCharArray()) { // Verifica se o caractere é uma letra if (Character.isLetter(c)) { // Aplica a criptografia para letras do alfabeto char criptografado = (char) (((c - 'a' + 3) % 26) + 'a'); sb.append(criptografado); } else { // Mantém caracteres não alfabéticos intactos sb.append(c); } } return sb.toString(); } } TCPServer.java import java.io.*; import java.net.*; public class TCPServer { public static void main(String[] args) { try ( // Cria um socket de servidor para aguardar conexões na porta 6789 ServerSocket serverSocket = new ServerSocket(6789); // Aguarda e aceita uma conexão do cliente Socket clientSocket = serverSocket.accept(); // Cria fluxos de entrada e saída para comunicação PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream())); ) { // Lê a palavra criptografada enviada pelo cliente String palavraCriptografada = in.readLine(); // Descriptografa a palavra String palavraOriginal = descriptografar(palavraCriptografada); // Envia a palavra original e a palavra criptografada de volta para o cliente out.println(palavraOriginal + ":" + palavraCriptografada); } catch (IOException e) { System.err.println("Erro de I/O no servidor"); System.exit(1); } } // Método para descriptografar a palavra private static String descriptografar(String palavraCriptografada) { StringBuilder sb = new StringBuilder(); for (char c : palavraCriptografada.toCharArray()) { // Verifica se o caractere é uma letra if (Character.isLetter(c)) { // Aplica a descriptografia para letras do alfabeto char descriptografado = (char) (((c - 'a' + 26 - 3) % 26) + 'a'); sb.append(descriptografado); } else { // Mantém caracteres não alfabéticos intactos sb.append(c); } } return sb.toString(); } } 7. Faça um jogo do tipo embaralha palavras, de tal forma que o jogador solicite uma palavra ao serviço... TCPClient.java a import java.io.*; import java.net.*; public class TCPEmbaralhaPalavrasClient { public static void main(String[] args) { if (args.length != 1) { System.out.println("Uso: java TCPEmbaralhaPalavrasClient <endereço IP do servidor>"); return; } String serverAddress = args[0]; try (Socket socket = new Socket(serverAddress, 12345); PrintWriter out = new PrintWriter(socket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(socket.getInputStream())); BufferedReader userInput = new BufferedReader(new InputStreamReader(System.in))) { // Envia solicitação para o servidor out.println("SOLICITAR_PALAVRA"); // Recebe a palavra embaralhada do servidor String palavraEmbaralhada = in.readLine(); System.out.println("Palavra embaralhada recebida: " + palavraEmbaralhada); } catch (UnknownHostException e) { System.err.println("Host desconhecido: " + serverAddress); } catch (IOException e) { e.printStackTrace(); } } } TCPServer.java import java.io.*; import java.net.*; import java.util.*; public class TCPEmbaralhaPalavrasServer { private static final String[] PALAVRAS = {"cachorro", "gato", "elefante", "pássaro", "tigre", "leão", "macaco"}; public static void main(String[] args){ try (ServerSocket serverSocket = new ServerSocket(12345)) { System.out.println("Servidor aguardando conexões..."); while (true) { try (Socket clientSocket = serverSocket.accept(); PrintWriter out = new PrintWriter(clientSocket.getOutputStream(), true); BufferedReader in = new BufferedReader(new InputStreamReader(clientSocket.getInputStream()))) { System.out.println("Cliente conectado: " + clientSocket.getInetAddress()); // Recebe a solicitação do cliente String request = in.readLine(); System.out.println("Cliente solicita palavra."); // Gera uma palavra aleatória String palavraEmbaralhada = embaralharPalavra(); // Envia a palavra embaralhada para o cliente out.println(palavraEmbaralhada); System.out.println("Palavra enviada para o cliente: " + palavraEmbaralhada); } catch (IOException e) { e.printStackTrace(); } } } catch (IOException e) { e.printStackTrace(); } } private static String embaralharPalavra() { Random random = new Random(); String palavra = PALAVRAS[random.nextInt(PALAVRAS.length)]; List<Character> caracteres = new ArrayList<>(); for (char c : palavra.toCharArray()) { caracteres.add(c); } Collections.shuffle(caracteres); StringBuilder sb = new StringBuilder(); for (char c : caracteres) { sb.append(c); } return sb.toString(); } } 8. Elabore uma arquitetura em camadas, baseada em serviços entre camadas, a fim que as aplicações Cliente e Servidor possuam as camadas Apresentação, Negócio e Infraestrutura. Desenhe e demonstre a comunicação e os serviços entre as camadas. +----------------------------------+ | Aplicação Cliente | +----------------------------------+ | v +----------------------------------+ |Camada de Apresentação| +----------------------------------+ | v +----------------------------------+ | Camada de Negócio | +----------------------------------+ | v +----------------------------------+ |Camada de Infraestrutura| +----------------------------------+ | v +----------------------------------+ | Aplicação Servidor | +----------------------------------+ Aplicação Cliente: Solicita serviços da camada de Apresentação. Camada de Apresentação: Recebe solicitações do Cliente. Realiza validações básicas e formatação dos dados se necessário. Solicita serviços da camada de Negócio. Camada de Negócio: Recebe solicitações da Camada de Apresentação. Realiza processamento de negócios e lógica de aplicação. Solicita serviços da Camada de Infraestrutura, se necessário. Camada de Infraestrutura: Fornece acesso a recursos de infraestrutura, como banco de dados, sistemas externos, etc. Realiza operações de armazenamento, recuperação e manipulação de dados. Retorna resultados para a Camada de Negócio. Aplicação Servidor: Recebe solicitações da Camada de Infraestrutura. Realiza operações finais, como persistência de dados, se necessário. Retorna resultados para a Camada de Infraestrutura, que pode ser enviado de volta para a Camada de Negócio, se necessário.