Flutter, IA y pruebas: un nuevo método para programar más rápido y de forma más segura

Flutter, IA y pruebas: un nuevo método para programar más rápido y de forma más segura

En 2025, la llegada masiva de agentes IA en nuestros IDE cambió nuestra forma de programar. Pero sin un marco sólido, su velocidad puede convertirse en un riesgo. En este artículo, te muestro cómo estructuré un proyecto Flutter alrededor de un trío ganador: especificaciones claras, pruebas automatizadas, IA asistida. Resultado: un flujo de trabajo más fiable, más rápido y mucho más agradable.

1. Por qué revisé mi forma de programar en Flutter

Cuando empecé con Flutter, estaba sobre todo concentrado en la UX/UI, las animaciones y el rendimiento. Pero con la llegada de la IA, apareció un nuevo desafío:

¿Cómo colaborar con una IA sin poner en peligro la estabilidad de una app?

Programar más rápido es fácil. Programar más rápido con confianza, es otra cosa.

Y ahí redescubrí una idea antigua: no hay código sin una intención clara.

2. Antes del código: definir las intenciones (desarrollo guiado por especificaciones)

2.1. ¿Por qué una spec ante todo?

La mayoría de los prompts de IA fallan porque falta contexto. La IA tiene que adivinar lo que queremos.

Cuando precisas tus intenciones en un archivo de spec, transformas tu workspace en un entorno explícito y controlado.

Una spec puede contener:

  • la descripción de las pantallas y su rol
  • los flujos de usuario
  • las reglas de negocio
  • los casos límite
  • los errores a gestionar
  • las restricciones técnicas

Exemple minimal de spec :

# Story: Scan d'une carte Pokémon (PSA)

## Objectif

L'utilisateur scanne une carte Pokémon gradée PSA (via le QR code ou le code de certification) pour l'ajouter à sa collection numérique.

## Flux principal

1. L'utilisateur ouvre l'écran de scan.
2. La caméra s'active automatiquement.
3. Le QR code / code PSA est détecté.
4. L'app récupère les données de la carte via l'API PSA (nom du Pokémon, set, numéro, grade, numéro de certification, éventuellement visuel).
5. L'app affiche une fiche détaillée avec les infos PSA + les infos propres à l'app (collection, tags, notes…).

## Règles métier

- Si la carte est déjà dans la collection → afficher un dialogue « Cette carte PSA est déjà dans ta collection ».
- Si l'API PSA ne répond pas → afficher une erreur explicite et proposer de réessayer.
- Si le QR/code est illisible → afficher un message d'erreur et permettre de rescanner.
- Le scan + appel API PSA doivent s'effectuer en moins de 500 ms dans des conditions normales.

Este archivo se convierte en tu fuente de verdad, tanto para ti como para tu agente IA.

3. La IA como "dev junior ultrarrápido"... pero enmarcada

3.1. Lo que la IA hace muy bien

  • generar clases, servicios, etc.
  • crear widgets reutilizables
  • escribir boilerplates tediosos
  • refactorizar código
  • sugerir patrones más limpios

3.2. Lo que hace mal sin contexto

  • gestionar las reglas de negocio
  • mantener la coherencia global
  • anticipar los edge cases
  • comprender un flujo complejo sin spec

De ahí la importancia de un buen archivo AGENTS.md, o de una spec clara accesible para tus agentes. Tú construyes el marco, la IA construye el código.

4. El papel central de las pruebas en este workflow

Para transformar un agente IA en un desarrollador fiable, las pruebas se convierten en tu red de seguridad.

4.1. Los tres niveles de pruebas en Flutter

🟦 Pruebas unitarias

Para probar la lógica de negocio:

import 'package:flutter_test/flutter_test.dart';
import 'package:myapp/domain/pokemon_service.dart';

void main() {
  group('PokemonService', () {
    test("ajout d'une carte PSA déjà présente", () {
      final service = PokemonService();

      service.addFromPsaCert('PSA-123');
      final result = service.addFromPsaCert('PSA-123');

      expect(result.isSuccess, false);
      expect(result.errorCode, 'already_exists');
    });
  });
}

🟨 Pruebas de widgets

Para validar la UI + interacciones sin lanzar la app completa. Ejemplo: verificar que la pantalla de scan muestra la vista previa de la carta PSA devuelta por la API.

import 'package:flutter_test/flutter_test.dart';
import 'package:flutter/material.dart';
import 'package:myapp/ui/scan_screen.dart';
import 'package:myapp/domain/pokemon_service.dart';

