Construyendo Aplicaciones Multijugador con Cloudflare Workers y Durable Objects

Spanish audio is available in the player settings
Rate this content
Bookmark

Los Durable Objects, parte de la plataforma Cloudflare Workers, son la solución para un almacenamiento y coordinación fuertemente consistentes en el borde. En esta charla, aprenderás sobre los Durable Objects, por qué son adecuados para casos de uso colaborativos y cómo construir aplicaciones multijugador con ellos!

28 min
14 Apr, 2023

Video Summary and Transcription

Los Durable Objects son parte del objetivo a largo plazo de CloudFlare para expandir las posibilidades de las aplicaciones en los workers, permitiendo la construcción de aplicaciones colaborativas escalables. Los Durable Objects proporcionan una forma de almacenar el estado global y coordinar aplicaciones multi-cliente. Pueden ser creados lo más cerca posible del usuario y tienen IDs únicos para el enrutamiento de solicitudes. Los Durable Objects tienen una API de almacenamiento persistente con semántica fuertemente consistente y compuertas de IO para prevenir errores de corrección. Son adecuados para aplicaciones colaborativas y pueden ser usados con WebSockets. El impacto en el rendimiento y las réplicas de lectura son consideraciones para acceder a los Durable Objects a nivel global.

Available in English

1. Introducción a los Durable Objects

Short description:

Soy Matt Alonzo, un ingeniero de software en CloudFlare. Trabajo en el equipo de datos distribuidos de los trabajadores y tengo una amplia experiencia con los durable objects. Los Durable Objects son parte del objetivo a largo plazo de CloudFlare para expandir las posibilidades de las aplicaciones en los trabajadores. No son solo un producto de almacenamiento, sino también ideales para construir aplicaciones colaborativas escalables como editores de documentos, servidores de juegos y salas de chat.

Soy Matt Alonzo y soy un ingeniero de software en CloudFlare. Trabajo en el equipo de datos distribuidos de los trabajadores que mantiene los durable objects. Trabajé en CloudFlare durante casi tres años y pasé casi todo el tiempo trabajando en durable objects. Estoy muy familiarizado con ellos. Y los durable objects son parte de un objetivo a largo plazo para CloudFlare donde estamos tratando de expandir los tipos de aplicaciones que los clientes pueden construir sobre los trabajadores. Y los durable objects se han pensado como una especie de producto de almacenamiento que se añade a esto. Puedes almacenar estado-en-el-borde en los durable objects, pero hay mucho más en ellos que solo eso. Los durable objects también son realmente adecuados para construir aplicaciones colaborativas infinitamente escalables como editores de documentos, servidores de juegos y salas de chat, y esta charla es toda sobre analizar por qué.

2. Resumen de Workers y Durable Objects

Short description:

Voy a hablar sobre los workers, dar un rápido resumen. Hablaré sobre los durable objects, su API y coordinación. Tengo un estudio de caso y una demostración. Workers es la plataforma de JavaScript sin servidor de Cloudflare. Utiliza su propio tiempo de ejecución y se ejecuta a nivel mundial. Está implementado con aislamientos V8, lo que permite una ejecución de código eficiente. Así es como los workers pueden existir hoy.

Si alguien tiene alguna pregunta después de la charla, no dude en enviarme un correo electrónico o contactarme en mis redes sociales. Y entonces, voy a tratar algunos temas hoy. Voy a hablar sobre los workers, dar un rápido resumen de ellos. Voy a hablar sobre los durable objects, qué son, cómo se ve la API y luego voy a hablar sobre la coordinación. ¿Por qué son útiles los durable objects para la coordinación? ¿Por qué querrías usarlos? Y luego tengo un poco de un case study, una aplicación que construí sobre los durable objects, y luego si todo va bien, haré una demostración de ella.

Y entonces, workers es la plataforma JavaScript serverless de Cloudflare. La idea es que escribas un manejador de fetch como este de arriba, que toma un objeto de solicitud, hace algún trabajo y devuelve una respuesta. Y entonces tomas tu code de worker, lo subes a Cloudflare, y nosotros nos encargamos del resto. Esto es bastante similar a muchas otras plataformas serverless, pero hay algunas grandes diferencias con los workers. Los workers usan su propio tiempo de ejecución, y los workers no se ejecutan en regiones. Realmente, solo hay una región con los workers. Es la Tierra. Despliegas una vez, y tu code se ejecuta en cualquiera de las ubicaciones de red de Cloudflare en todo el mundo. Cuando usas workers, tu dominio también está utilizando los productos CDN de Cloudflare, y por lo tanto las consultas DNS a tu dominio devuelven una IP Anycast de Cloudflare. Cuando envías tráfico a una IP Anycast en una de las de Cloudflare, va a ir al centro de datos de Cloudflare más cercano, sin importar dónde estés en el mundo. Y entonces esto significa que cuando haces una solicitud a un worker de Cloudflare, se va a ejecutar cerca de ti en el centro de datos de Cloudflare más cercano, sin importar desde dónde estés haciendo la solicitud. Y este mapa aquí es un mapa del último que pude encontrar de todas las ubicaciones de Cloudflare alrededor del mundo. Como puedes ver, es bastante difícil estar lejos de un lugar donde los workers pueden ejecutarse, a menos que estés en medio de la selva o algo así.

