Fundamentos de funcionamiento de una aplicación web

Arquitectura cliente-servidor y modelo de petición - respuesta

Antes de poder entrar a ver como se programa una aplicación con ASP.NET es necesario conocer algunos de los fundamentos de funcionamiento de una aplicación web.

Los primero que debemos saber es que las aplicaciones web se basan en una arquitectura cliente-servidor. Donde:

  • El servidor es el ordenador encargado de proporcionar el contenido. Para ello necesitamos instalar un servidor web en dicha máquina. Existen multitud de servidores web (Apache, LigHTTPd, IIS) pero no todos son capaces de ejecutar aplicaciones ASP.NET. Únicamente los servidores de Microsoft pueden desempeñar dicha tarea. En nuestro caso utilizaremos IIS Espress.
  • El cliente, que es el encargado de solicitar la información al servidor y mostrarla al usuario. Es el navegador (Interner Explorer, Firefox, Chrome, etc ). Si estas viendo está pagina estas utilizando un navegador web.

El funcionamiento de una aplicación es simple, el cliente emite una petición de un recurso que se encuentra en el servidor, y el servidor devuelve el recurso solicitado que es mostrado por el navegador.

image

La petición del recurso en concreto se realiza a través de una URL. Una URL no es mas que una cadena de texto, expresada en un formato determinado en la que indicamos el protocolo, el puerto, el servidor y el recurso que estamos solicitando. Por ejemplo:

http://www.devjoker.com:80/default.aspx

En nuestro caso el protocolo es HTTP, el servidor www.devjoker.com, el puerto el 80 y el recurso default.aspx. El puerto estándar para el protocolo HTTP es el 80, por lo que no se suele especificar. Dependiendo de la configuración del servidor podríamos omitir el recurso y asignar uno por defecto. De este modo la siguiente URL seria equivalente a esta otra:

http://www.devjoker.com

La petición HTTP tendría la siguiente forma:

