Capítulo 1. La Web moderna
Este trabajo se ha traducido utilizando IA. Agradecemos tus opiniones y comentarios: translation-feedback@oreilly.com
La Web tal y como la imaginé, aún no la hemos visto. El futuro es aún mucho más grande que el pasado.
Tim Berners-Lee
Vista previa
Érase una vez una web pequeña y sencilla, en la que los desarrolladores se divertían lanzando llamadas a PHP, HTML y MySQL en archivos individuales y diciendo con orgullo a todo el mundo que visitara su sitio web. Pero la web creció con el tiempo hasta tener miles de millones de páginas, y el primer patio de recreo se convirtió en un metaverso de parques temáticos.
En este capítulo, señalaré algunas áreas que se han vuelto cada vez más relevantes para la web moderna:
-
Servicios y API
-
Concurrencia
-
Capas
-
Datos
El próximo capítulo mostrará lo que ofrece Python en estas áreas. Después, nos sumergiremos en el framework web FastAPI y veremos lo que puede ofrecer.
Servicios y API
La web es un gran tejido de conexiones. Aunque gran parte de la actividad sigue produciéndose en el ladodel contenido -HTML, JavaScript, imágenes, etc.-, cada vez se hace más hincapié en las interfaces de programación de aplicaciones (API) que conectan las cosas.
Normalmente, un servicio web gestiona el acceso de bajo nivel a la base de datos y la lógica empresarial de nivel medio (a menudo agrupados comobackend ), mientras que las aplicaciones JavaScript o móviles proporcionan un ricofrontendde nivel superior (interfaz de usuario interactiva). Estos mundos de frontend y backend se han vuelto más complejos y divergentes, y normalmente requieren que los desarrolladores se especialicen en uno u otro. Es más difícil ser un desarrollador full stack de lo que era antes.1
Estos dos mundos se comunican entre sí mediante API. En la web moderna, el diseño de las API es tan importante como el diseño de los propios sitios web. Una API es un contrato, similar al esquema de una base de datos. Definir y modificar las API es ahora un trabajo de gran envergadura.
Tipos de API
Cada API de define lo siguiente:
- Protocolo
-
La estructura de control
- Formato
-
La estructura del contenido
Se han desarrollado múltiples métodos de API a medida que la tecnología ha evolucionado de máquinas aisladas, a sistemas multitarea y a servidores en red. Probablemente te encuentres con uno o varios de ellos en algún momento, así que lo que sigue es un breve resumen antes de llegar aHTTP y sus amigos, que aparecen en este libro:
-
Antes de la interconexión, una API solía significar una conexión muy estrecha, como una llamada a una función de una biblioteca en el mismo lenguaje que tu aplicación -por ejemplo, calcular una raíz cuadrada en una biblioteca matemática.
-
Las llamadas a procedimientos remotos (RPC) se inventaron para llamar a funciones de otros procesos, en la misma máquina o en otras, como si estuvieran en la aplicación que llama. Un ejemplo popular actual es gRPC.
-
Mensajería envía pequeños trozos de datos en cadenas entre procesos. Los mensajes pueden ser órdenes similares a verbos o simplemente indicar eventos de interés similares a sustantivos. Las soluciones de mensajería populares actuales, que varían ampliamente desde conjuntos de herramientas a servidores completos, incluyenApache Kafka,RabbitMQ,NATS yZeroMQ. La comunicación puede seguir diferentes patrones:
- Solicitud-respuesta
-
Uno: uno, como un navegador web que llama a un servidor web.
- Publicar-suscribir, o pub-sub
-
Un publicador emite mensajes, y los suscriptores actúan sobre cada uno en función de algunos datos del mensaje, como un asunto.
- Colas
-
Como pub-sub, pero sólo uno de un conjunto de suscriptores capta el mensaje y actúa en consecuencia.
Cualquiera de ellos puede utilizarse junto a un servicio web, por ejemplo, para realizar una tarea backend lenta como enviar un correo electrónico o crear una imagen en miniatura.
HTTP
Berners-Lee propuso tres componentes para su World Wide Web:
- HTML
-
Un lenguaje para mostrar datos
- HTTP
-
Un protocolo cliente-servidor
- URLs
-
Un esquema de direccionamiento para recursos web
Aunque en retrospectiva parezcan obvias, resultaron ser una combinación ridículamente útil. A medida que la web evolucionaba, la gente experimentaba, y algunas ideas, como la etiqueta IMG
, sobrevivieron a la lucha darwiniana. Y a medida que las necesidades se hicieron más claras, la gente se tomó en serio la definición de normas.
REST(ful)
Un capítulo de en latesis doctoral de de Roy Fielding definió la Transferencia de Estado Representacional (REST), unestilo arquitectónico para el uso de HTTP.2 Aunque se menciona a menudo, se hamalinterpretado en gran medida.
Una adaptación más o menos compartida ha evolucionado y domina la web moderna. Se llama RESTful, con estas características:
-
Utiliza HTTP y el protocolo cliente-servidor
-
Sin estado (cada conexión es independiente)
-
Almacenable en caché
-
Basado en los recursos
Un recurso son datos que puedes distinguir y sobre los que puedes realizar operaciones. Un servicio web proporciona un punto final -unaURL distinta y un verbo HTTP (acción)- para cada función que quiera exponer. Un punto final también se llama ruta, porque dirige la URL a una función.
Los usuarios de bases de datos están familiarizados con el acrónimo CRUDde procedimientos: crear, leer, actualizar, borrar. Los verbos HTTP son bastante CRUD:
POST
-
Crear (escribir)
PUT
-
Modificar completamente (sustituir)
PATCH
-
Modificar parcialmente (actualizar)
GET
-
Um, obtener (leer, recuperar)
DELETE
-
Borrar
Un cliente envía una solicitud a un punto final RESTful con datos en una de las siguientes áreas de un mensaje HTTP:
-
Cabeceras
-
La cadena URL
-
Parámetros de consulta
-
Valores corporales
A su vez, una respuesta HTTP devuelve esto:
-
Uncódigo de estadoentero que indica lo siguiente:
- 100s
-
Info, sigue adelante
- 200s
-
Éxito
- 300s
-
Redirección
- 400s
-
Error del cliente
- 500s
-
Error del servidor
-
Varias cabeceras
-
Un cuerpo, que puede estar vacío, solo o troceado (en trozos sucesivos)
Al menos un código de estado es un huevo de Pascua:418
(Soy una tetera) se supone que lo devuelve una tetera conectada a la web, si se le pide que prepare café.
Encontrarás muchos sitios web y libros sobre el diseño de API RESTful, todos ellos con útiles reglas generales. Este libro repartirá algunas por el camino.
Formatos de datos JSON y API
Las aplicaciones frontales pueden intercambiar texto ASCII sin formato con los servicios web backend, pero ¿cómo puedes expresar estructuras de datos como listas de cosas?
Justo cuando empezamos a necesitarla de verdad, llegó la Notación de Objetos JavaScript (JSON), otra idea sencilla que resuelve un problema importante y que parece obvia en retrospectiva. Aunque la J significa JavaScript, la sintaxis también se parece mucho a la de Python.
JSON ha sustituido en gran medida a antiguos intentos como XML y SOAP. En el resto de este libro, verás que JSON es el formato de entrada y salida por defecto de los servicios web.
JSON:API
La combinación de diseño RESTful y formatos de datos JSON ya es habitual, pero aún queda cierto margen para la ambigüedad y las peleas de empollones. La reciente propuesta JSON:API pretende endurecer un poco las especificaciones. Este libro utilizará el enfoque RESTful flexible, pero JSON:API o algo similarmente riguroso puede ser útil si tienes peleas importantes.
GraphQL
Las interfaces RESTful pueden ser engorrosas para algunos propósitos. Facebook (ahora Meta) diseñóel lenguaje Graph Query Language (GraphQL)para especificar consultas de servicio más flexibles. No entraré en GraphQL en este libro, pero puede que quieras investigarlo si el diseño RESTful te parece inadecuado para tu aplicación.
Concurrencia
Además del crecimiento de la orientación a los servicios, la rápida expansión del número de conexiones a los servicios web exige cada vez mayor eficiencia y escala.
Queremos reducir lo siguiente:
- Latencia
-
El tiempo de espera inicial
- Rendimiento
-
El número de bytes por segundo entre el servicio y sus llamantes
En los viejos tiempos de la web3 la gente soñaba con soportar cientos de conexiones simultáneas, luego se preocupaban por el "problema de los 10K", y ahora asumen millones a la vez.
El término concurrencia no significa paralelismo total. El procesamiento múltiple no se produce en el mismo nanosegundo, en una sola CPU. En cambio, la concurrencia evita sobre todola espera ocupada (dejar inactiva la CPU hasta que se obtiene una respuesta). Las CPU son veloces, pero las redes y los discos son miles o millones de veces más lentos. Por eso, siempre que hablamos con una red o un disco, no queremos quedarnos con la mirada perdida hasta que responda.
La ejecución normal de Python es síncrona: una cosa cada vez, en el orden especificado por el código. A veces queremos ser asíncronos: hacer un poco de una cosa, luego un poco de otra, volver a la primera, etc. Si todo nuestro código utiliza la CPU para calcular cosas(ligado ala CPU), realmente no hay tiempo libre para ser asíncrono. Pero si realizamos algo que hace que la CPU espere a que se complete algo externo (ligado a la E/S), podemos ser asíncronos.
Los sistemas asíncronos proporcionan un bucle de eventos: las solicitudes de operaciones lentas se envían y anotan, pero no retenemos la CPU esperando sus respuestas, sino que se realiza algún procesamiento inmediato en cada pasada por el bucle, y las respuestas que hayan llegado durante ese tiempo se gestionan en la siguiente pasada.
Más adelante verás cómo el procesamiento asíncrono de FastAPI lo hace mucho más rápido que los típicos frameworks web.
El procesamiento asíncrono no es mágico. Todavía tienes que tener cuidado de evitar hacer demasiado trabajo intensivo de CPU durante el bucle de eventos, porque eso ralentizará todo. Más adelante en este libro, verás los usos de las palabras claveasync
y await
de Python, y cómo FastAPI te permite mezclar tanto el procesamiento síncrono como el asíncrono.
Capas
Los fansde Shrek recordarán que señaló sus capas de personalidad, a lo que Burro respondió: "¿Como una cebolla?".
Bueno, si los ogros y los vegetales llorosos pueden tener capas, entonces también puede tenerlas el software. Para gestionar el tamaño y la complejidad, muchas aplicaciones han utilizado durante mucho tiempo el llamadomodelo de tres capas.4 Esto no es terriblemente nuevo. Los términos difieren,5 pero para este libro utilizaré la siguiente separación simple de términos (ver Figura 1-1):
- Web
-
Capa de entrada/salida sobre HTTP, que reúne las solicitudes de los clientes, llama a la Capa de Servicio y devuelve las respuestas
- Servicio
-
La lógica empresarial, que llama a la capa de Datos cuando es necesario
- Datos
-
Acceso a almacenes de datos y otros servicios
- Modelo
-
Definiciones de datos compartidas por todas las capas
- Cliente web
-
Navegador web u otro software HTTP del lado del cliente
- Base de datos
-
El almacén de datos, a menudo un servidor SQL o NoSQL
Estos componentes te ayudarán a escalar tu sitio sin tener que empezar de cero. No son leyes de la mecánica cuántica, así que considéralas directrices para la exposición de este libro.
Las capas se comunican entre sí a través de las API de . Éstas pueden ser simples llamadas a funciones de módulos separados de Python, pero podrían acceder a código externo a través de cualquier método. Como he mostrado antes, esto podría incluir RPCs, mensajes, etc. En este libro, estoy suponiendo un único servidor web, con código Python importando otros módulos Python. La separación y la ocultación de información son gestionadas por los módulos.
Lacapa Web es la que ven los usuarios, a través de las aplicaciones cliente y las API. Normalmente hablamos de una interfaz Web RESTful, con URL y solicitudes y respuestas codificadas en JSON. Pero también podrían construirse clientes alternativos de texto (o interfaz de línea de comandos, CLI) junto a la capa Web. El código Web de Python puede importar módulos de la capa de Servicio, pero no debe importar módulos de Datos.
Lacapa de servicio contiene los detalles reales de lo que ofrece este sitio web. Esta capa parece esencialmente una biblioteca. Importa módulos de datos para acceder a bases de datos y servicios externos, pero no debe conocer los detalles.
Lacapa de Datos de proporciona a la capa de Servicios acceso a los datos, a través de archivos o llamadas de clientes a otros servicios. También pueden existir capas de Datos alternativas, que se comuniquen con una única capa de Servicios.
Lacasilla Model no es una capa propiamente dicha, sino una fuente de definiciones de datos compartida por las capas. No es necesaria si pasas estructuras de datos Python incorporadas entre ellas. Como verás, la inclusión de Pydantic en FastAPI permite definir estructuras de datos con muchas características útiles.
¿Por qué hacer estas divisiones? Entre otras muchas razones, cada capa puede ser:
-
Escrito por especialistas.
-
Probado en aislamiento.
-
Sustituida o complementada: podrías añadir una segunda capa Web, utilizando una API diferente como gRPC, junto a una Web.
Sigue una regla de Los Cazafantasmas: no cruces los arroyos. Es decir, no dejes que los detalles de la Web se filtren fuera de la capa Web, ni los detalles de la base de datos fuera de la capa Datos.
Puedes visualizarlas capas como una pila vertical, como un pastel en el Great British Bake Off.6
He aquí algunas razones para separar las capas:
-
Si no separas las capas, espera un meme web consagrado: Ahora tienes dos problemas.
-
Una vez mezcladas las capas, la separación posterior será muy difícil.
-
Necesitarás conocer dos o más especialidades para comprender y escribir pruebas si la lógica del código se confunde.
Por cierto, aunque yo las llame capas, no tienes por qué suponer que una capa está "encima" o "debajo" de otra, y que los comandos fluyen con la gravedad ¡Cauvinismo vertical! También podrías ver las capas como cajas que se comunican lateralmente(Figura 1-2).
Las visualices como las visualices, las únicas vías de comunicación entre las cajas/capas son las flechas (API). Esto es importante para las pruebas y la depuración. Si en una fábrica existen puertas sin documentar, el vigilante nocturno se llevará inevitablemente una sorpresa.
Las flechas entre el cliente web y la capa Web utilizan HTTP o HTTPS para transportar principalmente texto JSON. Las flechas entre la capa de Datos y la base de datos utilizan un protocolo específico de la base de datos y transportan texto SQL (u otro). Las flechas entre las propias capas son llamadas a funciones que transportan modelos de datos.
Además, los formatos de datos recomendados que fluyen a través de las flechas son los siguientes:
- Cliente ⇔ Web
-
RESTful HTTP con JSON
- Web ⇔ Servicio
-
Modelos
- Servicio ⇔ Datos
-
Modelos
- Datos ⇔ Bases de datos y servicios
-
API específicas
Basándome en mi propia experiencia, así es como he decidido estructurar los temas de este libro. Es factible y se ha adaptado a sitios bastante complejos, pero no es sagrado. Puede que tú tengas un diseño mejor. Lo hagas como lo hagas, estos son los puntos importantes:
-
Separar los detalles específicos del dominio.
-
Define API estándar entre las capas.
-
No hagas trampas; no filtres.
A veces, decidir qué capa es el mejor hogar para el código es todo un reto. Por ejemplo, el Capítulo 11 examina los requisitos de autenticación y autorización y cómo implementarlos, como una capa adicional entre la Web y el Servicio, o dentro de uno de ellos. El desarrollo de software es a veces tanto arte como ciencia.
Datos
La web se ha utilizado a menudo como frontend de las bases de datos relacionales, aunque han evolucionado muchas otras formas de almacenar y acceder a los datos, como las bases de datos NoSQL o NewSQL.
Pero más allá de las bases de datos,el aprendizaje automático (ML)-o aprendizaje profundo o simplemente IA- está rehaciendo fundamentalmente el panorama tecnológico. El desarrollo de grandes modelos requiere muchotrabajo con los datos, lo que tradicionalmente se ha denominado extraer, transformar, cargar (ETL).
Como arquitectura de servicios de uso general, la web puede ayudar con muchas de las partes más complicadas de los sistemas de ML.
Revisa
La web utiliza muchas API, pero especialmente las RESTful. Las llamadas asíncronas permiten una mejor concurrencia, lo que acelera el proceso en general. Las aplicaciones de servicios web suelen ser lo suficientemente grandes como para dividirlas en capas. Los datos se han convertido en un área importante por derecho propio. Todos estos conceptos se abordan en el lenguaje de programación Python, en el próximo capítulo.
1 Dejé de intentarlo hace unos años.
2 Estilo significa un patrón de nivel superior, como cliente-servidor, más que un diseño específico.
3 Alrededor de cuando el hombre de las cavernas jugaba al hacky sack con perezosos terrestres gigantes.
4 Elige tu propio dialecto: grada/capa, tomate/tomahto/arigato.
5 A menudo verás el término Modelo-Vista-Controlador (MVC) y las variaciones de . Suele ir acompañado de guerras religiosas, hacia las que soy agnóstico.
6 Como saben los espectadores, si tus capas se descuidan, puede que no vuelvas a la tienda a la semana siguiente.
Get FastAPI now with the O’Reilly learning platform.
O’Reilly members experience books, live events, courses curated by job role, and more from O’Reilly and nearly 200 top publishers.