Y entonces una parte central de poder ejecutar code de esta manera en el borde de Cloudflare es la forma en que los workers están implementados es muy diferente de otras plataformas serverless. Tenemos nuestro propio tiempo de ejecución de JavaScript construido sobre V8. Y este es el mismo motor de JavaScript utilizado por Node.js y Chromium. Y en lugar de implementar la multi-tenencia iniciando múltiples instancias de tiempo de ejecución como funcionan otras plataformas serverless, lo que hacen los workers es que implementamos la multi-tenencia con aislamientos V8. Esta es una característica de V8 que te permite ejecutar code separado, todo en el mismo proceso. Y entonces ejecutamos el code de varios clientes en el mismo proceso del sistema operativo, todos corren en diferentes aislamientos, y están completamente aislados entre sí, no pueden interferir con cada uno, cambiar el estado global, o algo así. Y entonces los aislamientos son mucho más baratos de iniciar que todo un proceso del sistema operativo. Y entonces cuando una solicitud para un worker en frío llega al tiempo de ejecución del worker, detectamos un nuevo aislamiento. Y esto solo toma unos pocos milisegundos, en comparación con cientos de milisegundos para iniciar en frío todo un tiempo de ejecución. Y esto es realmente importante para los workers. No sería posible para nosotros ejecutar todo un tiempo de ejecución por cliente en el Edge. Esta idea es cómo los workers son capaces de existir hoy.

3. Introducción a los Durable Objects Continuada

Short description:

Antes de DribbbleObjects, los workers eran sin estado y carecían de una forma de almacenar el estado global. Los Durable Objects se introdujeron para abordar la necesidad de coordinación en aplicaciones multi-cliente. Los Durable Objects aplican la filosofía serverless del estado al permitir la división del cálculo en piezas de grano fino. Cada instancia de una clase Durable Object tiene un ID único, asegurando que las solicitudes de diferentes ubicaciones llamen al mismo FetchMethod en la misma instancia del objeto.

Y así, quiero volver a este ejemplo de cómo se ve un worker normal. Así puedo ver el hueco que DribbbleObjects llenó. Antes de que DribbbleObjects existiera, los workers eran completamente sin estado. Si miras este code fragmento, no hay dónde almacenar el estado global. Puedes lanzar cosas en el ámbito global, pero el 99% del tiempo, no es lo que quieres. Porque los workers se ejecutan en tantos lugares alrededor del mundo, y cada uno de estos lugares tiene cientos de servidores.

Cuando tu worker se está ejecutando, está recibiendo tráfico de muchos lugares, tienes toneladas y toneladas de instancias de tu worker. Y todas van a tener ámbitos globales completamente separados. Así que almacenar data en el ámbito global no es una solución para realizar la coordinación. Pero todas estas diferentes instancias son realmente buenas para la scaling. Y en conjunto, pueden manejar una gran cantidad de rendimiento. Y así, los DribbbleObjects fueron una solución para poder ejecutar cargas de trabajo que necesitan realizar coordinación.

¿Y qué quiero decir cuando digo coordinación? La coordinación es lo que hace útiles a las aplicaciones multijugador. Y las aplicaciones multijugador son aplicaciones que tienen múltiples clientes conectándose a la aplicación para realizar una tarea juntos. Piensa en personas colaborando en un documento, jugando un juego juntos, o chateando en un chat. Y todas estas aplicaciones, lo que tienen en común es que todas tratan sobre el estado. Todos los clientes están enviando actualizaciones de estado a la aplicación, y la aplicación es responsable de asegurarse de que esas actualizaciones de estado se reflejen en otros clientes y este estado es de larga duración y necesita ser procesado a través de múltiples solicitudes.

Y entonces, ¿qué son los Durable Objects? Diría que un Nokia 3310 antes de mi tiempo, pero definitivamente parece bastante duradero aquí. Pero realmente lo que son es aplicar la filosofía serverless del estado. El cálculo serverless trata de dividir el cálculo en piezas de grano fino que son fáciles de activar según sea necesario, como en cada solicitud entrante. Los Durable Objects toman este concepto y lo aplican al estado y la coordinación. Con los workers normales, escribes tu FetchHandler y el tiempo de ejecución lo invoca por solicitud, y implementa alguna lógica sin estado.

