144 lines
3.8 KiB
Dart
144 lines
3.8 KiB
Dart
import 'package:flutter_test/flutter_test.dart';
|
|
import 'package:ikar/backend/modules/contacts.dart';
|
|
import 'package:ikar/core/contacts/phonebook_contact_sync.dart';
|
|
|
|
void main() {
|
|
const existing = CachedContact(
|
|
id: 2,
|
|
accountId: 1,
|
|
firstName: 'Existing',
|
|
phone: 79000000002,
|
|
updateTime: 0,
|
|
);
|
|
var current = true;
|
|
late List<String> lookups;
|
|
late List<String> additions;
|
|
late Map<String, int> accounts;
|
|
|
|
setUp(() {
|
|
current = true;
|
|
lookups = [];
|
|
additions = [];
|
|
accounts = {'+79000000003': 3};
|
|
});
|
|
|
|
Future<int> sync(
|
|
Map<String, String> book, {
|
|
int accountId = 1,
|
|
List<CachedContact> contacts = const [existing],
|
|
Future<PhoneLookupResult?> Function(String)? lookup,
|
|
Future<AddContactResult> Function(String, String)? add,
|
|
}) => PhonebookContactSync.importContacts(
|
|
phonebook: book,
|
|
contacts: contacts,
|
|
accountId: accountId,
|
|
lookup:
|
|
lookup ??
|
|
(phone) async {
|
|
lookups.add(phone);
|
|
final id = accounts[phone];
|
|
return id == null ? null : PhoneLookupResult(id: id);
|
|
},
|
|
add:
|
|
add ??
|
|
(phone, name) async {
|
|
additions.add('$phone:$name');
|
|
return const AddContactResult(AddContactStatus.added);
|
|
},
|
|
isCurrent: () => current,
|
|
requestDelay: Duration.zero,
|
|
);
|
|
|
|
test(
|
|
'adds registered numbers once, skips existing and absent accounts',
|
|
() async {
|
|
expect(
|
|
await sync({
|
|
'+79000000002': 'Do not rename',
|
|
'8 (900) 000-00-03': 'New',
|
|
'+79000000003': 'Duplicate',
|
|
'+79000000004': 'No ИКАР',
|
|
'123': 'Invalid',
|
|
}),
|
|
1,
|
|
);
|
|
expect(lookups, ['+79000000003', '+79000000004']);
|
|
expect(additions, ['+79000000003:New']);
|
|
},
|
|
);
|
|
|
|
test('skips own account and existing contacts with hidden numbers', () async {
|
|
accounts = {'+79000000003': 2, '+79000000004': 1};
|
|
expect(await sync({'+79000000003': 'Hidden', '+79000000004': 'Self'}), 0);
|
|
expect(additions, isEmpty);
|
|
});
|
|
|
|
test(
|
|
'a later pass discovers new phone entries and newly registered users',
|
|
() async {
|
|
expect(await sync({'+79000000004': 'Later'}), 0);
|
|
accounts['+79000000004'] = 4;
|
|
expect(await sync({'+79000000003': 'New', '+79000000004': 'Later'}), 2);
|
|
},
|
|
);
|
|
|
|
test(
|
|
'account switch during lookup prevents adding to another account',
|
|
() async {
|
|
expect(
|
|
await sync(
|
|
{'+79000000003': 'New'},
|
|
lookup: (_) async {
|
|
current = false;
|
|
return const PhoneLookupResult(id: 3);
|
|
},
|
|
),
|
|
0,
|
|
);
|
|
expect(additions, isEmpty);
|
|
},
|
|
);
|
|
|
|
test('lookup failure stops the pass and can be retried', () async {
|
|
await expectLater(
|
|
sync(
|
|
{'+79000000003': 'New'},
|
|
lookup: (_) async {
|
|
throw StateError('offline');
|
|
},
|
|
),
|
|
throwsStateError,
|
|
);
|
|
expect(additions, isEmpty);
|
|
expect(await sync({'+79000000003': 'New'}), 1);
|
|
});
|
|
|
|
test('add failure stops further requests and remains retryable', () async {
|
|
await expectLater(
|
|
sync({
|
|
'+79000000003': 'New',
|
|
'+79000000004': 'Next',
|
|
}, add: (_, _) async => const AddContactResult(AddContactStatus.error)),
|
|
throwsStateError,
|
|
);
|
|
expect(lookups, ['+79000000003']);
|
|
expect(await sync({'+79000000003': 'New'}), 1);
|
|
});
|
|
|
|
test('registration disappearing before add is not counted', () async {
|
|
expect(
|
|
await sync(
|
|
{'+79000000003': 'New'},
|
|
add: (_, _) async => const AddContactResult(AddContactStatus.notFound),
|
|
),
|
|
0,
|
|
);
|
|
});
|
|
|
|
test('empty phonebook sends no requests', () async {
|
|
expect(await sync({}), 0);
|
|
expect(lookups, isEmpty);
|
|
expect(additions, isEmpty);
|
|
});
|
|
}
|