GET http://www.devjoker.com/ HTTP/1.1
Accept: text/html, application/xhtml+xml, */*
Accept-Language: es-ES
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0)
Accept-Encoding: gzip, deflate
Host: www.devjoker.com
If-Modified-Since: Fri, 03 Aug 2012 10:57:59 GMT
Connection: Keep-Alive
Pragma: no-cache
Cookie: ASP.NET_SessionId=nullimt1wzjmbtik5ferit4w;

Aunque nosotros solo especifiquemos la URL, el navegador web añadirá cierta información adicional a la petición como el tipo de contenido que acepta como respuesta, el lenguaje, tipo de navegador …

Y la respuesta sería algo similar a esto (se acorta el contenido del documento HTML devuelto por razones de espacio):

HTTP/1.1 200 OK
Cache-Control: public
Content-Type: text/html; charset=utf-8
Expires: Fri, 03 Aug 2012 10:58:48 GMT
Last-Modified: Fri, 03 Aug 2012 10:58:38 GMT
Vary: Accept-Encoding
Server: Microsoft-IIS/7.5
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Fri, 03 Aug 2012 10:58:39 GMT
Content-Length: 42013

<!DOCTYPE html >
<html lang="es">
<head id="Head1">
<title>www.devjoker.com</title>
</head>
<body>
<!-- Contenido de la página!!!! -->
....

</body>
</html>

Tanto la petición como la respuesta pueden tener dos secciones diferenciadas: Las cabeceras de HTTP (indicadas en cursiva y color gris en el ejemplo) y el cuerpo. Profundizaremos algo más en estos conceptos en capítulos posteriores de este tutorial. De momento diremos que en el caso de la petición HTTP podemos enviar información adicional (normalmente los datos de un formulario web), y que en el caso de la respuesta HTTP recibiremos el contenido HTML, el lenguaje de marcado que utilizará el navegador para visualizar la página.

Afortunadamente ASP.NET (y todos los framework de desarrollo web) encapsulan el manejo de la solicitud y la respuesta en objetos de fácil acceso.

Servidores DNS

Falta aún por introducir un elemento importante. Los servidores en internet (en realidad cualquier ordenador dentro de una red) se identifica por una direccion IP. Sin embargo, en el ejemplo anterior, al proporcionar la URL, no nos hemos referido a una dirección IP, sino al nombre del servidor (mas concretamente al nombre de “dominio”). Entonces … ¿Como sabe el navegador que un determinado servidor “www.devjoker.com” se corresponde con una dirección IP concreta? La respuesta es simple: Los servidores DNS.

Un servidor DNS es una especie de “centralita de internet”, de forma que cuando un navegador solicita una URL a un servidor desconocido, primero se consulta la “centralita” para obtener la dirección IP. Por motivos de rendimiento, una vez que se ha resuelto el nombre de dominio se almacena localmente para que no sea necesario volver a preguntar.

image

Podemos realizar consultas directamente al servidor DNS con la aplicación nslookup:

Microsoft Windows [Versión 6.1.7601]
Copyright (c) 2009 Microsoft Corporation. Reservados todos los derechos.

C:\Users\pedro_herrarte>nslookup
Servidor predeterminado: google-public-dns-a.google.com
Address: 8.8.8.8

> devjoker.com
Servidor: google-public-dns-a.google.com
Address: 8.8.8.8

Respuesta no autoritativa:
Nombre: devjoker.com
Address: 188.165.132.77

> 188.165.132.77

En el ejemplo anterior estamos utilizando los servidores DNS de Google (IP 8.8.8.8).

Por ultimo, nos faltaría conocer como es capaz el servidor DNS de obtener la IP correcta de nuestro servidor www.devjoker.com. Cuando registramos un dominio en internet, debemos configurar dicha información a través del panel de control DNS (opción que proveen TODOS los registradores de dominio … ¿TODOS? NO! MoviStar no te permite configurar los registros de DNS y te obliga a contratarlo como servicio aparte. Mi recomendación es que NUNCA registréis un dominio con MoviStar). De este modo, publicamos que nuestro nombre de dominio “devjoker.com”, se corresponde un servidor (o conjunto de servidores) con una dirección IP concreta.

La siguiente imagen muestra la configuración DNS de devjoker.com:

image

De un modo similar funciona el envío de correos electrónicos, con las salvedad de que el servidor DNS es consultado para registros de tipo MX – Mail eXchange, es decir, que para que nuestro servidor sea capaz de enviar y recibir correos debemos haber configurado correctamente ambos servidores y haber configurado los servidores DNS adecuadamente.

Protocolo HTTP

El protocolo de comunicaciones que se utiliza para solicitar y recibir páginas web es HTTP. HTTP es el acrónimo de HyperText Transfer Protocol, siendo el aspecto mas relevante que se trata de un protocolo de transmisión de texto. Solo texto. Es sumamente importante entender este aspecto, ya que condiciona como funciona la web.

Si analizamos los elementos base en los que sostiene la web hoy en día, nos encontramos los siguientes elementos fundamentales:

  • El lenguaje para la definición de los elementos de una página y su contenido es texto – HTML. Veremos una pequeña introducción a HTML en el siguiente capitulo.
  • El lenguaje para la definición del aspecto visual de la página es texto. CSS. También veremos una introducción a CSS en este tutorial.
  • El lenguaje para la programación del lado del cliente JavaScript, que se recibe en cuerpo de la respuesta como texto, y se compila e interpreta en el cliente. (Esto tiene interesantes matices, como la posibilidad de escribir código dinámicamente en el servidor …)

HTTP es un protocolo sin estado, es decir, HTTP no guarda ninguna información sobre conexiones anteriores. Esto significa que cuando enviamos varias solicitudes HTTP, la solicitud actual no conoce en los datos que han enviado y recibido las peticiones anteriores.

Por ejemplo, si en una primera solicitud enviamos la información de un usuario, y luego visitamos una segunda página, esta segunda página no sabe que usuario utilizamos en la anterior. Este es un factor que condiciona completamente la forma de trabajar cuando desarrollamos aplicaciones web, ya que al no proporcionarnos esta información el protocolo vamos a tener que realizarlo a nivel de aplicación.

Además las peticiones HTTP responden a una serie de “verbos” predefinidos, según el verbo de la solicitud el servidor actuará de una forma u otra. Los verbos mas comunes son GET y POST, aunque existen mas. Veremos mas adelante que ASP.NET MVC permite especificar que un método de un controlador responda únicamente a un conjunto de verbos concretos.

Cuando veamos la parte dedicada a AJAX y jQuery veremos que existen métodos $.get() y $.post() para realizar peticiones utilizando uno u otro verbo de forma simple desde JavaScript.

Ha continuación vamos a ver un par de ejemplos sobre GET y POST.

GET
Solicita un recurso especifico. Se utiliza sobre todo cuando solicitamos un recurso sin necesidad de enviar información adicional, aunque el verbo GET permite enviar datos adicionales como parte de la URL solicitada, su uso debe realizarse con cuidado, ya que es una información que un usuario malintencionado podría modificar para realizar un ataque.
GET /images/logo.png HTTP/1.1 obtiene un recurso llamado logo.png
POST
Envía los datos incluyéndolos en el cuerpo de la petición. Es muy habitual para el envío de datos (a través de formularios), en los que el usuario rellena cierta información y la envía al servidor.

POST http://devjoker.com/login.aspx HTTP/1.1

Accept: text/html, application/xhtml+xml, */*