class FakePokemonService extends PokemonService {
  @override
  Future<PokemonCard> fetchFromPsa(String certId) async {
    return PokemonCard(
      id: 'PSA-123',
      name: 'Pikachu',
      setName: 'Base Set',
      grade: '10',
    );
  }
}

void main() {
  testWidgets('affiche la fiche PSA après scan réussi', (WidgetTester tester) async {
    await tester.pumpWidget(
      MaterialApp(
        home: ScanScreen(
          pokemonService: FakePokemonService(),
        ),
      ),
    );

    // On simule ici le résultat d'un scan réussi (par ex. via un callback).
    final state = tester.state<ScanScreenState>(find.byType(ScanScreen));
    await state.onScanResult('PSA-123');
    await tester.pumpAndSettle();

    expect(find.text('Pikachu'), findsOneWidget);
    expect(find.text('Base Set'), findsOneWidget);
    expect(find.text('PSA 10'), findsOneWidget);
  });
}

🟩 Pruebas de integración

Para simular un recorrido real de usuario: abrir la app, ir a la pantalla de scan, escanear una carta PSA, ver la ficha y, eventualmente, tomar una screenshot utilizable en una issue.

import 'package:flutter_test/flutter_test.dart';
import 'package:integration_test/integration_test.dart';
import 'package:myapp/main.dart' as app;
import 'dart:io';

void main() {
  IntegrationTestWidgetsFlutterBinding.ensureInitialized();

  testWidgets('parcours complet de scan PSA', (WidgetTester tester) async {
    app.main();
    await tester.pumpAndSettle();

    // Aller sur l'écran de scan
    await tester.tap(find.byKey(const Key('go-to-scan-button')));
    await tester.pumpAndSettle();

    // Ici tu peux mocker la couche caméra / scan pour renvoyer un certId PSA.
    // Par exemple via un FakeScanner ou un flag de debug.

    // Une fois le scan simulé, on attend le chargement de la fiche.
    await tester.pumpAndSettle(const Duration(seconds: 1));

    expect(find.text('Pikachu'), findsOneWidget);

    // Prendre un screenshot et le stocker dans un dossier lié à une issue
    final binding = IntegrationTestWidgetsFlutterBinding.instance;
    final bytes = await binding.takeScreenshot('scan_psa_flow');
    final dir = Directory('test_screenshots/issue-123');
    if (!dir.existsSync()) {
      dir.createSync(recursive: true);
    }
    final file = File('test_screenshots/issue-123/scan_psa_flow.png');
    await file.writeAsBytes(bytes);
  });
}

Este patrón es super poderoso: cada bug identificado puede tener su escenario de integración + su screenshot en una carpeta dedicada (por ejemplo test_screenshots/issue-123/). Es valioso para documentar regresiones y facilitar la comunicación en el equipo (o contigo mismo en el futuro).

4.2. El ciclo completo IA + pruebas

  1. Escribes/completas la spec.
  2. Se la dejas procesar a tu agente IA.
  3. La IA propone código.
  4. Ejecutas las pruebas (unitarias, de widgets, integración).
  5. Todo está verde → merge.
  6. Una prueba falla → ajuste del código o de la spec.

4.3. Esquema del flujo de trabajo completo

Se puede resumir este workflow en un bucle simple:

Loading diagram...

La idea importante: la doc y la spec no son un ejercicio para hacer una sola vez. Evolucionan al mismo ritmo que el código y las pruebas.

4.4. Aprovechar mejor las capturas de pantalla en el proceso de pruebas

Tomar una captura al final de una prueba de integración no es solo "por la estética". Puedes convertirla en una verdadera herramienta de trabajo:

  • 📌 Documentación de bug: cuando abres una issue (GitHub, Jira...), puedes adjuntar la captura generada por la prueba (test_screenshots/issue-123/scan_psa_flow.png). Sabemos exactamente cómo se veía la pantalla en el momento en que falló.
  • 🧪 Regresión visual "simple pero eficaz": sin montar una gran infraestructura de visual testing, ya puedes comparar capturas entre dos ramas / dos versiones. Una diff visual tosca puede revelar omisiones (botón que desaparece, texto que se desborda, etc.).
  • 🧭 Onboarding y storytelling: una carpeta test_screenshots bien ordenada también es una forma rápida de mostrar "cómo se ve" tal o cual flujo, sin arrancar la app. Útil cuando incorporas a un nuevo dev, un QA o cuando documentas para ti mismo.
  • 🔁 Trazabilidad: el ID de la issue en la ruta (issue-123) crea un vínculo natural entre spec → prueba → captura → ticket. Cuando cierras el ticket, puedes conservar la captura como "foto antes/después" en la conversación.

