Con esta interface, cuando se desee enviar un correo, primero hay que colocar la dirección completa, tanto del remitente como del destinatario, es decir, jose@algunsitio.edu, y no sólo jose. Sólo se puede enviar correo a un destinatario. Además, la parte de la dirección que identifica el dominio del receptor debe escribirse con el nombre canónico del servidor SMTP que acepta el correo en el sistio del destinatario. Por ejemplo, si se desea enviar correo a usuario@algunsitio.edu y el servidor SMTP de algunsitio.edu es correo.algunsitio.edu, se debe utilizar la dirección usuario@correo.algunsitio.edu.
Cuando se termine de construir un mensaje de correo, se debe presionar Enviar para enviarlo.
ClienteDeCorreo | La interface de usuario |
Mensaje | El mensaje de correo |
Envoltura | Envoltura SMTP alrededor del Mensaje |
ConexionSmtp | Conexión al servidor SMTP server |
Usted debe completar el código de la clase ConexionSmtp para lograr tener un programa que pueda enviar un mensaje de correo a cualquier destinatario.
Los lugares donde usted debe completar código han sido marcados con el comentario /* Para completar */. Cada parte a completar requiere una o más líneas de código.
La clase ClienteDeCorreo implementa una interface de usuario e invoca las otras clases a medida que sea necesario. Cuando se presiones el botón Enviar, la clase ClienteDeCorreo construira un objeto de la clase Mensaje para colocar el mensaje de correo. El objeto Mensaje mantendrá los headers y el cuerpo del mensaje real. Luego el objeto ClienteDeCorreo construira una envoltura SMTP utilizando la clase Envoltura. Esta clase guardará la información del remitente y el destinatario SMTP, el servidor SMTP del dominio del destinatario, y el objeto Mensaje. Entonces el objeto ClienteDeCorreo creará el objeto ConexionSmtp que abre una conexión al servidor SMTP y el objeto ClienteDeCorreo enviará el mensaje sobre la conexión. El envío del correo sucede en tres etapas:
Comando | Código de respuesta |
---|---|
DATA | 354 |
HELO | 250 |
MAIL FROM | 250 |
QUIT | 221 |
RCPT TO | 250 |
La tabla anterior también lista los códigos de respuesta aceptados para cada uno de los comandos SMTP que se deben implementar. Por simplicidad, se puede asumir que cualquier otra respuesta desde el servidor indica un error fatal y se terminará inmediatamente el envío del mensaje. En realidad, SMTP distingue entre errores transientes (códigos de respuesta 4xx) y permanentes (códigos de respuesta 5xx), y al emisor se le permite repetir comandos que hayan generado un error transiente. Revise el apéndice E del RFC 821 para más información.
Además, cuando se abra la conexión con el servidor, él responderá con el código 220.
Nota: El RFC 821 permite el código 251 como respuesta al comando RCPT TO-comando que indica que el destinatario no es un usuario local. Si lo desea, puede verificar manualmente con el comando telnet qué responde su servidor SMTP local.
Para facilitar la depuración del programa, al comienzo, no incluya el código que abre el socket. Se recomienda que utilice las sisguientes definiciones para desdeElServidor y haciaElServidor. Con estas definiciones su programa enviará los comandos a la pantalla. Actuando como servidor SMTP, usted debe proporcionar los códigos de respuesta correctos. Cuando su programa funcione, agregue el código para abrir el socket hacia el servidor.
desdeElServidor = new BufferedReader(new InputStreamReader(System.in)); haciaElServidor = new DataOutputStream(System.out);Las líneas para abrir y cerrar el socket, es decir las líneas socketParaConexion = ... en el método constructor y la línea socketParaConexion.close() en la función close(), han sido comentadas de antemano.
Comience completando la función analiceRespuesta(). Usted necesitará esta función en varias partes del código. En la función analiceRespuesta(), se debe utilizar la clase StringTokenizer para analizar sintácticamente las líneas de respuesta. Se puede convertir una cadena a un entero de la siguiente manera:
int i = Integer.parseInt(argv[0]);En la función envieComandoSmtp(), se debe utilizar la función writeBytes() para escribir los comandos al servidor. La ventaja de utilizar writeBytes() en lugar de write() es que el primero automáticamente convierte la cadena a bytes, que es lo que el servidor espera. No olvide terminar cada comando con la cadena CRLF.
Usted puede lanzar excepciones como esta:
throw new IOException();
Usted no debe preocuparse por los detalles, ya que las excepciones en esta práctica son utilizadas sólo para señalar un error, sin dar información detallada sobre qué resultó mal.