veilid/veilid-flutter/example/integration_test/test_routing_context.dart

270 lines
8.5 KiB
Dart
Raw Normal View History

2024-03-16 23:57:46 -04:00
import 'dart:async';
import 'dart:convert';
import 'dart:math';
import 'package:flutter_test/flutter_test.dart';
import 'package:veilid/veilid.dart';
Future<void> testRoutingContexts() async {
{
final rc = await Veilid.instance.routingContext();
rc.close();
}
{
final rc = await Veilid.instance.routingContext();
final rcp = rc.withDefaultSafety();
2024-05-02 14:15:42 -04:00
// ignore: cascade_invocations
2024-03-16 23:57:46 -04:00
rcp.close();
rc.close();
}
{
final rc = await Veilid.instance.routingContext();
final rcp = rc.withSequencing(Sequencing.ensureOrdered);
2024-05-02 14:15:42 -04:00
// ignore: cascade_invocations
2024-03-16 23:57:46 -04:00
rcp.close();
rc.close();
}
{
final rc = await Veilid.instance.routingContext();
final rcp = rc.withSafety(const SafetySelectionSafe(
safetySpec: SafetySpec(
hopCount: 2,
stability: Stability.lowLatency,
sequencing: Sequencing.noPreference)));
2024-05-02 14:15:42 -04:00
// ignore: cascade_invocations
2024-03-16 23:57:46 -04:00
rcp.close();
rc.close();
}
{
final rc = await Veilid.instance.routingContext();
final rcp = rc.withSafety(
const SafetySelectionUnsafe(sequencing: Sequencing.preferOrdered));
2024-05-02 14:15:42 -04:00
// ignore: cascade_invocations
2024-03-16 23:57:46 -04:00
rcp.close();
rc.close();
}
}
Future<void> testAppMessageLoopback(Stream<VeilidUpdate> updateStream) async {
final appMessageQueue = StreamController<VeilidAppMessage>();
final appMessageSubscription = updateStream.listen((update) {
if (update is VeilidAppMessage) {
appMessageQueue.sink.add(update);
}
});
try {
2024-05-02 14:15:42 -04:00
await Veilid.instance.debug('purge routes');
2024-03-16 23:57:46 -04:00
// make a routing context that uses a safety route
final rc = await Veilid.instance.routingContext();
2024-03-16 23:57:46 -04:00
try {
// make a new local private route
final prl = await Veilid.instance.newPrivateRoute();
try {
// import it as a remote route as well so we can send to it
final prr = await Veilid.instance.importRemotePrivateRoute(prl.blob);
try {
// send an app message to our own private route
2024-05-02 14:15:42 -04:00
final message = utf8.encode('abcd1234');
2024-03-16 23:57:46 -04:00
await rc.appMessage(prr, message);
// we should get the same message back
final update = await appMessageQueue.stream.first;
expect(update.message, equals(message));
expect(update.routeId, isNotNull);
} finally {
await Veilid.instance.releasePrivateRoute(prr);
}
} finally {
await Veilid.instance.releasePrivateRoute(prl.routeId);
}
} finally {
rc.close();
}
} finally {
await appMessageSubscription.cancel();
2024-05-02 14:15:42 -04:00
await appMessageQueue.close();
2024-03-16 23:57:46 -04:00
}
}
Future<void> testAppCallLoopback(Stream<VeilidUpdate> updateStream) async {
final appCallQueue = StreamController<VeilidAppCall>();
final appMessageSubscription = updateStream.listen((update) {
if (update is VeilidAppCall) {
appCallQueue.sink.add(update);
}
});
try {
2024-05-02 14:15:42 -04:00
await Veilid.instance.debug('purge routes');
2024-03-16 23:57:46 -04:00
// make a routing context that uses a safety route
final rc = await Veilid.instance.routingContext();
2024-03-16 23:57:46 -04:00
try {
// make a new local private route
final prl = await Veilid.instance.newPrivateRoute();
try {
// import it as a remote route as well so we can send to it
final prr = await Veilid.instance.importRemotePrivateRoute(prl.blob);
try {
// send an app call to our own private route
2024-05-02 14:15:42 -04:00
final message = utf8.encode('abcd1234');
2024-03-16 23:57:46 -04:00
final appCallFuture = rc.appCall(prr, message);
// we should get the same call back
final update = await appCallQueue.stream.first;
final appcallid = update.callId;
expect(update.message, equals(message));
expect(update.routeId, isNotNull);
// now we reply to the request
2024-05-02 14:15:42 -04:00
final reply = utf8.encode('qwer5678');
2024-03-16 23:57:46 -04:00
await Veilid.instance.appCallReply(appcallid, reply);
// now we should get the reply from the call
final result = await appCallFuture;
expect(result, equals(reply));
} finally {
await Veilid.instance.releasePrivateRoute(prr);
}
} finally {
await Veilid.instance.releasePrivateRoute(prl.routeId);
}
} finally {
rc.close();
}
} finally {
await appMessageSubscription.cancel();
2024-05-02 14:15:42 -04:00
await appCallQueue.close();
2024-03-16 23:57:46 -04:00
}
}
Future<void> testAppMessageLoopbackBigPackets(
Stream<VeilidUpdate> updateStream) async {
final appMessageQueue = StreamController<VeilidAppMessage>();
final appMessageSubscription = updateStream.listen((update) {
if (update is VeilidAppMessage) {
appMessageQueue.sink.add(update);
}
});
final sentMessages = <String>{};
final random = Random.secure();
final cs = await Veilid.instance.bestCryptoSystem();
try {
2024-05-02 14:15:42 -04:00
await Veilid.instance.debug('purge routes');
2024-03-16 23:57:46 -04:00
// make a routing context that uses a safety route
final rc = await Veilid.instance.routingContext();
2024-03-16 23:57:46 -04:00
try {
// make a new local private route
final prl = await Veilid.instance.newPrivateRoute();
try {
// import it as a remote route as well so we can send to it
final prr = await Veilid.instance.importRemotePrivateRoute(prl.blob);
2024-05-02 14:15:42 -04:00
final appMessageQueueIterator = StreamIterator(appMessageQueue.stream);
2024-03-16 23:57:46 -04:00
try {
for (var i = 0; i < 5; i++) {
// send an app message to our own private route
final message = await cs.randomBytes(random.nextInt(32768));
await rc.appMessage(prr, message);
sentMessages.add(base64Url.encode(message));
}
// we should get the same messages back
for (var i = 0; i < sentMessages.length; i++) {
if (await appMessageQueueIterator.moveNext()) {
final update = appMessageQueueIterator.current;
expect(sentMessages.contains(base64Url.encode(update.message)),
isTrue);
} else {
2024-05-02 14:15:42 -04:00
fail('not enough messages in the queue');
2024-03-16 23:57:46 -04:00
}
}
} finally {
2024-05-02 14:15:42 -04:00
await appMessageQueueIterator.cancel();
2024-03-16 23:57:46 -04:00
await Veilid.instance.releasePrivateRoute(prr);
}
} finally {
await Veilid.instance.releasePrivateRoute(prl.routeId);
}
} finally {
rc.close();
}
} finally {
await appMessageSubscription.cancel();
2024-05-02 14:15:42 -04:00
await appMessageQueue.close();
2024-03-16 23:57:46 -04:00
}
}
Future<void> testAppCallLoopbackBigPackets(
Stream<VeilidUpdate> updateStream) async {
final appCallQueue = StreamController<VeilidAppCall>();
final appMessageSubscription = updateStream.listen((update) {
if (update is VeilidAppCall) {
appCallQueue.sink.add(update);
}
});
final appCallQueueHandler = () async {
await for (final update in appCallQueue.stream) {
await Veilid.instance.appCallReply(update.callId, update.message);
}
}();
final sentMessages = <String>{};
final random = Random.secure();
final cs = await Veilid.instance.bestCryptoSystem();
try {
2024-05-02 14:15:42 -04:00
await Veilid.instance.debug('purge routes');
2024-03-16 23:57:46 -04:00
// make a routing context that uses a safety route
final rc = await Veilid.instance.routingContext();
2024-03-16 23:57:46 -04:00
try {
// make a new local private route
final prl = await Veilid.instance.newPrivateRoute();
2024-03-16 23:57:46 -04:00
try {
// import it as a remote route as well so we can send to it
final prr = await Veilid.instance.importRemotePrivateRoute(prl.blob);
2024-05-02 14:15:42 -04:00
final appMessageQueueIterator = StreamIterator(appCallQueue.stream);
2024-03-16 23:57:46 -04:00
try {
for (var i = 0; i < 5; i++) {
// send an app message to our own private route
final message = await cs.randomBytes(random.nextInt(32768));
final outmessage = await rc.appCall(prr, message);
expect(message, equals(outmessage));
}
// we should get the same messages back
for (var i = 0; i < sentMessages.length; i++) {
if (await appMessageQueueIterator.moveNext()) {
final update = appMessageQueueIterator.current;
expect(sentMessages.contains(base64Url.encode(update.message)),
isTrue);
} else {
2024-05-02 14:15:42 -04:00
fail('not enough messages in the queue');
2024-03-16 23:57:46 -04:00
}
}
} finally {
2024-05-02 14:15:42 -04:00
await appMessageQueueIterator.cancel();
2024-03-16 23:57:46 -04:00
await Veilid.instance.releasePrivateRoute(prr);
}
} finally {
await Veilid.instance.releasePrivateRoute(prl.routeId);
}
} finally {
rc.close();
}
} finally {
await appMessageSubscription.cancel();
}
await appCallQueue.close();
await appCallQueueHandler;
}