diff --git a/CHANGELOG.md b/CHANGELOG.md index 7f169520..84628f07 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,10 @@ +**Changes in Veilid 0.1.7** + +- Fix for connection table crash +- Fix for incorrect set_dht_value return value +- Python test updates +- Various VeilidChat-prompted veilid-flutter updates + **Changes in Veilid 0.1.6** - Fix for 'find_node' too many nodes returned issue diff --git a/veilid-core/src/network_manager/connection_table.rs b/veilid-core/src/network_manager/connection_table.rs index 2ece5f05..a6d60ec6 100644 --- a/veilid-core/src/network_manager/connection_table.rs +++ b/veilid-core/src/network_manager/connection_table.rs @@ -177,10 +177,10 @@ impl ConnectionTable { // then drop the least recently used connection let mut out_conn = None; if inner.conn_by_id[protocol_index].len() > inner.max_connections[protocol_index] { - if let Some((lruk, lru_conn)) = inner.conn_by_id[protocol_index].remove_lru() { + if let Some((lruk, lru_conn)) = inner.conn_by_id[protocol_index].peek_lru() { + let lruk = *lruk; log_net!(debug "connection lru out: {:?}", lru_conn); - out_conn = Some(lru_conn); - Self::remove_connection_records(&mut *inner, lruk); + out_conn = Some(Self::remove_connection_records(&mut *inner, lruk)); } } diff --git a/veilid-core/src/storage_manager/mod.rs b/veilid-core/src/storage_manager/mod.rs index b6dad7a2..4b21abb7 100644 --- a/veilid-core/src/storage_manager/mod.rs +++ b/veilid-core/src/storage_manager/mod.rs @@ -347,8 +347,9 @@ impl StorageManager { if last_signed_value_data.value_data().data() == &data && last_signed_value_data.value_data().writer() == &writer.key { - // Data and writer is the name, nothing is changing, just return the same ValueData - return Ok(Some(last_signed_value_data.into_value_data())); + // Data and writer is the same, nothing is changing, + // just return that we set it, but no network activity needs to happen + return Ok(None); } let seq = last_signed_value_data.value_data().seq(); ValueData::new_with_seq(seq + 1, data, writer.key) diff --git a/veilid-core/src/tests/files/flag.txt b/veilid-core/src/tests/files/flag.txt new file mode 100644 index 00000000..f7ab4830 --- /dev/null +++ b/veilid-core/src/tests/files/flag.txt @@ -0,0 +1 @@ +Ray says "Go SubSix!" \ No newline at end of file diff --git a/veilid-flutter/analysis_options.yaml b/veilid-flutter/analysis_options.yaml index e07e9e94..d262dc94 100644 --- a/veilid-flutter/analysis_options.yaml +++ b/veilid-flutter/analysis_options.yaml @@ -1,5 +1,11 @@ -include: package:flutter_lints/flutter.yaml - +include: package:lint_hard/all.yaml analyzer: errors: invalid_annotation_target: ignore + exclude: + - '**/*.g.dart' + - '**/*.freezed.dart' + +linter: + rules: + avoid_positional_boolean_parameters: false \ No newline at end of file diff --git a/veilid-flutter/example/analysis_options.yaml b/veilid-flutter/example/analysis_options.yaml index e07e9e94..bf4898d6 100644 --- a/veilid-flutter/example/analysis_options.yaml +++ b/veilid-flutter/example/analysis_options.yaml @@ -3,3 +3,7 @@ include: package:flutter_lints/flutter.yaml analyzer: errors: invalid_annotation_target: ignore + +linter: + rules: + - unawaited_futures \ No newline at end of file diff --git a/veilid-flutter/lib/default_config.dart b/veilid-flutter/lib/default_config.dart index 815c0793..9b877dbc 100644 --- a/veilid-flutter/lib/default_config.dart +++ b/veilid-flutter/lib/default_config.dart @@ -1,10 +1,11 @@ import 'dart:io'; import 'package:flutter/foundation.dart' show kIsWeb; -import 'package:path_provider/path_provider.dart'; import 'package:path/path.dart' as p; +import 'package:path_provider/path_provider.dart'; import 'package:system_info2/system_info2.dart' as sysinfo; import 'package:system_info_plus/system_info_plus.dart'; + import 'veilid.dart'; const int megaByte = 1024 * 1024; @@ -57,136 +58,129 @@ int getRemoteMaxStorageSpaceMb() { return 256; } -Future getDefaultVeilidConfig(String programName) async { - return VeilidConfig( - programName: programName, - namespace: "", - capabilities: const VeilidConfigCapabilities(disable: []), - protectedStore: const VeilidConfigProtectedStore( - allowInsecureFallback: false, - alwaysUseInsecureStorage: false, - directory: "", - delete: false, - deviceEncryptionKeyPassword: "", - newDeviceEncryptionKeyPassword: null, - ), - tableStore: VeilidConfigTableStore( - directory: kIsWeb - ? "" - : p.join((await getApplicationSupportDirectory()).absolute.path, - "table_store"), - delete: false, - ), - blockStore: VeilidConfigBlockStore( - directory: kIsWeb - ? "" - : p.join((await getApplicationSupportDirectory()).absolute.path, - "block_store"), - delete: false, - ), - network: VeilidConfigNetwork( - connectionInitialTimeoutMs: 2000, - connectionInactivityTimeoutMs: 60000, - maxConnectionsPerIp4: 32, - maxConnectionsPerIp6Prefix: 32, - maxConnectionsPerIp6PrefixSize: 56, - maxConnectionFrequencyPerMin: 128, - clientWhitelistTimeoutMs: 300000, - reverseConnectionReceiptTimeMs: 5000, - holePunchReceiptTimeMs: 5000, - routingTable: const VeilidConfigRoutingTable( - nodeId: [], - nodeIdSecret: [], - bootstrap: kIsWeb - ? ["ws://bootstrap.veilid.net:5150/ws"] - : ["bootstrap.veilid.net"], - limitOverAttached: 64, - limitFullyAttached: 32, - limitAttachedStrong: 16, - limitAttachedGood: 8, - limitAttachedWeak: 4, +Future getDefaultVeilidConfig(String programName) async => + VeilidConfig( + programName: programName, + namespace: '', + capabilities: const VeilidConfigCapabilities(disable: []), + protectedStore: const VeilidConfigProtectedStore( + allowInsecureFallback: false, + alwaysUseInsecureStorage: false, + directory: '', + delete: false, + deviceEncryptionKeyPassword: '', ), - rpc: const VeilidConfigRPC( - concurrency: 0, - queueSize: 1024, - maxTimestampBehindMs: 10000, - maxTimestampAheadMs: 10000, - timeoutMs: 5000, - maxRouteHopCount: 4, - defaultRouteHopCount: 1, + tableStore: VeilidConfigTableStore( + directory: kIsWeb + ? '' + : p.join((await getApplicationSupportDirectory()).absolute.path, + 'table_store'), + delete: false, ), - dht: VeilidConfigDHT( - resolveNodeTimeoutMs: 10000, - resolveNodeCount: 20, - resolveNodeFanout: 3, - maxFindNodeCount: 20, - getValueTimeoutMs: 10000, - getValueCount: 20, - getValueFanout: 3, - setValueTimeoutMs: 10000, - setValueCount: 20, - setValueFanout: 5, - minPeerCount: 20, - minPeerRefreshTimeMs: 60000, - validateDialInfoReceiptTimeMs: 2000, - localSubkeyCacheSize: getLocalSubkeyCacheSize(), - localMaxSubkeyCacheMemoryMb: await getLocalMaxSubkeyCacheMemoryMb(), - remoteSubkeyCacheSize: getRemoteSubkeyCacheSize(), - remoteMaxRecords: getRemoteMaxRecords(), - remoteMaxSubkeyCacheMemoryMb: await getRemoteMaxSubkeyCacheMemoryMb(), - remoteMaxStorageSpaceMb: getRemoteMaxStorageSpaceMb()), - upnp: true, - detectAddressChanges: true, - restrictedNatRetries: 0, - tls: const VeilidConfigTLS( - certificatePath: "", - privateKeyPath: "", + blockStore: VeilidConfigBlockStore( + directory: kIsWeb + ? '' + : p.join((await getApplicationSupportDirectory()).absolute.path, + 'block_store'), + delete: false, + ), + network: VeilidConfigNetwork( connectionInitialTimeoutMs: 2000, - ), - application: const VeilidConfigApplication( - https: VeilidConfigHTTPS( - enabled: false, - listenAddress: "", - path: "", - url: null, + connectionInactivityTimeoutMs: 60000, + maxConnectionsPerIp4: 32, + maxConnectionsPerIp6Prefix: 32, + maxConnectionsPerIp6PrefixSize: 56, + maxConnectionFrequencyPerMin: 128, + clientWhitelistTimeoutMs: 300000, + reverseConnectionReceiptTimeMs: 5000, + holePunchReceiptTimeMs: 5000, + routingTable: const VeilidConfigRoutingTable( + nodeId: [], + nodeIdSecret: [], + bootstrap: kIsWeb + ? ['ws://bootstrap.veilid.net:5150/ws'] + : ['bootstrap.veilid.net'], + limitOverAttached: 64, + limitFullyAttached: 32, + limitAttachedStrong: 16, + limitAttachedGood: 8, + limitAttachedWeak: 4, + ), + rpc: const VeilidConfigRPC( + concurrency: 0, + queueSize: 1024, + maxTimestampBehindMs: 10000, + maxTimestampAheadMs: 10000, + timeoutMs: 5000, + maxRouteHopCount: 4, + defaultRouteHopCount: 1, + ), + dht: VeilidConfigDHT( + resolveNodeTimeoutMs: 10000, + resolveNodeCount: 20, + resolveNodeFanout: 3, + maxFindNodeCount: 20, + getValueTimeoutMs: 10000, + getValueCount: 20, + getValueFanout: 3, + setValueTimeoutMs: 10000, + setValueCount: 20, + setValueFanout: 5, + minPeerCount: 20, + minPeerRefreshTimeMs: 60000, + validateDialInfoReceiptTimeMs: 2000, + localSubkeyCacheSize: getLocalSubkeyCacheSize(), + localMaxSubkeyCacheMemoryMb: await getLocalMaxSubkeyCacheMemoryMb(), + remoteSubkeyCacheSize: getRemoteSubkeyCacheSize(), + remoteMaxRecords: getRemoteMaxRecords(), + remoteMaxSubkeyCacheMemoryMb: + await getRemoteMaxSubkeyCacheMemoryMb(), + remoteMaxStorageSpaceMb: getRemoteMaxStorageSpaceMb()), + upnp: true, + detectAddressChanges: true, + restrictedNatRetries: 0, + tls: const VeilidConfigTLS( + certificatePath: '', + privateKeyPath: '', + connectionInitialTimeoutMs: 2000, + ), + application: const VeilidConfigApplication( + https: VeilidConfigHTTPS( + enabled: false, + listenAddress: '', + path: '', + ), + http: VeilidConfigHTTP( + enabled: false, + listenAddress: '', + path: '', + )), + protocol: const VeilidConfigProtocol( + udp: VeilidConfigUDP( + enabled: !kIsWeb, + socketPoolSize: 0, + listenAddress: '', + ), + tcp: VeilidConfigTCP( + connect: !kIsWeb, + listen: !kIsWeb, + maxConnections: 32, + listenAddress: '', + ), + ws: VeilidConfigWS( + connect: true, + listen: !kIsWeb, + maxConnections: 16, + listenAddress: '', + path: 'ws', + ), + wss: VeilidConfigWSS( + connect: true, + listen: false, + maxConnections: 16, + listenAddress: '', + path: 'ws', ), - http: VeilidConfigHTTP( - enabled: false, - listenAddress: "", - path: "", - url: null, - )), - protocol: const VeilidConfigProtocol( - udp: VeilidConfigUDP( - enabled: !kIsWeb, - socketPoolSize: 0, - listenAddress: "", - publicAddress: null, - ), - tcp: VeilidConfigTCP( - connect: !kIsWeb, - listen: !kIsWeb, - maxConnections: 32, - listenAddress: "", - publicAddress: null, - ), - ws: VeilidConfigWS( - connect: true, - listen: !kIsWeb, - maxConnections: 16, - listenAddress: "", - path: "ws", - url: null, - ), - wss: VeilidConfigWSS( - connect: true, - listen: false, - maxConnections: 16, - listenAddress: "", - path: "ws", - url: null, ), ), - ), - ); -} + ); diff --git a/veilid-flutter/lib/routing_context.dart b/veilid-flutter/lib/routing_context.dart index f71cd285..5060e98e 100644 --- a/veilid-flutter/lib/routing_context.dart +++ b/veilid-flutter/lib/routing_context.dart @@ -26,7 +26,7 @@ extension ValidateDFLT on DHTSchemaDFLT { extension ValidateSMPL on DHTSchemaSMPL { bool validate() { - final totalsv = members.fold(0, (acc, v) => (acc + v.mCnt)) + oCnt; + final totalsv = members.fold(0, (acc, v) => acc + v.mCnt) + oCnt; if (totalsv > 65535) { return false; } @@ -76,8 +76,8 @@ class DHTRecordDescriptor with _$DHTRecordDescriptor { const factory DHTRecordDescriptor({ required TypedKey key, required PublicKey owner, - PublicKey? ownerSecret, required DHTSchema schema, + PublicKey? ownerSecret, }) = _DHTRecordDescriptor; factory DHTRecordDescriptor.fromJson(dynamic json) => _$DHTRecordDescriptorFromJson(json as Map); @@ -138,9 +138,9 @@ enum Stability { lowLatency, reliable; - String toJson() => name.toPascalCase(); factory Stability.fromJson(dynamic j) => Stability.values.byName((j as String).toCamelCase()); + String toJson() => name.toPascalCase(); } ////////////////////////////////////// @@ -151,76 +151,70 @@ enum Sequencing { preferOrdered, ensureOrdered; - String toJson() => name.toPascalCase(); factory Sequencing.fromJson(dynamic j) => Sequencing.values.byName((j as String).toCamelCase()); + String toJson() => name.toPascalCase(); } ////////////////////////////////////// /// SafetySelection @immutable -abstract class SafetySelection extends Equatable { +abstract class SafetySelection { factory SafetySelection.fromJson(dynamic jsond) { final json = jsond as Map; - if (json.containsKey("Unsafe")) { + if (json.containsKey('Unsafe')) { return SafetySelectionUnsafe( - sequencing: Sequencing.fromJson(json["Unsafe"])); - } else if (json.containsKey("Safe")) { - return SafetySelectionSafe(safetySpec: SafetySpec.fromJson(json["Safe"])); + sequencing: Sequencing.fromJson(json['Unsafe'])); + } else if (json.containsKey('Safe')) { + return SafetySelectionSafe(safetySpec: SafetySpec.fromJson(json['Safe'])); } else { - throw const VeilidAPIExceptionInternal("Invalid SafetySelection"); + throw const VeilidAPIExceptionInternal('Invalid SafetySelection'); } } Map toJson(); } @immutable -class SafetySelectionUnsafe implements SafetySelection { +class SafetySelectionUnsafe extends Equatable implements SafetySelection { + // + const SafetySelectionUnsafe({ + required this.sequencing, + }); final Sequencing sequencing; @override List get props => [sequencing]; @override bool? get stringify => null; - // - const SafetySelectionUnsafe({ - required this.sequencing, - }); - @override - Map toJson() { - return {'Unsafe': sequencing.toJson()}; - } + Map toJson() => {'Unsafe': sequencing.toJson()}; } @immutable -class SafetySelectionSafe implements SafetySelection { +class SafetySelectionSafe extends Equatable implements SafetySelection { + // + const SafetySelectionSafe({ + required this.safetySpec, + }); final SafetySpec safetySpec; @override List get props => [safetySpec]; @override bool? get stringify => null; - // - const SafetySelectionSafe({ - required this.safetySpec, - }); - @override - Map toJson() { - return {'Safe': safetySpec.toJson()}; - } + Map toJson() => {'Safe': safetySpec.toJson()}; } /// Options for safety routes (sender privacy) @freezed class SafetySpec with _$SafetySpec { const factory SafetySpec({ - String? preferredRoute, required int hopCount, required Stability stability, required Sequencing sequencing, + String? preferredRoute, }) = _SafetySpec; factory SafetySpec.fromJson(dynamic json) => diff --git a/veilid-flutter/lib/veilid.dart b/veilid-flutter/lib/veilid.dart index b9c370e6..b65ac68d 100644 --- a/veilid-flutter/lib/veilid.dart +++ b/veilid-flutter/lib/veilid.dart @@ -4,28 +4,26 @@ import 'dart:typed_data'; import 'package:equatable/equatable.dart'; import 'package:freezed_annotation/freezed_annotation.dart'; -import 'veilid_stub.dart' - if (dart.library.io) 'veilid_ffi.dart' - if (dart.library.js) 'veilid_js.dart'; - ////////////////////////////////////////////////////////// import 'routing_context.dart'; import 'veilid_config.dart'; import 'veilid_crypto.dart'; -import 'veilid_table_db.dart'; import 'veilid_state.dart'; +import 'veilid_stub.dart' + if (dart.library.io) 'veilid_ffi.dart' + if (dart.library.js) 'veilid_js.dart'; +import 'veilid_table_db.dart'; export 'default_config.dart'; export 'routing_context.dart'; - -export 'veilid_encoding.dart'; +export 'veilid.dart'; +export 'veilid_api_exception.dart'; export 'veilid_config.dart'; export 'veilid_crypto.dart'; -export 'veilid_table_db.dart'; -export 'veilid_api_exception.dart'; +export 'veilid_encoding.dart'; export 'veilid_state.dart'; -export 'veilid.dart'; +export 'veilid_table_db.dart'; ////////////////////////////////////// /// JSON Encode Helper @@ -41,57 +39,39 @@ Object? veilidApiToEncodable(Object? value) { throw UnsupportedError('Cannot convert to JSON: $value'); } -T? Function(dynamic) optFromJson( - T Function(Map) jsonConstructor) { - return (dynamic j) { - if (j == null) { - return null; - } else { - return jsonConstructor(j); - } - }; -} - List Function(dynamic) jsonListConstructor( - T Function(Map) jsonConstructor) { - return (dynamic j) { - return (j as List>) - .map((e) => jsonConstructor(e)) - .toList(); - }; -} + T Function(dynamic) jsonConstructor) => + (dynamic j) => (j as List).map((e) => jsonConstructor(e)).toList(); ////////////////////////////////////// /// VeilidVersion @immutable class VeilidVersion extends Equatable { + const VeilidVersion(this.major, this.minor, this.patch); final int major; final int minor; final int patch; @override List get props => [major, minor, patch]; - - const VeilidVersion(this.major, this.minor, this.patch); } ////////////////////////////////////// /// Timestamp @immutable class Timestamp extends Equatable { + const Timestamp({required this.value}); + factory Timestamp.fromString(String s) => Timestamp(value: BigInt.parse(s)); + factory Timestamp.fromJson(dynamic json) => + Timestamp.fromString(json as String); final BigInt value; @override List get props => [value]; - const Timestamp({required this.value}); - @override String toString() => value.toString(); - factory Timestamp.fromString(String s) => Timestamp(value: BigInt.parse(s)); String toJson() => toString(); - factory Timestamp.fromJson(dynamic json) => - Timestamp.fromString(json as String); TimestampDuration diff(Timestamp other) => TimestampDuration(value: value - other.value); @@ -102,20 +82,19 @@ class Timestamp extends Equatable { @immutable class TimestampDuration extends Equatable { + const TimestampDuration({required this.value}); + factory TimestampDuration.fromString(String s) => + TimestampDuration(value: BigInt.parse(s)); + factory TimestampDuration.fromJson(dynamic json) => + TimestampDuration.fromString(json as String); final BigInt value; @override List get props => [value]; - const TimestampDuration({required this.value}); - @override String toString() => value.toString(); - factory TimestampDuration.fromString(String s) => - TimestampDuration(value: BigInt.parse(s)); String toJson() => toString(); - factory TimestampDuration.fromJson(dynamic json) => - TimestampDuration.fromString(json as String); int toMillis() => (value ~/ BigInt.from(1000)).toInt(); BigInt toMicros() => value; diff --git a/veilid-flutter/lib/veilid_api_exception.dart b/veilid-flutter/lib/veilid_api_exception.dart index e08525bb..433114e9 100644 --- a/veilid-flutter/lib/veilid_api_exception.dart +++ b/veilid-flutter/lib/veilid_api_exception.dart @@ -5,70 +5,73 @@ import 'package:freezed_annotation/freezed_annotation.dart'; @immutable abstract class VeilidAPIException implements Exception { - factory VeilidAPIException.fromJson(dynamic json) { - switch (json["kind"]) { - case "NotInitialized": + factory VeilidAPIException.fromJson(dynamic j) { + final json = j as Map; + switch (json['kind']! as String) { + case 'NotInitialized': { return VeilidAPIExceptionNotInitialized(); } - case "AlreadyInitialized": + case 'AlreadyInitialized': { return VeilidAPIExceptionAlreadyInitialized(); } - case "Timeout": + case 'Timeout': { return VeilidAPIExceptionTimeout(); } - case "TryAgain": + case 'TryAgain': { return VeilidAPIExceptionTryAgain(); } - case "Shutdown": + case 'Shutdown': { return VeilidAPIExceptionShutdown(); } - case "InvalidTarget": + case 'InvalidTarget': { return VeilidAPIExceptionInvalidTarget(); } - case "NoConnection": + case 'NoConnection': { - return VeilidAPIExceptionNoConnection(json["message"]); + return VeilidAPIExceptionNoConnection(json['message']! as String); } - case "KeyNotFound": + case 'KeyNotFound': { - return VeilidAPIExceptionKeyNotFound(json["key"]); + return VeilidAPIExceptionKeyNotFound(json['key']! as String); } - case "Internal": + case 'Internal': { - return VeilidAPIExceptionInternal(json["message"]); + return VeilidAPIExceptionInternal(json['message']! as String); } - case "Unimplemented": + case 'Unimplemented': { - return VeilidAPIExceptionUnimplemented(json["unimplemented"]); + return VeilidAPIExceptionUnimplemented( + json['unimplemented']! as String); } - case "ParseError": + case 'ParseError': { - return VeilidAPIExceptionParseError(json["message"], json["value"]); + return VeilidAPIExceptionParseError( + json['message']! as String, json['value']! as String); } - case "InvalidArgument": + case 'InvalidArgument': { - return VeilidAPIExceptionInvalidArgument( - json["context"], json["argument"], json["value"]); + return VeilidAPIExceptionInvalidArgument(json['context']! as String, + json['argument']! as String, json['value']! as String); } - case "MissingArgument": + case 'MissingArgument': { return VeilidAPIExceptionMissingArgument( - json["context"], json["argument"]); + json['context']! as String, json['argument']! as String); } - case "Generic": + case 'Generic': { - return VeilidAPIExceptionGeneric(json["message"]); + return VeilidAPIExceptionGeneric(json['message']! as String); } default: { throw VeilidAPIExceptionInternal( - "Invalid VeilidAPIException type: ${json['kind']}"); + "Invalid VeilidAPIException type: ${json['kind']! as String}"); } } } @@ -79,224 +82,163 @@ abstract class VeilidAPIException implements Exception { @immutable class VeilidAPIExceptionNotInitialized implements VeilidAPIException { @override - String toString() { - return "VeilidAPIException: NotInitialized"; - } + String toString() => 'VeilidAPIException: NotInitialized'; @override - String toDisplayError() { - return "Not initialized"; - } + String toDisplayError() => 'Not initialized'; } @immutable class VeilidAPIExceptionAlreadyInitialized implements VeilidAPIException { @override - String toString() { - return "VeilidAPIException: AlreadyInitialized"; - } + String toString() => 'VeilidAPIException: AlreadyInitialized'; @override - String toDisplayError() { - return "Already initialized"; - } + String toDisplayError() => 'Already initialized'; } @immutable class VeilidAPIExceptionTimeout implements VeilidAPIException { @override - String toString() { - return "VeilidAPIException: Timeout"; - } + String toString() => 'VeilidAPIException: Timeout'; @override - String toDisplayError() { - return "Timeout"; - } + String toDisplayError() => 'Timeout'; } @immutable class VeilidAPIExceptionTryAgain implements VeilidAPIException { @override - String toString() { - return "VeilidAPIException: TryAgain"; - } + String toString() => 'VeilidAPIException: TryAgain'; @override - String toDisplayError() { - return "Try again"; - } + String toDisplayError() => 'Try again'; } @immutable class VeilidAPIExceptionShutdown implements VeilidAPIException { @override - String toString() { - return "VeilidAPIException: Shutdown"; - } + String toString() => 'VeilidAPIException: Shutdown'; @override - String toDisplayError() { - return "Currently shut down"; - } + String toDisplayError() => 'Currently shut down'; } @immutable class VeilidAPIExceptionInvalidTarget implements VeilidAPIException { @override - String toString() { - return "VeilidAPIException: InvalidTarget"; - } + String toString() => 'VeilidAPIException: InvalidTarget'; @override - String toDisplayError() { - return "Invalid target"; - } + String toDisplayError() => 'Invalid target'; } @immutable class VeilidAPIExceptionNoConnection implements VeilidAPIException { - final String message; - @override - String toString() { - return "VeilidAPIException: NoConnection (message: $message)"; - } - - @override - String toDisplayError() { - return "No connection: $message"; - } - // const VeilidAPIExceptionNoConnection(this.message); + final String message; + @override + String toString() => 'VeilidAPIException: NoConnection (message: $message)'; + + @override + String toDisplayError() => 'No connection: $message'; } @immutable class VeilidAPIExceptionKeyNotFound implements VeilidAPIException { - final String key; - @override - String toString() { - return "VeilidAPIException: KeyNotFound (key: $key)"; - } - - @override - String toDisplayError() { - return "Key not found: $key"; - } - // const VeilidAPIExceptionKeyNotFound(this.key); + final String key; + @override + String toString() => 'VeilidAPIException: KeyNotFound (key: $key)'; + + @override + String toDisplayError() => 'Key not found: $key'; } @immutable class VeilidAPIExceptionInternal implements VeilidAPIException { + // + const VeilidAPIExceptionInternal(this.message); final String message; @override - String toString() { - return "VeilidAPIException: Internal ($message)"; - } + String toString() => 'VeilidAPIException: Internal ($message)'; @override - String toDisplayError() { - return "Internal error: $message"; - } - - // - const VeilidAPIExceptionInternal(this.message); + String toDisplayError() => 'Internal error: $message'; } @immutable class VeilidAPIExceptionUnimplemented implements VeilidAPIException { + // + const VeilidAPIExceptionUnimplemented(this.message); final String message; @override - String toString() { - return "VeilidAPIException: Unimplemented ($message)"; - } + String toString() => 'VeilidAPIException: Unimplemented ($message)'; @override - String toDisplayError() { - return "Unimplemented: $message"; - } - - // - const VeilidAPIExceptionUnimplemented(this.message); + String toDisplayError() => 'Unimplemented: $message'; } @immutable class VeilidAPIExceptionParseError implements VeilidAPIException { + // + const VeilidAPIExceptionParseError(this.message, this.value); final String message; final String value; @override - String toString() { - return "VeilidAPIException: ParseError ($message)\n value: $value"; - } + String toString() => + 'VeilidAPIException: ParseError ($message)\n value: $value'; @override - String toDisplayError() { - return "Parse error: $message"; - } - - // - const VeilidAPIExceptionParseError(this.message, this.value); + String toDisplayError() => 'Parse error: $message'; } @immutable class VeilidAPIExceptionInvalidArgument implements VeilidAPIException { + // + const VeilidAPIExceptionInvalidArgument( + this.context, this.argument, this.value); final String context; final String argument; final String value; @override - String toString() { - return "VeilidAPIException: InvalidArgument ($context:$argument)\n value: $value"; - } + String toString() => 'VeilidAPIException: InvalidArgument' + ' ($context:$argument)\n value: $value'; @override - String toDisplayError() { - return "Invalid argument for $context: $argument"; - } - - // - const VeilidAPIExceptionInvalidArgument( - this.context, this.argument, this.value); + String toDisplayError() => 'Invalid argument for $context: $argument'; } @immutable class VeilidAPIExceptionMissingArgument implements VeilidAPIException { + // + const VeilidAPIExceptionMissingArgument(this.context, this.argument); final String context; final String argument; @override - String toString() { - return "VeilidAPIException: MissingArgument ($context:$argument)"; - } + String toString() => + 'VeilidAPIException: MissingArgument ($context:$argument)'; @override - String toDisplayError() { - return "Missing argument for $context: $argument"; - } - - // - const VeilidAPIExceptionMissingArgument(this.context, this.argument); + String toDisplayError() => 'Missing argument for $context: $argument'; } @immutable class VeilidAPIExceptionGeneric implements VeilidAPIException { + // + const VeilidAPIExceptionGeneric(this.message); final String message; @override - String toString() { - return "VeilidAPIException: Generic (message: $message)"; - } + String toString() => 'VeilidAPIException: Generic (message: $message)'; @override - String toDisplayError() { - return message; - } - - // - const VeilidAPIExceptionGeneric(this.message); + String toDisplayError() => message; } diff --git a/veilid-flutter/lib/veilid_config.dart b/veilid-flutter/lib/veilid_config.dart index bce2437f..09de9ac6 100644 --- a/veilid-flutter/lib/veilid_config.dart +++ b/veilid-flutter/lib/veilid_config.dart @@ -1,9 +1,8 @@ -import 'package:freezed_annotation/freezed_annotation.dart'; -import 'package:flutter/foundation.dart'; import 'package:change_case/change_case.dart'; +import 'package:flutter/foundation.dart'; +import 'package:freezed_annotation/freezed_annotation.dart'; + import 'veilid.dart'; -import 'veilid_encoding.dart'; -import 'veilid_crypto.dart'; part 'veilid_config.freezed.dart'; part 'veilid_config.g.dart'; @@ -126,13 +125,9 @@ enum VeilidConfigLogLevel { debug, trace; - String toJson() { - return name.toPascalCase(); - } - - factory VeilidConfigLogLevel.fromJson(dynamic j) { - return VeilidConfigLogLevel.values.byName((j as String).toCamelCase()); - } + factory VeilidConfigLogLevel.fromJson(dynamic j) => + VeilidConfigLogLevel.values.byName((j as String).toCamelCase()); + String toJson() => name.toPascalCase(); } ////////////////////////////////////// @@ -300,11 +295,11 @@ class VeilidConfigRPC with _$VeilidConfigRPC { const factory VeilidConfigRPC( {required int concurrency, required int queueSize, - int? maxTimestampBehindMs, - int? maxTimestampAheadMs, required int timeoutMs, required int maxRouteHopCount, - required int defaultRouteHopCount}) = _VeilidConfigRPC; + required int defaultRouteHopCount, + int? maxTimestampBehindMs, + int? maxTimestampAheadMs}) = _VeilidConfigRPC; factory VeilidConfigRPC.fromJson(dynamic json) => _$VeilidConfigRPCFromJson(json as Map); @@ -343,7 +338,6 @@ class VeilidConfigNetwork with _$VeilidConfigNetwork { required int clientWhitelistTimeoutMs, required int reverseConnectionReceiptTimeMs, required int holePunchReceiptTimeMs, - String? networkKeyPassword, required VeilidConfigRoutingTable routingTable, required VeilidConfigRPC rpc, required VeilidConfigDHT dht, @@ -353,6 +347,7 @@ class VeilidConfigNetwork with _$VeilidConfigNetwork { required VeilidConfigTLS tls, required VeilidConfigApplication application, required VeilidConfigProtocol protocol, + String? networkKeyPassword, }) = _VeilidConfigNetwork; factory VeilidConfigNetwork.fromJson(dynamic json) => diff --git a/veilid-flutter/lib/veilid_crypto.dart b/veilid-flutter/lib/veilid_crypto.dart index 98c20f90..97686ec7 100644 --- a/veilid-flutter/lib/veilid_crypto.dart +++ b/veilid-flutter/lib/veilid_crypto.dart @@ -5,7 +5,6 @@ import 'package:charcode/charcode.dart'; import 'package:equatable/equatable.dart'; import 'package:freezed_annotation/freezed_annotation.dart'; -import 'veilid_encoding.dart'; import 'veilid.dart'; ////////////////////////////////////// @@ -17,24 +16,23 @@ const CryptoKind cryptoKindVLD0 = const CryptoKind cryptoKindNONE = $N << 0 | $O << 8 | $N << 16 | $E << 24; // "NONE" -String cryptoKindToString(CryptoKind kind) { - return cryptoKindToBytes(kind).map((c) => String.fromCharCode(c)).join(); -} +String cryptoKindToString(CryptoKind kind) => + cryptoKindToBytes(kind).map(String.fromCharCode).join(); const CryptoKind bestCryptoKind = cryptoKindVLD0; Uint8List cryptoKindToBytes(CryptoKind kind) { - var b = Uint8List(4); - ByteData.sublistView(b).setUint32(0, kind, Endian.big); + final b = Uint8List(4); + ByteData.sublistView(b).setUint32(0, kind); return b; } CryptoKind cryptoKindFromString(String s) { if (s.codeUnits.length != 4) { - throw const FormatException("malformed string"); + throw const FormatException('malformed string'); } - CryptoKind kind = ByteData.sublistView(Uint8List.fromList(s.codeUnits)) - .getUint32(0, Endian.big); + final kind = + ByteData.sublistView(Uint8List.fromList(s.codeUnits)).getUint32(0); return kind; } @@ -43,103 +41,95 @@ CryptoKind cryptoKindFromString(String s) { @immutable class Typed extends Equatable { + const Typed({required this.kind, required this.value}); + + factory Typed.fromString(String s) { + final parts = s.split(':'); + if (parts.length < 2 || parts[0].codeUnits.length != 4) { + throw const FormatException('malformed string'); + } + final kind = cryptoKindFromString(parts[0]); + final value = EncodedString.fromString(parts.sublist(1).join(':')); + return Typed(kind: kind, value: value); + } + factory Typed.fromJson(dynamic json) => Typed.fromString(json as String); final CryptoKind kind; final V value; @override List get props => [kind, value]; - const Typed({required this.kind, required this.value}); - @override - String toString() { - return "${cryptoKindToString(kind)}:$value"; - } - - factory Typed.fromString(String s) { - final parts = s.split(":"); - if (parts.length < 2 || parts[0].codeUnits.length != 4) { - throw const FormatException("malformed string"); - } - final kind = cryptoKindFromString(parts[0]); - final value = EncodedString.fromString(parts.sublist(1).join(":")); - return Typed(kind: kind, value: value); - } + String toString() => '${cryptoKindToString(kind)}:$value'; Uint8List decode() { - var b = BytesBuilder(); - b.add(cryptoKindToBytes(kind)); - b.add(value.decode()); + final b = BytesBuilder() + ..add(cryptoKindToBytes(kind)) + ..add(value.decode()); return b.toBytes(); } String toJson() => toString(); - factory Typed.fromJson(dynamic json) => Typed.fromString(json as String); } @immutable class KeyPair extends Equatable { - final PublicKey key; - final PublicKey secret; - @override - List get props => [key, secret]; - const KeyPair({required this.key, required this.secret}); - @override - String toString() { - return "${key.toString()}:${secret.toString()}"; - } - factory KeyPair.fromString(String s) { - final parts = s.split(":"); + final parts = s.split(':'); if (parts.length != 2 || parts[0].codeUnits.length != 43 || parts[1].codeUnits.length != 43) { - throw const FormatException("malformed string"); + throw const FormatException('malformed string'); } final key = PublicKey.fromString(parts[0]); final secret = PublicKey.fromString(parts[1]); return KeyPair(key: key, secret: secret); } + factory KeyPair.fromJson(dynamic json) => KeyPair.fromString(json as String); + final PublicKey key; + final PublicKey secret; + @override + List get props => [key, secret]; + + @override + String toString() => '$key:$secret'; String toJson() => toString(); - factory KeyPair.fromJson(dynamic json) => KeyPair.fromString(json as String); } @immutable class TypedKeyPair extends Equatable { - final CryptoKind kind; - final PublicKey key; - final PublicKey secret; - @override - List get props => [kind, key, secret]; - const TypedKeyPair( {required this.kind, required this.key, required this.secret}); - @override - String toString() => - "${cryptoKindToString(kind)}:${key.toString()}:${secret.toString()}"; - factory TypedKeyPair.fromString(String s) { - final parts = s.split(":"); + final parts = s.split(':'); if (parts.length != 3 || parts[0].codeUnits.length != 4 || parts[1].codeUnits.length != 43 || parts[2].codeUnits.length != 43) { - throw VeilidAPIExceptionInvalidArgument("malformed string", "s", s); + throw VeilidAPIExceptionInvalidArgument('malformed string', 's', s); } final kind = cryptoKindFromString(parts[0]); final key = PublicKey.fromString(parts[1]); final secret = PublicKey.fromString(parts[2]); return TypedKeyPair(kind: kind, key: key, secret: secret); } - - String toJson() => toString(); factory TypedKeyPair.fromJson(dynamic json) => TypedKeyPair.fromString(json as String); factory TypedKeyPair.fromKeyPair(CryptoKind kind, KeyPair keyPair) => TypedKeyPair(kind: kind, key: keyPair.key, secret: keyPair.secret); + final CryptoKind kind; + final PublicKey key; + final PublicKey secret; + @override + List get props => [kind, key, secret]; + + @override + String toString() => '${cryptoKindToString(kind)}:$key:$secret'; + + String toJson() => toString(); } typedef CryptoKey = FixedEncodedString43; @@ -176,17 +166,15 @@ abstract class VeilidCryptoSystem { Future generateHash(Uint8List data); //Future generateHashReader(Stream> reader); Future validateKeyPair(PublicKey key, SecretKey secret); - Future validateKeyPairWithKeyPair(KeyPair keyPair) { - return validateKeyPair(keyPair.key, keyPair.secret); - } + Future validateKeyPairWithKeyPair(KeyPair keyPair) => + validateKeyPair(keyPair.key, keyPair.secret); Future validateHash(Uint8List data, HashDigest hash); //Future validateHashReader(Stream> reader, HashDigest hash); Future distance(CryptoKey key1, CryptoKey key2); Future sign(PublicKey key, SecretKey secret, Uint8List data); - Future signWithKeyPair(KeyPair keyPair, Uint8List data) { - return sign(keyPair.key, keyPair.secret, data); - } + Future signWithKeyPair(KeyPair keyPair, Uint8List data) => + sign(keyPair.key, keyPair.secret, data); Future verify(PublicKey key, Uint8List data, Signature signature); Future aeadOverhead(); diff --git a/veilid-flutter/lib/veilid_encoding.dart b/veilid-flutter/lib/veilid_encoding.dart index d10c1f28..316df202 100644 --- a/veilid-flutter/lib/veilid_encoding.dart +++ b/veilid-flutter/lib/veilid_encoding.dart @@ -34,15 +34,13 @@ class Uint8ListJsonConverter implements JsonConverter { @immutable abstract class EncodedString extends Equatable { + + const EncodedString(String s) : contents = s; final String contents; @override List get props => [contents]; - const EncodedString(String s) : contents = s; - - Uint8List decode() { - return base64UrlNoPadDecode(contents); - } + Uint8List decode() => base64UrlNoPadDecode(contents); @override String toString() => contents; @@ -76,96 +74,82 @@ abstract class EncodedString extends Equatable { @immutable class FixedEncodedString32 extends EncodedString { - const FixedEncodedString32._(String s) : super(s); - static int encodedLength() { - return 32; - } - - static int decodedLength() { - return 24; - } factory FixedEncodedString32.fromBytes(Uint8List bytes) { if (bytes.length != decodedLength()) { - throw Exception("length ${bytes.length} should be ${decodedLength()}"); + throw Exception('length ${bytes.length} should be ${decodedLength()}'); } return FixedEncodedString32._(base64UrlNoPadEncode(bytes)); } factory FixedEncodedString32.fromString(String s) { - var d = base64UrlNoPadDecode(s); + final d = base64UrlNoPadDecode(s); if (d.length != decodedLength()) { - throw Exception("length ${s.length} should be ${encodedLength()}"); + throw Exception('length ${s.length} should be ${encodedLength()}'); } return FixedEncodedString32._(s); } - - String toJson() => toString(); factory FixedEncodedString32.fromJson(dynamic json) => FixedEncodedString32.fromString(json as String); + const FixedEncodedString32._(super.s); + static int encodedLength() => 32; + + static int decodedLength() => 24; + + String toJson() => toString(); } @immutable class FixedEncodedString43 extends EncodedString { - const FixedEncodedString43._(String s) : super(s); - static int encodedLength() { - return 43; - } - - static int decodedLength() { - return 32; - } factory FixedEncodedString43.fromBytes(Uint8List bytes) { if (bytes.length != decodedLength()) { - throw Exception("length ${bytes.length} should be ${decodedLength()}"); + throw Exception('length ${bytes.length} should be ${decodedLength()}'); } return FixedEncodedString43._(base64UrlNoPadEncode(bytes)); } factory FixedEncodedString43.fromString(String s) { - var d = base64UrlNoPadDecode(s); + final d = base64UrlNoPadDecode(s); if (d.length != decodedLength()) { - throw Exception("length ${s.length} should be ${encodedLength()}"); + throw Exception('length ${s.length} should be ${encodedLength()}'); } return FixedEncodedString43._(s); } - - String toJson() => toString(); factory FixedEncodedString43.fromJson(dynamic json) => FixedEncodedString43.fromString(json as String); + const FixedEncodedString43._(super.s); + static int encodedLength() => 43; + + static int decodedLength() => 32; + + String toJson() => toString(); } @immutable class FixedEncodedString86 extends EncodedString { - const FixedEncodedString86._(String s) : super(s); - static int encodedLength() { - return 86; - } - - static int decodedLength() { - return 64; - } - - String toJson() { - return toString(); - } factory FixedEncodedString86.fromBytes(Uint8List bytes) { if (bytes.length != decodedLength()) { - throw Exception("length ${bytes.length} should be ${decodedLength()}"); + throw Exception('length ${bytes.length} should be ${decodedLength()}'); } return FixedEncodedString86._(base64UrlNoPadEncode(bytes)); } factory FixedEncodedString86.fromString(String s) { - var d = base64UrlNoPadDecode(s); + final d = base64UrlNoPadDecode(s); if (d.length != decodedLength()) { - throw Exception("length ${s.length} should be ${encodedLength()}"); + throw Exception('length ${s.length} should be ${encodedLength()}'); } return FixedEncodedString86._(s); } factory FixedEncodedString86.fromJson(dynamic json) => FixedEncodedString86.fromString(json as String); + const FixedEncodedString86._(super.s); + static int encodedLength() => 86; + + static int decodedLength() => 64; + + String toJson() => toString(); } diff --git a/veilid-flutter/lib/veilid_ffi.dart b/veilid-flutter/lib/veilid_ffi.dart index 73880aa3..cf899832 100644 --- a/veilid-flutter/lib/veilid_ffi.dart +++ b/veilid-flutter/lib/veilid_ffi.dart @@ -1,14 +1,13 @@ import 'dart:async'; +import 'dart:convert'; import 'dart:ffi'; import 'dart:io'; import 'dart:isolate'; -import 'dart:convert'; import 'dart:typed_data'; import 'package:ffi/ffi.dart'; import 'veilid.dart'; -import 'veilid_encoding.dart'; ////////////////////////////////////////////////////////// @@ -26,282 +25,199 @@ final _dylib = typedef _DartPostCObject = NativeFunction)>; // fn free_string(s: *mut std::os::raw::c_char) -typedef _FreeStringC = Void Function(Pointer); typedef _FreeStringDart = void Function(Pointer); -// fn initialize_veilid_flutter(dart_post_c_object_ptr: ffi::DartPostCObjectFnType) -typedef _InitializeVeilidFlutterC = Void Function(Pointer<_DartPostCObject>); -typedef _InitializeVeilidFlutterDart = void Function(Pointer<_DartPostCObject>); +// fn initialize_veilid_flutter( +// dart_post_c_object_ptr: ffi::DartPostCObjectFnType) // fn initialize_veilid_core(platform_config: FfiStr) -typedef _InitializeVeilidCoreC = Void Function(Pointer); typedef _InitializeVeilidCoreDart = void Function(Pointer); // fn change_log_level(layer: FfiStr, log_level: FfiStr) -typedef _ChangeLogLevelC = Void Function(Pointer, Pointer); typedef _ChangeLogLevelDart = void Function(Pointer, Pointer); // fn startup_veilid_core(port: i64, config: FfiStr) -typedef _StartupVeilidCoreC = Void Function(Int64, Int64, Pointer); typedef _StartupVeilidCoreDart = void Function(int, int, Pointer); // fn get_veilid_state(port: i64) -typedef _GetVeilidStateC = Void Function(Int64); typedef _GetVeilidStateDart = void Function(int); // fn attach(port: i64) -typedef _AttachC = Void Function(Int64); typedef _AttachDart = void Function(int); // fn detach(port: i64) -typedef _DetachC = Void Function(Int64); typedef _DetachDart = void Function(int); // fn routing_context(port: i64) -typedef _RoutingContextC = Void Function(Int64); typedef _RoutingContextDart = void Function(int); // fn release_routing_context(id: u32) -typedef _ReleaseRoutingContextC = Int32 Function(Uint32); typedef _ReleaseRoutingContextDart = int Function(int); // fn routing_context_with_privacy(id: u32) -> u32 -typedef _RoutingContextWithPrivacyC = Uint32 Function(Uint32); typedef _RoutingContextWithPrivacyDart = int Function(int); // fn routing_context_with_custom_privacy(id: u32, stability: FfiStr) -typedef _RoutingContextWithCustomPrivacyC = Uint32 Function( - Uint32, Pointer); typedef _RoutingContextWithCustomPrivacyDart = int Function(int, Pointer); // fn routing_context_with_sequencing(id: u32, sequencing: FfiStr) -typedef _RoutingContextWithSequencingC = Uint32 Function(Uint32, Pointer); typedef _RoutingContextWithSequencingDart = int Function(int, Pointer); -// fn routing_context_app_call(port: i64, id: u32, target: FfiStr, request: FfiStr) -typedef _RoutingContextAppCallC = Void Function( - Int64, Uint32, Pointer, Pointer); +// fn routing_context_app_call(port: i64, +// id: u32, target: FfiStr, request: FfiStr) typedef _RoutingContextAppCallDart = void Function( int, int, Pointer, Pointer); -// fn routing_context_app_message(port: i64, id: u32, target: FfiStr, request: FfiStr) -typedef _RoutingContextAppMessageC = Void Function( - Int64, Uint32, Pointer, Pointer); +// fn routing_context_app_message(port: i64, +// id: u32, target: FfiStr, request: FfiStr) typedef _RoutingContextAppMessageDart = void Function( int, int, Pointer, Pointer); -// fn routing_context_create_dht_record(port: i64, id: u32, kind: u32, schema: FfiStr) -typedef _RoutingContextCreateDHTRecordC = Void Function( - Int64, Uint32, Pointer, Uint32); +// fn routing_context_create_dht_record(port: i64, +// id: u32, kind: u32, schema: FfiStr) typedef _RoutingContextCreateDHTRecordDart = void Function( int, int, Pointer, int); -// fn routing_context_open_dht_record(port: i64, id: u32, key: FfiStr, writer: FfiStr) -typedef _RoutingContextOpenDHTRecordC = Void Function( - Int64, Uint32, Pointer, Pointer); +// fn routing_context_open_dht_record(port: i64, +// id: u32, key: FfiStr, writer: FfiStr) typedef _RoutingContextOpenDHTRecordDart = void Function( int, int, Pointer, Pointer); // fn routing_context_close_dht_record(port: i64, id: u32, key: FfiStr) -typedef _RoutingContextCloseDHTRecordC = Void Function( - Int64, Uint32, Pointer); typedef _RoutingContextCloseDHTRecordDart = void Function( int, int, Pointer); // fn routing_context_delete_dht_record(port: i64, id: u32, key: FfiStr) -typedef _RoutingContextDeleteDHTRecordC = Void Function( - Int64, Uint32, Pointer); typedef _RoutingContextDeleteDHTRecordDart = void Function( int, int, Pointer); -// fn routing_context_get_dht_value(port: i64, id: u32, key: FfiStr, subkey: u32, force_refresh: bool) -typedef _RoutingContextGetDHTValueC = Void Function( - Int64, Uint32, Pointer, Uint32, Bool); +// fn routing_context_get_dht_value(port: i64, +// id: u32, key: FfiStr, subkey: u32, force_refresh: bool) typedef _RoutingContextGetDHTValueDart = void Function( int, int, Pointer, int, bool); -// fn routing_context_set_dht_value(port: i64, id: u32, key: FfiStr, subkey: u32, data: FfiStr) -typedef _RoutingContextSetDHTValueC = Void Function( - Int64, Uint32, Pointer, Uint32, Pointer); +// fn routing_context_set_dht_value(port: i64, +// id: u32, key: FfiStr, subkey: u32, data: FfiStr) typedef _RoutingContextSetDHTValueDart = void Function( int, int, Pointer, int, Pointer); -// fn routing_context_watch_dht_values(port: i64, id: u32, key: FfiStr, subkeys: FfiStr, expiration: FfiStr, count: u32) -typedef _RoutingContextWatchDHTValuesC = Void Function( - Int64, Uint32, Pointer, Pointer, Uint64, Uint32); +// fn routing_context_watch_dht_values(port: i64, +// id: u32, key: FfiStr, subkeys: FfiStr, expiration: FfiStr, count: u32) typedef _RoutingContextWatchDHTValuesDart = void Function( int, int, Pointer, Pointer, int, int); -// fn routing_context_cancel_dht_watch(port: i64, id: u32, key: FfiStr, subkeys: FfiStr) -typedef _RoutingContextCancelDHTWatchC = Void Function( - Int64, Uint32, Pointer, Pointer); +// fn routing_context_cancel_dht_watch(port: i64, +// id: u32, key: FfiStr, subkeys: FfiStr) typedef _RoutingContextCancelDHTWatchDart = void Function( int, int, Pointer, Pointer); // fn new_private_route(port: i64) -typedef _NewPrivateRouteC = Void Function(Int64); typedef _NewPrivateRouteDart = void Function(int); // fn new_custom_private_route(port: i64, stability: FfiStr, sequencing: FfiStr) -typedef _NewCustomPrivateRouteC = Void Function( - Int64, Pointer, Pointer); typedef _NewCustomPrivateRouteDart = void Function( int, Pointer, Pointer); // fn import_remote_private_route(port: i64, blob: FfiStr) -typedef _ImportRemotePrivateRouteC = Void Function(Int64, Pointer); typedef _ImportRemotePrivateRouteDart = void Function(int, Pointer); // fn release_private_route(port:i64, key: FfiStr) -typedef _ReleasePrivateRouteC = Void Function(Int64, Pointer); typedef _ReleasePrivateRouteDart = void Function(int, Pointer); // fn app_call_reply(port: i64, id: FfiStr, message: FfiStr) -typedef _AppCallReplyC = Void Function(Int64, Pointer, Pointer); typedef _AppCallReplyDart = void Function(int, Pointer, Pointer); // fn open_table_db(port: i64, name: FfiStr, column_count: u32) -typedef _OpenTableDbC = Void Function(Int64, Pointer, Uint32); typedef _OpenTableDbDart = void Function(int, Pointer, int); // fn release_table_db(id: u32) -> i32 -typedef _ReleaseTableDbC = Int32 Function(Uint32); typedef _ReleaseTableDbDart = int Function(int); // fn delete_table_db(port: i64, name: FfiStr) -typedef _DeleteTableDbC = Void Function(Int64, Pointer); typedef _DeleteTableDbDart = void Function(int, Pointer); // fn table_db_get_column_count(id: u32) -> u32 -typedef _TableDbGetColumnCountC = Uint32 Function(Uint32); typedef _TableDbGetColumnCountDart = int Function(int); // fn table_db_get_keys(port: i64, id: u32, col: u32) -typedef _TableDbGetKeysC = Pointer Function(Uint64, Uint32, Uint32); typedef _TableDbGetKeysDart = Pointer Function(int, int, int); // fn table_db_store(port: i64, id: u32, col: u32, key: FfiStr, value: FfiStr) -typedef _TableDbStoreC = Void Function( - Int64, Uint32, Uint32, Pointer, Pointer); typedef _TableDbStoreDart = void Function( int, int, int, Pointer, Pointer); // fn table_db_load(port: i64, id: u32, col: u32, key: FfiStr) -typedef _TableDbLoadC = Void Function(Int64, Uint32, Uint32, Pointer); typedef _TableDbLoadDart = void Function(int, int, int, Pointer); // fn table_db_delete(port: i64, id: u32, col: u32, key: FfiStr) -typedef _TableDbDeleteC = Void Function(Int64, Uint32, Uint32, Pointer); typedef _TableDbDeleteDart = void Function(int, int, int, Pointer); // fn table_db_transact(id: u32) -> u32 -typedef _TableDbTransactC = Uint32 Function(Uint32); typedef _TableDbTransactDart = int Function(int); // fn release_table_db_transaction(id: u32) -> i32 -typedef _ReleaseTableDbTransactionC = Int32 Function(Uint32); typedef _ReleaseTableDbTransactionDart = int Function(int); // fn table_db_transaction_commit(port: i64, id: u32) -typedef _TableDbTransactionCommitC = Void Function(Uint64, Uint32); typedef _TableDbTransactionCommitDart = void Function(int, int); // fn table_db_transaction_rollback(port: i64, id: u32) -typedef _TableDbTransactionRollbackC = Void Function(Uint64, Uint32); typedef _TableDbTransactionRollbackDart = void Function(int, int); -// fn table_db_transaction_store(port: i64, id: u32, col: u32, key: FfiStr, value: FfiStr) -typedef _TableDbTransactionStoreC = Void Function( - Int64, Uint32, Uint32, Pointer, Pointer); +// fn table_db_transaction_store(port: i64, +// id: u32, col: u32, key: FfiStr, value: FfiStr) typedef _TableDbTransactionStoreDart = void Function( int, int, int, Pointer, Pointer); // fn table_db_transaction_delete(port: i64, id: u32, col: u32, key: FfiStr) -typedef _TableDbTransactionDeleteC = Void Function( - Int64, Uint32, Uint32, Pointer); typedef _TableDbTransactionDeleteDart = void Function( int, int, int, Pointer); // fn valid_crypto_kinds() -> *mut c_char -typedef _ValidCryptoKindsC = Pointer Function(); typedef _ValidCryptoKindsDart = Pointer Function(); // fn best_crypto_kind() -> u32 -typedef _BestCryptoKindC = Uint32 Function(); typedef _BestCryptoKindDart = int Function(); -// fn verify_signatures(port: i64, node_ids: FfiStr, data: FfiStr, signatures: FfiStr) -typedef _VerifySignaturesC = Void Function( - Int64, Pointer, Pointer, Pointer); +// fn verify_signatures(port: i64, +// node_ids: FfiStr, data: FfiStr, signatures: FfiStr) typedef _VerifySignaturesDart = void Function( int, Pointer, Pointer, Pointer); // fn generate_signatures(port: i64, data: FfiStr, key_pairs: FfiStr) -typedef _GenerateSignaturesC = Void Function( - Int64, Pointer, Pointer); typedef _GenerateSignaturesDart = void Function( int, Pointer, Pointer); // fn generate_key_pair(port: i64, kind: u32) { -typedef _GenerateKeyPairC = Void Function(Int64, Uint32); typedef _GenerateKeyPairDart = void Function(int, int); // fn crypto_cached_dh(port: i64, kind: u32, key: FfiStr, secret: FfiStr) -typedef _CryptoCachedDHC = Void Function( - Int64, Uint32, Pointer, Pointer); typedef _CryptoCachedDHDart = void Function( int, int, Pointer, Pointer); // fn crypto_compute_dh(port: i64, kind: u32, key: FfiStr, secret: FfiStr) -typedef _CryptoComputeDHC = Void Function( - Int64, Uint32, Pointer, Pointer); typedef _CryptoComputeDHDart = void Function( int, int, Pointer, Pointer); // fn crypto_random_bytes(port: i64, kind: u32, len: u32) -typedef _CryptoRandomBytesC = Void Function(Int64, Uint32, Uint32); typedef _CryptoRandomBytesDart = void Function(int, int, int); // fn crypto_default_salt_length(port: i64, kind: u32) -typedef _CryptoDefaultSaltLengthC = Void Function(Int64, Uint32); typedef _CryptoDefaultSaltLengthDart = void Function(int, int); -// fn crypto_hash_password(port: i64, kind: u32, password: FfiStr, salt: FfiStr ) -typedef _CryptoHashPasswordC = Void Function( - Int64, Uint32, Pointer, Pointer); +// fn crypto_hash_password(port: i64, kind: u32, password: FfiStr, salt: FfiStr) typedef _CryptoHashPasswordDart = void Function( int, int, Pointer, Pointer); -// fn crypto_verify_password(port: i64, kind: u32, password: FfiStr, password_hash: FfiStr ) -typedef _CryptoVerifyPasswordC = Void Function( - Int64, Uint32, Pointer, Pointer); +// fn crypto_verify_password(port: i64, +// kind: u32, password: FfiStr, password_hash: FfiStr ) typedef _CryptoVerifyPasswordDart = void Function( int, int, Pointer, Pointer); -// fn crypto_derive_shared_secret(port: i64, kind: u32, password: FfiStr, salt: FfiStr ) -typedef _CryptoDeriveSharedSecretC = Void Function( - Int64, Uint32, Pointer, Pointer); -typedef _CryptoDeriveSharedSecretDart = void Function( - int, int, Pointer, Pointer); +// fn crypto_derive_shared_secret(port: i64, +// kind: u32, password: FfiStr, salt: FfiStr ) // fn crypto_random_nonce(port: i64, kind: u32) -typedef _CryptoRandomNonceC = Void Function(Int64, Uint32); typedef _CryptoRandomNonceDart = void Function(int, int); // fn crypto_random_shared_secret(port: i64, kind: u32) -typedef _CryptoRandomSharedSecretC = Void Function(Int64, Uint32); typedef _CryptoRandomSharedSecretDart = void Function(int, int); // fn crypto_generate_key_pair(port: i64, kind: u32) -typedef _CryptoGenerateKeyPairC = Void Function(Int64, Uint32); typedef _CryptoGenerateKeyPairDart = void Function(int, int); // fn crypto_generate_hash(port: i64, kind: u32, data: FfiStr) -typedef _CryptoGenerateHashC = Void Function(Int64, Uint32, Pointer); typedef _CryptoGenerateHashDart = void Function(int, int, Pointer); -// fn crypto_validate_key_pair(port: i64, kind: u32, key: FfiStr, secret: FfiStr) -typedef _CryptoValidateKeyPairC = Void Function( - Int64, Uint32, Pointer, Pointer); +// fn crypto_validate_key_pair(port: i64, +// kind: u32, key: FfiStr, secret: FfiStr) typedef _CryptoValidateKeyPairDart = void Function( int, int, Pointer, Pointer); // fn crypto_validate_hash(port: i64, kind: u32, data: FfiStr, hash: FfiStr) -typedef _CryptoValidateHashC = Void Function( - Int64, Uint32, Pointer, Pointer); typedef _CryptoValidateHashDart = void Function( int, int, Pointer, Pointer); // fn crypto_distance(port: i64, kind: u32, key1: FfiStr, key2: FfiStr) -typedef _CryptoDistanceC = Void Function( - Int64, Uint32, Pointer, Pointer); typedef _CryptoDistanceDart = void Function( int, int, Pointer, Pointer); -// fn crypto_sign(port: i64, kind: u32, key: FfiStr, secret: FfiStr, data: FfiStr) -typedef _CryptoSignC = Void Function( - Int64, Uint32, Pointer, Pointer, Pointer); +// fn crypto_sign(port: i64, +// kind: u32, key: FfiStr, secret: FfiStr, data: FfiStr) typedef _CryptoSignDart = void Function( int, int, Pointer, Pointer, Pointer); -// fn crypto_verify(port: i64, kind: u32, key: FfiStr, data: FfiStr, signature: FfiStr) -typedef _CryptoVerifyC = Void Function( - Int64, Uint32, Pointer, Pointer, Pointer); +// fn crypto_verify(port: i64, +// kind: u32, key: FfiStr, data: FfiStr, signature: FfiStr) typedef _CryptoVerifyDart = void Function( int, int, Pointer, Pointer, Pointer); // fn crypto_aead_overhead(port: i64, kind: u32) -typedef _CryptoAeadOverheadC = Void Function(Int64, Uint32); typedef _CryptoAeadOverheadDart = void Function(int, int); -// fn crypto_decrypt_aead(port: i64, kind: u32, body: FfiStr, nonce: FfiStr, shared_secret: FfiStr, associated_data: FfiStr) -typedef _CryptoDecryptAeadC = Void Function( - Int64, Uint32, Pointer, Pointer, Pointer, Pointer); +// fn crypto_decrypt_aead(port: i64, +// kind: u32, body: FfiStr, nonce: FfiStr, +// shared_secret: FfiStr, associated_data: FfiStr) typedef _CryptoDecryptAeadDart = void Function( int, int, Pointer, Pointer, Pointer, Pointer); -// fn crypto_encrypt_aead(port: i64, kind: u32, body: FfiStr, nonce: FfiStr, shared_secret: FfiStr, associated_data: FfiStr) -typedef _CryptoEncryptAeadC = Void Function( - Int64, Uint32, Pointer, Pointer, Pointer, Pointer); +// fn crypto_encrypt_aead(port: i64, +// kind: u32, body: FfiStr, nonce: FfiStr, +// shared_secret: FfiStr, associated_data: FfiStr) typedef _CryptoEncryptAeadDart = void Function( int, int, Pointer, Pointer, Pointer, Pointer); -// fn crypto_crypt_no_auth(port: i64, kind: u32, body: FfiStr, nonce: FfiStr, shared_secret: FfiStr) -typedef _CryptoCryptNoAuthC = Void Function( - Int64, Uint32, Pointer, Pointer, Pointer); +// fn crypto_crypt_no_auth(port: i64, +// kind: u32, body: FfiStr, nonce: FfiStr, shared_secret: FfiStr) typedef _CryptoCryptNoAuthDart = void Function( int, int, Pointer, Pointer, Pointer); // fn now() -> u64 -typedef _NowC = Uint64 Function(); typedef _NowDart = int Function(); // fn debug(port: i64, log_level: FfiStr) -typedef _DebugC = Void Function(Int64, Pointer); typedef _DebugDart = void Function(int, Pointer); // fn shutdown_veilid_core(port: i64) -typedef _ShutdownVeilidCoreC = Void Function(Int64); typedef _ShutdownVeilidCoreDart = void Function(int); // fn veilid_version_string() -> *mut c_char -typedef _VeilidVersionStringC = Pointer Function(); typedef _VeilidVersionStringDart = Pointer Function(); // fn veilid_version() -> VeilidVersion @@ -314,7 +230,6 @@ final class VeilidVersionFFI extends Struct { external int patch; } -typedef _VeilidVersionC = VeilidVersionFFI Function(); typedef _VeilidVersionDart = VeilidVersionFFI Function(); // Async message types @@ -332,263 +247,250 @@ const int messageStreamClose = 8; Veilid getVeilid() => VeilidFFI(_dylib); // Parse handle async returns -Future processFuturePlain(Future future) { - return future.then((value) { - final list = value as List; - switch (list[0] as int) { - case messageOk: - { - if (list[1] == null && null is! T) { - throw const VeilidAPIExceptionInternal( - "Null MESSAGE_OK value on non-nullable type"); +Future processFuturePlain(Future future) async => + future.then((value) { + final list = value as List; + switch (list[0] as int) { + case messageOk: + { + if (list[1] == null && null is! T) { + throw const VeilidAPIExceptionInternal( + 'Null MESSAGE_OK value on non-nullable type'); + } + return list[1] as T; } - return list[1] as T; - } - case messageErr: - { - throw VeilidAPIExceptionInternal("Internal API Error: ${list[1]}"); - } - case messageErrJson: - { - throw VeilidAPIException.fromJson(jsonDecode(list[1])); - } - default: - { - throw VeilidAPIExceptionInternal( - "Unexpected async return message type: ${list[0]}"); - } - } - }).catchError((e) { - // Wrap all other errors in VeilidAPIExceptionInternal - throw VeilidAPIExceptionInternal(e.toString()); - }, test: (e) { - // Pass errors that are already VeilidAPIException through without wrapping - return e is! VeilidAPIException; - }); -} + case messageErr: + { + throw VeilidAPIExceptionInternal('Internal API Error: ${list[1]}'); + } + case messageErrJson: + { + throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); + } + default: + { + throw VeilidAPIExceptionInternal( + 'Unexpected async return message type: ${list[0]}'); + } + } + // ignore: inference_failure_on_untyped_parameter + }).catchError((e) { + // Wrap all other errors in VeilidAPIExceptionInternal + throw VeilidAPIExceptionInternal(e.toString()); + }, test: (e) => e is! VeilidAPIException); Future processFutureJson( - T Function(dynamic) jsonConstructor, Future future) { - return future.then((value) { - final list = value as List; - switch (list[0] as int) { - case messageErr: - { - throw VeilidAPIExceptionInternal("Internal API Error: ${list[1]}"); - } - case messageOkJson: - { - if (list[1] is! String) { - throw const VeilidAPIExceptionInternal( - "Non-string MESSAGE_OK_JSON value"); + T Function(dynamic) jsonConstructor, Future future) async => + future.then((value) { + final list = value as List; + switch (list[0] as int) { + case messageErr: + { + throw VeilidAPIExceptionInternal('Internal API Error: ${list[1]}'); } - var ret = jsonDecode(list[1] as String); - if (ret == null) { - throw const VeilidAPIExceptionInternal( - "Null JSON object on non nullable type"); + case messageOkJson: + { + if (list[1] is! String) { + throw const VeilidAPIExceptionInternal( + 'Non-string MESSAGE_OK_JSON value'); + } + final ret = jsonDecode(list[1] as String); + if (ret == null) { + throw const VeilidAPIExceptionInternal( + 'Null JSON object on non nullable type'); + } + return jsonConstructor(ret); } - return jsonConstructor(ret); - } - case messageErrJson: - { - throw VeilidAPIException.fromJson(jsonDecode(list[1])); - } - default: - { - throw VeilidAPIExceptionInternal( - "Unexpected async return message type: ${list[0]}"); - } - } - }).catchError((e) { - // Wrap all other errors in VeilidAPIExceptionInternal - throw VeilidAPIExceptionInternal(e.toString()); - }, test: (e) { - // Pass errors that are already VeilidAPIException through without wrapping - return e is! VeilidAPIException; - }); -} + case messageErrJson: + { + throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); + } + default: + { + throw VeilidAPIExceptionInternal( + 'Unexpected async return message type: ${list[0]}'); + } + } + // ignore: inference_failure_on_untyped_parameter + }).catchError((e) { + // Wrap all other errors in VeilidAPIExceptionInternal + throw VeilidAPIExceptionInternal(e.toString()); + }, test: (e) => e is! VeilidAPIException); Future processFutureOptJson( - T Function(dynamic) jsonConstructor, Future future) { - return future.then((value) { - final list = value as List; - switch (list[0] as int) { - case messageErr: - { - throw VeilidAPIExceptionInternal("Internal API Error: ${list[1]}"); - } - case messageOkJson: - { - if (list[1] == null) { - return null; + T Function(dynamic) jsonConstructor, Future future) async => + future.then((value) { + final list = value as List; + switch (list[0] as int) { + case messageErr: + { + throw VeilidAPIExceptionInternal('Internal API Error: ${list[1]}'); } - if (list[1] is! String) { - throw const VeilidAPIExceptionInternal( - "Non-string MESSAGE_OK_JSON optional value"); + case messageOkJson: + { + if (list[1] == null) { + return null; + } + if (list[1] is! String) { + throw const VeilidAPIExceptionInternal( + 'Non-string MESSAGE_OK_JSON optional value'); + } + final ret = jsonDecode(list[1] as String); + if (ret == null) { + return null; + } + return jsonConstructor(ret); } - var ret = jsonDecode(list[1] as String); - if (ret == null) { - return null; + case messageErrJson: + { + throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); } - return jsonConstructor(ret); - } - case messageErrJson: - { - throw VeilidAPIException.fromJson(jsonDecode(list[1])); - } - default: - { - throw VeilidAPIExceptionInternal( - "Unexpected async return message type: ${list[0]}"); - } - } - }).catchError((e) { - // Wrap all other errors in VeilidAPIExceptionInternal - throw VeilidAPIExceptionInternal(e.toString()); - }, test: (e) { - // Pass errors that are already VeilidAPIException through without wrapping - return e is! VeilidAPIException; - }); -} + default: + { + throw VeilidAPIExceptionInternal( + 'Unexpected async return message type: ${list[0]}'); + } + } + // ignore: inference_failure_on_untyped_parameter + }).catchError((e) { + // Wrap all other errors in VeilidAPIExceptionInternal + throw VeilidAPIExceptionInternal(e.toString()); + }, test: (e) => e is! VeilidAPIException); -Future processFutureVoid(Future future) { - return future.then((value) { - final list = value as List; - switch (list[0] as int) { - case messageOk: - { - if (list[1] != null) { - throw VeilidAPIExceptionInternal( - "Unexpected MESSAGE_OK value '${list[1]}' where null expected"); +Future processFutureVoid(Future future) async => + future.then((value) { + final list = value as List; + switch (list[0] as int) { + case messageOk: + { + if (list[1] != null) { + throw VeilidAPIExceptionInternal('Unexpected MESSAGE_OK value' + ' "${list[1]}" where null expected'); + } + return; } - return; - } - case messageErr: - { - throw VeilidAPIExceptionInternal("Internal API Error: ${list[1]}"); - } - case messageOkJson: - { - var ret = jsonDecode(list[1] as String); - if (ret != null) { - throw VeilidAPIExceptionInternal( - "Unexpected MESSAGE_OK_JSON value '$ret' where null expected"); + case messageErr: + { + throw VeilidAPIExceptionInternal('Internal API Error: ${list[1]}'); } - return; - } - case messageErrJson: - { - throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); - } - default: - { - throw VeilidAPIExceptionInternal( - "Unexpected async return message type: ${list[0]}"); - } - } - }).catchError((e) { - // Wrap all other errors in VeilidAPIExceptionInternal - throw VeilidAPIExceptionInternal(e.toString()); - }, test: (e) { - // Pass errors that are already VeilidAPIException through without wrapping - return e is! VeilidAPIException; - }); -} + case messageOkJson: + { + final ret = jsonDecode(list[1] as String); + if (ret != null) { + throw VeilidAPIExceptionInternal( + 'Unexpected MESSAGE_OK_JSON value' + ' "$ret" where null expected'); + } + return; + } + case messageErrJson: + { + throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); + } + default: + { + throw VeilidAPIExceptionInternal( + 'Unexpected async return message type: ${list[0]}'); + } + } + // ignore: inference_failure_on_untyped_parameter + }).catchError((e) { + // Wrap all other errors in VeilidAPIExceptionInternal + throw VeilidAPIExceptionInternal(e.toString()); + }, test: (e) => e is! VeilidAPIException); Future> processFutureStream( - Stream returnStream, Future future) { - return future.then((value) { - final list = value as List; - switch (list[0] as int) { - case messageOk: - { - if (list[1] != null) { - throw VeilidAPIExceptionInternal( - "Unexpected MESSAGE_OK value '${list[1]}' where null expected"); + Stream returnStream, Future future) async => + future.then((value) { + final list = value as List; + switch (list[0] as int) { + case messageOk: + { + if (list[1] != null) { + throw VeilidAPIExceptionInternal('Unexpected MESSAGE_OK value' + ' "${list[1]}" where null expected'); + } + return returnStream; } - return returnStream; - } - case messageErr: - { - throw VeilidAPIExceptionInternal("Internal API Error: ${list[1]}"); - } - case messageOkJson: - { - var ret = jsonDecode(list[1] as String); - if (ret != null) { - throw VeilidAPIExceptionInternal( - "Unexpected MESSAGE_OK_JSON value '$ret' where null expected"); + case messageErr: + { + throw VeilidAPIExceptionInternal('Internal API Error: ${list[1]}'); } - return returnStream; - } - case messageErrJson: - { - throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); - } - default: - { - throw VeilidAPIExceptionInternal( - "Unexpected async return message type: ${list[0]}"); - } - } - }).catchError((e) { - // Wrap all other errors in VeilidAPIExceptionInternal - throw VeilidAPIExceptionInternal(e.toString()); - }, test: (e) { - // Pass errors that are already VeilidAPIException through without wrapping - return e is! VeilidAPIException; - }); -} + case messageOkJson: + { + final ret = jsonDecode(list[1] as String); + if (ret != null) { + throw VeilidAPIExceptionInternal( + 'Unexpected MESSAGE_OK_JSON value' + ' "$ret" where null expected'); + } + return returnStream; + } + case messageErrJson: + { + throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); + } + default: + { + throw VeilidAPIExceptionInternal( + 'Unexpected async return message type: ${list[0]}'); + } + } + // ignore: inference_failure_on_untyped_parameter + }).catchError((e) { + // Wrap all other errors in VeilidAPIExceptionInternal + throw VeilidAPIExceptionInternal(e.toString()); + }, test: (e) => e is! VeilidAPIException); Stream processStreamJson( T Function(dynamic) jsonConstructor, ReceivePort port) async* { try { - await for (var value in port) { + await for (final value in port) { final list = value as List; switch (list[0] as int) { case messageStreamItemJson: { if (list[1] == null) { throw const VeilidAPIExceptionInternal( - "Null MESSAGE_STREAM_ITEM_JSON value"); + 'Null MESSAGE_STREAM_ITEM_JSON value'); } - var ret = jsonDecode(list[1] as String); + final ret = jsonDecode(list[1] as String); yield jsonConstructor(ret); break; } case messageStreamAbort: { - port.close(); - throw VeilidAPIExceptionInternal("Internal API Error: ${list[1]}"); + throw VeilidAPIExceptionInternal('Internal API Error: ${list[1]}'); } case messageStreamAbortJson: { - port.close(); - throw VeilidAPIException.fromJson(jsonDecode(list[1])); + throw VeilidAPIException.fromJson(jsonDecode(list[1] as String)); } case messageStreamClose: { - port.close(); break; } default: { throw VeilidAPIExceptionInternal( - "Unexpected async return message type: ${list[0]}"); + 'Unexpected async return message type: ${list[0]}'); } } } - } catch (e, s) { + } on VeilidAPIException catch (_) { + rethrow; + } on Exception catch (e, s) { // Wrap all other errors in VeilidAPIExceptionInternal - throw VeilidAPIExceptionInternal( - "${e.toString()}\nStack Trace:\n${s.toString()}"); + throw VeilidAPIExceptionInternal('$e\nStack Trace:\n$s'); + } finally { + port.close(); } } class _Ctx { + _Ctx(int this.id, this.ffi); int? id; final VeilidFFI ffi; - _Ctx(int this.id, this.ffi); void ensureValid() { if (id == null) { @@ -606,12 +508,11 @@ class _Ctx { // FFI implementation of VeilidRoutingContext class VeilidRoutingContextFFI extends VeilidRoutingContext { - final _Ctx _ctx; - static final Finalizer<_Ctx> _finalizer = Finalizer((ctx) => ctx.close()); - VeilidRoutingContextFFI._(this._ctx) { _finalizer.attach(this, _ctx, detach: this); } + final _Ctx _ctx; + static final Finalizer<_Ctx> _finalizer = Finalizer((ctx) => ctx.close()); @override void close() { @@ -644,28 +545,28 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { @override Future appCall(String target, Uint8List request) async { _ctx.ensureValid(); - var nativeEncodedTarget = target.toNativeUtf8(); - var nativeEncodedRequest = base64UrlNoPadEncode(request).toNativeUtf8(); + final nativeEncodedTarget = target.toNativeUtf8(); + final nativeEncodedRequest = base64UrlNoPadEncode(request).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_app_call"); + final recvPort = ReceivePort('routing_context_app_call'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextAppCall(sendPort.nativePort, _ctx.id!, nativeEncodedTarget, nativeEncodedRequest); - final out = await processFuturePlain(recvPort.first); + final out = await processFuturePlain(recvPort.first); return base64UrlNoPadDecode(out); } @override - Future appMessage(String target, Uint8List message) { + Future appMessage(String target, Uint8List message) async { _ctx.ensureValid(); final nativeEncodedTarget = target.toNativeUtf8(); final nativeEncodedMessage = base64UrlNoPadEncode(message).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_app_message"); + final recvPort = ReceivePort('routing_context_app_message'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextAppMessage(sendPort.nativePort, _ctx.id!, nativeEncodedTarget, nativeEncodedMessage); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override @@ -673,7 +574,7 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { {CryptoKind kind = 0}) async { _ctx.ensureValid(); final nativeSchema = jsonEncode(schema).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_create_dht_record"); + final recvPort = ReceivePort('routing_context_create_dht_record'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextCreateDHTRecord( sendPort.nativePort, _ctx.id!, nativeSchema, kind); @@ -689,7 +590,7 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeWriter = writer != null ? jsonEncode(writer).toNativeUtf8() : nullptr; - final recvPort = ReceivePort("routing_context_open_dht_record"); + final recvPort = ReceivePort('routing_context_open_dht_record'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextOpenDHTRecord( sendPort.nativePort, _ctx.id!, nativeKey, nativeWriter); @@ -699,25 +600,25 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { } @override - Future closeDHTRecord(TypedKey key) { + Future closeDHTRecord(TypedKey key) async { _ctx.ensureValid(); final nativeKey = jsonEncode(key).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_close_dht_record"); + final recvPort = ReceivePort('routing_context_close_dht_record'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextCloseDHTRecord( sendPort.nativePort, _ctx.id!, nativeKey); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override - Future deleteDHTRecord(TypedKey key) { + Future deleteDHTRecord(TypedKey key) async { _ctx.ensureValid(); final nativeKey = jsonEncode(key).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_delete_dht_record"); + final recvPort = ReceivePort('routing_context_delete_dht_record'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextDeleteDHTRecord( sendPort.nativePort, _ctx.id!, nativeKey); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override @@ -725,12 +626,12 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { TypedKey key, int subkey, bool forceRefresh) async { _ctx.ensureValid(); final nativeKey = jsonEncode(key).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_get_dht_value"); + final recvPort = ReceivePort('routing_context_get_dht_value'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextGetDHTValue( sendPort.nativePort, _ctx.id!, nativeKey, subkey, forceRefresh); - final valueData = await processFutureOptJson( - optFromJson(ValueData.fromJson), recvPort.first); + final valueData = + await processFutureOptJson(ValueData.fromJson, recvPort.first); return valueData; } @@ -741,12 +642,12 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeData = base64UrlNoPadEncode(data).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_set_dht_value"); + final recvPort = ReceivePort('routing_context_set_dht_value'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextSetDHTValue( sendPort.nativePort, _ctx.id!, nativeKey, subkey, nativeData); - final valueData = await processFutureOptJson( - optFromJson(ValueData.fromJson), recvPort.first); + final valueData = + await processFutureOptJson(ValueData.fromJson, recvPort.first); return valueData; } @@ -758,7 +659,7 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { final nativeSubkeys = jsonEncode(subkeys).toNativeUtf8(); final nativeExpiration = expiration.value.toInt(); - final recvPort = ReceivePort("routing_context_watch_dht_values"); + final recvPort = ReceivePort('routing_context_watch_dht_values'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextWatchDHTValues(sendPort.nativePort, _ctx.id!, nativeKey, nativeSubkeys, nativeExpiration, count); @@ -774,7 +675,7 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeSubkeys = jsonEncode(subkeys).toNativeUtf8(); - final recvPort = ReceivePort("routing_context_cancel_dht_watch"); + final recvPort = ReceivePort('routing_context_cancel_dht_watch'); final sendPort = recvPort.sendPort; _ctx.ffi._routingContextCancelDHTWatch( sendPort.nativePort, _ctx.id!, nativeKey, nativeSubkeys); @@ -784,11 +685,10 @@ class VeilidRoutingContextFFI extends VeilidRoutingContext { } class _TDBT { + _TDBT(int this.id, this.tdbffi, this.ffi); int? id; final VeilidTableDBFFI tdbffi; final VeilidFFI ffi; - - _TDBT(int this.id, this.tdbffi, this.ffi); void ensureValid() { if (id == null) { throw VeilidAPIExceptionNotInitialized(); @@ -805,22 +705,19 @@ class _TDBT { // FFI implementation of VeilidTableDBTransaction class VeilidTableDBTransactionFFI extends VeilidTableDBTransaction { - final _TDBT _tdbt; - static final Finalizer<_TDBT> _finalizer = Finalizer((tdbt) => tdbt.close()); - VeilidTableDBTransactionFFI._(this._tdbt) { _finalizer.attach(this, _tdbt, detach: this); } + final _TDBT _tdbt; + static final Finalizer<_TDBT> _finalizer = Finalizer((tdbt) => tdbt.close()); @override - bool isDone() { - return _tdbt.id == null; - } + bool isDone() => _tdbt.id == null; @override Future commit() async { _tdbt.ensureValid(); - final recvPort = ReceivePort("veilid_table_db_transaction_commit"); + final recvPort = ReceivePort('veilid_table_db_transaction_commit'); final sendPort = recvPort.sendPort; _tdbt.ffi._tableDbTransactionCommit( sendPort.nativePort, @@ -833,7 +730,7 @@ class VeilidTableDBTransactionFFI extends VeilidTableDBTransaction { @override Future rollback() async { _tdbt.ensureValid(); - final recvPort = ReceivePort("veilid_table_db_transaction_rollback"); + final recvPort = ReceivePort('veilid_table_db_transaction_rollback'); final sendPort = recvPort.sendPort; _tdbt.ffi._tableDbTransactionRollback( sendPort.nativePort, @@ -844,12 +741,12 @@ class VeilidTableDBTransactionFFI extends VeilidTableDBTransaction { } @override - Future store(int col, Uint8List key, Uint8List value) { + Future store(int col, Uint8List key, Uint8List value) async { _tdbt.ensureValid(); final nativeEncodedKey = base64UrlNoPadEncode(key).toNativeUtf8(); final nativeEncodedValue = base64UrlNoPadEncode(value).toNativeUtf8(); - final recvPort = ReceivePort("veilid_table_db_transaction_store"); + final recvPort = ReceivePort('veilid_table_db_transaction_store'); final sendPort = recvPort.sendPort; _tdbt.ffi._tableDbTransactionStore( sendPort.nativePort, @@ -858,15 +755,15 @@ class VeilidTableDBTransactionFFI extends VeilidTableDBTransaction { nativeEncodedKey, nativeEncodedValue, ); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override - Future delete(int col, Uint8List key) { + Future delete(int col, Uint8List key) async { _tdbt.ensureValid(); final nativeEncodedKey = base64UrlNoPadEncode(key).toNativeUtf8(); - final recvPort = ReceivePort("veilid_table_db_transaction_delete"); + final recvPort = ReceivePort('veilid_table_db_transaction_delete'); final sendPort = recvPort.sendPort; _tdbt.ffi._tableDbTransactionDelete( sendPort.nativePort, @@ -874,14 +771,14 @@ class VeilidTableDBTransactionFFI extends VeilidTableDBTransaction { col, nativeEncodedKey, ); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } } class _TDB { + _TDB(int this.id, this.ffi); int? id; final VeilidFFI ffi; - _TDB(int this.id, this.ffi); void ensureValid() { if (id == null) { throw VeilidAPIExceptionNotInitialized(); @@ -898,12 +795,11 @@ class _TDB { // FFI implementation of VeilidTableDB class VeilidTableDBFFI extends VeilidTableDB { - final _TDB _tdb; - static final Finalizer<_TDB> _finalizer = Finalizer((tdb) => tdb.close()); - VeilidTableDBFFI._(this._tdb) { _finalizer.attach(this, _tdb, detach: this); } + final _TDB _tdb; + static final Finalizer<_TDB> _finalizer = Finalizer((tdb) => tdb.close()); @override void close() { @@ -917,15 +813,15 @@ class VeilidTableDBFFI extends VeilidTableDB { } @override - Future> getKeys(int col) { + Future> getKeys(int col) async { _tdb.ensureValid(); - final recvPort = ReceivePort("veilid_table_db_get_keys"); + final recvPort = ReceivePort('veilid_table_db_get_keys'); final sendPort = recvPort.sendPort; _tdb.ffi._tableDbGetKeys(sendPort.nativePort, _tdb.id!, col); - return processFutureJson( + return await processFutureJson( jsonListConstructor(base64UrlNoPadDecodeDynamic), recvPort.first); } @@ -939,13 +835,13 @@ class VeilidTableDBFFI extends VeilidTableDB { } @override - Future store(int col, Uint8List key, Uint8List value) { + Future store(int col, Uint8List key, Uint8List value) async { _tdb.ensureValid(); final nativeEncodedKey = base64UrlNoPadEncode(key).toNativeUtf8(); final nativeEncodedValue = base64UrlNoPadEncode(value).toNativeUtf8(); - final recvPort = ReceivePort("veilid_table_db_store"); + final recvPort = ReceivePort('veilid_table_db_store'); final sendPort = recvPort.sendPort; _tdb.ffi._tableDbStore( sendPort.nativePort, @@ -954,7 +850,7 @@ class VeilidTableDBFFI extends VeilidTableDB { nativeEncodedKey, nativeEncodedValue, ); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override @@ -962,7 +858,7 @@ class VeilidTableDBFFI extends VeilidTableDB { _tdb.ensureValid(); final nativeEncodedKey = base64UrlNoPadEncode(key).toNativeUtf8(); - final recvPort = ReceivePort("veilid_table_db_load"); + final recvPort = ReceivePort('veilid_table_db_load'); final sendPort = recvPort.sendPort; _tdb.ffi._tableDbLoad( sendPort.nativePort, @@ -970,7 +866,7 @@ class VeilidTableDBFFI extends VeilidTableDB { col, nativeEncodedKey, ); - String? out = await processFuturePlain(recvPort.first); + final out = await processFuturePlain(recvPort.first); if (out == null) { return null; } @@ -982,7 +878,7 @@ class VeilidTableDBFFI extends VeilidTableDB { _tdb.ensureValid(); final nativeEncodedKey = base64UrlNoPadEncode(key).toNativeUtf8(); - final recvPort = ReceivePort("veilid_table_db_delete"); + final recvPort = ReceivePort('veilid_table_db_delete'); final sendPort = recvPort.sendPort; _tdb.ffi._tableDbDelete( sendPort.nativePort, @@ -990,7 +886,7 @@ class VeilidTableDBFFI extends VeilidTableDB { col, nativeEncodedKey, ); - String? out = await processFuturePlain(recvPort.first); + final out = await processFuturePlain(recvPort.first); if (out == null) { return null; } @@ -1000,195 +896,195 @@ class VeilidTableDBFFI extends VeilidTableDB { // FFI implementation of VeilidCryptoSystem class VeilidCryptoSystemFFI extends VeilidCryptoSystem { + VeilidCryptoSystemFFI._(this._ffi, this._kind); final CryptoKind _kind; final VeilidFFI _ffi; - VeilidCryptoSystemFFI._(this._ffi, this._kind); + @override + CryptoKind kind() => _kind; @override - CryptoKind kind() { - return _kind; - } - - @override - Future cachedDH(PublicKey key, SecretKey secret) { + Future cachedDH(PublicKey key, SecretKey secret) async { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeSecret = jsonEncode(secret).toNativeUtf8(); - final recvPort = ReceivePort("crypto_cached_dh"); + final recvPort = ReceivePort('crypto_cached_dh'); final sendPort = recvPort.sendPort; _ffi._cryptoCachedDH(sendPort.nativePort, _kind, nativeKey, nativeSecret); - return processFutureJson(SharedSecret.fromJson, recvPort.first); + return await processFutureJson(SharedSecret.fromJson, recvPort.first); } @override - Future computeDH(PublicKey key, SecretKey secret) { + Future computeDH(PublicKey key, SecretKey secret) async { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeSecret = jsonEncode(secret).toNativeUtf8(); - final recvPort = ReceivePort("crypto_compute_dh"); + final recvPort = ReceivePort('crypto_compute_dh'); final sendPort = recvPort.sendPort; _ffi._cryptoComputeDH(sendPort.nativePort, _kind, nativeKey, nativeSecret); - return processFutureJson(SharedSecret.fromJson, recvPort.first); + return await processFutureJson(SharedSecret.fromJson, recvPort.first); } @override Future randomBytes(int len) async { - final recvPort = ReceivePort("crypto_random_bytes"); + final recvPort = ReceivePort('crypto_random_bytes'); final sendPort = recvPort.sendPort; _ffi._cryptoRandomBytes(sendPort.nativePort, _kind, len); - final out = await processFuturePlain(recvPort.first); + final out = await processFuturePlain(recvPort.first); return base64UrlNoPadDecode(out); } @override - Future defaultSaltLength() { - final recvPort = ReceivePort("crypto_default_salt_length"); + Future defaultSaltLength() async { + final recvPort = ReceivePort('crypto_default_salt_length'); final sendPort = recvPort.sendPort; _ffi._cryptoDefaultSaltLength(sendPort.nativePort, _kind); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } @override - Future hashPassword(Uint8List password, Uint8List salt) { + Future hashPassword(Uint8List password, Uint8List salt) async { final nativeEncodedPassword = base64UrlNoPadEncode(password).toNativeUtf8(); final nativeEncodedSalt = base64UrlNoPadEncode(salt).toNativeUtf8(); - final recvPort = ReceivePort("crypto_hash_password"); + final recvPort = ReceivePort('crypto_hash_password'); final sendPort = recvPort.sendPort; _ffi._cryptoHashPassword( sendPort.nativePort, _kind, nativeEncodedPassword, nativeEncodedSalt); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } @override - Future verifyPassword(Uint8List password, String passwordHash) { + Future verifyPassword(Uint8List password, String passwordHash) async { final nativeEncodedPassword = base64UrlNoPadEncode(password).toNativeUtf8(); final nativeEncodedPasswordHash = passwordHash.toNativeUtf8(); - final recvPort = ReceivePort("crypto_verify_password"); + final recvPort = ReceivePort('crypto_verify_password'); final sendPort = recvPort.sendPort; _ffi._cryptoVerifyPassword(sendPort.nativePort, _kind, nativeEncodedPassword, nativeEncodedPasswordHash); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } @override - Future deriveSharedSecret(Uint8List password, Uint8List salt) { + Future deriveSharedSecret( + Uint8List password, Uint8List salt) async { final nativeEncodedPassword = base64UrlNoPadEncode(password).toNativeUtf8(); final nativeEncodedSalt = base64UrlNoPadEncode(salt).toNativeUtf8(); - final recvPort = ReceivePort("crypto_derive_shared_secret"); + final recvPort = ReceivePort('crypto_derive_shared_secret'); final sendPort = recvPort.sendPort; _ffi._cryptoDeriveSharedSecret( sendPort.nativePort, _kind, nativeEncodedPassword, nativeEncodedSalt); - return processFutureJson(SharedSecret.fromJson, recvPort.first); + return await processFutureJson(SharedSecret.fromJson, recvPort.first); } @override - Future randomNonce() { - final recvPort = ReceivePort("crypto_random_nonce"); + Future randomNonce() async { + final recvPort = ReceivePort('crypto_random_nonce'); final sendPort = recvPort.sendPort; _ffi._cryptoRandomNonce(sendPort.nativePort, _kind); - return processFutureJson(Nonce.fromJson, recvPort.first); + return await processFutureJson(Nonce.fromJson, recvPort.first); } @override - Future randomSharedSecret() { - final recvPort = ReceivePort("crypto_random_shared_secret"); + Future randomSharedSecret() async { + final recvPort = ReceivePort('crypto_random_shared_secret'); final sendPort = recvPort.sendPort; _ffi._cryptoRandomSharedSecret(sendPort.nativePort, _kind); - return processFutureJson(SharedSecret.fromJson, recvPort.first); + return await processFutureJson(SharedSecret.fromJson, recvPort.first); } @override - Future generateKeyPair() { - final recvPort = ReceivePort("crypto_generate_key_pair"); + Future generateKeyPair() async { + final recvPort = ReceivePort('crypto_generate_key_pair'); final sendPort = recvPort.sendPort; _ffi._cryptoGenerateKeyPair(sendPort.nativePort, _kind); - return processFutureJson(KeyPair.fromJson, recvPort.first); + return await processFutureJson(KeyPair.fromJson, recvPort.first); } @override - Future generateHash(Uint8List data) { + Future generateHash(Uint8List data) async { final nativeEncodedData = base64UrlNoPadEncode(data).toNativeUtf8(); - final recvPort = ReceivePort("crypto_generate_hash"); + final recvPort = ReceivePort('crypto_generate_hash'); final sendPort = recvPort.sendPort; _ffi._cryptoGenerateHash(sendPort.nativePort, _kind, nativeEncodedData); - return processFutureJson(HashDigest.fromJson, recvPort.first); + return await processFutureJson(HashDigest.fromJson, recvPort.first); } @override - Future validateKeyPair(PublicKey key, SecretKey secret) { + Future validateKeyPair(PublicKey key, SecretKey secret) async { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeSecret = jsonEncode(secret).toNativeUtf8(); - final recvPort = ReceivePort("crypto_validate_key_pair"); + final recvPort = ReceivePort('crypto_validate_key_pair'); final sendPort = recvPort.sendPort; _ffi._cryptoValidateKeyPair( sendPort.nativePort, _kind, nativeKey, nativeSecret); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } @override - Future validateHash(Uint8List data, HashDigest hash) { + Future validateHash(Uint8List data, HashDigest hash) async { final nativeEncodedData = base64UrlNoPadEncode(data).toNativeUtf8(); final nativeHash = jsonEncode(hash).toNativeUtf8(); - final recvPort = ReceivePort("crypto_validate_hash"); + final recvPort = ReceivePort('crypto_validate_hash'); final sendPort = recvPort.sendPort; _ffi._cryptoValidateHash( sendPort.nativePort, _kind, nativeEncodedData, nativeHash); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } @override - Future distance(CryptoKey key1, CryptoKey key2) { + Future distance(CryptoKey key1, CryptoKey key2) async { final nativeKey1 = jsonEncode(key1).toNativeUtf8(); final nativeKey2 = jsonEncode(key2).toNativeUtf8(); - final recvPort = ReceivePort("crypto_distance"); + final recvPort = ReceivePort('crypto_distance'); final sendPort = recvPort.sendPort; _ffi._cryptoDistance(sendPort.nativePort, _kind, nativeKey1, nativeKey2); - return processFutureJson(CryptoKeyDistance.fromJson, recvPort.first); + return await processFutureJson(CryptoKeyDistance.fromJson, recvPort.first); } @override - Future sign(PublicKey key, SecretKey secret, Uint8List data) { + Future sign( + PublicKey key, SecretKey secret, Uint8List data) async { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeSecret = jsonEncode(secret).toNativeUtf8(); final nativeEncodedData = base64UrlNoPadEncode(data).toNativeUtf8(); - final recvPort = ReceivePort("crypto_sign"); + final recvPort = ReceivePort('crypto_sign'); final sendPort = recvPort.sendPort; _ffi._cryptoSign( sendPort.nativePort, _kind, nativeKey, nativeSecret, nativeEncodedData); - return processFutureJson(Signature.fromJson, recvPort.first); + return await processFutureJson(Signature.fromJson, recvPort.first); } @override - Future verify(PublicKey key, Uint8List data, Signature signature) { + Future verify( + PublicKey key, Uint8List data, Signature signature) async { final nativeKey = jsonEncode(key).toNativeUtf8(); final nativeEncodedData = base64UrlNoPadEncode(data).toNativeUtf8(); final nativeSignature = jsonEncode(signature).toNativeUtf8(); - final recvPort = ReceivePort("crypto_verify"); + final recvPort = ReceivePort('crypto_verify'); final sendPort = recvPort.sendPort; _ffi._cryptoVerify(sendPort.nativePort, _kind, nativeKey, nativeEncodedData, nativeSignature); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override - Future aeadOverhead() { - final recvPort = ReceivePort("crypto_aead_overhead"); + Future aeadOverhead() async { + final recvPort = ReceivePort('crypto_aead_overhead'); final sendPort = recvPort.sendPort; _ffi._cryptoAeadOverhead( sendPort.nativePort, _kind, ); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } @override @@ -1201,11 +1097,11 @@ class VeilidCryptoSystemFFI extends VeilidCryptoSystem { ? jsonEncode(associatedData).toNativeUtf8() : nullptr; - final recvPort = ReceivePort("crypto_decrypt_aead"); + final recvPort = ReceivePort('crypto_decrypt_aead'); final sendPort = recvPort.sendPort; _ffi._cryptoDecryptAead(sendPort.nativePort, _kind, nativeEncodedBody, nativeNonce, nativeSharedSecret, nativeSignature); - final out = await processFuturePlain(recvPort.first); + final out = await processFuturePlain(recvPort.first); return base64UrlNoPadDecode(out); } @@ -1219,11 +1115,11 @@ class VeilidCryptoSystemFFI extends VeilidCryptoSystem { ? jsonEncode(associatedData).toNativeUtf8() : nullptr; - final recvPort = ReceivePort("crypto_encrypt_aead"); + final recvPort = ReceivePort('crypto_encrypt_aead'); final sendPort = recvPort.sendPort; _ffi._cryptoEncryptAead(sendPort.nativePort, _kind, nativeEncodedBody, nativeNonce, nativeSharedSecret, nativeSignature); - final out = await processFuturePlain(recvPort.first); + final out = await processFuturePlain(recvPort.first); return base64UrlNoPadDecode(out); } @@ -1234,17 +1130,239 @@ class VeilidCryptoSystemFFI extends VeilidCryptoSystem { final nativeNonce = jsonEncode(nonce).toNativeUtf8(); final nativeSharedSecret = jsonEncode(sharedSecret).toNativeUtf8(); - final recvPort = ReceivePort("crypto_crypt_no_auth"); + final recvPort = ReceivePort('crypto_crypt_no_auth'); final sendPort = recvPort.sendPort; _ffi._cryptoCryptNoAuth(sendPort.nativePort, _kind, nativeEncodedBody, nativeNonce, nativeSharedSecret); - final out = await processFuturePlain(recvPort.first); + final out = await processFuturePlain(recvPort.first); return base64UrlNoPadDecode(out); } } // FFI implementation of high level Veilid API class VeilidFFI extends Veilid { + VeilidFFI(DynamicLibrary dylib) + : _dylib = dylib, + _freeString = + dylib.lookupFunction), _FreeStringDart>( + 'free_string'), + _initializeVeilidCore = dylib.lookupFunction< + Void Function(Pointer), + _InitializeVeilidCoreDart>('initialize_veilid_core'), + _changeLogLevel = dylib.lookupFunction< + Void Function(Pointer, Pointer), + _ChangeLogLevelDart>('change_log_level'), + _startupVeilidCore = dylib.lookupFunction< + Void Function(Int64, Int64, Pointer), + _StartupVeilidCoreDart>('startup_veilid_core'), + _getVeilidState = + dylib.lookupFunction( + 'get_veilid_state'), + _attach = + dylib.lookupFunction('attach'), + _detach = + dylib.lookupFunction('detach'), + _shutdownVeilidCore = + dylib.lookupFunction( + 'shutdown_veilid_core'), + _routingContext = + dylib.lookupFunction( + 'routing_context'), + _releaseRoutingContext = dylib.lookupFunction('release_routing_context'), + _routingContextWithPrivacy = dylib.lookupFunction< + Uint32 Function(Uint32), + _RoutingContextWithPrivacyDart>('routing_context_with_privacy'), + _routingContextWithCustomPrivacy = dylib.lookupFunction< + Uint32 Function(Uint32, Pointer), + _RoutingContextWithCustomPrivacyDart>( + 'routing_context_with_custom_privacy'), + _routingContextWithSequencing = dylib.lookupFunction< + Uint32 Function(Uint32, Pointer), + _RoutingContextWithSequencingDart>( + 'routing_context_with_sequencing'), + _routingContextAppCall = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _RoutingContextAppCallDart>('routing_context_app_call'), + _routingContextAppMessage = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _RoutingContextAppMessageDart>('routing_context_app_message'), + _routingContextCreateDHTRecord = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Uint32), + _RoutingContextCreateDHTRecordDart>( + 'routing_context_create_dht_record'), + _routingContextOpenDHTRecord = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _RoutingContextOpenDHTRecordDart>( + 'routing_context_open_dht_record'), + _routingContextCloseDHTRecord = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer), + _RoutingContextCloseDHTRecordDart>( + 'routing_context_close_dht_record'), + _routingContextDeleteDHTRecord = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer), + _RoutingContextDeleteDHTRecordDart>( + 'routing_context_delete_dht_record'), + _routingContextGetDHTValue = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Uint32, Bool), + _RoutingContextGetDHTValueDart>('routing_context_get_dht_value'), + _routingContextSetDHTValue = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Uint32, Pointer), + _RoutingContextSetDHTValueDart>('routing_context_set_dht_value'), + _routingContextWatchDHTValues = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer, + Uint64, Uint32), + _RoutingContextWatchDHTValuesDart>( + 'routing_context_watch_dht_values'), + _routingContextCancelDHTWatch = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _RoutingContextCancelDHTWatchDart>( + 'routing_context_cancel_dht_watch'), + _newPrivateRoute = + dylib.lookupFunction( + 'new_private_route'), + _newCustomPrivateRoute = dylib.lookupFunction< + Void Function(Int64, Pointer, Pointer), + _NewCustomPrivateRouteDart>('new_custom_private_route'), + _importRemotePrivateRoute = dylib.lookupFunction< + Void Function(Int64, Pointer), + _ImportRemotePrivateRouteDart>('import_remote_private_route'), + _releasePrivateRoute = dylib.lookupFunction< + Void Function(Int64, Pointer), + _ReleasePrivateRouteDart>('release_private_route'), + _appCallReply = dylib.lookupFunction< + Void Function(Int64, Pointer, Pointer), + _AppCallReplyDart>('app_call_reply'), + _openTableDb = dylib.lookupFunction< + Void Function(Int64, Pointer, Uint32), + _OpenTableDbDart>('open_table_db'), + _releaseTableDb = + dylib.lookupFunction( + 'release_table_db'), + _deleteTableDb = dylib.lookupFunction< + Void Function(Int64, Pointer), + _DeleteTableDbDart>('delete_table_db'), + _tableDbGetColumnCount = dylib.lookupFunction('table_db_get_column_count'), + _tableDbGetKeys = dylib.lookupFunction< + Pointer Function(Uint64, Uint32, Uint32), + _TableDbGetKeysDart>('table_db_get_keys'), + _tableDbStore = dylib.lookupFunction< + Void Function(Int64, Uint32, Uint32, Pointer, Pointer), + _TableDbStoreDart>('table_db_store'), + _tableDbLoad = dylib.lookupFunction< + Void Function(Int64, Uint32, Uint32, Pointer), + _TableDbLoadDart>('table_db_load'), + _tableDbDelete = dylib.lookupFunction< + Void Function(Int64, Uint32, Uint32, Pointer), + _TableDbDeleteDart>('table_db_delete'), + _tableDbTransact = + dylib.lookupFunction( + 'table_db_transact'), + _releaseTableDbTransaction = dylib.lookupFunction< + Int32 Function(Uint32), + _ReleaseTableDbTransactionDart>('release_table_db_transaction'), + _tableDbTransactionCommit = dylib.lookupFunction< + Void Function(Uint64, Uint32), + _TableDbTransactionCommitDart>('table_db_transaction_commit'), + _tableDbTransactionRollback = dylib.lookupFunction< + Void Function(Uint64, Uint32), + _TableDbTransactionRollbackDart>('table_db_transaction_rollback'), + _tableDbTransactionStore = dylib.lookupFunction< + Void Function(Int64, Uint32, Uint32, Pointer, Pointer), + _TableDbTransactionStoreDart>('table_db_transaction_store'), + _tableDbTransactionDelete = dylib.lookupFunction< + Void Function(Int64, Uint32, Uint32, Pointer), + _TableDbTransactionDeleteDart>('table_db_transaction_delete'), + _validCryptoKinds = dylib.lookupFunction Function(), + _ValidCryptoKindsDart>('valid_crypto_kinds'), + _bestCryptoKind = + dylib.lookupFunction( + 'best_crypto_kind'), + _verifySignatures = dylib.lookupFunction< + Void Function(Int64, Pointer, Pointer, Pointer), + _VerifySignaturesDart>('verify_signatures'), + _generateSignatures = dylib.lookupFunction< + Void Function(Int64, Pointer, Pointer), + _GenerateSignaturesDart>('generate_signatures'), + _generateKeyPair = dylib.lookupFunction('generate_key_pair'), + _cryptoCachedDH = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoCachedDHDart>('crypto_cached_dh'), + _cryptoComputeDH = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoComputeDHDart>('crypto_compute_dh'), + _cryptoRandomBytes = dylib.lookupFunction< + Void Function(Int64, Uint32, Uint32), + _CryptoRandomBytesDart>('crypto_random_bytes'), + _cryptoDefaultSaltLength = dylib.lookupFunction< + Void Function(Int64, Uint32), + _CryptoDefaultSaltLengthDart>('crypto_default_salt_length'), + _cryptoHashPassword = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoHashPasswordDart>('crypto_hash_password'), + _cryptoVerifyPassword = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoVerifyPasswordDart>('crypto_verify_password'), + _cryptoDeriveSharedSecret = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoVerifyPasswordDart>('crypto_derive_shared_secret'), + _cryptoRandomNonce = dylib.lookupFunction('crypto_random_nonce'), + _cryptoRandomSharedSecret = dylib.lookupFunction< + Void Function(Int64, Uint32), + _CryptoRandomSharedSecretDart>('crypto_random_shared_secret'), + _cryptoGenerateKeyPair = dylib.lookupFunction< + Void Function(Int64, Uint32), + _CryptoGenerateKeyPairDart>('crypto_generate_key_pair'), + _cryptoGenerateHash = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer), + _CryptoGenerateHashDart>('crypto_generate_hash'), + _cryptoValidateKeyPair = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoValidateKeyPairDart>('crypto_validate_key_pair'), + _cryptoValidateHash = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoValidateHashDart>('crypto_validate_hash'), + _cryptoDistance = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer), + _CryptoDistanceDart>('crypto_distance'), + _cryptoSign = dylib.lookupFunction< + Void Function( + Int64, Uint32, Pointer, Pointer, Pointer), + _CryptoSignDart>('crypto_sign'), + _cryptoVerify = dylib.lookupFunction< + Void Function( + Int64, Uint32, Pointer, Pointer, Pointer), + _CryptoVerifyDart>('crypto_verify'), + _cryptoAeadOverhead = dylib.lookupFunction('crypto_aead_overhead'), + _cryptoDecryptAead = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer, + Pointer, Pointer), + _CryptoDecryptAeadDart>('crypto_decrypt_aead'), + _cryptoEncryptAead = dylib.lookupFunction< + Void Function(Int64, Uint32, Pointer, Pointer, + Pointer, Pointer), + _CryptoEncryptAeadDart>('crypto_encrypt_aead'), + _cryptoCryptNoAuth = dylib.lookupFunction< + Void Function( + Int64, Uint32, Pointer, Pointer, Pointer), + _CryptoCryptNoAuthDart>('crypto_crypt_no_auth'), + _now = dylib.lookupFunction('now'), + _debug = dylib.lookupFunction), + _DebugDart>('debug'), + _veilidVersionString = dylib.lookupFunction Function(), + _VeilidVersionStringDart>('veilid_version_string'), + _veilidVersion = dylib.lookupFunction('veilid_version') { + // Get veilid_flutter initializer + final initializeVeilidFlutter = _dylib.lookupFunction< + Void Function(Pointer<_DartPostCObject>), + void Function(Pointer<_DartPostCObject>)>('initialize_veilid_flutter'); + initializeVeilidFlutter(NativeApi.postCObject); + } // veilid_core shared library final DynamicLibrary _dylib; @@ -1309,7 +1427,8 @@ class VeilidFFI extends Veilid { final _CryptoDefaultSaltLengthDart _cryptoDefaultSaltLength; final _CryptoHashPasswordDart _cryptoHashPassword; final _CryptoVerifyPasswordDart _cryptoVerifyPassword; - final _CryptoDeriveSharedSecretDart _cryptoDeriveSharedSecret; + final void Function(int, int, Pointer, Pointer) + _cryptoDeriveSharedSecret; final _CryptoRandomNonceDart _cryptoRandomNonce; final _CryptoRandomSharedSecretDart _cryptoRandomSharedSecret; @@ -1330,214 +1449,9 @@ class VeilidFFI extends Veilid { final _VeilidVersionStringDart _veilidVersionString; final _VeilidVersionDart _veilidVersion; - VeilidFFI(DynamicLibrary dylib) - : _dylib = dylib, - _freeString = - dylib.lookupFunction<_FreeStringC, _FreeStringDart>('free_string'), - _initializeVeilidCore = dylib.lookupFunction<_InitializeVeilidCoreC, - _InitializeVeilidCoreDart>('initialize_veilid_core'), - _changeLogLevel = - dylib.lookupFunction<_ChangeLogLevelC, _ChangeLogLevelDart>( - 'change_log_level'), - _startupVeilidCore = - dylib.lookupFunction<_StartupVeilidCoreC, _StartupVeilidCoreDart>( - 'startup_veilid_core'), - _getVeilidState = - dylib.lookupFunction<_GetVeilidStateC, _GetVeilidStateDart>( - 'get_veilid_state'), - _attach = dylib.lookupFunction<_AttachC, _AttachDart>('attach'), - _detach = dylib.lookupFunction<_DetachC, _DetachDart>('detach'), - _shutdownVeilidCore = - dylib.lookupFunction<_ShutdownVeilidCoreC, _ShutdownVeilidCoreDart>( - 'shutdown_veilid_core'), - _routingContext = - dylib.lookupFunction<_RoutingContextC, _RoutingContextDart>( - 'routing_context'), - _releaseRoutingContext = dylib.lookupFunction<_ReleaseRoutingContextC, - _ReleaseRoutingContextDart>('release_routing_context'), - _routingContextWithPrivacy = dylib.lookupFunction< - _RoutingContextWithPrivacyC, - _RoutingContextWithPrivacyDart>('routing_context_with_privacy'), - _routingContextWithCustomPrivacy = dylib.lookupFunction< - _RoutingContextWithCustomPrivacyC, - _RoutingContextWithCustomPrivacyDart>( - 'routing_context_with_custom_privacy'), - _routingContextWithSequencing = dylib.lookupFunction< - _RoutingContextWithSequencingC, - _RoutingContextWithSequencingDart>( - 'routing_context_with_sequencing'), - _routingContextAppCall = dylib.lookupFunction<_RoutingContextAppCallC, - _RoutingContextAppCallDart>('routing_context_app_call'), - _routingContextAppMessage = dylib.lookupFunction< - _RoutingContextAppMessageC, - _RoutingContextAppMessageDart>('routing_context_app_message'), - _routingContextCreateDHTRecord = dylib.lookupFunction< - _RoutingContextCreateDHTRecordC, - _RoutingContextCreateDHTRecordDart>( - 'routing_context_create_dht_record'), - _routingContextOpenDHTRecord = dylib.lookupFunction< - _RoutingContextOpenDHTRecordC, - _RoutingContextOpenDHTRecordDart>( - 'routing_context_open_dht_record'), - _routingContextCloseDHTRecord = dylib.lookupFunction< - _RoutingContextCloseDHTRecordC, - _RoutingContextCloseDHTRecordDart>( - 'routing_context_close_dht_record'), - _routingContextDeleteDHTRecord = dylib.lookupFunction< - _RoutingContextDeleteDHTRecordC, - _RoutingContextDeleteDHTRecordDart>( - 'routing_context_delete_dht_record'), - _routingContextGetDHTValue = dylib.lookupFunction< - _RoutingContextGetDHTValueC, - _RoutingContextGetDHTValueDart>('routing_context_get_dht_value'), - _routingContextSetDHTValue = dylib.lookupFunction< - _RoutingContextSetDHTValueC, - _RoutingContextSetDHTValueDart>('routing_context_set_dht_value'), - _routingContextWatchDHTValues = dylib.lookupFunction< - _RoutingContextWatchDHTValuesC, - _RoutingContextWatchDHTValuesDart>( - 'routing_context_watch_dht_values'), - _routingContextCancelDHTWatch = dylib.lookupFunction< - _RoutingContextCancelDHTWatchC, - _RoutingContextCancelDHTWatchDart>( - 'routing_context_cancel_dht_watch'), - _newPrivateRoute = - dylib.lookupFunction<_NewPrivateRouteC, _NewPrivateRouteDart>( - 'new_private_route'), - _newCustomPrivateRoute = dylib.lookupFunction<_NewCustomPrivateRouteC, - _NewCustomPrivateRouteDart>('new_custom_private_route'), - _importRemotePrivateRoute = dylib.lookupFunction< - _ImportRemotePrivateRouteC, - _ImportRemotePrivateRouteDart>('import_remote_private_route'), - _releasePrivateRoute = dylib.lookupFunction<_ReleasePrivateRouteC, - _ReleasePrivateRouteDart>('release_private_route'), - _appCallReply = dylib.lookupFunction<_AppCallReplyC, _AppCallReplyDart>( - 'app_call_reply'), - _openTableDb = dylib - .lookupFunction<_OpenTableDbC, _OpenTableDbDart>('open_table_db'), - _releaseTableDb = - dylib.lookupFunction<_ReleaseTableDbC, _ReleaseTableDbDart>( - 'release_table_db'), - _deleteTableDb = - dylib.lookupFunction<_DeleteTableDbC, _DeleteTableDbDart>( - 'delete_table_db'), - _tableDbGetColumnCount = dylib.lookupFunction<_TableDbGetColumnCountC, - _TableDbGetColumnCountDart>('table_db_get_column_count'), - _tableDbGetKeys = - dylib.lookupFunction<_TableDbGetKeysC, _TableDbGetKeysDart>( - 'table_db_get_keys'), - _tableDbStore = dylib.lookupFunction<_TableDbStoreC, _TableDbStoreDart>( - 'table_db_store'), - _tableDbLoad = dylib - .lookupFunction<_TableDbLoadC, _TableDbLoadDart>('table_db_load'), - _tableDbDelete = - dylib.lookupFunction<_TableDbDeleteC, _TableDbDeleteDart>( - 'table_db_delete'), - _tableDbTransact = - dylib.lookupFunction<_TableDbTransactC, _TableDbTransactDart>( - 'table_db_transact'), - _releaseTableDbTransaction = dylib.lookupFunction< - _ReleaseTableDbTransactionC, - _ReleaseTableDbTransactionDart>('release_table_db_transaction'), - _tableDbTransactionCommit = dylib.lookupFunction< - _TableDbTransactionCommitC, - _TableDbTransactionCommitDart>('table_db_transaction_commit'), - _tableDbTransactionRollback = dylib.lookupFunction< - _TableDbTransactionRollbackC, - _TableDbTransactionRollbackDart>('table_db_transaction_rollback'), - _tableDbTransactionStore = dylib.lookupFunction< - _TableDbTransactionStoreC, - _TableDbTransactionStoreDart>('table_db_transaction_store'), - _tableDbTransactionDelete = dylib.lookupFunction< - _TableDbTransactionDeleteC, - _TableDbTransactionDeleteDart>('table_db_transaction_delete'), - _validCryptoKinds = - dylib.lookupFunction<_ValidCryptoKindsC, _ValidCryptoKindsDart>( - 'valid_crypto_kinds'), - _bestCryptoKind = - dylib.lookupFunction<_BestCryptoKindC, _BestCryptoKindDart>( - 'best_crypto_kind'), - _verifySignatures = - dylib.lookupFunction<_VerifySignaturesC, _VerifySignaturesDart>( - 'verify_signatures'), - _generateSignatures = - dylib.lookupFunction<_GenerateSignaturesC, _GenerateSignaturesDart>( - 'generate_signatures'), - _generateKeyPair = - dylib.lookupFunction<_GenerateKeyPairC, _GenerateKeyPairDart>( - 'generate_key_pair'), - _cryptoCachedDH = - dylib.lookupFunction<_CryptoCachedDHC, _CryptoCachedDHDart>( - 'crypto_cached_dh'), - _cryptoComputeDH = - dylib.lookupFunction<_CryptoComputeDHC, _CryptoComputeDHDart>( - 'crypto_compute_dh'), - _cryptoRandomBytes = - dylib.lookupFunction<_CryptoRandomBytesC, _CryptoRandomBytesDart>( - 'crypto_random_bytes'), - _cryptoDefaultSaltLength = dylib.lookupFunction< - _CryptoDefaultSaltLengthC, - _CryptoDefaultSaltLengthDart>('crypto_default_salt_length'), - _cryptoHashPassword = - dylib.lookupFunction<_CryptoHashPasswordC, _CryptoHashPasswordDart>( - 'crypto_hash_password'), - _cryptoVerifyPassword = dylib.lookupFunction<_CryptoVerifyPasswordC, - _CryptoVerifyPasswordDart>('crypto_verify_password'), - _cryptoDeriveSharedSecret = dylib.lookupFunction< - _CryptoDeriveSharedSecretC, - _CryptoVerifyPasswordDart>('crypto_derive_shared_secret'), - _cryptoRandomNonce = - dylib.lookupFunction<_CryptoRandomNonceC, _CryptoRandomNonceDart>( - 'crypto_random_nonce'), - _cryptoRandomSharedSecret = dylib.lookupFunction< - _CryptoRandomSharedSecretC, - _CryptoRandomSharedSecretDart>('crypto_random_shared_secret'), - _cryptoGenerateKeyPair = dylib.lookupFunction<_CryptoGenerateKeyPairC, - _CryptoGenerateKeyPairDart>('crypto_generate_key_pair'), - _cryptoGenerateHash = - dylib.lookupFunction<_CryptoGenerateHashC, _CryptoGenerateHashDart>( - 'crypto_generate_hash'), - _cryptoValidateKeyPair = dylib.lookupFunction<_CryptoValidateKeyPairC, - _CryptoValidateKeyPairDart>('crypto_validate_key_pair'), - _cryptoValidateHash = - dylib.lookupFunction<_CryptoValidateHashC, _CryptoValidateHashDart>( - 'crypto_validate_hash'), - _cryptoDistance = - dylib.lookupFunction<_CryptoDistanceC, _CryptoDistanceDart>( - 'crypto_distance'), - _cryptoSign = - dylib.lookupFunction<_CryptoSignC, _CryptoSignDart>('crypto_sign'), - _cryptoVerify = dylib - .lookupFunction<_CryptoVerifyC, _CryptoVerifyDart>('crypto_verify'), - _cryptoAeadOverhead = - dylib.lookupFunction<_CryptoAeadOverheadC, _CryptoAeadOverheadDart>( - 'crypto_aead_overhead'), - _cryptoDecryptAead = - dylib.lookupFunction<_CryptoDecryptAeadC, _CryptoDecryptAeadDart>( - 'crypto_decrypt_aead'), - _cryptoEncryptAead = - dylib.lookupFunction<_CryptoEncryptAeadC, _CryptoEncryptAeadDart>( - 'crypto_encrypt_aead'), - _cryptoCryptNoAuth = - dylib.lookupFunction<_CryptoCryptNoAuthC, _CryptoCryptNoAuthDart>( - 'crypto_crypt_no_auth'), - _now = dylib.lookupFunction<_NowC, _NowDart>('now'), - _debug = dylib.lookupFunction<_DebugC, _DebugDart>('debug'), - _veilidVersionString = dylib.lookupFunction<_VeilidVersionStringC, - _VeilidVersionStringDart>('veilid_version_string'), - _veilidVersion = - dylib.lookupFunction<_VeilidVersionC, _VeilidVersionDart>( - 'veilid_version') { - // Get veilid_flutter initializer - var initializeVeilidFlutter = _dylib.lookupFunction< - _InitializeVeilidFlutterC, - _InitializeVeilidFlutterDart>('initialize_veilid_flutter'); - initializeVeilidFlutter(NativeApi.postCObject); - } - @override void initializeVeilidCore(Map platformConfigJson) { - var nativePlatformConfig = jsonEncode(platformConfigJson).toNativeUtf8(); + final nativePlatformConfig = jsonEncode(platformConfigJson).toNativeUtf8(); _initializeVeilidCore(nativePlatformConfig); @@ -1546,136 +1460,136 @@ class VeilidFFI extends Veilid { @override void changeLogLevel(String layer, VeilidConfigLogLevel logLevel) { - var nativeLogLevel = jsonEncode(logLevel).toNativeUtf8(); - var nativeLayer = layer.toNativeUtf8(); + final nativeLogLevel = jsonEncode(logLevel).toNativeUtf8(); + final nativeLayer = layer.toNativeUtf8(); _changeLogLevel(nativeLayer, nativeLogLevel); - malloc.free(nativeLayer); - malloc.free(nativeLogLevel); + malloc + ..free(nativeLayer) + ..free(nativeLogLevel); } @override - Future> startupVeilidCore(VeilidConfig config) { - var nativeConfig = jsonEncode(config).toNativeUtf8(); - final recvStreamPort = ReceivePort("veilid_api_stream"); + Future> startupVeilidCore(VeilidConfig config) async { + final nativeConfig = jsonEncode(config).toNativeUtf8(); + final recvStreamPort = ReceivePort('veilid_api_stream'); final sendStreamPort = recvStreamPort.sendPort; - final recvPort = ReceivePort("startup_veilid_core"); + final recvPort = ReceivePort('startup_veilid_core'); final sendPort = recvPort.sendPort; _startupVeilidCore( sendPort.nativePort, sendStreamPort.nativePort, nativeConfig); malloc.free(nativeConfig); - return processFutureStream( + return await processFutureStream( processStreamJson(VeilidUpdate.fromJson, recvStreamPort), recvPort.first); } @override - Future getVeilidState() { - final recvPort = ReceivePort("get_veilid_state"); + Future getVeilidState() async { + final recvPort = ReceivePort('get_veilid_state'); final sendPort = recvPort.sendPort; _getVeilidState(sendPort.nativePort); - return processFutureJson(VeilidState.fromJson, recvPort.first); + return await processFutureJson(VeilidState.fromJson, recvPort.first); } @override - Future attach() { - final recvPort = ReceivePort("attach"); + Future attach() async { + final recvPort = ReceivePort('attach'); final sendPort = recvPort.sendPort; _attach(sendPort.nativePort); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override - Future detach() { - final recvPort = ReceivePort("detach"); + Future detach() async { + final recvPort = ReceivePort('detach'); final sendPort = recvPort.sendPort; _detach(sendPort.nativePort); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override - Future shutdownVeilidCore() { - final recvPort = ReceivePort("shutdown_veilid_core"); + Future shutdownVeilidCore() async { + final recvPort = ReceivePort('shutdown_veilid_core'); final sendPort = recvPort.sendPort; _shutdownVeilidCore(sendPort.nativePort); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override Future routingContext() async { - final recvPort = ReceivePort("routing_context"); + final recvPort = ReceivePort('routing_context'); final sendPort = recvPort.sendPort; _routingContext(sendPort.nativePort); - final id = await processFuturePlain(recvPort.first); + final id = await processFuturePlain(recvPort.first); return VeilidRoutingContextFFI._(_Ctx(id, this)); } @override - Future newPrivateRoute() { - final recvPort = ReceivePort("new_private_route"); + Future newPrivateRoute() async { + final recvPort = ReceivePort('new_private_route'); final sendPort = recvPort.sendPort; _newPrivateRoute(sendPort.nativePort); - return processFutureJson(RouteBlob.fromJson, recvPort.first); + return await processFutureJson(RouteBlob.fromJson, recvPort.first); } @override Future newCustomPrivateRoute( - Stability stability, Sequencing sequencing) { - final recvPort = ReceivePort("new_custom_private_route"); + Stability stability, Sequencing sequencing) async { + final recvPort = ReceivePort('new_custom_private_route'); final sendPort = recvPort.sendPort; _newCustomPrivateRoute( sendPort.nativePort, jsonEncode(stability).toNativeUtf8(), jsonEncode(sequencing).toNativeUtf8()); - return processFutureJson(RouteBlob.fromJson, recvPort.first); + return await processFutureJson(RouteBlob.fromJson, recvPort.first); } @override - Future importRemotePrivateRoute(Uint8List blob) { + Future importRemotePrivateRoute(Uint8List blob) async { final nativeEncodedBlob = base64UrlNoPadEncode(blob).toNativeUtf8(); - final recvPort = ReceivePort("import_remote_private_route"); + final recvPort = ReceivePort('import_remote_private_route'); final sendPort = recvPort.sendPort; _importRemotePrivateRoute(sendPort.nativePort, nativeEncodedBlob); - return processFuturePlain(recvPort.first); + return await processFuturePlain(recvPort.first); } @override - Future releasePrivateRoute(String key) { + Future releasePrivateRoute(String key) async { final nativeEncodedKey = key.toNativeUtf8(); - final recvPort = ReceivePort("release_private_route"); + final recvPort = ReceivePort('release_private_route'); final sendPort = recvPort.sendPort; _releasePrivateRoute(sendPort.nativePort, nativeEncodedKey); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override - Future appCallReply(String callId, Uint8List message) { + Future appCallReply(String callId, Uint8List message) async { final nativeCallId = callId.toNativeUtf8(); final nativeEncodedMessage = base64UrlNoPadEncode(message).toNativeUtf8(); - final recvPort = ReceivePort("app_call_reply"); + final recvPort = ReceivePort('app_call_reply'); final sendPort = recvPort.sendPort; _appCallReply(sendPort.nativePort, nativeCallId, nativeEncodedMessage); - return processFutureVoid(recvPort.first); + return await processFutureVoid(recvPort.first); } @override Future openTableDB(String name, int columnCount) async { - final recvPort = ReceivePort("open_table_db"); + final recvPort = ReceivePort('open_table_db'); final sendPort = recvPort.sendPort; _openTableDb(sendPort.nativePort, name.toNativeUtf8(), columnCount); - final id = await processFuturePlain(recvPort.first); + final id = await processFuturePlain(recvPort.first); return VeilidTableDBFFI._(_TDB(id, this)); } @override Future deleteTableDB(String name) async { - final recvPort = ReceivePort("delete_table_db"); + final recvPort = ReceivePort('delete_table_db'); final sendPort = recvPort.sendPort; _deleteTableDb(sendPort.nativePort, name.toNativeUtf8()); - final deleted = await processFuturePlain(recvPort.first); - return deleted; + return await processFuturePlain(recvPort.first); } @override @@ -1689,41 +1603,40 @@ class VeilidFFI extends Veilid { @override Future getCryptoSystem(CryptoKind kind) async { if (!validCryptoKinds().contains(kind)) { - throw const VeilidAPIExceptionGeneric("unsupported cryptosystem"); + throw const VeilidAPIExceptionGeneric('unsupported cryptosystem'); } return VeilidCryptoSystemFFI._(this, kind); } @override - Future bestCryptoSystem() async { - return VeilidCryptoSystemFFI._(this, _bestCryptoKind()); - } + Future bestCryptoSystem() async => + VeilidCryptoSystemFFI._(this, _bestCryptoKind()); @override - Future> verifySignatures( - List nodeIds, Uint8List data, List signatures) { + Future> verifySignatures(List nodeIds, + Uint8List data, List signatures) async { final nativeNodeIds = jsonEncode(nodeIds).toNativeUtf8(); final nativeData = base64UrlNoPadEncode(data).toNativeUtf8(); final nativeSignatures = jsonEncode(signatures).toNativeUtf8(); - final recvPort = ReceivePort("verify_signatures"); + final recvPort = ReceivePort('verify_signatures'); final sendPort = recvPort.sendPort; _verifySignatures( sendPort.nativePort, nativeNodeIds, nativeData, nativeSignatures); - return processFutureJson( + return await processFutureJson( jsonListConstructor(TypedKey.fromJson), recvPort.first); } @override Future> generateSignatures( - Uint8List data, List keyPairs) { + Uint8List data, List keyPairs) async { final nativeData = base64UrlNoPadEncode(data).toNativeUtf8(); final nativeKeyPairs = jsonEncode(keyPairs).toNativeUtf8(); - final recvPort = ReceivePort("generate_signatures"); + final recvPort = ReceivePort('generate_signatures'); final sendPort = recvPort.sendPort; _generateSignatures(sendPort.nativePort, nativeData, nativeKeyPairs); - return processFutureJson( + return await processFutureJson( jsonListConstructor(TypedSignature.fromJson), recvPort.first); } @@ -1735,17 +1648,17 @@ class VeilidFFI extends Veilid { } @override - Future generateKeyPair(CryptoKind kind) { - final recvPort = ReceivePort("generate_key_pair"); + Future generateKeyPair(CryptoKind kind) async { + final recvPort = ReceivePort('generate_key_pair'); final sendPort = recvPort.sendPort; _generateKeyPair(sendPort.nativePort, kind); - return processFutureJson(TypedKeyPair.fromJson, recvPort.first); + return await processFutureJson(TypedKeyPair.fromJson, recvPort.first); } @override Future debug(String command) async { - var nativeCommand = command.toNativeUtf8(); - final recvPort = ReceivePort("debug"); + final nativeCommand = command.toNativeUtf8(); + final recvPort = ReceivePort('debug'); final sendPort = recvPort.sendPort; _debug(sendPort.nativePort, nativeCommand); return processFuturePlain(recvPort.first); @@ -1754,7 +1667,7 @@ class VeilidFFI extends Veilid { @override String veilidVersionString() { final versionString = _veilidVersionString(); - String ret = versionString.toDartString(); + final ret = versionString.toDartString(); _freeString(versionString); return ret; } diff --git a/veilid-flutter/lib/veilid_js.dart b/veilid-flutter/lib/veilid_js.dart index 42045dd1..3ef1f283 100644 --- a/veilid-flutter/lib/veilid_js.dart +++ b/veilid-flutter/lib/veilid_js.dart @@ -1,52 +1,53 @@ -import 'veilid.dart'; - +import 'dart:async'; +import 'dart:convert'; import 'dart:html' as html; import 'dart:js' as js; import 'dart:js_util' as js_util; -import 'dart:async'; -import 'dart:convert'; import 'dart:typed_data'; -import 'veilid_encoding.dart'; +import 'veilid.dart'; ////////////////////////////////////////////////////////// Veilid getVeilid() => VeilidJS(); -Object wasm = js_util.getProperty(html.window, "veilid_wasm"); +Object wasm = js_util.getProperty(html.window, 'veilid_wasm'); -Future _wrapApiPromise(Object p) { - return js_util.promiseToFuture(p).then((value) => value as T).catchError( - (error) => Future.error( - VeilidAPIException.fromJson(jsonDecode(error as String)))); -} +Future _wrapApiPromise(Object p) => js_util + .promiseToFuture(p) + .then((value) => value) + // ignore: inference_failure_on_untyped_parameter + .catchError((e) { + // Wrap all other errors in VeilidAPIExceptionInternal + throw VeilidAPIExceptionInternal(e.toString()); + }, test: (e) => e is! VeilidAPIException); class _Ctx { - int? id; + _Ctx(int id, this.js) : _id = id; + int? _id; final VeilidJS js; - _Ctx(int this.id, this.js); - void ensureValid() { - if (id == null) { + int requireId() { + if (_id == null) { throw VeilidAPIExceptionNotInitialized(); } + return _id!; } void close() { - if (id != null) { - js_util.callMethod(wasm, "release_routing_context", [id!]); - id = null; + if (_id != null) { + js_util.callMethod(wasm, 'release_routing_context', [_id]); + _id = null; } } } // JS implementation of VeilidRoutingContext class VeilidRoutingContextJS extends VeilidRoutingContext { - final _Ctx _ctx; - static final Finalizer<_Ctx> _finalizer = Finalizer((ctx) => ctx.close()); - VeilidRoutingContextJS._(this._ctx) { _finalizer.attach(this, _ctx, detach: this); } + final _Ctx _ctx; + static final Finalizer<_Ctx> _finalizer = Finalizer((ctx) => ctx.close()); @override void close() { @@ -55,113 +56,113 @@ class VeilidRoutingContextJS extends VeilidRoutingContext { @override VeilidRoutingContextJS withPrivacy() { - _ctx.ensureValid(); - int newId = - js_util.callMethod(wasm, "routing_context_with_privacy", [_ctx.id!]); + final id = _ctx.requireId(); + final int newId = + js_util.callMethod(wasm, 'routing_context_with_privacy', [id]); return VeilidRoutingContextJS._(_Ctx(newId, _ctx.js)); } @override VeilidRoutingContextJS withCustomPrivacy(SafetySelection safetySelection) { - _ctx.ensureValid(); - final newId = js_util.callMethod( + final id = _ctx.requireId(); + final newId = js_util.callMethod( wasm, - "routing_context_with_custom_privacy", - [_ctx.id!, jsonEncode(safetySelection)]); + 'routing_context_with_custom_privacy', + [id, jsonEncode(safetySelection)]); return VeilidRoutingContextJS._(_Ctx(newId, _ctx.js)); } @override VeilidRoutingContextJS withSequencing(Sequencing sequencing) { - _ctx.ensureValid(); - final newId = js_util.callMethod(wasm, "routing_context_with_sequencing", - [_ctx.id!, jsonEncode(sequencing)]); + final id = _ctx.requireId(); + final newId = js_util.callMethod( + wasm, 'routing_context_with_sequencing', [id, jsonEncode(sequencing)]); return VeilidRoutingContextJS._(_Ctx(newId, _ctx.js)); } @override Future appCall(String target, Uint8List request) async { - _ctx.ensureValid(); - var encodedRequest = base64UrlNoPadEncode(request); + final id = _ctx.requireId(); + final encodedRequest = base64UrlNoPadEncode(request); return base64UrlNoPadDecode(await _wrapApiPromise(js_util.callMethod( - wasm, "routing_context_app_call", [_ctx.id!, target, encodedRequest]))); + wasm, 'routing_context_app_call', [id, target, encodedRequest]))); } @override Future appMessage(String target, Uint8List message) { - _ctx.ensureValid(); - var encodedMessage = base64UrlNoPadEncode(message); + final id = _ctx.requireId(); + final encodedMessage = base64UrlNoPadEncode(message); - return _wrapApiPromise(js_util.callMethod(wasm, - "routing_context_app_message", [_ctx.id!, target, encodedMessage])); + return _wrapApiPromise(js_util.callMethod( + wasm, 'routing_context_app_message', [id, target, encodedMessage])); } @override Future createDHTRecord(DHTSchema schema, {CryptoKind kind = 0}) async { - _ctx.ensureValid(); + final id = _ctx.requireId(); return DHTRecordDescriptor.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "routing_context_create_dht_record", - [_ctx.id!, jsonEncode(schema), kind])))); + .callMethod(wasm, 'routing_context_create_dht_record', + [id, jsonEncode(schema), kind])))); } @override Future openDHTRecord( TypedKey key, KeyPair? writer) async { - _ctx.ensureValid(); + final id = _ctx.requireId(); return DHTRecordDescriptor.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "routing_context_open_dht_record", [ - _ctx.id!, + .callMethod(wasm, 'routing_context_open_dht_record', [ + id, jsonEncode(key), - writer != null ? jsonEncode(writer) : null + if (writer != null) jsonEncode(writer) else null ])))); } @override Future closeDHTRecord(TypedKey key) { - _ctx.ensureValid(); + final id = _ctx.requireId(); return _wrapApiPromise(js_util.callMethod( - wasm, "routing_context_close_dht_record", [_ctx.id!, jsonEncode(key)])); + wasm, 'routing_context_close_dht_record', [id, jsonEncode(key)])); } @override Future deleteDHTRecord(TypedKey key) { - _ctx.ensureValid(); - return _wrapApiPromise(js_util.callMethod(wasm, - "routing_context_delete_dht_record", [_ctx.id!, jsonEncode(key)])); + final id = _ctx.requireId(); + return _wrapApiPromise(js_util.callMethod( + wasm, 'routing_context_delete_dht_record', [id, jsonEncode(key)])); } @override Future getDHTValue( TypedKey key, int subkey, bool forceRefresh) async { - _ctx.ensureValid(); - final opt = await _wrapApiPromise(js_util.callMethod( + final id = _ctx.requireId(); + final opt = await _wrapApiPromise(js_util.callMethod( wasm, - "routing_context_get_dht_value", - [_ctx.id!, jsonEncode(key), subkey, forceRefresh])); + 'routing_context_get_dht_value', + [id, jsonEncode(key), subkey, forceRefresh])); return opt == null ? null : ValueData.fromJson(jsonDecode(opt)); } @override Future setDHTValue( TypedKey key, int subkey, Uint8List data) async { - _ctx.ensureValid(); - final opt = await _wrapApiPromise(js_util.callMethod( + final id = _ctx.requireId(); + final opt = await _wrapApiPromise(js_util.callMethod( wasm, - "routing_context_set_dht_value", - [_ctx.id!, jsonEncode(key), subkey, base64UrlNoPadEncode(data)])); + 'routing_context_set_dht_value', + [id, jsonEncode(key), subkey, base64UrlNoPadEncode(data)])); return opt == null ? null : ValueData.fromJson(jsonDecode(opt)); } @override Future watchDHTValues(TypedKey key, List subkeys, Timestamp expiration, int count) async { - _ctx.ensureValid(); - final ts = await _wrapApiPromise(js_util.callMethod( - wasm, "routing_context_watch_dht_values", [ - _ctx.id!, + final id = _ctx.requireId(); + final ts = await _wrapApiPromise(js_util.callMethod( + wasm, 'routing_context_watch_dht_values', [ + id, jsonEncode(key), jsonEncode(subkeys), expiration.toString(), @@ -172,195 +173,176 @@ class VeilidRoutingContextJS extends VeilidRoutingContext { @override Future cancelDHTWatch(TypedKey key, List subkeys) { - _ctx.ensureValid(); + final id = _ctx.requireId(); return _wrapApiPromise(js_util.callMethod( wasm, - "routing_context_cancel_dht_watch", - [_ctx.id!, jsonEncode(key), jsonEncode(subkeys)])); + 'routing_context_cancel_dht_watch', + [id, jsonEncode(key), jsonEncode(subkeys)])); } } // JS implementation of VeilidCryptoSystem class VeilidCryptoSystemJS extends VeilidCryptoSystem { + VeilidCryptoSystemJS._(this._js, this._kind); + final CryptoKind _kind; + // Keep the reference + // ignore: unused_field final VeilidJS _js; - VeilidCryptoSystemJS._(this._js, this._kind) { - // Keep the reference - _js; - } + @override + CryptoKind kind() => _kind; @override - CryptoKind kind() { - return _kind; - } + Future cachedDH(PublicKey key, SecretKey secret) async => + SharedSecret.fromJson(jsonDecode(await _wrapApiPromise(js_util.callMethod( + wasm, + 'crypto_cached_dh', + [_kind, jsonEncode(key), jsonEncode(secret)])))); @override - Future cachedDH(PublicKey key, SecretKey secret) async { - return SharedSecret.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "crypto_cached_dh", - [_kind, jsonEncode(key), jsonEncode(secret)])))); - } + Future computeDH(PublicKey key, SecretKey secret) async => + SharedSecret.fromJson(jsonDecode(await _wrapApiPromise(js_util.callMethod( + wasm, + 'crypto_compute_dh', + [_kind, jsonEncode(key), jsonEncode(secret)])))); @override - Future computeDH(PublicKey key, SecretKey secret) async { - return SharedSecret.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "crypto_compute_dh", - [_kind, jsonEncode(key), jsonEncode(secret)])))); - } + Future randomBytes(int len) async => + base64UrlNoPadDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_random_bytes', [_kind, len]))); @override - Future randomBytes(int len) async { - return base64UrlNoPadDecode(await _wrapApiPromise( - js_util.callMethod(wasm, "crypto_random_bytes", [_kind, len]))); - } + Future defaultSaltLength() => _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_default_salt_length', [_kind])); @override - Future defaultSaltLength() { - return _wrapApiPromise( - js_util.callMethod(wasm, "crypto_default_salt_length", [_kind])); - } + Future hashPassword(Uint8List password, Uint8List salt) => + _wrapApiPromise(js_util.callMethod(wasm, 'crypto_hash_password', + [_kind, base64UrlNoPadEncode(password), base64UrlNoPadEncode(salt)])); @override - Future hashPassword(Uint8List password, Uint8List salt) { - return _wrapApiPromise(js_util.callMethod(wasm, "crypto_hash_password", - [_kind, base64UrlNoPadEncode(password), base64UrlNoPadEncode(salt)])); - } - - @override - Future verifyPassword(Uint8List password, String passwordHash) { - return _wrapApiPromise(js_util.callMethod(wasm, "crypto_verify_password", - [_kind, base64UrlNoPadEncode(password), passwordHash])); - } + Future verifyPassword(Uint8List password, String passwordHash) => + _wrapApiPromise(js_util.callMethod(wasm, 'crypto_verify_password', + [_kind, base64UrlNoPadEncode(password), passwordHash])); @override Future deriveSharedSecret( - Uint8List password, Uint8List salt) async { - return SharedSecret.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "crypto_derive_shared_secret", [ - _kind, - base64UrlNoPadEncode(password), - base64UrlNoPadEncode(salt) - ])))); - } + Uint8List password, Uint8List salt) async => + SharedSecret.fromJson(jsonDecode(await _wrapApiPromise(js_util.callMethod( + wasm, 'crypto_derive_shared_secret', [ + _kind, + base64UrlNoPadEncode(password), + base64UrlNoPadEncode(salt) + ])))); @override - Future randomNonce() async { - return Nonce.fromJson(jsonDecode(await _wrapApiPromise( - js_util.callMethod(wasm, "crypto_random_nonce", [_kind])))); - } + Future randomNonce() async => + Nonce.fromJson(jsonDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_random_nonce', [_kind])))); @override - Future randomSharedSecret() async { - return SharedSecret.fromJson(jsonDecode(await _wrapApiPromise( - js_util.callMethod(wasm, "crypto_random_shared_secret", [_kind])))); - } + Future randomSharedSecret() async => + SharedSecret.fromJson(jsonDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_random_shared_secret', [_kind])))); @override - Future generateKeyPair() async { - return KeyPair.fromJson(jsonDecode(await _wrapApiPromise( - js_util.callMethod(wasm, "crypto_generate_key_pair", [_kind])))); - } + Future generateKeyPair() async => + KeyPair.fromJson(jsonDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_generate_key_pair', [_kind])))); @override - Future generateHash(Uint8List data) async { - return HashDigest.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "crypto_generate_hash", - [_kind, base64UrlNoPadEncode(data)])))); - } + Future generateHash(Uint8List data) async => + HashDigest.fromJson(jsonDecode(await _wrapApiPromise(js_util.callMethod( + wasm, 'crypto_generate_hash', [_kind, base64UrlNoPadEncode(data)])))); @override - Future validateKeyPair(PublicKey key, SecretKey secret) { - return _wrapApiPromise(js_util.callMethod(wasm, "crypto_validate_key_pair", - [_kind, jsonEncode(key), jsonEncode(secret)])); - } + Future validateKeyPair(PublicKey key, SecretKey secret) => + _wrapApiPromise(js_util.callMethod(wasm, 'crypto_validate_key_pair', + [_kind, jsonEncode(key), jsonEncode(secret)])); @override - Future validateHash(Uint8List data, HashDigest hash) { - return _wrapApiPromise(js_util.callMethod(wasm, "crypto_validate_hash", - [_kind, base64UrlNoPadEncode(data), jsonEncode(hash)])); - } + Future validateHash(Uint8List data, HashDigest hash) => + _wrapApiPromise(js_util.callMethod(wasm, 'crypto_validate_hash', + [_kind, base64UrlNoPadEncode(data), jsonEncode(hash)])); @override - Future distance(CryptoKey key1, CryptoKey key2) async { - return CryptoKeyDistance.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "crypto_distance", - [_kind, jsonEncode(key1), jsonEncode(key2)])))); - } + Future distance(CryptoKey key1, CryptoKey key2) async => + CryptoKeyDistance.fromJson(jsonDecode(await _wrapApiPromise(js_util + .callMethod(wasm, 'crypto_distance', + [_kind, jsonEncode(key1), jsonEncode(key2)])))); @override Future sign( - PublicKey key, SecretKey secret, Uint8List data) async { - return Signature.fromJson(jsonDecode(await _wrapApiPromise(js_util - .callMethod(wasm, "crypto_sign", [ - _kind, - jsonEncode(key), - jsonEncode(secret), - base64UrlNoPadEncode(data) - ])))); - } + PublicKey key, SecretKey secret, Uint8List data) async => + Signature.fromJson(jsonDecode(await _wrapApiPromise(js_util.callMethod( + wasm, 'crypto_sign', [ + _kind, + jsonEncode(key), + jsonEncode(secret), + base64UrlNoPadEncode(data) + ])))); @override - Future verify(PublicKey key, Uint8List data, Signature signature) { - return _wrapApiPromise(js_util.callMethod(wasm, "crypto_verify", [ - _kind, - jsonEncode(key), - base64UrlNoPadEncode(data), - jsonEncode(signature), - ])); - } + Future verify(PublicKey key, Uint8List data, Signature signature) => + _wrapApiPromise(js_util.callMethod(wasm, 'crypto_verify', [ + _kind, + jsonEncode(key), + base64UrlNoPadEncode(data), + jsonEncode(signature), + ])); @override - Future aeadOverhead() { - return _wrapApiPromise( - js_util.callMethod(wasm, "crypto_aead_overhead", [_kind])); - } + Future aeadOverhead() => _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_aead_overhead', [_kind])); @override Future decryptAead(Uint8List body, Nonce nonce, - SharedSecret sharedSecret, Uint8List? associatedData) async { - return base64UrlNoPadDecode( - await _wrapApiPromise(js_util.callMethod(wasm, "crypto_decrypt_aead", [ - _kind, - base64UrlNoPadEncode(body), - jsonEncode(nonce), - jsonEncode(sharedSecret), - associatedData != null ? base64UrlNoPadEncode(associatedData) : null - ]))); - } + SharedSecret sharedSecret, Uint8List? associatedData) async => + base64UrlNoPadDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_decrypt_aead', [ + _kind, + base64UrlNoPadEncode(body), + jsonEncode(nonce), + jsonEncode(sharedSecret), + if (associatedData != null) + base64UrlNoPadEncode(associatedData) + else + null + ]))); @override Future encryptAead(Uint8List body, Nonce nonce, - SharedSecret sharedSecret, Uint8List? associatedData) async { - return base64UrlNoPadDecode( - await _wrapApiPromise(js_util.callMethod(wasm, "crypto_encrypt_aead", [ - _kind, - base64UrlNoPadEncode(body), - jsonEncode(nonce), - jsonEncode(sharedSecret), - associatedData != null ? base64UrlNoPadEncode(associatedData) : null - ]))); - } + SharedSecret sharedSecret, Uint8List? associatedData) async => + base64UrlNoPadDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'crypto_encrypt_aead', [ + _kind, + base64UrlNoPadEncode(body), + jsonEncode(nonce), + jsonEncode(sharedSecret), + if (associatedData != null) + base64UrlNoPadEncode(associatedData) + else + null + ]))); @override Future cryptNoAuth( - Uint8List body, Nonce nonce, SharedSecret sharedSecret) async { - return base64UrlNoPadDecode(await _wrapApiPromise(js_util.callMethod( - wasm, "crypto_crypt_no_auth", [ - _kind, - base64UrlNoPadEncode(body), - jsonEncode(nonce), - jsonEncode(sharedSecret) - ]))); - } + Uint8List body, Nonce nonce, SharedSecret sharedSecret) async => + base64UrlNoPadDecode(await _wrapApiPromise(js_util.callMethod( + wasm, 'crypto_crypt_no_auth', [ + _kind, + base64UrlNoPadEncode(body), + jsonEncode(nonce), + jsonEncode(sharedSecret) + ]))); } class _TDBT { + _TDBT(this.id, this.tdbjs, this.js); int? id; final VeilidTableDBJS tdbjs; final VeilidJS js; - - _TDBT(this.id, this.tdbjs, this.js); void ensureValid() { if (id == null) { throw VeilidAPIExceptionNotInitialized(); @@ -369,7 +351,7 @@ class _TDBT { void close() { if (id != null) { - js_util.callMethod(wasm, "release_table_db_transaction", [id!]); + js_util.callMethod(wasm, 'release_table_db_transaction', [id]); id = null; } } @@ -377,81 +359,83 @@ class _TDBT { // JS implementation of VeilidTableDBTransaction class VeilidTableDBTransactionJS extends VeilidTableDBTransaction { - final _TDBT _tdbt; - static final Finalizer<_TDBT> _finalizer = Finalizer((tdbt) => tdbt.close()); - VeilidTableDBTransactionJS._(this._tdbt) { _finalizer.attach(this, _tdbt, detach: this); } + final _TDBT _tdbt; + static final Finalizer<_TDBT> _finalizer = Finalizer((tdbt) => tdbt.close()); @override - bool isDone() { - return _tdbt.id == null; - } + bool isDone() => _tdbt.id == null; @override Future commit() async { _tdbt.ensureValid(); - await _wrapApiPromise( - js_util.callMethod(wasm, "table_db_transaction_commit", [_tdbt.id!])); + final id = _tdbt.id!; + await _wrapApiPromise( + js_util.callMethod(wasm, 'table_db_transaction_commit', [id])); _tdbt.close(); } @override Future rollback() async { _tdbt.ensureValid(); - await _wrapApiPromise( - js_util.callMethod(wasm, "table_db_transaction_rollback", [_tdbt.id!])); + final id = _tdbt.id!; + await _wrapApiPromise( + js_util.callMethod(wasm, 'table_db_transaction_rollback', [id])); _tdbt.close(); } @override Future store(int col, Uint8List key, Uint8List value) async { _tdbt.ensureValid(); + final id = _tdbt.id!; final encodedKey = base64UrlNoPadEncode(key); final encodedValue = base64UrlNoPadEncode(value); - await _wrapApiPromise(js_util.callMethod(wasm, "table_db_transaction_store", - [_tdbt.id!, col, encodedKey, encodedValue])); + await _wrapApiPromise(js_util.callMethod(wasm, + 'table_db_transaction_store', [id, col, encodedKey, encodedValue])); } @override Future delete(int col, Uint8List key) async { _tdbt.ensureValid(); + final id = _tdbt.id!; final encodedKey = base64UrlNoPadEncode(key); - await _wrapApiPromise(js_util.callMethod( - wasm, "table_db_transaction_delete", [_tdbt.id!, col, encodedKey])); + await _wrapApiPromise(js_util.callMethod( + wasm, 'table_db_transaction_delete', [id, col, encodedKey])); } } class _TDB { - int? id; - final VeilidJS js; + _TDB(int id, this.js) : _id = id; - _TDB(int this.id, this.js); - void ensureValid() { - if (id == null) { + int? _id; + + final VeilidJS js; + int requireId() { + if (_id == null) { throw VeilidAPIExceptionNotInitialized(); } + return _id!; } void close() { - if (id != null) { - js_util.callMethod(wasm, "release_table_db", [id!]); - id = null; + if (_id != null) { + js_util.callMethod(wasm, 'release_table_db', [_id]); + _id = null; } } } // JS implementation of VeilidTableDB class VeilidTableDBJS extends VeilidTableDB { - final _TDB _tdb; - static final Finalizer<_TDB> _finalizer = Finalizer((tdb) => tdb.close()); - VeilidTableDBJS._(this._tdb) { _finalizer.attach(this, _tdb, detach: this); } + final _TDB _tdb; + static final Finalizer<_TDB> _finalizer = Finalizer((tdb) => tdb.close()); @override void close() { @@ -460,42 +444,42 @@ class VeilidTableDBJS extends VeilidTableDB { @override int getColumnCount() { - _tdb.ensureValid(); - return js_util.callMethod(wasm, "table_db_get_column_count", [_tdb.id!]); + final id = _tdb.requireId(); + return js_util.callMethod(wasm, 'table_db_get_column_count', [id]); } @override Future> getKeys(int col) async { - _tdb.ensureValid(); + final id = _tdb.requireId(); return jsonListConstructor(base64UrlNoPadDecodeDynamic)(jsonDecode( - await js_util.callMethod(wasm, "table_db_get_keys", [_tdb.id!, col]))); + await js_util.callMethod(wasm, 'table_db_get_keys', [id, col]))); } @override VeilidTableDBTransaction transact() { - _tdb.ensureValid(); - final id = js_util.callMethod(wasm, "table_db_transact", [_tdb.id!]); + final id = _tdb.requireId(); + final xid = js_util.callMethod(wasm, 'table_db_transact', [id]); - return VeilidTableDBTransactionJS._(_TDBT(id, this, _tdb.js)); + return VeilidTableDBTransactionJS._(_TDBT(xid, this, _tdb.js)); } @override Future store(int col, Uint8List key, Uint8List value) { - _tdb.ensureValid(); + final id = _tdb.requireId(); final encodedKey = base64UrlNoPadEncode(key); final encodedValue = base64UrlNoPadEncode(value); return _wrapApiPromise(js_util.callMethod( - wasm, "table_db_store", [_tdb.id!, col, encodedKey, encodedValue])); + wasm, 'table_db_store', [id, col, encodedKey, encodedValue])); } @override Future load(int col, Uint8List key) async { - _tdb.ensureValid(); + final id = _tdb.requireId(); final encodedKey = base64UrlNoPadEncode(key); - String? out = await _wrapApiPromise( - js_util.callMethod(wasm, "table_db_load", [_tdb.id!, col, encodedKey])); + final out = await _wrapApiPromise( + js_util.callMethod(wasm, 'table_db_load', [id, col, encodedKey])); if (out == null) { return null; } @@ -503,12 +487,16 @@ class VeilidTableDBJS extends VeilidTableDB { } @override - Future delete(int col, Uint8List key) { - _tdb.ensureValid(); + Future delete(int col, Uint8List key) async { + final id = _tdb.requireId(); final encodedKey = base64UrlNoPadEncode(key); - return _wrapApiPromise(js_util - .callMethod(wasm, "table_db_delete", [_tdb.id!, col, encodedKey])); + final out = await _wrapApiPromise( + js_util.callMethod(wasm, 'table_db_delete', [id, col, encodedKey])); + if (out == null) { + return null; + } + return base64UrlNoPadDecode(out); } } @@ -517,61 +505,57 @@ class VeilidTableDBJS extends VeilidTableDB { class VeilidJS extends Veilid { @override void initializeVeilidCore(Map platformConfigJson) { - var platformConfigJsonString = jsonEncode(platformConfigJson); - js_util - .callMethod(wasm, "initialize_veilid_core", [platformConfigJsonString]); + final platformConfigJsonString = jsonEncode(platformConfigJson); + js_util.callMethod( + wasm, 'initialize_veilid_core', [platformConfigJsonString]); } @override void changeLogLevel(String layer, VeilidConfigLogLevel logLevel) { - var logLevelJsonString = jsonEncode(logLevel); - js_util.callMethod(wasm, "change_log_level", [layer, logLevelJsonString]); + final logLevelJsonString = jsonEncode(logLevel); + js_util.callMethod( + wasm, 'change_log_level', [layer, logLevelJsonString]); } @override Future> startupVeilidCore(VeilidConfig config) async { - var streamController = StreamController(); - updateCallback(String update) { - var updateJson = jsonDecode(update); - if (updateJson["kind"] == "Shutdown") { - streamController.close(); + final streamController = StreamController(); + void updateCallback(String update) { + final updateJson = jsonDecode(update) as Map; + if (updateJson['kind'] == 'Shutdown') { + unawaited(streamController.close()); } else { - var update = VeilidUpdate.fromJson(updateJson); + final update = VeilidUpdate.fromJson(updateJson); streamController.add(update); } } - await _wrapApiPromise(js_util.callMethod(wasm, "startup_veilid_core", + await _wrapApiPromise(js_util.callMethod(wasm, 'startup_veilid_core', [js.allowInterop(updateCallback), jsonEncode(config)])); return streamController.stream; } @override - Future getVeilidState() async { - return VeilidState.fromJson(jsonDecode(await _wrapApiPromise( - js_util.callMethod(wasm, "get_veilid_state", [])))); - } + Future getVeilidState() async => + VeilidState.fromJson(jsonDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'get_veilid_state', [])))); @override - Future attach() { - return _wrapApiPromise(js_util.callMethod(wasm, "attach", [])); - } + Future attach() => + _wrapApiPromise(js_util.callMethod(wasm, 'attach', [])); @override - Future detach() { - return _wrapApiPromise(js_util.callMethod(wasm, "detach", [])); - } + Future detach() => + _wrapApiPromise(js_util.callMethod(wasm, 'detach', [])); @override - Future shutdownVeilidCore() { - return _wrapApiPromise( - js_util.callMethod(wasm, "shutdown_veilid_core", [])); - } + Future shutdownVeilidCore() => + _wrapApiPromise(js_util.callMethod(wasm, 'shutdown_veilid_core', [])); @override List validCryptoKinds() { - final vck = jsonDecode(js_util.callMethod(wasm, "valid_crypto_kinds", [])) + final vck = jsonDecode(js_util.callMethod(wasm, 'valid_crypto_kinds', [])) as List; return vck.map((v) => v as CryptoKind).toList(); } @@ -579,118 +563,106 @@ class VeilidJS extends Veilid { @override Future getCryptoSystem(CryptoKind kind) async { if (!validCryptoKinds().contains(kind)) { - throw const VeilidAPIExceptionGeneric("unsupported cryptosystem"); + throw const VeilidAPIExceptionGeneric('unsupported cryptosystem'); } return VeilidCryptoSystemJS._(this, kind); } @override - Future bestCryptoSystem() async { - return VeilidCryptoSystemJS._( - this, js_util.callMethod(wasm, "best_crypto_kind", [])); - } + Future bestCryptoSystem() async => VeilidCryptoSystemJS._( + this, js_util.callMethod(wasm, 'best_crypto_kind', [])); @override Future> verifySignatures(List nodeIds, - Uint8List data, List signatures) async { - return jsonListConstructor(TypedKey.fromJson)(jsonDecode( - await _wrapApiPromise(js_util.callMethod(wasm, "verify_signatures", [ - jsonEncode(nodeIds), - base64UrlNoPadEncode(data), - jsonEncode(signatures) - ])))); - } + Uint8List data, List signatures) async => + jsonListConstructor(TypedKey.fromJson)(jsonDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'verify_signatures', [ + jsonEncode(nodeIds), + base64UrlNoPadEncode(data), + jsonEncode(signatures) + ])))); @override Future> generateSignatures( - Uint8List data, List keyPairs) async { - return jsonListConstructor(TypedSignature.fromJson)(jsonDecode( - await _wrapApiPromise(js_util.callMethod(wasm, "generate_signatures", - [base64UrlNoPadEncode(data), jsonEncode(keyPairs)])))); - } + Uint8List data, List keyPairs) async => + jsonListConstructor(TypedSignature.fromJson)(jsonDecode( + await _wrapApiPromise(js_util.callMethod(wasm, 'generate_signatures', + [base64UrlNoPadEncode(data), jsonEncode(keyPairs)])))); @override - Future generateKeyPair(CryptoKind kind) async { - return TypedKeyPair.fromJson(jsonDecode(await _wrapApiPromise( - js_util.callMethod(wasm, "generate_key_pair", [kind])))); - } + Future generateKeyPair(CryptoKind kind) async => + TypedKeyPair.fromJson(jsonDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'generate_key_pair', [kind])))); @override Future routingContext() async { - int id = - await _wrapApiPromise(js_util.callMethod(wasm, "routing_context", [])); - return VeilidRoutingContextJS._(_Ctx(id, this)); + final rcid = await _wrapApiPromise( + js_util.callMethod(wasm, 'routing_context', [])); + return VeilidRoutingContextJS._(_Ctx(rcid, this)); } @override - Future newPrivateRoute() async { - return RouteBlob.fromJson(jsonDecode(await _wrapApiPromise( - js_util.callMethod(wasm, "new_private_route", [])))); - } + Future newPrivateRoute() async => + RouteBlob.fromJson(jsonDecode(await _wrapApiPromise( + js_util.callMethod(wasm, 'new_private_route', [])))); @override Future newCustomPrivateRoute( Stability stability, Sequencing sequencing) async { - var stabilityString = jsonEncode(stability); - var sequencingString = jsonEncode(sequencing); + final stabilityString = jsonEncode(stability); + final sequencingString = jsonEncode(sequencing); return RouteBlob.fromJson(jsonDecode(await _wrapApiPromise(js_util .callMethod( - wasm, "new_private_route", [stabilityString, sequencingString])))); + wasm, 'new_private_route', [stabilityString, sequencingString])))); } @override Future importRemotePrivateRoute(Uint8List blob) { - var encodedBlob = base64UrlNoPadEncode(blob); + final encodedBlob = base64UrlNoPadEncode(blob); return _wrapApiPromise( - js_util.callMethod(wasm, "import_remote_private_route", [encodedBlob])); + js_util.callMethod(wasm, 'import_remote_private_route', [encodedBlob])); } @override - Future releasePrivateRoute(String key) { - return _wrapApiPromise( - js_util.callMethod(wasm, "release_private_route", [key])); - } + Future releasePrivateRoute(String key) => + _wrapApiPromise(js_util.callMethod(wasm, 'release_private_route', [key])); @override Future appCallReply(String callId, Uint8List message) { - var encodedMessage = base64UrlNoPadEncode(message); + final encodedMessage = base64UrlNoPadEncode(message); return _wrapApiPromise( - js_util.callMethod(wasm, "app_call_reply", [callId, encodedMessage])); + js_util.callMethod(wasm, 'app_call_reply', [callId, encodedMessage])); } @override Future openTableDB(String name, int columnCount) async { - int id = await _wrapApiPromise( - js_util.callMethod(wasm, "open_table_db", [name, columnCount])); - return VeilidTableDBJS._(_TDB(id, this)); + final dbid = await _wrapApiPromise( + js_util.callMethod(wasm, 'open_table_db', [name, columnCount])); + return VeilidTableDBJS._(_TDB(dbid, this)); } @override - Future deleteTableDB(String name) { - return _wrapApiPromise(js_util.callMethod(wasm, "delete_table_db", [name])); - } + Future deleteTableDB(String name) => + _wrapApiPromise(js_util.callMethod(wasm, 'delete_table_db', [name])); @override - Timestamp now() { - return Timestamp.fromString(js_util.callMethod(wasm, "now", [])); - } + Timestamp now() => Timestamp.fromString(js_util.callMethod(wasm, 'now', [])); @override - Future debug(String command) async { - return await _wrapApiPromise(js_util.callMethod(wasm, "debug", [command])); - } + Future debug(String command) async => + _wrapApiPromise(js_util.callMethod(wasm, 'debug', [command])); @override - String veilidVersionString() { - return js_util.callMethod(wasm, "veilid_version_string", []); - } + String veilidVersionString() => + js_util.callMethod(wasm, 'veilid_version_string', []); @override VeilidVersion veilidVersion() { - Map jsonVersion = - jsonDecode(js_util.callMethod(wasm, "veilid_version", [])); - return VeilidVersion( - jsonVersion["major"], jsonVersion["minor"], jsonVersion["patch"]); + final jsonVersion = + jsonDecode(js_util.callMethod(wasm, 'veilid_version', [])) + as Map; + return VeilidVersion(jsonVersion['major'] as int, + jsonVersion['minor'] as int, jsonVersion['patch'] as int); } } diff --git a/veilid-flutter/lib/veilid_plugin_stub_web.dart b/veilid-flutter/lib/veilid_plugin_stub_web.dart index 77a8436a..8a7c3022 100644 --- a/veilid-flutter/lib/veilid_plugin_stub_web.dart +++ b/veilid-flutter/lib/veilid_plugin_stub_web.dart @@ -11,7 +11,7 @@ class VeilidPluginStubWeb { Future handleMethodCall(MethodCall call) async { throw PlatformException( code: 'Unimplemented', - details: 'Veilid for Web doesn\'t implement \'${call.method}\'', + details: "Veilid for Web doesn't implement '${call.method}'", ); } } diff --git a/veilid-flutter/lib/veilid_state.dart b/veilid-flutter/lib/veilid_state.dart index 9a7146d5..9ed85a5d 100644 --- a/veilid-flutter/lib/veilid_state.dart +++ b/veilid-flutter/lib/veilid_state.dart @@ -21,9 +21,10 @@ enum AttachmentState { overAttached, detaching; - String toJson() => name.toPascalCase(); factory AttachmentState.fromJson(dynamic j) => AttachmentState.values.byName((j as String).toCamelCase()); + + String toJson() => name.toPascalCase(); } ////////////////////////////////////// @@ -36,9 +37,10 @@ enum VeilidLogLevel { debug, trace; - String toJson() => name.toPascalCase(); factory VeilidLogLevel.fromJson(dynamic j) => VeilidLogLevel.values.byName((j as String).toCamelCase()); + + String toJson() => name.toPascalCase(); } //////////// @@ -109,8 +111,8 @@ class PeerStats with _$PeerStats { const factory PeerStats({ required Timestamp timeAdded, required RPCStats rpcStats, - LatencyStats? latency, required TransferStatsDownUp transfer, + LatencyStats? latency, }) = _PeerStats; factory PeerStats.fromJson(dynamic json) => @@ -142,13 +144,13 @@ sealed class VeilidUpdate with _$VeilidUpdate { String? backtrace, }) = VeilidLog; const factory VeilidUpdate.appMessage({ - TypedKey? sender, @Uint8ListJsonConverter() required Uint8List message, + TypedKey? sender, }) = VeilidAppMessage; const factory VeilidUpdate.appCall({ - TypedKey? sender, @Uint8ListJsonConverter() required Uint8List message, required String callId, + TypedKey? sender, }) = VeilidAppCall; const factory VeilidUpdate.attachment( {required AttachmentState state, diff --git a/veilid-flutter/lib/veilid_table_db.dart b/veilid-flutter/lib/veilid_table_db.dart index 43868c0b..a78569bb 100644 --- a/veilid-flutter/lib/veilid_table_db.dart +++ b/veilid-flutter/lib/veilid_table_db.dart @@ -1,6 +1,6 @@ import 'dart:async'; -import 'dart:typed_data'; import 'dart:convert'; +import 'dart:typed_data'; ///////////////////////////////////// /// VeilidTableDB @@ -12,16 +12,14 @@ abstract class VeilidTableDBTransaction { Future delete(int col, Uint8List key); Future storeJson(int col, Uint8List key, Object? object, - {Object? Function(Object? nonEncodable)? toEncodable}) async { - return store(col, key, - utf8.encoder.convert(jsonEncode(object, toEncodable: toEncodable))); - } + {Object? Function(Object? nonEncodable)? toEncodable}) async => + store(col, key, + utf8.encoder.convert(jsonEncode(object, toEncodable: toEncodable))); Future storeStringJson(int col, String key, Object? object, - {Object? Function(Object? nonEncodable)? toEncodable}) { - return storeJson(col, utf8.encoder.convert(key), object, - toEncodable: toEncodable); - } + {Object? Function(Object? nonEncodable)? toEncodable}) => + storeJson(col, utf8.encoder.convert(key), object, + toEncodable: toEncodable); } abstract class VeilidTableDB { @@ -34,20 +32,18 @@ abstract class VeilidTableDB { Future delete(int col, Uint8List key); Future storeJson(int col, Uint8List key, Object? object, - {Object? Function(Object? nonEncodable)? toEncodable}) { - return store(col, key, - utf8.encoder.convert(jsonEncode(object, toEncodable: toEncodable))); - } + {Object? Function(Object? nonEncodable)? toEncodable}) => + store(col, key, + utf8.encoder.convert(jsonEncode(object, toEncodable: toEncodable))); Future storeStringJson(int col, String key, Object? object, - {Object? Function(Object? nonEncodable)? toEncodable}) { - return storeJson(col, utf8.encoder.convert(key), object, - toEncodable: toEncodable); - } + {Object? Function(Object? nonEncodable)? toEncodable}) => + storeJson(col, utf8.encoder.convert(key), object, + toEncodable: toEncodable); Future loadJson(int col, Uint8List key, {Object? Function(Object? key, Object? value)? reviver}) async { - var s = await load(col, key); + final s = await load(col, key); if (s == null) { return null; } @@ -55,13 +51,12 @@ abstract class VeilidTableDB { } Future loadStringJson(int col, String key, - {Object? Function(Object? key, Object? value)? reviver}) { - return loadJson(col, utf8.encoder.convert(key), reviver: reviver); - } + {Object? Function(Object? key, Object? value)? reviver}) => + loadJson(col, utf8.encoder.convert(key), reviver: reviver); Future deleteJson(int col, Uint8List key, {Object? Function(Object? key, Object? value)? reviver}) async { - var s = await delete(col, key); + final s = await delete(col, key); if (s == null) { return null; } @@ -69,7 +64,6 @@ abstract class VeilidTableDB { } Future deleteStringJson(int col, String key, - {Object? Function(Object? key, Object? value)? reviver}) { - return deleteJson(col, utf8.encoder.convert(key), reviver: reviver); - } + {Object? Function(Object? key, Object? value)? reviver}) => + deleteJson(col, utf8.encoder.convert(key), reviver: reviver); } diff --git a/veilid-flutter/pubspec.yaml b/veilid-flutter/pubspec.yaml index d4638878..daea35ca 100644 --- a/veilid-flutter/pubspec.yaml +++ b/veilid-flutter/pubspec.yaml @@ -8,28 +8,28 @@ environment: sdk: '>=3.0.0 <4.0.0' dependencies: + change_case: ^1.0.1 + charcode: ^1.3.1 + equatable: ^2.0.5 + ffi: ^2.0.0 flutter: sdk: flutter flutter_web_plugins: sdk: flutter - ffi: ^2.0.0 - change_case: ^1.0.1 - path_provider: ^2.0.9 - path: ^1.8.0 - system_info2: ^3.0.2 - system_info_plus: ^0.0.5 - charcode: ^1.3.1 freezed_annotation: ^2.2.0 json_annotation: ^4.8.1 - equatable: ^2.0.5 - + path: ^1.8.0 + path_provider: ^2.0.9 + system_info2: ^3.0.2 + system_info_plus: ^0.0.5 + dev_dependencies: + build_runner: ^2.4.6 flutter_test: sdk: flutter - flutter_lints: ^2.0.1 - build_runner: ^2.4.6 freezed: ^2.3.5 json_serializable: ^6.7.1 + lint_hard: ^4.0.0 # The following section is specific to Flutter. flutter: diff --git a/veilid-flutter/test/veilid_test.dart b/veilid-flutter/test/veilid_test.dart index 82a21982..8e419017 100644 --- a/veilid-flutter/test/veilid_test.dart +++ b/veilid-flutter/test/veilid_test.dart @@ -2,7 +2,7 @@ import 'package:flutter_test/flutter_test.dart'; import 'package:veilid/veilid.dart'; void main() { - Veilid api = Veilid.instance; + final api = Veilid.instance; TestWidgetsFlutterBinding.ensureInitialized(); diff --git a/veilid-python/tests/test_dht.py b/veilid-python/tests/test_dht.py index 8faae302..713f5675 100644 --- a/veilid-python/tests/test_dht.py +++ b/veilid-python/tests/test_dht.py @@ -7,7 +7,9 @@ import json from . import * ################################################################## -BOGUS_KEY = veilid.TypedKey.from_value(veilid.CryptoKind.CRYPTO_KIND_VLD0, veilid.PublicKey.from_bytes(b' ')) +BOGUS_KEY = veilid.TypedKey.from_value( + veilid.CryptoKind.CRYPTO_KIND_VLD0, veilid.PublicKey.from_bytes(b' ')) + @pytest.mark.asyncio async def test_get_dht_value_unopened(api_connection: veilid.VeilidAPI): @@ -24,6 +26,7 @@ async def test_open_dht_record_nonexistent_no_writer(api_connection: veilid.Veil with pytest.raises(veilid.VeilidAPIError): out = await rc.open_dht_record(BOGUS_KEY, None) + @pytest.mark.asyncio async def test_close_dht_record_nonexistent(api_connection: veilid.VeilidAPI): rc = await api_connection.new_routing_context() @@ -31,13 +34,15 @@ async def test_close_dht_record_nonexistent(api_connection: veilid.VeilidAPI): with pytest.raises(veilid.VeilidAPIError): await rc.close_dht_record(BOGUS_KEY) + @pytest.mark.asyncio async def test_delete_dht_record_nonexistent(api_connection: veilid.VeilidAPI): rc = await api_connection.new_routing_context() async with rc: with pytest.raises(veilid.VeilidAPIError): await rc.delete_dht_record(BOGUS_KEY) - + + @pytest.mark.asyncio async def test_create_delete_dht_record_simple(api_connection: veilid.VeilidAPI): rc = await api_connection.new_routing_context() @@ -46,6 +51,7 @@ async def test_create_delete_dht_record_simple(api_connection: veilid.VeilidAPI) await rc.close_dht_record(rec.key) await rc.delete_dht_record(rec.key) + @pytest.mark.asyncio async def test_get_dht_value_nonexistent(api_connection: veilid.VeilidAPI): rc = await api_connection.new_routing_context() @@ -55,34 +61,34 @@ async def test_get_dht_value_nonexistent(api_connection: veilid.VeilidAPI): await rc.close_dht_record(rec.key) await rc.delete_dht_record(rec.key) + @pytest.mark.asyncio async def test_set_get_dht_value(api_connection: veilid.VeilidAPI): rc = await api_connection.new_routing_context() async with rc: rec = await rc.create_dht_record(veilid.DHTSchema.dflt(2)) - + vd = await rc.set_dht_value(rec.key, 0, b"BLAH BLAH BLAH") - assert vd != None - + assert vd == None + vd2 = await rc.get_dht_value(rec.key, 0, False) assert vd2 != None - + vd3 = await rc.get_dht_value(rec.key, 0, True) assert vd3 != None vd4 = await rc.get_dht_value(rec.key, 1, False) assert vd4 == None - print("vd: {}", vd.__dict__) print("vd2: {}", vd2.__dict__) print("vd3: {}", vd3.__dict__) - assert vd == vd2 assert vd2 == vd3 await rc.close_dht_record(rec.key) await rc.delete_dht_record(rec.key) + @pytest.mark.asyncio async def test_open_writer_dht_value(api_connection: veilid.VeilidAPI): rc = await api_connection.new_routing_context() @@ -104,10 +110,7 @@ async def test_open_writer_dht_value(api_connection: veilid.VeilidAPI): # Test subkey writes vdtemp = await rc.set_dht_value(key, 1, va) - assert vdtemp != None - assert vdtemp.data == va - assert vdtemp.seq == 0 - assert vdtemp.writer == owner + assert vdtemp == None vdtemp = await rc.get_dht_value(key, 1, False) assert vdtemp.data == va @@ -118,8 +121,7 @@ async def test_open_writer_dht_value(api_connection: veilid.VeilidAPI): assert vdtemp == None vdtemp = await rc.set_dht_value(key, 0, vb) - assert vdtemp.data == vb - assert vdtemp.seq == 0 + assert vdtemp == None vdtemp = await rc.get_dht_value(key, 0, True) assert vdtemp.data == vb @@ -129,17 +131,11 @@ async def test_open_writer_dht_value(api_connection: veilid.VeilidAPI): # Equal value should not trigger sequence number update vdtemp = await rc.set_dht_value(key, 1, va) - assert vdtemp != None - assert vdtemp.data == va - assert vdtemp.seq == 0 - assert vdtemp.writer == owner + assert vdtemp == None # Different value should trigger sequence number update vdtemp = await rc.set_dht_value(key, 1, vb) - assert vdtemp != None - assert vdtemp.data == vb - assert vdtemp.seq == 1 - assert vdtemp.writer == owner + assert vdtemp == None # Now that we initialized some subkeys # and verified they stored correctly @@ -166,11 +162,8 @@ async def test_open_writer_dht_value(api_connection: veilid.VeilidAPI): # Verify subkey 1 can be set a second time and it updates because seq is newer vdtemp = await rc.set_dht_value(key, 1, vc) - assert vdtemp != None - assert vdtemp.data == vc - assert vdtemp.seq == 2 - assert vdtemp.writer == owner - + assert vdtemp == None + # Verify the network got the subkey update with a refresh check vdtemp = await rc.get_dht_value(key, 1, True) assert vdtemp != None @@ -183,7 +176,7 @@ async def test_open_writer_dht_value(api_connection: veilid.VeilidAPI): await rc.close_dht_record(key) await rc.delete_dht_record(key) - + rec = await rc.open_dht_record(key, other_keypair) assert rec != None assert rec.key == key @@ -195,12 +188,11 @@ async def test_open_writer_dht_value(api_connection: veilid.VeilidAPI): # Verify subkey 1 can NOT be set because we have the wrong writer with pytest.raises(veilid.VeilidAPIError): vdtemp = await rc.set_dht_value(key, 1, va) - + # Verify subkey 0 can NOT be set because we have the wrong writer with pytest.raises(veilid.VeilidAPIError): vdtemp = await rc.set_dht_value(key, 0, va) - + # Clean up await rc.close_dht_record(key) await rc.delete_dht_record(key) -