Con los Durable Objects, escribes una clase Javascript con el método FetchHandler, y este FetchHandler se invoca en instancias de esa clase, en lugar de un método Fetch que se llama en este objeto Handler, como con un worker normal. Con los Durable Objects, todavía hablan HTTP como los workers normales, y el FetchHandler todavía se invoca en cada solicitud entrante, pero no son enrutables desde el internet público. En cambio, cada instancia de una clase Durable Object tiene un ID asociado con ella. Esto permite a los workers que conocen el ID de esa instancia de Durable Object enviar solicitudes a ella. La plataforma garantiza que este ID identifica una única instancia en todo el mundo. Cuando esta instancia es única, no vas a obtener diferentes instancias con el mismo ID. Si varios workers envían una solicitud al mismo ID de Durable Object desde diferentes ubicaciones en el mundo, todas esas solicitudes terminan llamando al mismo FetchMethod en la misma instancia del objeto.

Aquí hay un ejemplo de cómo se ve esta API para los Durable Objects.

4. Vinculación de Worker y Ubicación de Durable Object

Short description:

Para que un worker envíe una solicitud a un Durable Object, necesita una vinculación a él. El tiempo de ejecución dirige la solicitud al Durable Object en función de su ubicación. Los Durable Objects pueden crearse lo más cerca posible del usuario. Hay dos tipos de ID para Durable Objects: ID únicos y ID nombrados. Los ID únicos son simples de manejar, mientras que los ID nombrados requieren un proceso más complejo. El proceso implica el hashing del ID nombrado para determinar la ubicación del Durable Object y dirigir la solicitud en consecuencia. El punto de coordinación almacena la ubicación, permitiendo que las solicitudes posteriores procedan directamente al objeto.

Para que un worker envíe una solicitud a un Durable Object determinado, tiene que tener una vinculación a él. Esta vinculación aparece en el objeto env que se pasa a cada solicitud entrante a un worker. Este objeto env se utiliza para crear un ID. Puedes crear un subobjeto utilizando ese ID, y así es como envías solicitudes a un Durable Object.

Cuando haces eso, el tiempo de ejecución dirigirá la solicitud al Durable Object, dependiendo de dónde se encuentre en el mundo, y se encargará de encontrar esa ubicación y toda la ruta. Así que una parte importante de los Durable Objects es que cuando creas uno por primera vez, son creados lo más cerca posible de ti. Así que hay un subconjunto de centros de datos de Cloudflare que soportan la ejecución de Durable Objects. Y cuando tenemos una solicitud para un nuevo objeto, necesitamos averiguar en cuál de estos centros de datos vamos a ejecutar ese Durable Object. Y la respuesta a eso es que depende de cómo lo hagamos.

Y la razón de esto es que hay dos tipos de ID para Durable Objects. Puedes crear un ID único, que es una cadena generada aleatoriamente, o puedes crear un ID basado en una cadena, como en este ejemplo aquí. Y con los ID únicos, averiguar la ubicación del objeto es realmente simple. No puedes hacer dos números generados aleatoriamente que sean idénticos si son de suficiente longitud, así que puedes añadir algunos metadatos extra al ID y hacer que estos metadatos codifiquen donde se encuentra originalmente el objeto. Pero para los ID nombrados, no puedes hacer esto porque quieres que varias personas puedan usar el mismo ID y obtener el mismo objeto. Y así que hacemos algo un poco más complejo.

Esta es una imagen de cómo se ve el proceso si varios workers intentan crear el mismo Durable Object con el mismo ID al mismo tiempo. Uso códigos de aeropuerto para nombrar todas estas ubicaciones porque soy un nerd de la infraestructura, pero están funcionando en Virginia, Nueva Jersey, Ámsterdam y Francia. Y todos estos workers, intentan crear un Durable Object con el ID Bob. Y Bob, este ID nombrado, en realidad tiene un... Hashes a una ubicación. Y esta ubicación particular se utiliza como un punto de coordinación para determinar dónde vamos a poner ese Durable Object. Y en este caso, Bob hace hash al DFW, Dallas-Fort Worth. Y así que todos los tiempos de ejecución involucrados aquí saben que Bob hace hash a Dallas-Fort Worth, y ellos necesitan tomar esta solicitud de Durable Object y enviarla a Dallas-Fort Worth. La primera solicitud que llega allí va a ser utilizada para tomar la decisión de ubicación. En este caso, probablemente sea la de Virginia porque Virginia está más cerca de Dallas. Y así que el punto de coordinación almacena que Bob va a estar en Virginia y lo pone en el Centro de Datos IAD en Virginia. Y así que este punto de coordinación en realidad tiene que ser comprobado para más solicitudes a Bob en algunos casos. Pero la gran mayoría de las veces, vamos a almacenar en caché la ubicación de un objeto. Y así que si estás usando un objeto más de una vez, la caché va a estar caliente y no vas a tener que comprobar el punto de coordinación extra y tu solicitud puede proceder directamente a donde se encuentra el objeto DERVL. Y así que ahora tenemos este concepto de una instancia de objeto que es globalmente direccionable y es única, y podemos enviar solicitudes a ella.