Para ir más lejos, incluso puedes automatizar la subida de estas capturas como artefactos de CI, o publicarlas automáticamente en un comentario del PR para flujos críticos.

5. Ejemplo concreto sobre una base Flutter

Aquí tienes un ejemplo de estructura de pruebas + código generados en un proyecto Flutter real:

lib/
  domain/
    pokemon_service.dart
  ui/
    scan_screen.dart
    pokemon_card.dart
  data/
    pokemon_repository.dart

test/
  unit/
    pokemon_service_test.dart
  widget/
    scan_screen_test.dart
  integration/
    scan_flow_test.dart

specs/
  scan_pokemon.md
  add_to_collection.md
  error_cases.md

Y en CI:

flutter test
flutter test integration_test

Este tipo de organización hace que la colaboración IA + desarrollador sea extremadamente fluida.

6. Por qué este método lo cambia todo

Más rápido

La IA hace el trabajo tedioso. Tú te concentras en la lógica, el negocio y la UX.

Más fiable

La spec + las pruebas transforman a la IA en una herramienta segura.

Más mantenible

Refactorizar código se vuelve un verdadero placer cuando todo está probado.

Más alineado con el negocio

El razonamiento parte de la spec, no de una implementación azarosa.

7. Actualización de la doc: cerrar el ciclo

A menudo falta una etapa en nuestros workflows: volver a la doc una vez que el trabajo está hecho.

Cada vez que:

  • añades una nueva regla de negocio,
  • corriges un bug,
  • modificas un flujo,

...deberías actualizar:

  • la spec correspondiente,
  • eventualmente el archivo de contexto (AGENTS.md, doc de arquitectura),
  • la referencia hacia la prueba y la captura asociadas,

Eso es lo que convierte tu doc en documentación viva, alineada con el código. La IA se beneficia (mejor contexto), y tú también cuando vuelvas al proyecto dentro de 6 meses.

8. Límites (seamos honestos)

  • Sobredimensionado para pequeñas features.
  • Una mala spec = un mal resultado, incluso con IA.
  • La UI compleja aún requiere mucha fineza manual.
  • Requiere una pequeña disciplina (pero la ganancia en mantenibilidad es significativa).

9. Para profundizar: Spec Kit y las specs pilotadas por IA

Si quieres llevar la metodología más lejos, puedes echar un vistazo a Spec Kit, la herramienta open source de GitHub pensada para el desarrollo guiado por especificaciones:

  • primero escribes una spec detallada (el "qué" y el "por qué"),
  • la herramienta te ayuda a derivar un plan técnico y una lista de tareas,
  • después dejas que tu agente IA genere el código a partir de esos artefactos,
  • y vinculas todo eso con tus pruebas existentes.

La idea es la misma que hemos visto, pero formalizada en una herramienta genérica, pensada para funcionar con varios asistentes IA. Aunque Spec Kit apunta más al ecosistema web por ahora, la filosofía es 100% reutilizable en otro contexto:

  • empezar con specs sólidas,
  • mantener una separación clara entre la intención (docs) y la implementación (código),
  • usar la IA como un ejecutor rápido, no como la fuente de verdad,
  • asegurar todo con pruebas automatizadas.

Puedes imaginar un futuro donde:

  • Spec Kit (o un equivalente) describe tus features a alto nivel,
  • un agente IA genera la capa Flutter (UI + lógica),
  • y tus pruebas Flutter validan que la implementación se ajusta a la spec.

En resumen, si eres lead dev o estás pensando en industrializar tu workflow con IA, vale la pena experimentar con este tipo de herramientas, aunque solo sea para ver cómo evoluciona tu forma de pensar las specs.

Conclusión

El futuro del desarrollo en Flutter no será solo "programar más rápido con IA". Será:

programar con intención + programar con asistencia + programar con seguridad.

Un workflow donde:

  • la spec dice lo que queremos,
  • la IA propone cómo hacerlo,
  • las pruebas garantizan que está bien hecho.

Y tú, ¿ya has probado este tipo de workflow en Flutter? Me encantaría leer tu experiencia.

Enlaces útiles

Etiquetas

  • flutter

  • ios

  • android

  • pruebas

  • IA

  • desarrollo-guiado-por-especificaciones

  • flujo de trabajo

  • retorno-de-experiencia

  • arquitectura

  • mejores-prácticas

Este artículo fue publicado el

Comentarios

Cargando...

Flutter, IA y pruebas: un nuevo método para programar más rápido y de forma más segura | DEMILY Clément