Combine es un framework de Apple presentado en WWDC 2019. El framework proporciona una API Swift declarativa para procesar valores a lo largo del tiempo. Entonces, ¿Qué puedo hacer: comenzar a usar este framework o seguir con RxSwift?
SwiftUI es el futuro del desarrollo de aplicaciones de Apple y hace un uso intensivo de este framework de Swift. Además, muchos frameworks de sistemas proporcionan capacidades de observación a través de este framework.
¿Por qué usar Combine? O ¿Por qué seguir usando RxSwift?
¿Cuál de los dos será mejor? ¿Qué significa en realidad? ¿Por qué usar Combine? O ¿Por qué usar RxSwift? Los desarrolladores ciertamente están expuestos a estas interrogantes.
El framework Combine se presentó en WWDC2019. Es un framework muy similar a RxSwift. Apple describe este framework como:
Una API declarativa de Swift para procesar valores a lo largo del tiempo.
Esto debería sonar familiar; mira cómo ReactiveX (el proyecto principal de RxSwift) se describe a sí mismo:
Una API para programación asincrónica con flujos observables.
En ambos casos, se dice lo mismo. Es solo que la descripción de ReactiveX usa términos específicos. Se puede reformular de la siguiente manera:
Una API para programación asincrónica con valores a lo largo del tiempo.
¿Qué es combine?
Este framework se puede comparar con frameworks como RxSwift y ReactiveSwift (formalmente conocido como ReactiveCocoa). Permite escribir código reactivo funcional al proporcionar una API Swift declarativa.
Los lenguajes de programación reactiva funcional (FRP) permiten procesar valores con el tiempo. Los ejemplos de este tipo de valores incluyen respuestas de red, eventos de interfaz de usuario y otros tipos de datos asincrónicos.
A continuación, se detallan las principales semejanzas y diferencias:
Editores y suscriptores
El framework de Apple tiene Editores y suscriptores:
- Los Editores (Publishers) equivalen a los Observables en RxSwift
- Los Suscriptores (Subscribers) equivalen a los Observadores en RxSwift
Distintos nombres con el mismo propósito.
Manejo de memoria
RxSwift viene con DisposeBag y Combine viene con AnyCancellable. Esta clase llama cancel() a deinit y se asegura de que las suscripciones no finalicen antes de tiempo. Sin implementar esto, puede terminar con ciclos de retención.
Manejo de errores
Aquí radica la dramática diferencia entre los dos frameworks.
En Swift, todos los errores pueden rastrearse eventualmente hasta uno solo protocol Error. Este protocolo es básicamente solo un marcador; no lleva consigo ninguna funcionalidad particular.
Cuando se trata de Observables / Publishers, hay dos enfoques básicos entre los que los diseñadores de API pueden elegir:
- Suponer que cada transmisión puede terminar en un Error, y no ser específico sobre qué tipo de transmisión de Errores.
- Especificar por adelantado con precisión qué tipo de Error puede emitirse.
Manejo de errores en RxSwift
En RxSwift (toma el primer enfoque), cada flujo puede tener errores con cualquier tipo de error.
Naturalmente, la ventaja de esto es una cantidad dramáticamente reducida de contabilidad. No necesita preocuparse por especificar qué tipo de error puede ser emitido, porque la respuesta se asume: cualquier Error puede ser emitido.
Sin embargo, eso también hace un poco más difícil entender qué puede salir mal, o quizás, cómo puede salir mal.
Literalmente cada error en Swift es también un error. Por lo tanto, es (desde la perspectiva de un sistema tipo) posible que cualquier error sea emitido desde cualquier secuencia.
Manejo de errores en Combine
Es fácil adivinar lo que pasa al otro lado de la valla.
En el framework de Apple, cada Observable debe especificar el tipo de error exacto por adelantado.
Esto lleva a un poco más de contabilidad; cada vez que se crea un Observable también se debe especificar qué tipo de Error podría emitir ese Observable.
La ventaja aquí es que sabes exactamente qué tipo de Error puede ser emitido. Si no es un tipo preciso, en el peor de los casos, una jerarquía de tipos donde se conoce la base. Eso mejora tanto el razonamiento local, como el significado semántico.
Además, se puede engañar de un par de maneras diferentes. No hay nada que le impida especificar el tipo de Error como… bueno… Error. Eso nos sitúa básicamente en el mundo de RxSwift: una transmisión que puede emitir cualquier Error.
Además, uno puede realmente hacer trampa usando un tipo especial en Swift: Nunca (Never).
Never es un tipo especial que, por diseño, nunca puede ser instanciado. (Entre bastidores es una enumeración que no tiene casos).
Si el tipo de error en un Observable es Never, ¿adivina con qué frecuencia puede equivocarse ese Observable? Ni una sola vez. Ni siquiera un poco.
Rendimiento
RxSwift es un software bastante optimizado y da buen rendimiento cuando se usa correctamente.
Pero Combine establece nuevos estándares. Es una bestia de rendimiento, que se diseñó teniendo en cuenta el rendimiento. Ofrece enormes beneficios de rendimiento, las pruebas indican mayor transferencia de datos (en promedio 40%) al usarlo correctamente.
Contrapresión(Backpressure)
¿Contrapresión? La contrapresión permite que los componentes que no pueden consumir elementos sean lo suficientemente rápidos como para comunicar su situación a sus componentes mediante el envío de un parche o corrección (upstream, “aguas arriba”). Esto evita que en los componentes bajo estrés caigan mensajes de forma incontrolada o fallen de manera catastrófica.
Esto permite manejar esta situación y reducir la carga para los componentes consumidores. Esto evita que en los componentes bajo estrés caigan mensajes de forma incontrolada o fallen de manera catastrófica.
RxSwift no admite contrapresión, mientras que el framework de Apple soporta backpressure out of the box.
¿Cuándo debo usar Combine?
Al adoptar Combine, hará que su código sea más fácil de leer y mantener, centralizando su código de procesamiento de eventos y eliminando técnicas problemáticas como cierres anidados y devoluciones de llamadas basadas en convenciones.
Conclusión
No hay muchas diferencias entre RxSwift y Combine. El framework Apple está inspirado en Rx. Es igual de poderoso que RxSwift y más eficiente.
Permite a los desarrolladores expresar fácilmente flujos de datos (asíncronos), evaluarlos automáticamente y propagar los cambios de datos. Su complicado código de procesamiento de eventos se vuelve más fácil de leer y mantener.
De alguna manera, el framework de Apple es aún más fácil de entender y usar, por ejemplo, utiliza una combinación de metáforas más significativa de «suscribirse» a «editores» y no requiere DisposeBags.
Combine y RxSwift solo son un caso en donde el delta es simplemente eso: una diferencia. Decir si uno es mejor o peor que el otro dependerá del tipo de desarrollador: Algunos podrían comenzar a usar Combine, mientras que otros seguirán usando RxSwift.
¿Qué te pareció el artículo? ¿Te gustaría dejarme comentario? Ah, y si te ha gustado no te olvides de compartirla 😄