5. Uso de Objetos DERVL y API de Almacenamiento

Short description:

Y esto es una distracción realmente, realmente útil. Cuando escribes un objeto en los objetos DERVL, tomas el estado de tu aplicación y encuentras la unidad lógica más pequeña. Implementas una clase de objeto DERVL que define el comportamiento común. Cada instancia de objeto tiene acceso a una API de almacenamiento persistente específica para ella. La API de almacenamiento tiene semánticas fuertemente consistentes y está ubicada junto a cada instancia de objeto. El backend de almacenamiento tiene una capa de caché en proceso, lo que hace que las lecturas sean muy rápidas. La API de almacenamiento y los objetos Drupal tienen una característica llamada IO Gates que previene errores de corrección. Hay puertas de entrada y puertas de salida, que impiden que se entreguen nuevos eventos al objeto mientras está esperando en el almacenamiento.

Y esto es una distracción realmente, realmente útil. Y la forma en que lo usas es cuando escribes un objeto en los objetos DERVL, tomas tu aplicación y encuentras la unidad lógica más pequeña. Piensa en salas de chat en una aplicación de mensajería o documentos en un editor colaborativo. Y una vez que tienes una idea de cómo deberían verse tus objetos, implementas una clase de objeto DERVL que define el comportamiento común. Y dado que creamos una instancia real de JavaScript usando tu clase de objeto DERVL, puedes almacenar un estado transitorio como miembros de esa clase. Y con la id asignada a cada instancia de objeto, puedes enviar eficazmente solicitudes a un subconjunto particular de tus data y realizar operaciones en él localmente.

Así que esta instancia de objeto que creamos por id es de larga duración hasta cierto punto. Si tu instancia de objeto está recibiendo solicitudes de manera regular o tiene una conexión WebSocket activa, permanecerá viva. Una vez que deja de recibir solicitudes, las conexiones WebSocket están presentes, se irá a dormir. Y también necesitamos una solución para cómo vamos a almacenar data una vez que el objeto se va a dormir. Así que necesitamos soportar eso. Hay una API de almacenamiento persistente como parte de los objetos Drupal. Y cada instancia de objeto tiene acceso a esta API. Y el almacenamiento dentro de ella es específico para cada instancia de objeto. Y la API de almacenamiento parece una API de clave-valor. Tiene semánticas fuertemente consistentes. Y el almacenamiento está ubicado junto a cada instancia de objeto. Y hay una capa de caché en proceso frente a nuestro backend de almacenamiento. Así que las lecturas al almacenamiento suelen estar en caché, y son muy, muy rápidas.

Y este fragmento es un ejemplo de uso de esa API para implementar un contador atómico. Y las personas que han estado leyendo el fragmento probablemente tienen alarmas sonando en su cabeza. Esto es arriesgado. No estoy esperando mis puestas. Esto parece realmente, realmente mal. Y en los objetos Drupal, este code es completamente correcto. La API de almacenamiento y los objetos Drupal tienen una característica llamada IO Gates. Y lo que hacen las IO Gates es que te previenen de cometer errores de corrección que son muy fáciles de cometer en las aplicaciones actuales. Y lo hacen con dos, es IO, así que hay dos tipos de puertas. Hay puertas de entrada y puertas de salida. La puerta de entrada se cierra cuando, y previene la entrega de nuevos eventos entrantes al objeto siempre que el objeto está esperando en el almacenamiento.

6. Puertas de Entrada y Salida en Objetos Duraderos

Short description:

En este ejemplo, las puertas de entrada y salida evitan problemas de concurrencia y garantizan un almacenamiento de datos consistente. La API de Almacenamiento no es el foco de esta masterclass, pero hay una publicación de blog disponible para obtener más información.

Entonces, en este ejemplo aquí, cuando hacemos este get, es imposible que se entregue un nuevo evento al objeto y que otro evento pase y haga ese get al mismo tiempo, evitando que dos gets se ejecuten simultáneamente y obtengan el mismo valor y luego escriban los mismos incrementos de valor en el almacenamiento. Eso haría que este contador atómico solo se incrementara una vez para dos solicitudes en lugar de dos veces. Así que las puertas de entrada evitan ese problema. Las puertas de salida hacen algo diferente. Evitan cualquier mensaje de red saliente de los objetos duraderos cuando el objeto duradero está esperando que se completen sus escrituras de almacenamiento. Así que te impiden tener cualquier cliente de tu objeto duradero tomando algún tipo de decisión basada en información desactualizada que no ha, o basada en información no confirmada que no ha sido persistida en el almacenamiento. No voy a profundizar demasiado en la API de Almacenamiento ya que tenemos una publicación de blog realmente genial sobre ella y no es el foco de la masterclass. Pero la gente puede buscar eso y preguntarme el nombre de la publicación del blog después de la masterclass si tienes curiosidad.