Accept-Language: es-ES

User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0)

Content-Type: application/x-www-form-urlencoded

Accept-Encoding: gzip, deflate

Host: devjoker.com

Content-Length: 650

Connection: Keep-Alive

Pragma: no-cache

UserName=nombreUsuario&Password=laclave

El ejemplo anterior corresponde a la captura de una petición HTTP de un formulario de identificación de usuario a través de POST. Podemos ver que la información se envía en el cuerpo de la petición, y fácilmente podemos obtener el usuario y el password, siendo muy fáciles de capturar (al menos desde el propio equipo que realiza las peticiones!). Es por este motivo, por el existe una versión cifrada de HTTP – HTTPS –, que se encarga de cifrar todas comunicaciones que se producen entre el navegador y el servidor. Es un aspecto que tendremos que tener en cuenta siempre que nuestras aplicaciones requieran del manejo de datos sensibles.

Por último, comentar que HTTP responde a cada petición con un código de estado predefinido que permite al navegador identificar que acción debe realizar. A continuación vamos a ver algunos de los códigos HTTP mas comunes.

Códigos de estado HTTP.

Cada respuesta HTTP identifica el resultado de la petición a través de un código HTTP. Dependiendo de este código de respuesta de HTTP el navegador realizará una acción u otra. Por ejemplo, mostrará la pantalla solicitada si el estado es 200 (OK) o mostrará la pantalla de error en caso de que reciba un error 500 (error de servidor).

Los códigos de error de HTTP con códigos numéricos, agrupados en familias por centenas. De forma que los errores 200 corresponden a peticiones correctas, los errores 300 redirecciones, los 400 errores en la petición y los errores 500 errores de ejecución del lado del servidor.

De manera muy breve veremos los principales códigos de respuesta de HTTP.

200 OK

Indica que el servidor a obtenido y enviado correctamente el recurso solicitado por la petición. En este caso el cuerpo de la respuesta contendrá el contenido en texto (HTML, CSS, Javascript, etc) del recurso solicitado, permitiendo al navegador mostrarlo en la pantalla.

El siguiente ejemplo muestra una petición GET al recurso http://devjoker.com :

