En esta página se ofrecen prácticas recomendadas para desarrollar y probar tu flujo de procesamiento de Dataflow.
Información general
La forma en que se implementa el código de tu flujo de procesamiento influye significativamente en el rendimiento del flujo en producción. Para ayudarte a crear código de canalización que funcione correctamente y de forma eficiente, en este documento se explica lo siguiente:
- Ejecutores de la canalización para admitir la ejecución de código en las diferentes fases de desarrollo e implementación.
- Entornos de implementación que te permiten ejecutar flujos de trabajo durante el desarrollo, las pruebas, la preproducción y la producción.
- Código y plantillas de canalizaciones de código abierto que puedes usar tal cual o como base para crear nuevas canalizaciones y acelerar el desarrollo de código.
- Un enfoque de prácticas recomendadas para probar el código de la canalización. En primer lugar, este documento ofrece una descripción general que incluye el alcance y la relación de los distintos tipos de pruebas, como las pruebas unitarias, las pruebas de integración y las pruebas completas. En segundo lugar, se analiza en detalle cada tipo de prueba, incluidos los métodos para crear e integrar datos de prueba, y los ejecutores de canalización que se deben usar en cada prueba.
Ejecutores de flujos de procesamiento
Durante el desarrollo y las pruebas, se usan diferentes ejecutores de Apache Beam para ejecutar el código de la canalización. El SDK de Apache Beam proporciona un ejecutor directo para el desarrollo y las pruebas locales. Tus herramientas de automatización de lanzamientos también pueden usar Direct Runner para pruebas unitarias y de integración. Por ejemplo, puedes usar Direct Runner en tu pipeline de integración continua (CI).
Los flujos de procesamiento que se implementan en Dataflow usan Dataflow Runner, que ejecuta tu flujo de procesamiento en entornos similares a los de producción. Además, puedes usar Dataflow Runner para hacer pruebas de desarrollo ad hoc y pruebas de extremo a extremo de la canalización.
Aunque esta página se centra en la ejecución de flujos de procesamiento creados con el SDK de Apache Beam para Java, Dataflow también admite flujos de procesamiento de Apache Beam desarrollados con Python y Go. Los SDKs de Apache Beam para Java, Python y Go están disponibles de forma general para Dataflow. Los desarrolladores de SQL también pueden usar Apache Beam SQL para crear flujos de procesamiento que usen dialectos de SQL conocidos.
Configurar un entorno de desarrollo
Para separar los usuarios, los datos, el código y otros recursos en las diferentes fases de desarrollo, crea entornos de implementación. Cuando sea posible, usa Google Cloud proyectos independientes para proporcionar entornos aislados a las diferentes fases del desarrollo de la canalización.
En las siguientes secciones se describe un conjunto típico de entornos de implementación.
Entorno local
El entorno local es la estación de trabajo de un desarrollador. Para el desarrollo y las pruebas rápidas, usa Direct Runner para ejecutar el código de la canalización de forma local.
Las canalizaciones que se ejecutan de forma local mediante Direct Runner pueden interactuar con recursos remotos de Google Cloud Platform, como temas de Pub/Sub o tablas de BigQuery. Asigna a cada desarrollador proyectosGoogle Cloud independientes para que tengan un entorno aislado en el que hacer pruebas ad hoc con los servicios de Google Cloud Platform.
Algunos Google Cloud servicios, como Pub/Sub y Bigtable, proporcionan emuladores para el desarrollo local. Puedes usar estos emuladores con Direct Runner para habilitar el desarrollo y las pruebas locales integrales.
Entorno aislado
El entorno de pruebas es un Google Cloud proyecto que proporciona a los desarrolladores acceso a los Google Cloud servicios durante el desarrollo del código. Los desarrolladores de canalizaciones pueden compartir un proyecto de Google Cloud con otros desarrolladores o usar sus propios proyectos individuales. Usar proyectos individuales reduce la complejidad de la planificación relacionada con el uso de recursos compartidos y la gestión de cuotas.
Los desarrolladores usan el entorno aislado para ejecutar flujos de procesamiento ad hoc con Dataflow Runner. El entorno de pruebas es útil para depurar y probar el código en un runner de producción durante la fase de desarrollo del código. Por ejemplo, la ejecución de flujos de trabajo ad hoc permite a los desarrolladores hacer lo siguiente:
- Observa el efecto de los cambios en el código en el comportamiento de escalado.
- Conocer las posibles diferencias entre el comportamiento de DirectRunner y Dataflow Runner.
- Entender cómo aplica Dataflow las optimizaciones de gráficos.
Para las pruebas ad hoc, los desarrolladores pueden desplegar código desde su entorno local para ejecutar Dataflow en su entorno aislado.
Entorno de preproducción
El entorno de preproducción se usa en las fases de desarrollo que deben ejecutarse en condiciones similares a las de producción, como las pruebas integrales. Usa un proyecto independiente para el entorno de preproducción y configúralo para que sea lo más parecido posible al de producción. Del mismo modo, para permitir pruebas integrales con una escala similar a la de producción, haz que las Google Cloud cuotas de proyectos de Dataflow y otros servicios sean lo más parecidas posible al entorno de producción.
En función de tus requisitos, puedes separar aún más la preproducción en varios entornos. Por ejemplo, un entorno de control de calidad puede ayudar a los analistas de calidad a probar los objetivos de nivel de servicio (SLOs), como la exactitud, la actualización y el rendimiento de los datos en diferentes condiciones de carga de trabajo.
Las pruebas completas incluyen la integración con fuentes y receptores de datos dentro del ámbito de las pruebas. Piensa cómo puedes ponerlos a disposición en el entorno de preproducción. Puedes almacenar datos de prueba en el propio entorno de preproducción. Por ejemplo, los datos de prueba se almacenan en un segmento de Cloud Storage junto con los datos de entrada. En otros casos, los datos de prueba pueden proceder de fuera del entorno de preproducción, como un tema de Pub/Sub a través de una suscripción independiente que se encuentre en el entorno de producción. En el caso de las canalizaciones de streaming, también puedes realizar pruebas integrales con datos generados. Por ejemplo, puedes usar el generador de datos de streaming de Dataflow para emular las características y los volúmenes de datos de producción.
En el caso de las canalizaciones de streaming, usa el entorno de preproducción para probar las actualizaciones de la canalización antes de aplicar ningún cambio en el entorno de producción. Es importante probar y verificar los procedimientos de actualización de las canalizaciones de streaming, sobre todo si tienes que coordinar varios pasos, como cuando ejecutas canalizaciones paralelas para evitar el tiempo de inactividad.
Entorno de producción
El entorno de producción es un proyecto Google Cloud dedicado. La entrega continua copia los artefactos de implementación en el entorno de producción cuando se han superado todas las pruebas completas.
Prácticas recomendadas de desarrollo
Consulta las prácticas recomendadas para las canalizaciones de Dataflow.
Probar un flujo de procesamiento
En el desarrollo de software, las pruebas unitarias, las pruebas de integración y las pruebas completas son tipos habituales de pruebas de software. Estos tipos de pruebas también se pueden aplicar a las pipelines de datos.
El SDK de Apache Beam proporciona funciones para habilitar estas pruebas. Lo ideal es que cada tipo de prueba se dirija a un entorno de implementación diferente. En el siguiente diagrama se muestra cómo se aplican las pruebas unitarias, las pruebas de integración y las pruebas completas a las diferentes partes de tu flujo de procesamiento y tus datos.
En el diagrama se muestra el ámbito de las diferentes pruebas y cómo se relacionan con las transformaciones (subclases DoFn
y PTransform
), las canalizaciones, las fuentes de datos y los receptores de datos.
En las siguientes secciones se describe cómo se aplican varias pruebas de software formales a las canalizaciones de datos que usan Dataflow. Mientras lees esta sección, vuelve al diagrama para entender cómo se relacionan los distintos tipos de pruebas.
Muestreo de datos
Para observar los datos en cada paso de un flujo de procesamiento de Dataflow, habilita el muestreo de datos durante las pruebas. De esta forma, puedes ver los resultados de las transformaciones para asegurarte de que son correctos.
Pruebas unitarias
Las pruebas unitarias evalúan el correcto funcionamiento de las subclases DoFn
y las transformaciones compuestas
(subclases PTransform
) comparando la salida de esas transformaciones con un conjunto verificado de entradas y salidas de datos. Por lo general, los desarrolladores pueden ejecutar estas pruebas en el entorno local. Las pruebas también se pueden ejecutar automáticamente mediante la automatización de pruebas unitarias con la integración continua (CI) en el entorno de compilación.
Direct Runner ejecuta pruebas unitarias con un subconjunto más pequeño de datos de prueba de referencia que se centra en probar la lógica empresarial de tus transformaciones. Los datos de prueba deben ser lo suficientemente pequeños como para caber en la memoria local del equipo en el que se ejecuta la prueba.
El SDK de Apache Beam proporciona una regla de JUnit llamada
TestPipeline
para probar unidades de transformaciones individuales (subclases de DoFn
), transformaciones compuestas (subclases de PTransform
) y flujos de procesamiento completos. Puedes usar TestPipeline
en un
ejecutor de canalizaciones de Apache Beam, como Direct Runner o
Dataflow Runner, para aplicar aserciones al contenido de los objetos PCollection
mediante
PAssert
,
como se muestra en el siguiente fragmento de código de una
clase de prueba de JUnit:
@Rule
public final transient TestPipeline p = TestPipeline.create();
@Test
@Category(NeedsRunner.class)
public void myPipelineTest() throws Exception {
final PCollection<String> pcol = p.apply(...)
PAssert.that(pcol).containsInAnyOrder(...);
p.run();
}
Pruebas unitarias de transformaciones individuales
Si factorizas tu código en transformaciones reutilizables, por ejemplo, como clases anidadas estáticas o de nivel superior, puedes crear pruebas específicas para diferentes partes de tu canalización. Además de las ventajas de las pruebas, las transformaciones reutilizables mejoran la capacidad de mantenimiento y la reutilización del código, ya que encapsulan de forma natural la lógica empresarial de tu canalización en componentes. Por el contrario, probar partes individuales de tu canal puede ser difícil si el canal usa clases internas anónimas para implementar transformaciones.
El siguiente fragmento de Java muestra la implementación de las transformaciones como clases internas anónimas, lo que no permite realizar pruebas fácilmente.
PipelineOptions options = PipelineOptionsFactory.create();
Pipeline p = Pipeline.create(options)
PCollection<Integer> output =
p.apply("Read from text", TextIO.Read.from(...))
.apply("Split words", ParDo.of(new DoFn() {
// Untestable anonymous transform 1
}))
.apply("Generate anagrams", ParDo.of(new DoFn() {
// Untestable anonymous transform 2
}))
.apply("Count words", Count.perElement());
Compara el ejemplo anterior con el siguiente, en el que las clases internas anónimas se refactorizan en subclases concretas con nombre DoFn
. Puedes crear pruebas unitarias individuales para cada subclase DoFn
concreta que forme parte de la canalización de extremo a extremo.
PipelineOptions options = PipelineOptionsFactory.create();
Pipeline p = Pipeline.create(options)
PCollection<Integer> output =
p.apply("Read from text", TextIO.Read.from(...))
.apply("Split words", ParDo.of(new SplitIntoWordsFn()))
.apply("Generate anagrams", ParDo.of(new GenerateAnagramsFn()))
.apply("Count words", Count.perElement());
Probar cada subclase DoFn
es similar a probar por unidades una canalización de un lote que contiene una sola transformación. Usa la transformación Create
para crear un objeto PCollection
de datos de prueba y, a continuación, pásalo al objeto DoFn
. Usa PAssert
para afirmar que el contenido del objeto PCollection
es correcto. En el siguiente ejemplo de código Java se usa la clase PAssert
para comprobar que el formato de salida es correcto.
@Rule
public final transient TestPipeline p = TestPipeline.create();
@Test
@Category(NeedsRunner.class)
public void testGenerateAnagramsFn() {
// Create the test input
PCollection<String> words = p.apply(Create.of("friend"));
// Test a single DoFn using the test input
PCollection<String> anagrams =
words.apply("Generate anagrams", ParDo.of(new GenerateAnagramsFn()));
// Assert correct output from
PAssert.that(anagrams).containsInAnyOrder(
"finder", "friend", "redfin", "refind");
p.run();
}
Pruebas de integración
Las pruebas de integración verifican el correcto funcionamiento de toda la canalización. Ten en cuenta los siguientes tipos de pruebas de integración:
- Una prueba de integración de transformaciones que evalúa la funcionalidad integrada de todas las transformaciones individuales que componen tu canalización de datos. Las pruebas de integración de transformaciones son como pruebas unitarias de toda la canalización, excepto la integración con fuentes y receptores de datos externos. El SDK de Apache Beam proporciona métodos para suministrar datos de prueba a tu flujo de datos y para verificar los resultados del procesamiento. Direct Runner se usa para ejecutar pruebas de integración de transformaciones.
Prueba de integración del sistema que evalúa la integración de tu canalización de datos con fuentes y receptores de datos activos. Para que tu canal pueda comunicarse con sistemas externos, debes configurar tus pruebas con las credenciales adecuadas para acceder a servicios externos. Los flujos de procesamiento de streaming se ejecutan indefinidamente, por lo que debes decidir cuándo y cómo detener el flujo de procesamiento en ejecución. Si usas Direct Runner para ejecutar pruebas de integración del sistema, puedes verificar rápidamente la integración entre tu canalización y otros sistemas sin tener que enviar un trabajo de Dataflow y esperar a que finalice.
Diseña pruebas de transformación e integración de sistemas para detectar defectos y obtener comentarios rápidamente sin ralentizar la productividad de los desarrolladores. En el caso de las pruebas de larga duración, como las que se ejecutan como trabajos de Dataflow, puede que te interese usar una prueba integral que se ejecute con menos frecuencia.
Una canalización de datos es una o varias transformaciones relacionadas. Puedes crear una transformación compuesta encapsuladora para tu flujo de procesamiento y usar TestPipeline
para hacer una prueba de integración de todo el flujo. En función de si quieres probar la canalización en modo por lotes o en modo de streaming, debes proporcionar datos de prueba mediante las transformaciones Create
o TestStream
.
Usar datos de prueba para las pruebas de integración
En tu entorno de producción, es probable que tu flujo de procesamiento se integre con diferentes fuentes y receptores de datos. Sin embargo, en las pruebas unitarias y de integración de transformaciones, céntrate en verificar la lógica empresarial del código de tu canalización proporcionando entradas de prueba y verificando la salida directamente. Además de simplificar las pruebas, este enfoque te permite aislar los problemas específicos de la canalización de los que puedan deberse a las fuentes y los sumideros de datos.
Probar flujos de procesamiento por lotes
En el caso de las canalizaciones por lotes, utilice la transformación Create
para crear un objeto PCollection
de los datos de prueba de entrada a partir de una colección estándar en memoria, como un objeto List
de Java. Usar la transformación Create
es adecuado si tus datos de prueba son lo suficientemente pequeños como para incluirlos en el código. Después, puedes usar PAssert
en los objetos PCollection
de salida para determinar si el código de tu flujo de trabajo es correcto.
El Direct Runner y el Dataflow Runner admiten este enfoque.
El siguiente fragmento de código Java muestra aserciones en objetos PCollection
de salida de una transformación compuesta que incluye algunas o todas las transformaciones individuales que constituyen una canalización (WeatherStatsPipeline
). El enfoque es similar a las pruebas unitarias de transformaciones individuales en una canalización.
private class WeatherStatsPipeline extends
PTransform<PCollection<Integer>, PCollection<WeatherSummary>> {
@Override
public PCollection<WeatherSummary> expand(PCollection<Integer> input) {
// Pipeline transforms …
}
}
@Rule
public final transient TestPipeline p = TestPipeline.create();
@Test
@Category(NeedsRunner.class)
public void testWeatherPipeline() {
// Create test input consisting of temperature readings
PCollection<Integer> tempCelsius =
p.apply(Create.of(24, 22, 20, 22, 21, 21, 20));
// CalculateWeatherStats calculates the min, max, and average temperature
PCollection<WeatherSummary> result =
tempCelsius.apply("Calculate weather statistics", new WeatherStatsPipeline());
// Assert correct output from CalculateWeatherStats
PAssert.thatSingleton(result).isEqualTo(new WeatherSummary.Builder()
.withAverageTemp(21)
.withMaxTemp(24)
.withMinTemp(20)
.build());
p.run();
}
Para probar el comportamiento de las ventanas, también puedes usar la transformación Create
para crear elementos con marcas de tiempo, como se muestra en el siguiente fragmento de código:
private static final Duration WINDOW_DURATION = Duration.standardMinutes(3);
@Rule
public final transient TestPipeline p = TestPipeline.create();
@Test
@Category(NeedsRunner.class)
public void testWindowedData() {
PCollection<String> input =
p.apply(
Create.timestamped(
TimestampedValue.of("a", new Instant(0L)),
TimestampedValue.of("a", new Instant(0L)),
TimestampedValue.of("b", new Instant(0L)),
TimestampedValue.of("c", new Instant(0L)),
TimestampedValue.of("c", new Instant(0L).plus(WINDOW_DURATION)))
.withCoder(StringUtf8Coder.of()));
PCollection<KV<String, Long>> windowedCount =
input
.apply(Window.into(FixedWindows.of(WINDOW_DURATION)))
.apply(Count.perElement());
PAssert.that(windowedCount)
.containsInAnyOrder(
// Output from first window
KV.of("a", 2L),
KV.of("b", 1L),
KV.of("c", 1L),
// Output from second window
KV.of("c", 1L));
p.run();
}
Probar flujos de procesamiento en streaming
Los flujos de procesamiento contienen supuestos que definen cómo gestionar los datos ilimitados. Estas suposiciones suelen estar relacionadas con la oportunidad de los datos en condiciones reales y, por lo tanto, influyen en la exactitud en función de si las suposiciones resultan ser verdaderas o falsas. Las pruebas de integración de flujos de procesamiento de streaming deben incluir pruebas que simulen la naturaleza no determinista de la llegada de datos de streaming.
Para habilitar estas pruebas, el SDK de Apache Beam proporciona la clase TestStream
para modelar los efectos de los tiempos de los elementos (datos tempranos, a tiempo o tardíos) en los resultados de tu flujo de datos. Usa estas pruebas junto con la clase PAssert
para verificar los resultados esperados.
TestStream
es compatible con Direct Runner y Dataflow Runner. El siguiente código de ejemplo crea una transformación TestStream
:
final Duration WINDOW_DURATION = Duration.standardMinutes(3);
@Rule
public final transient TestPipeline p = TestPipeline.create();
@Test
@Category(NeedsRunner.class)
public void testDroppedLateData() {
TestStream<String> input = TestStream.create(StringUtf8Coder.of())
// Add elements arriving before the watermark
.addElements(
TimestampedValue.of("a", new Instant(0L)),
TimestampedValue.of("a", new Instant(0L)),
TimestampedValue.of("b", new Instant(0L)),
TimestampedValue.of("c", new Instant(0L).plus(Duration.standardMinutes(3))))
// Advance the watermark past the end of the window
.advanceWatermarkTo(new Instant(0L).plus(WINDOW_DURATION).plus(Duration.standardMinutes(1)))
// Add elements which will be dropped due to lateness
.addElements(
TimestampedValue.of("c", new Instant(0L)))
// Advance the watermark to infinity which will close all windows
.advanceWatermarkToInfinity();
PCollection<KV<String, Long>> windowedCount =
p.apply(input)
.apply(Window.into(FixedWindows.of(WINDOW_DURATION)))
.apply(Count.perElement());
PAssert.that(windowedCount)
.containsInAnyOrder(
// Output from first window
KV.of("a", 2L),
KV.of("b", 1L),
KV.of("c", 1L));
p.run();
}
Para obtener más información sobre TestStream
, consulta el artículo Probar canalizaciones ilimitadas en Apache Beam.
Para obtener más información sobre cómo usar el SDK de Apache Beam para pruebas unitarias, consulta la documentación de Apache Beam.
Usar Google Cloud servicios en pruebas de integración
El ejecutor directo se puede integrar con servicios de Google Cloud , por lo que las pruebas ad hoc en el entorno local y las pruebas de integración del sistema pueden usar Pub/Sub, BigQuery y otros servicios según sea necesario. Cuando usas Direct Runner, tu flujo de trabajo usa credenciales de aplicación predeterminadas (ADC) para obtener credenciales. La forma de configurar ADC depende de dónde se ejecute tu canalización. Para obtener más información, consulta Configurar credenciales predeterminadas de la aplicación.
Antes de ejecutar la canalización, debes conceder los permisos suficientes a la cuenta que utiliza para acceder a los recursos necesarios. Para obtener más información, consulta Seguridad y permisos de los flujos de datos.
Para las pruebas de integración totalmente locales, puedes usar emuladores locales para algunosGoogle Cloud servicios. Hay emuladores locales disponibles para Pub/Sub y Bigtable.
Para probar la integración del sistema de los flujos de procesamiento de transmisión, puedes usar el método setBlockOnRun
(definido en la interfaz DirectOptions
) para que Direct Runner ejecute tu flujo de procesamiento de forma asíncrona.
De lo contrario, la ejecución de la canalización bloqueará el proceso principal de llamada (por ejemplo, una secuencia de comandos en tu canalización de compilación) hasta que se detenga manualmente. Si ejecutas la canalización de forma asíncrona, puedes usar la instancia PipelineResult
devuelta para cancelar la ejecución de la canalización, como se muestra en el siguiente ejemplo de código:
public interface StreamingIntegrationTestOptions extends
DirectOptions, StreamingOptions, MyOtherPipelineOptions {
...
}
@Rule
public final transient TestPipeline p = TestPipeline.create();
@Test
@Category(NeedsRunner.class)
public void testNonBlockingPipeline() {
StreamingIntegrationTestOptions options =
p.getOptions().as(StreamingIntegrationOptions.class);
options.setBlockOnRun(false); // Set non-blocking pipeline execution
options.setStreaming(true); // Set streaming mode
p.apply(...); // Apply pipeline transformations
PipelineResult result = p.run(); // Run the pipeline
// Generate input, verify output, etc
...
// Later on, cancel the pipeline using the previously returned
result.cancel();
}
Pruebas completas
Las pruebas completas verifican el funcionamiento correcto de tu canalización completa ejecutándola en el ejecutor de Dataflow en condiciones que se asemejan a las de producción. Las pruebas verifican que la lógica empresarial funciona correctamente con Dataflow Runner y comprueban si la canalización se comporta como se espera con cargas similares a las de producción. Normalmente, las pruebas integrales se ejecutan en un Google Cloud proyecto específico que se designa como entorno de preproducción.
Para probar tu canalización a diferentes escalas, usa distintos tipos de pruebas integrales. Por ejemplo:
- Realiza pruebas integrales a pequeña escala con una pequeña proporción (por ejemplo, el 1 %) de tu conjunto de datos de prueba para validar rápidamente la funcionalidad de la canalización en el entorno de preproducción.
- Realiza pruebas integrales a gran escala con un conjunto de datos de prueba completo para validar la funcionalidad de la canalización con volúmenes y condiciones de datos similares a los de producción.
En el caso de las canalizaciones de streaming, te recomendamos que ejecutes canalizaciones de prueba en paralelo con la canalización de producción si pueden usar los mismos datos. Este proceso le permite comparar resultados y comportamientos operativos, como el autoescalado y el rendimiento.
Las pruebas integrales ayudan a predecir si tu canalización cumplirá los SLOs de producción. El entorno de preproducción prueba tu flujo de procesamiento en condiciones similares a las de producción. En las pruebas de extremo a extremo, las canalizaciones se ejecutan con Dataflow Runner para procesar conjuntos de datos de referencia completos que coincidan o se parezcan mucho a los conjuntos de datos de producción.
Es posible que no se puedan generar datos sintéticos para realizar pruebas que simulen con precisión datos reales. Para solucionar este problema, una opción es usar extractos depurados de fuentes de datos de producción para crear conjuntos de datos de referencia, en los que se anonimicen los datos sensibles mediante las transformaciones adecuadas. Te recomendamos que utilices Protección de Datos Sensibles para ello. Protección de Datos Sensibles puede detectar datos sensibles de una amplia gama de tipos de contenido y fuentes de datos, así como aplicar diversas técnicas de desidentificación, como la ocultación, el enmascaramiento, el encriptado con conservación del formato y el cambio de fechas.
Diferencias en las pruebas integrales de las canalizaciones por lotes y de streaming
Antes de ejecutar una prueba completa de principio a fin con un conjunto de datos de prueba de gran tamaño, te recomendamos que realices una prueba con un porcentaje menor de los datos de prueba (por ejemplo, el 1 %) y que verifiques el comportamiento esperado en menos tiempo. Al igual que con las pruebas de integración que usan Direct Runner, puedes usar PAssert
en objetos PCollection
cuando ejecutas canalizaciones con Dataflow Runner. Para obtener más información sobre PAssert
, consulta la sección Pruebas unitarias de esta página.
En función de tu caso práctico, verificar resultados muy grandes de pruebas integrales puede ser poco práctico, costoso o difícil. En ese caso, puedes verificar muestras representativas del conjunto de resultados. Por ejemplo, puedes usar BigQuery para muestrear y comparar filas de salida con un conjunto de datos de referencia de resultados esperados.
En el caso de las canalizaciones de streaming, puede ser difícil simular condiciones de streaming realistas con datos sintéticos. Una forma habitual de proporcionar datos de streaming para las pruebas integrales es integrar las pruebas con fuentes de datos de producción. Si usas Pub/Sub como fuente de datos, puedes habilitar un flujo de datos independiente para las pruebas de extremo a extremo mediante suscripciones adicionales a temas. Después, puede comparar los resultados de diferentes flujos de procesamiento que consumen los mismos datos, lo que resulta útil para verificar los flujos de procesamiento candidatos con otros flujos de procesamiento de preproducción y producción.
En el siguiente diagrama se muestra cómo este método permite que una canalización de producción y una canalización de prueba se ejecuten en paralelo en diferentes entornos de implementación.
En el diagrama, ambas canalizaciones leen del mismo tema de Pub/Sub, pero usan suscripciones independientes. Esta configuración permite que las dos canalizaciones procesen los mismos datos de forma independiente y te permite comparar los resultados. La canalización de prueba usa una cuenta de servicio independiente del proyecto de producción y, por lo tanto, no utiliza la cuota de suscriptores de Pub/Sub del proyecto de producción.
A diferencia de los flujos de procesamiento por lotes, los flujos de procesamiento continuos siguen ejecutándose hasta que se cancelan explícitamente. En las pruebas de extremo a extremo, debe decidir si quiere dejar que la canalización se ejecute, quizás hasta que se realice la siguiente prueba de extremo a extremo, o cancelar la canalización en un punto que represente la finalización de la prueba para poder inspeccionar los resultados.
El tipo de datos de prueba que utilices influirá en esta decisión. Por ejemplo, si usas un conjunto limitado de datos de prueba que se proporciona al flujo de procesamiento, puedes cancelar el flujo de procesamiento cuando se hayan procesado todos los elementos. De lo contrario, si usas una fuente de datos real, como un tema de Pub/Sub que se utilice en producción, o si generas datos de prueba continuamente, puede que te interese mantener las canalizaciones de prueba en funcionamiento durante un periodo más largo. Esta última opción te permite comparar el comportamiento con el entorno de producción o incluso con otras pipelines de prueba.