7. Objetos Duraderos para Aplicaciones Colaborativas

Short description:

Los Objetos Duraderos son muy adecuados para aplicaciones colaborativas, proporcionando un único punto de coordinación entre múltiples clientes. Esto elimina la necesidad de despliegues multi-región complejos y enrutamiento. Tomemos el ejemplo de un editor de documentos colaborativo donde múltiples clientes están enviando ediciones. Los Objetos Duraderos manejan la coordinación para tales aplicaciones, permitiendo una arquitectura simple y fácil de razonar. Otro ejemplo es una versión multijugador del Juego de la Vida de Conway implementado usando Objetos Duraderos.

Así que he estado hablando un poco ahora sobre los objetos duraderos, cuál es la superficie de la API y las características, pero aún no he entrado en por qué son tan adecuados para aplicaciones colaborativas. Y esta abstracción de una instancia de objeto que puedes crear a demanda es realmente útil para crear puntos únicos de coordinación entre múltiples clientes y para crear ese punto de coordinación cerca de esos clientes. ¿Y cómo se ve esto en la práctica? Imagina que estás construyendo un editor de documentos colaborativo y tienes múltiples clientes y todos están enviando ediciones, pulsaciones de teclas a la aplicación y la aplicación necesita decidir cuáles de estas pulsaciones de teclas van a ir a dónde, especialmente si estás editando la misma frase, necesitas samba-grate entre los dos clientes qué letras van a ir a dónde.

Y el enfoque simple aquí es tener un único punto de coordinación para determinar esto. Puedes hacerlo de otras maneras, hay CRDTs y cosas así, pero no funciona para cada modelo de data y así que me voy a centrar en un único punto de coordinación en esta charla. Y así para la mayoría de los desarrolladores, una arquitectura como esta donde tienes un único punto de coordinación para implementar la lógica de tu aplicación es realmente difícil de hacer. Necesitas hacer un despliegue multi-región, necesitas averiguar el enrutamiento, y si estás almacenando data, tienes que manejar la replicación y la lógica de failover y esto es algo que es muy difícil de hacer en muchas ubicaciones alrededor del mundo. Y los Objetos Duraderos resuelven este problema por completo. Llegas a tener tu simple, fácil de razonar sobre el pastel de un único punto de coordinación y llegas a comértelo también sin preocuparte por las operaciones y el enrutamiento.

Así que vamos a pasar por otro ejemplo. Digamos que estoy escribiendo un documento sobre mis lugares favoritos de barbacoa en Texas. Este es un tema bastante polémico, así que imagino que alguien va a querer discutir conmigo sobre ello. Así que estoy escribiendo mi lista, digamos que estoy en casa en Austin y me estoy conectando a un trabajador en el centro de datos de DFW y estoy enviando todas mis ediciones y ese trabajador va a obtener un Objeto Duradero con un ID basado en el nombre de mi documento, eso es Barbacoa en Texas, y va a enviar todas mis ediciones a ese objeto. Y le digo a mi amigo, de vuelta de donde soy originalmente en Miami, él visitó recientemente y tiene algunos desacuerdos conmigo sobre qué restaurantes de barbacoa le gustan. Y así que él empieza a hacer sus propias ediciones, se conecta al mismo documento. Y como ambos estamos usando el mismo ID, ambos vamos a conectarnos al mismo Objeto Duradero y este Objeto Duradero manejará toda la coordinación para ese documento. Tengo un ejemplo más concreto aquí. Para esta charla, construí una especie de aplicación de demostración basada en Objetos Duraderos que implementa el Juego de la Vida de Conway. Y versión multijugador donde varias personas pueden conectarse y añadir cosas a la simulación. Y si no estás familiarizado con el Juego de la Vida de Conway, es un autómata celular, es un tipo de simulación de rejilla. Y tiene reglas definidas para cuándo las celdas en la rejilla deben ser consideradas vivas, como coloreadas de negro o muertas coloreadas de blanco. Y para el Juego de la Vida de Conway, las reglas son las siguientes. Cualquier celda con dos o tres vecinos vivos vive hasta el siguiente tick. Cualquier celda muerta con tres vecinos vivos se vuelve viva y luego todas las demás celdas vivas morirán y todas las demás celdas muertas permanecerán muertas. Estas reglas se aplican para cada rejilla individual, cada celda en la rejilla en cada tick individual y cada tick ocurre en un ritmo regular, digamos 500 milisegundos. Y así es como implementé esto con dos clases de Objetos Duraderos. Hay una clase de Objeto Duradero de Lobby que almacena una lista de IDs de Objetos Duraderos de Sala de Juego. Y así cuando un cliente se conecta a la aplicación, ve la página del Lobby y hay una lista de salas de juego. Así que elige una sala de juego y esa sala de juego tiene un ID de Objeto Duradero para un Objeto Duradero específico para esa sala de juego. Y el cliente usa eso para conectarse al juego y luego empieza a enviar actualizaciones de qué celdas coloca en el juego.