GET http://devjoker.com/ HTTP/1.1
Accept: text/html, application/xhtml+xml, */*
Accept-Language: es-ES
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0)
Accept-Encoding: gzip, deflate
Host: devjoker.com
If-Modified-Since: Sun, 19 Aug 2012 22:22:57 GMT
Connection: Keep-Alive

Y la respuesta obtenida:

HTTP/1.1 200 OK
Cache-Control: public, max-age=10
Content-Type: text/html; charset=utf-8
Content-Encoding: gzip
Expires: Sat, 22 Sep 2012 22:37:05 GMT
Last-Modified: Sat, 22 Sep 2012 22:36:55 GMT
Vary: Accept-Encoding
Server: Microsoft-IIS/7.5
X-AspNet-Version: 4.0.30319
X-Powered-By: ASP.NET
Date: Sat, 22 Sep 2012 22:36:56 GMT
Content-Length: 9357

<html>

</html>

La respuesta incluye el código HTML de la página que permitirá al navegador mostrar el contenido solicitado. Por razones de espacio se omite el contenido HTML en este ejemplo.

301 Redirección permanentemente.

Ésta es la opción más habitual en el caso de migraciones o cambios de dominio, indica al navegador que el recurso solicitado no ha cambiado de ubicación y que debe solicitar una nueva URL. Además le insta a modificar cualquier enlace que conserve almacenado o información asociada a dicha URL (como por ejemplo, el índice de Google o Bing). Una redirección 301 es interpretada por los motores de búsqueda de forma que implica que toda la información asociados a la página original se transmitan a la de destino, por lo que es el más aconsejable para trasladar contenido.

302 Found.

Indica que un recurso ha sido localizado pero que no ha sido devuelto como parte de la respuesta, indicando una nueva localización para el recurso. Está es la opción que se utiliza cuando queremos efectuar la redirección de un recurso a otro diferente. El código 302 se suele usar para todos los traslados temporales, donde el servidor responde al navegador indicándole una nueva URL con el nuevo recurso. Es el navegador el que interpreta este código y realiza una nueva petición (esta vez al nuevo recurso). El siguiente ejemplo muestra una respuesta HTTP 302 en la que navegador redirecciona a un nuevo recurso (Location: /private/index.aspx)

HTTP/1.1 302 Found

Cache-Control: private, no-cache="Set-Cookie"

Content-Type: text/html; charset=utf-8

Location: /private/index.aspx

También Es muy común utilizar el código 302 para controlar la navegación dentro de un sitio web.

304 Not Modified.

Básicamente indica que el contenido no se ha modificado desde la última vez que se solicitó. Lo mas normal es que nunca se provoque este estado a propósito, sino que dejemos al servidor decida cuando usarlo. La consecuencia directa en que cuando un navegador recibe esté código, la respuesta no contiene contenido alguno es el cuerpo – el recurso se obtendrá del los archivos temporales almacenados por el navegador en peticiones anteriores. Por ejemplo, si una página no se ha modificado, no se transmite de nuevo el contenido de la misma, simplemente se indica que no se ha modificado a través del código 304 y el navegador utiliza la última versión de la que dispone.

HTTP/1.1 304 Not Modified

Last-Modified: Mon, 06 Aug 2012 17:12:08 GMT

Accept-Ranges: bytes

ETag: "35ec559cf673cd1:0"

Server: Microsoft-IIS/7.5

X-Powered-By: ASP.NET

Date: Sat, 22 Sep 2012 22:36:58 GMT

Podemos entender mejor este código de estado si pensamos en una imagen que se muestra en una página web, la primera vez que visitamos la página el servidor nos entrega la imagen, pero en peticiones sucesivas se detecta que la imagen no se ha modificado y se utiliza la versión que se descargo la ultima vez.

400 Bad Request.

Este código indica que la solicitud no está correctamente formada. Normalmente se produce este error cuando la URL no es correcta.

HTTP/1.1 400 Bad Request

Otros errores de la familia 400 son:

  • 401 No autorizado
  • 402 Pago requerido
  • 403 Prohibido

404 Not Found.

Sin lugar a dudas el error mas común. Indica que a pesar de que la petición es correcta el recurso solicitado no existe en el servidor. Normalmente esto se produce debido a que la URL apunta a un recurso que no existe en el servidor, pero también es posible que el servidor este ocultando el recurso intencionadamente.

HTTP/1.1 404 Not Found

Content-Type: text/html

Server: Microsoft-IIS/7.5

X-Powered-By: ASP.NET

Date: Sat, 22 Sep 2012 22:51:04 GMT

Content-Length: 1245

También se puede producir un error 404 cuando el servidor no tiene configurado el tipo de recurso correctamente.

405 Method Not Allowed.

Este código indica que el verbo utilizado en la petición no es válido. Se incluye como parte de la respuesta los verbos admitidos por el recurso.

HTTP/1.1 405 Method Not Allowed

Allow: GET, HEAD, OPTIONS, TRACE

Content-Type: text/html

500 Server Error

La familia de errores 500 corresponden con errores de servidor. Se pueden deber a multitud de causas, ya que suelen corresponder con un error de nuestra aplicación. Por ejemplo, si en nuestro programa cometemos un error de programación e intentamos realizar una división por cero, el cliente recibirá un error 500 como resultado de la respuesta.

También se produce un error 500 cuando el servidor no dispone de los recursos necesarios para atender la petición.

El siguiente ejemplo muestra un ejemplo de petición a devjoker.com en el que hemos detenido intencionadamente la aplicación. En este caso obtenemos un error con código 503 que nos indica que la aplicación no está disponible – 503 Service Unavaileable.

GET http://devjoker.com/ HTTP/1.1
Accept: text/html, application/xhtml+xml, */*
Accept-Language: es-ES
User-Agent: Mozilla/5.0 (compatible; MSIE 9.0; Windows NT 6.1; Trident/5.0)
Accept-Encoding: gzip, deflate
Host: devjoker.com
Connection: Keep-Alive

