107 lines
3.5 KiB
Dart
107 lines
3.5 KiB
Dart
import 'package:flutter/material.dart';
|
|
import 'package:flutter_bloc/flutter_bloc.dart';
|
|
import 'package:flutter_test/flutter_test.dart';
|
|
import 'package:record/record.dart';
|
|
import 'dart:async';
|
|
|
|
import 'package:flutter_app/core/network/api_repository.dart';
|
|
import 'package:flutter_app/features/chat/presentation/cubit/chat_cubit.dart';
|
|
import 'package:flutter_app/features/chat/presentation/cubit/chat_state.dart';
|
|
import 'package:flutter_app/features/audio/presentation/cubit/voice_cubit.dart';
|
|
import 'package:flutter_app/main.dart';
|
|
|
|
class _TestApiRepository extends ApiRepository {
|
|
_TestApiRepository() : super(baseUrl: 'http://127.0.0.1:8000');
|
|
|
|
@override
|
|
Future<String> getModelName() async => 'gemma4:e2b';
|
|
|
|
@override
|
|
Future<List<String>> getAvailableModels() async => ['gemma4:e2b'];
|
|
|
|
@override
|
|
Future<List<SavedConversation>> listConversations() async => [];
|
|
}
|
|
|
|
class _CancellableWidgetApi extends _TestApiRepository {
|
|
final controller = StreamController<String>();
|
|
|
|
@override
|
|
Future<void> saveConversation(SavedConversation conversation) async {}
|
|
|
|
@override
|
|
Stream<String> completeStream(List<ChatMessage> messages, {String? model}) =>
|
|
controller.stream;
|
|
|
|
@override
|
|
void cancelActiveRequest() {
|
|
controller.close();
|
|
}
|
|
}
|
|
|
|
void main() {
|
|
testWidgets('chat page fits a compact Windows window', (tester) async {
|
|
tester.view.physicalSize = const Size(800, 600);
|
|
tester.view.devicePixelRatio = 1;
|
|
addTearDown(tester.view.resetPhysicalSize);
|
|
addTearDown(tester.view.resetDevicePixelRatio);
|
|
|
|
final api = _TestApiRepository();
|
|
await tester.pumpWidget(
|
|
MultiRepositoryProvider(
|
|
providers: [RepositoryProvider<ApiRepository>.value(value: api)],
|
|
child: MultiBlocProvider(
|
|
providers: [
|
|
BlocProvider(create: (_) => ChatCubit(api)),
|
|
BlocProvider(create: (_) => VoiceCubit(api, AudioRecorder())),
|
|
],
|
|
child: const SovereignApp(),
|
|
),
|
|
),
|
|
);
|
|
await tester.pumpAndSettle();
|
|
|
|
expect(find.text('مساعدك المحلي'), findsOneWidget);
|
|
expect(tester.takeException(), isNull);
|
|
});
|
|
|
|
testWidgets('stop button cancels an active answer', (tester) async {
|
|
tester.view.physicalSize = const Size(1000, 700);
|
|
tester.view.devicePixelRatio = 1;
|
|
addTearDown(tester.view.resetPhysicalSize);
|
|
addTearDown(tester.view.resetDevicePixelRatio);
|
|
|
|
final api = _CancellableWidgetApi();
|
|
final cubit = ChatCubit(api);
|
|
await tester.pumpWidget(
|
|
MultiRepositoryProvider(
|
|
providers: [RepositoryProvider<ApiRepository>.value(value: api)],
|
|
child: MultiBlocProvider(
|
|
providers: [
|
|
BlocProvider<ChatCubit>.value(value: cubit),
|
|
BlocProvider(create: (_) => VoiceCubit(api, AudioRecorder())),
|
|
],
|
|
child: const SovereignApp(),
|
|
),
|
|
),
|
|
);
|
|
await tester.pumpAndSettle();
|
|
|
|
await tester.enterText(find.byType(TextField), 'أوقف هذا الرد');
|
|
await tester.tap(find.byTooltip('إرسال'));
|
|
await tester.pump();
|
|
await tester.pump(const Duration(milliseconds: 30));
|
|
expect(find.byTooltip('إيقاف التوليد'), findsOneWidget);
|
|
|
|
await tester.tap(find.byTooltip('إيقاف التوليد'));
|
|
await tester.pump();
|
|
await tester.pumpAndSettle(const Duration(milliseconds: 50));
|
|
|
|
expect(cubit.state.requestStatus, RequestStatus.cancelled);
|
|
expect(find.byTooltip('إرسال'), findsOneWidget);
|
|
expect(tester.takeException(), isNull);
|
|
await cubit.close();
|
|
await api.controller.close();
|
|
});
|
|
}
|