8. WebSockets, Objetos Duraderos y Modelo de Precios

Short description:

Todo esto ocurre a través de WebSockets, los workers reenvían las conexiones a los objetos duraderos. La sala de juegos ejecuta la simulación del Juego de la Vida de Conway, enviando losetas vivas a los clientes. Los objetos duraderos pueden funcionar en varios centros de datos a nivel mundial. Miles de personas pueden jugar al Juego de la Vida de Conway en salas separadas. Hay una demostración disponible para que los usuarios la prueben. El modelo de precios para los objetos duraderos se basa en la duración de la solicitud activa. Es rentable cuando se crean objetos a nivel mundial. Cada objeto duradero es un único hilo de ejecución de JavaScript.

Y todo esto sucede a través de WebSockets, los workers son capaces de reenviar una conexión WebSocket que ha sido enviada al worker al objeto duradero al que se conecta y todas estas losetas de la cuadrícula se pasan por WebSocket. Llegan a la sala de juegos y la sala de juegos está ejecutando la simulación real del Juego de la Vida de Conway. Y procesa todas las reglas a un ritmo regular y luego envía las losetas vivas reales cada vez que ha tenido lugar una nueva generación y las envía a todos los clientes conectados.

Y uno puede imaginar que esto sucede, vaya, este mapa es difícil de ver, uno puede imaginar que esto sucede en todo el mundo. Los Objetos Duraderos pueden funcionar en un subconjunto bastante grande de los centros de datos que opera Cloudflare. Ahora mismo, esto es principalmente en la costa este y oeste de los Estados Unidos, y en Europa oriental y occidental, y en Asia y el sudeste asiático, y no hay límite para el número de Objetos Duraderos que puedes crear. Así que con esta simple aplicación que tiene unas pocas líneas de código, puedes tener miles y miles y miles de personas jugando al Juego de la Vida de Conway unas con otras en salas separadas.

Y entonces, en realidad tengo una demostración de esto. Voy a abrir esto. Creo que el Wi-Fi aquí ha sido lo suficientemente bueno para permitir a la gente conectarse y probarlo. Así que, aquí, déjame mover esta ventana. Bien, así que si escaneas los códigos QR en la pantalla, deberías terminar en la misma página en la que estoy yo. Voy a hacer una sala de Congreso de Node, y voy a crear un juego, y vamos a unirnos. Y entonces, si colocas una sola loseta en la cuadrícula aquí, realmente no va a hacer nada. Necesitas colocar unas pocas. La forma aquí se llama un planeador, y debería moverse a través de la cuadrícula, y entonces, si hago clic en enviar celdas aquí en la parte inferior, va a enviarlo a través, y entonces, si otras personas se conectan, y colocan algunas losetas y las mueven, deberían aparecer en la pantalla, y deberías ver la misma simulación en el dispositivo que estés usando que lo que estás viendo aquí. Y toda esta simulación está teniendo lugar en un solo objeto duradero que ha sido creado cerca de nosotros. De memoria, creo que el centro de datos de objetos duraderos más cercano aquí está en Ámsterdam, y entonces, esto está funcionando en algún lugar de Ámsterdam en una máquina en un edificio de hormigón. Y, sí, eso es prácticamente mi charla, la dejaré funcionar un poco para que la gente pueda jugar con ella. Sí, espero que a la gente le guste esto. Esta es mi primera charla, así que estoy bastante emocionado por ello. Sí, eso es todo por mi parte.

Entonces, voy a hacer la pregunta literalmente y podría cambiarla un poco. Entonces, la pregunta es, ¿puedes entrar en el modelo de precios de usar objetos duraderos en producción? ¿Cuál sería un buen caso de uso donde los objetos duraderos son una solución más barata? No necesitamos entrar en el modelo de precios quizás en gran profundidad, pero vale la pena señalar, ¿dónde es esto una solución realmente viable? Entonces, con los objetos duraderos, el verdadero caso de uso clave es si quieres crear todos estos objetos alrededor del mundo, y sería realmente caro para ti ejecutar la infraestructura tú mismo. El modelo de precios se basa en la duración del reloj de cuando el objeto duradero está manejando una solicitud activa. Y entonces, si tu objeto duradero está manejando una solicitud, se te factura por ese tiempo, una vez que devuelve la respuesta, ya no se te factura. Entonces, sí, así es como funciona el modelo de facturación. ¿Hay momentos en los que no es, sabes, piensas, probablemente esta no es la solución correcta para un proyecto dado. Cada objeto duradero individual es un único hilo de ejecución de JavaScript, y entonces si tus objetos duraderos individuales necesitan manejar una cantidad significativa de carga, probablemente no sea el caso de uso correcto para ti. Es realmente mejor para cuando puedes dividir tu aplicación en muchos objetos duraderos, y en conjunto, tienes mucha carga, pero los objetos duraderos individuales no están tan ocupados.

