[{"data":1,"prerenderedAt":23},["ShallowReactive",2],{"articolo-test-in-flutter-guida-pratica-a-unit-widget-e-integration-test":3,"comments-article-test-in-flutter-guida-pratica-a-unit-widget-e-integration-test":22},{"id":4,"title":5,"slug":6,"excerpt":7,"body":8,"cover_image":9,"video_url":10,"status":11,"published_at":12,"meta_title":13,"meta_description":14,"category":15,"author":19},6,"Test in Flutter: guida pratica a unit, widget e integration test","test-in-flutter-guida-pratica-a-unit-widget-e-integration-test","Scopri come scrivere test efficaci in Flutter: dai unit test ai widget test fino agli integration test. Una guida pratica con esempi di codice per migliorare la qualità e l'affidabilità delle tue app.","## Perché testare un'app Flutter\n\nScrivere test è una delle pratiche più sottovalutate nello sviluppo mobile, eppure è ciò che distingue un progetto fragile da uno robusto. Flutter offre un ecosistema di testing maturo e ben integrato, suddiviso in tre livelli principali:\n\n- **Unit test**: verificano la logica di una singola funzione, metodo o classe.\n- **Widget test**: validano il comportamento e l'aspetto di un singolo widget.\n- **Integration test**: testano l'app completa o flussi significativi su un dispositivo reale o emulatore.\n\nIn questa guida vediamo come implementarli tutti e tre con esempi concreti.\n\n## Configurazione iniziale\n\nIl pacchetto `flutter_test` è già incluso nel SDK. Per gli integration test aggiungi le dipendenze nel `pubspec.yaml`:\n\n```yaml\ndev_dependencies:\n  flutter_test:\n    sdk: flutter\n  integration_test:\n    sdk: flutter\n  mockito: ^5.4.4\n  build_runner: ^2.4.9\n```\n\nLa convenzione vuole che i file di test risiedano nella cartella `test\u002F` e terminino con il suffisso `_test.dart`.\n\n## Unit test\n\nGli unit test sono i più veloci da eseguire e dovrebbero costituire la maggior parte della tua suite. Supponiamo di avere una semplice classe `Counter`:\n\n```dart\nclass Counter {\n  int value = 0;\n\n  void increment() => value++;\n  void decrement() => value--;\n}\n```\n\nIl test corrispondente:\n\n```dart\nimport 'package:flutter_test\u002Fflutter_test.dart';\nimport 'package:my_app\u002Fcounter.dart';\n\nvoid main() {\n  group('Counter', () {\n    test('il valore parte da zero', () {\n      expect(Counter().value, 0);\n    });\n\n    test('increment aumenta il valore', () {\n      final counter = Counter();\n      counter.increment();\n      expect(counter.value, 1);\n    });\n  });\n}\n```\n\nUsa `group` per organizzare test correlati e `expect` con i matcher (`equals`, `isNull`, `throwsA`, ecc.) per le asserzioni.\n\n## Mocking delle dipendenze\n\nQuando una classe dipende da servizi esterni (API, database), conviene simularne il comportamento con **mockito**. Definisci le annotazioni e genera i mock:\n\n```dart\nimport 'package:mockito\u002Fannotations.dart';\nimport 'package:mockito\u002Fmockito.dart';\nimport 'package:flutter_test\u002Fflutter_test.dart';\n\n@GenerateMocks([ApiService])\nvoid main() {\n  late MockApiService mockApi;\n\n  setUp(() {\n    mockApi = MockApiService();\n  });\n\n  test('restituisce i dati dell\\'utente', () async {\n    when(mockApi.fetchUser(1))\n        .thenAnswer((_) async => User(id: 1, name: 'Mario'));\n\n    final user = await mockApi.fetchUser(1);\n    expect(user.name, 'Mario');\n    verify(mockApi.fetchUser(1)).called(1);\n  });\n}\n```\n\nGenera i file mock con: `dart run build_runner build`.\n\n## Widget test\n\nI widget test eseguono i componenti in un ambiente headless, senza un dispositivo reale. Il cuore è il `WidgetTester`:\n\n```dart\nimport 'package:flutter\u002Fmaterial.dart';\nimport 'package:flutter_test\u002Fflutter_test.dart';\nimport 'package:my_app\u002Fcounter_page.dart';\n\nvoid main() {\n  testWidgets('il contatore si incrementa al tap', (tester) async {\n    await tester.pumpWidget(const MaterialApp(home: CounterPage()));\n\n    expect(find.text('0'), findsOneWidget);\n    expect(find.text('1'), findsNothing);\n\n    await tester.tap(find.byIcon(Icons.add));\n    await tester.pump();\n\n    expect(find.text('0'), findsNothing);\n    expect(find.text('1'), findsOneWidget);\n  });\n}\n```\n\nAlcuni metodi chiave:\n\n- `pumpWidget`: monta il widget nell'albero di test.\n- `find`: localizza i widget tramite testo, tipo, chiave o icona.\n- `tester.tap` \u002F `tester.enterText`: simulano l'interazione utente.\n- `pump` ricostruisce un singolo frame, mentre `pumpAndSettle` attende il completamento di tutte le animazioni.\n\n## Integration test\n\nGli integration test verificano l'app reale in esecuzione. Crea un file nella cartella `integration_test\u002F`:\n\n```dart\nimport 'package:flutter_test\u002Fflutter_test.dart';\nimport 'package:integration_test\u002Fintegration_test.dart';\nimport 'package:my_app\u002Fmain.dart' as app;\n\nvoid main() {\n  IntegrationTestWidgetsFlutterBinding.ensureInitialized();\n\n  testWidgets('flusso completo di login', (tester) async {\n    app.main();\n    await tester.pumpAndSettle();\n\n    await tester.enterText(find.byKey(const Key('email')), 'test@mail.it');\n    await tester.enterText(find.byKey(const Key('password')), 'segreta');\n    await tester.tap(find.byKey(const Key('loginBtn')));\n    await tester.pumpAndSettle();\n\n    expect(find.text('Benvenuto'), findsOneWidget);\n  });\n}\n```\n\nEsegui il test su un dispositivo collegato con:\n\n```bash\nflutter test integration_test\u002Fapp_test.dart\n```\n\n## Buone pratiche\n\n- **Piramide dei test**: molti unit test, un numero moderato di widget test, pochi integration test (lenti e costosi).\n- Mantieni i test **indipendenti**: usa `setUp` e `tearDown` per isolare lo stato.\n- Assegna delle **Key** ai widget interattivi per renderli facilmente individuabili.\n- Misura la copertura con `flutter test --coverage` e analizza il file `lcov.info`.\n- Integra i test nella tua pipeline **CI\u002FCD** per evitare regressioni.\n\n## Conclusione\n\nUna buona suite di test ti permette di rifattorizzare con sicurezza, individuare bug prima della produzione e documentare il comportamento atteso del codice. Inizia con piccoli unit test e amplia gradualmente la copertura: il tempo investito viene ripagato a ogni nuova release.","https:\u002F\u002Fflutter.it\u002Fstorage\u002Farticles\u002F76258296-e831-4bb8-8cb8-45c3b5bddc07.jpg",null,"published","2026-06-09T06:00:35+00:00","Test in Flutter: unit, widget e integration test","Guida pratica al testing in Flutter: scrivi unit, widget e integration test con esempi di codice e mockito per app affidabili e robuste.",{"id":16,"name":17,"slug":18},3,"Best practice","best-practice",{"id":20,"name":21},1,"Flutter Bot",[],1781247856978]