88 lines
3.6 KiB
Dart
88 lines
3.6 KiB
Dart
import 'package:flutter_test/flutter_test.dart';
|
|
import 'package:shared_preferences/shared_preferences.dart';
|
|
import 'package:words999/models/history_entry_model.dart';
|
|
import 'package:words999/models/interpreter_persona.dart';
|
|
import 'package:words999/services/ai_oracle_service.dart';
|
|
import 'package:words999/services/settings_repository.dart';
|
|
|
|
void main() {
|
|
TestWidgetsFlutterBinding.ensureInitialized();
|
|
|
|
setUp(() async {
|
|
SharedPreferences.setMockInitialValues({});
|
|
await SettingsRepository().init();
|
|
await SettingsRepository().setPersonaId(InterpreterPersona.defaultId);
|
|
await SettingsRepository().setRandomOrgApiKey('');
|
|
});
|
|
|
|
test('unknown persona id falls back to clear oracle', () {
|
|
expect(InterpreterPersona.byId('nope').id, InterpreterPersona.clear.id);
|
|
});
|
|
|
|
test('roster includes warhammer ork shaman and aeldari farseer', () {
|
|
expect(InterpreterPersona.orc.title, 'Орк-шаман');
|
|
expect(InterpreterPersona.orc.systemPrompt.toLowerCase(), contains('вааагх'));
|
|
expect(InterpreterPersona.aeldari.title, 'Всевидящий аэльдари');
|
|
expect(
|
|
InterpreterPersona.all.map((p) => p.id),
|
|
containsAll(['orc', 'aeldari', 'techpriest']),
|
|
);
|
|
});
|
|
|
|
test('settings persist the selected interpreter voice', () async {
|
|
await SettingsRepository().setPersonaId(InterpreterPersona.orc.id);
|
|
expect(SettingsRepository().persona.id, InterpreterPersona.orc.id);
|
|
|
|
SharedPreferences.setMockInitialValues({
|
|
'oracle_interpreter_persona_v1': InterpreterPersona.techpriest.id,
|
|
});
|
|
await SettingsRepository().init();
|
|
expect(SettingsRepository().persona.title, 'Техножрец');
|
|
});
|
|
|
|
test('interpretation prompt uses the selected voice and asks for a concrete step', () async {
|
|
await SettingsRepository().setPersonaId(InterpreterPersona.analyst.id);
|
|
final messages = AiOracleService().buildInterpretationMessages(
|
|
question: 'Стоит ли уходить?',
|
|
words: const [
|
|
SessionWord(
|
|
word: 'огонь',
|
|
sessionNumber: 0,
|
|
partOfSpeech: 'существительное',
|
|
category: 'Образ / Архетип',
|
|
symbolicMeaning: 'Очищающее пламя',
|
|
),
|
|
],
|
|
);
|
|
|
|
expect(messages.first.role.name, 'system');
|
|
expect(messages.first.content, contains('психоаналитик'));
|
|
expect(messages.last.content, contains('проверяемый шаг'));
|
|
expect(messages.last.content, contains('ОГОНЬ'));
|
|
expect(messages.last.content, contains('Стоит ли уходить?'));
|
|
expect(messages.last.content, contains('Закон знака побеждает голос'));
|
|
expect(messages.first.content.toLowerCase(), isNot(contains('голос самой вечности')));
|
|
});
|
|
|
|
test('empty canon is marked empty and aeldari voice does not invent a closed path', () async {
|
|
await SettingsRepository().setPersonaId(InterpreterPersona.aeldari.id);
|
|
final messages = AiOracleService().buildInterpretationMessages(
|
|
question: '',
|
|
words: const [
|
|
SessionWord(
|
|
word: 'ухо',
|
|
sessionNumber: 306,
|
|
partOfSpeech: 'существительное',
|
|
category: 'Образ / Архетип',
|
|
symbolicMeaning:
|
|
'Сакральный символ («ухо»): архетипический образ в поле судьбы.',
|
|
),
|
|
],
|
|
);
|
|
|
|
expect(messages.last.content, contains('КАНОН ПУСТ'));
|
|
expect(messages.last.content, contains('УХО'));
|
|
expect(messages.last.content.toLowerCase(), isNot(contains('тропа уже почти закрыта')));
|
|
});
|
|
}
|