9. Impacto en el Rendimiento y Réplicas de Lectura

Short description:

Los objetos duraderos se ejecutan en un solo centro de datos, por lo que acceder a ellos desde el otro lado del mundo puede resultar en una alta latencia. Crear objetos duraderos para la coordinación en lugar de reutilizarlos puede ayudar a localizarlos. Sin embargo, si estás utilizando objetos duraderos para datos de larga duración, tendrás que lidiar con la latencia de las solicitudes que atraviesan el mundo. Se están considerando las réplicas de lectura para proporcionar una vista más cercana de los datos almacenados.

Genial. Y, creo que ya has cubierto esto varias veces, pero haré la pregunta, ya que los objetos duraderos se ejecutan en un solo data centro, ¿cuáles son los impactos en el performance cuando se invocan desde el otro lado del mundo? Entonces, desafortunadamente, todavía tenemos que lidiar con la velocidad de la luz, así que si estás accediendo a un objeto duradero desde el otro lado del mundo, vas a tener una alta latencia. La forma de evitar esto es intentar crear objetos duraderos cada vez que necesites tener un punto de coordinación en lugar de reutilizarlos, y de esa manera, si todos tus clientes para una cosa particular que estás tratando de coordinar están en el mismo lugar, tus objetos deberían estar ubicados cerca de ellos, pero si no puedes evitar esto, los estás utilizando como un único punto de prueba o data de larga duración, desafortunadamente, no hay nada que puedas hacer. Tu solicitud tendrá que atravesar el mundo. Estamos considerando agregar réplicas de lectura, así que al menos podrás obtener una vista obsoleta de cualquier data almacenada en tus objetos duraderos, y eso podría estar ubicado más cerca de ti, pero no es algo que la plataforma soporte hoy.

QnA

Puerta de Salida de Objetos Duraderos y Deno KV

Short description:

La puerta de salida de los Objetos Duraderos tiene un tiempo de espera y puede fallar si la escritura de almacenamiento tarda demasiado. El código del usuario no puede cerrar manualmente la puerta de salida. Los Objetos Duraderos y Deno KV son diferentes en términos de función sin servidor y coordinación de almacenamiento. No hay límite para el tamaño de almacenamiento de los Objetos Duraderos individuales. No se pueden garantizar las características de rendimiento debido a las actualizaciones regulares y las prioridades de seguridad. Las conexiones WebSocket en Objetos Duraderos se tratan de la misma manera que las solicitudes HTTP, utilizando un formato RPC interno.

Um, ¿qué pasa si tienes alguna salida de objetos duraderos siempre ocupada, ¿entonces se retrasará o fallará al responder a la solicitud entrante? Creo que esta pregunta se refiere a la característica de la puerta de salida. Esta, la puerta de salida tiene un tiempo de espera, por lo que si la escritura de almacenamiento está tardando más de 10 segundos, esa es una de las muchas formas en que la puerta de salida puede fallar, por lo que si es una solicitud de almacenamiento subyacente que falla, o ese tiempo de espera se agota, la puerta de salida se romperá. Y esto simplemente reinicia el objeto, y cualquier cliente conectado debería entonces reconectarse a él, puedes hacer que empiece de nuevo. Realmente no hay una forma para que el usuario code cierre manualmente la puerta de salida y evite que salgan los mensajes salientes. Puedes controlar manualmente la puerta de entrada, no tengo un ejemplo de eso aquí, pero no es algo que la mayoría de las aplicaciones utilicen.

Interesante, genial. Esta pregunta surgió varias veces, como estoy seguro de que esperabas en muchas forms, pero ¿podrías explicar brevemente la diferencia entre los Objetos Duraderos y Deno KV? Así que Deno KV, por lo que entiendo, es un almacén de data al que accedes desde una función serverless sin estado, y Deno KV se replica en todo el mundo, por lo que no, es muy diferente de los Objetos Duraderos, donde los Objetos Duraderos tienes una función serverless específica que es específica para algún almacenamiento, y esa función serverless se ejecuta justo al lado del almacenamiento. Creo que Deno KV, desde el lado del almacenamiento duradero de los Objetos Duraderos, es un producto bastante similar, pero para hacer la coordinación en el borde, hasta donde puedo decir, no creo que tengan, hay una forma de dirigirse a una instancia específica para hacer la coordinación en memoria. Sí, esa surgió de varias maneras diferentes.