-----------------------------------------------------------------------------------------------------------------------------------

HTTP/1.1 503 Service Unavailable
Content-Type: text/html; charset=us-ascii
Server: Microsoft-HTTPAPI/2.0
Date: Sat, 06 Oct 2012 15:41:03 GMT
Connection: close
Content-Length: 326

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01//EN""http://www.w3.org/TR/html4/strict.dtd">
<HTML><HEAD><TITLE>Service Unavailable</TITLE>
<META HTTP-EQUIV="Content-Type" Content="text/html; charset=us-ascii"></HEAD>
<BODY><h2>Service Unavailable</h2>
<hr><p>HTTP Error 503. The service is unavailable.</p>
</BODY></HTML>

Los errores 500 definidos son: 501 No implementado, 502 Pasarela incorrecta, 503 Servicio no disponible, 504 Tiempo de espera de la pasarela agotado y 505 version not suported.

505 HTTP Version Not Supported.

Este error se produce cuando la petición solicita una versión de HTTP no soportada por el servidor. El siguiente ejemplo muestra una petición HTTP 2.0, y el error devuelto indicando que el servidor no soporta esta versión de HTTP.

GET http://www.devjoker.com/ HTTP/2.0

Host: www.devjoker.com

-------------------------------------------------------------------

HTTP/1.1 505 HTTP Version Not Supported
Content-Type: text/html; charset=us-ascii
Server: Microsoft-HTTPAPI/2.0

Un estudio mas detallado del HTTP escapa completamente del ámbito de este tutorial donde solo pretendemos dar una breve introducción para facilitar los conceptos de programación con ASP.NET MVC que veremos en capítulos posteriores.

Analizar el trafico HTTP.

Si queremos analizar el tráfico HTTP directamente podemos hacerlo directamente utilizando las herramientas de desarrollo que incorporan casi todos los navegadores (pulsando F12), o bien a través de herramientas especificas como Fiddler.

La siguiente imagen muestra Fiddler utilizado para capturar el tráfico.

image

Pedro  Herrarte  Sánchez
Fundamentos de funcionamiento de una aplicación web
Pedro Herrarte Sánchez

Pedro Herrarte, es consultor independiente, ofreciendo servicios de consultoría, análisis, desarrollo y formación. Posee mas de diez años de experiencia trabajando para las principales empresas de España. Es especialista en tecnologías .NET, entornos Web (ASP.NET, ASP.NET MVC,jQuery, HTML5), bases de datos (SQL Server y ORACLE) e integración de sistemas. Es experto en desarrollo (C#, VB.Net, T-SQL, PL/SQL, , ASP, CGI , C, Pro*C, Java, Essbase, Vignette, PowerBuilder y Visual Basic ...) y bases de datos (SQL Server y ORACLE). Pedro es MCP y MAP 2012, es fundador, diseñador y programador de www.devjoker.com..
Fecha de alta:06/10/2012
Última actualizacion:06/10/2012
Visitas totales:28021
Valorar el contenido:
Últimas consultas realizadas en los foros
Últimas preguntas sin contestar en los foros de devjoker.com