import 'package:flutter_test/flutter_test.dart'; import 'package:report_notebooklm_app/main.dart'; void main() { testWidgets('renders shell tabs and report detail modules', (tester) async { await tester.pumpWidget(MyApp(dataSource: FakeDataSource())); await tester.pumpAndSettle(); expect(find.text('推荐'), findsWidgets); expect(find.text('研报'), findsWidgets); expect(find.text('机构'), findsWidgets); expect(find.text('听单'), findsWidgets); expect(find.text('我的'), findsWidgets); expect(find.text('黄金月报:金价新高之后,谁在继续买?'), findsOneWidget); await tester.tap(find.text('黄金月报:金价新高之后,谁在继续买?')); await tester.pumpAndSettle(); expect(find.text('研报详情'), findsOneWidget); expect(find.text('报告要点'), findsWidgets); expect(find.text('报告中的关键数据'), findsWidgets); expect(find.text('查看详情'), findsWidgets); await tester.tap(find.text('报告摘要').last); await tester.pumpAndSettle(); expect(find.text('报告摘要'), findsWidgets); expect(find.text('需求结构'), findsOneWidget); }); } class FakeDataSource extends ReportDataSource { final institution = const Institution( id: 'inst_ssga', nameCn: '道富环球投资管理', nameEn: 'State Street Global Advisors', sourceTier: 'tier_2', coveredTopics: ['贵金属'], reportCount: 1, ); late final report = ReportCardModel( id: 'rep_ssga_gold', titleCn: '黄金月报:金价新高之后,谁在继续买?', oneLiner: '央行购金转向结构性,ETF 重新净流入。', institution: institution, topics: const ['贵金属', '跨资产'], releasedAt: '2026-05-22T00:00:00', hasAudio: true, interpretationLabel: '研报解读', sourceTier: 'authorized_partner', cacheVersion: 'rep_ssga_gold:v1', ); @override Future> recommended() async => [report]; @override Future> reports() async => [report]; @override Future> institutions() async => [institution]; @override Future institutionDetail(String institutionId) async { return Institution( id: institution.id, nameCn: institution.nameCn, nameEn: institution.nameEn, sourceTier: institution.sourceTier, coveredTopics: institution.coveredTopics, reportCount: 1, introCn: '道富环球投资管理的公开研究用于演示。', credibilityNote: 'tier_2 来源。', recentReports: [report], ); } @override Future> listen() async => [ AudioItem( audioId: 'aud_ssga_gold', titleCn: '金价新高之后,谁在继续买?', reportTitleCn: report.titleCn, durationSec: 180, reportId: report.id, institution: institution, ), ]; @override Future reportDetail(String reportId) async => ReportDetail( id: report.id, titleCn: report.titleCn, oneLiner: report.oneLiner, institution: institution, source: const { 'source_tier': 'authorized_partner', 'source_note': '原文来源于机构公开研究页。', }, topics: report.topics, hasAudio: true, releasedAt: report.releasedAt, cacheVersion: report.cacheVersion, modules: const [ DisplayModule( id: 'mod_ssga_gold_executive_overview', type: 'executive_overview', layer: 'p0', renderMode: 'card_plus_page', hasDetailPage: true, sortOrder: 1, titleCn: '报告摘要', preview: {'preview_summary': '本期月报拆解黄金买盘。', 'section_count': 3}, ), DisplayModule( id: 'mod_ssga_gold_core_insights', type: 'core_insights', layer: 'p0', renderMode: 'inline', hasDetailPage: true, sortOrder: 2, titleCn: '报告要点', content: { 'points': [ {'kind': 'view', 'text': '央行购金从机会性买入转向结构性配置。'}, ], }, ), DisplayModule( id: 'mod_ssga_gold_key_data', type: 'key_data', layer: 'p0', renderMode: 'card_plus_page', hasDetailPage: true, sortOrder: 3, titleCn: '报告中的关键数据', preview: { 'preview_headline': '10 个关键数据点', 'highlights': ['ETF 连续净流入'], }, ), ], ); @override Future moduleDetail(String reportId, String moduleId) async { return ModuleDetail( id: moduleId, type: 'executive_overview', titleCn: '报告摘要', content: const { 'sections': [ {'heading': '需求结构', 'body': '央行与 ETF 买盘提供支撑。'}, ], }, contentEtag: 'etag', cacheVersion: 'rep_ssga_gold:v1', ); } }