¿Cuál es el tamaño máximo para un Objetos Duraderos? ¿Esto es? No hay un límite para la cantidad de almacenamiento que un Objetos Duraderos individual puede almacenar. Tenemos un límite para cada clase de cuánta data puede almacenar toda una clase. No lo recuerdo de memoria. Ha pasado un tiempo desde que he mirado los límites de uso. Hay límites en los tamaños de valor individuales. Creo que los valores son de unos pocos megas, y las claves están en el rango de dos a cuatro kilobytes. Genial. Nos estamos quedando cortos de tiempo. Veamos qué otras preguntas podemos responder. ¿Tienen garantizadas las características de performance ya que la facturación depende del tiempo de reloj? No lo hacemos, desafortunadamente. Este es un problema realmente difícil de resolver cuando estás haciendo facturación en tiempo real porque actualizamos, como, el tiempo de ejecución de los trabajadores en un ritmo regular. Así que, siempre estamos al día con las actualizaciones de V8. Estamos siguiendo, como, el canal de lanzamiento beta de Chromium. Y entonces, digamos que surge un problema de security en V8, por lo que tenemos que actualizarlo, y luego hay una degradación de performance en ese nuevo lanzamiento. No hay nada que realmente podamos hacer allí. Necesitamos priorizar la security, y entonces, si tuviéramos alguna garantía en torno a la facturación, no podríamos garantizar esas en presencia de tener que hacer una actualización forzada como esa porque no estamos 100% en control del tiempo de ejecución de tu objeto.

Vale. ¿Las conexiones WebSocket anularían o reducirían en gran medida las ventajas de Edge, en términos de velocidad? No estoy seguro de entender completamente esta pregunta. WebSocket, quiero decir, internamente para los objetos duraderos, los mensajes de WebSocket y las solicitudes HTTP normales se tratan de la misma manera. En realidad no usamos HTTP como transporte bajo el capó. Todo se convierte en un formato RPC interno y se proxy a través de eso.

WebSockets, HTTP, Código de Demostración y Conclusión

Short description:

No hay diferencia entre WebSockets y HTTP en términos de rendimiento para objetos duraderos. Estamos trabajando en abordar la diferencia de facturación. El código para la demostración se publicará en Twitter después de la conferencia. Gracias por una gran charla.

Entonces, realmente no hay diferencia entre WebSockets y HTTP en términos de performance características para objetos duraderos. Existe una diferencia de facturación en la que estamos trabajando actualmente para abordar, pero eso debería eliminarse muy pronto.

Genial. Y la última pregunta es, ¿está disponible el code para esa demostración? Lo publicaré en mi Twitter después de la conferencia. Necesito hacer una limpieza de eso. Soy más desarrollador de C++ que de JavaScript. Probablemente soy el desarrollador de JavaScript más JavaScript en unos 10 años. Así que todos pueden decirme lo malo que es en Twitter. Nadie te va a decir lo malo que es en Twitter, pero sí publícalo, estaríamos muy interesados en verlo.

Muchas gracias por una gran charla. Realmente disfruté charlando aquí en la Q&A.

Check out more articles and videos

We constantly think of articles and videos that might spark Git people interest / skill us up or help building a stellar career

React Advanced Conference 2021React Advanced Conference 2021
36 min
Living on the Edge
React 18 introduces new APIs for rendering applications asynchronously on the server, enabling a simpler model for architecting and shipping user interfaces. When deployed on edge networking platforms like Cloudflare Workers, we can get dramatic performance and user experience improvements in our applications. In this talk, Sunil will demo and walk through this new model of writing React applications, with some insight into the implications for data fetching, styling, and overall direction of the React ecosystem.
Node Congress 2022Node Congress 2022
31 min
Database Access on the Edge with Cloudflare Workers & Prisma
Edge functions are pushing the limit of serverless computing – but with new tools, come new challenges. Due to their limitations, edge functions don't allow talking to popular databases like PostgreSQL and MySQL. In this talk, you will learn how you can connect and interact with your database from Cloudflare Workers using the Prisma Data Proxy.
You can check the slides for Alex's talk here. 
Node Congress 2022Node Congress 2022
30 min
Static first websites with Cloudflare Workers
Static websites give you all sorts of great benefits. You don’t have to worry about security or scalability. They are simple to cache, cheap to host and a breeze to maintain! But sometimes I miss all the fun things you can do with just a little bit of state! Combining the Cloudflare Pages platform with Durable Objects and the HTMLRewriter API, you can have your cake and eat it too! We’ll replicate a full WordPress experience with comments, top posts, like buttons and a page counter. All on Cloudflare’s free static site hosting platform.
You can check the slides for Jonathan's talk here.
React Advanced Conference 2022React Advanced Conference 2022
9 min
Building full-stack applications on the Edge
Scaling and maintaining applications can be a pain, especially when thinking of how to build to get the user experience to a level that you are proud of. With all these shifting parts to consider, it is important to abstract parts of your applications to global reliable services. In this talk, we will discuss some of the services that Cloudflare provides, and the role they play in improving the overall developer and user experience.

Workshops on related topic