From 316c45c32f0a137b468cc1749921102e70b8ddd3 Mon Sep 17 00:00:00 2001 From: Denver Coneybeare Date: Mon, 10 Aug 2026 22:17:34 +0000 Subject: [PATCH] feat(sql_connect): Add 15 second grace before disconnecting a streaming connection with the backend --- .../lib/firebase_data_connect.dart | 2 +- .../lib/src/firebase_data_connect.dart | 15 +- .../lib/src/network/websocket_transport.dart | 48 +- .../test/src/cache/cache_manager_test.dart | 2 +- .../src/cache/cache_manager_test.mocks.dart | 16 +- .../test/src/firebase_data_connect_test.dart | 27 +- .../src/firebase_data_connect_test.mocks.dart | 136 +--- .../network/rest_transport_test.mocks.dart | 24 +- .../src/network/routing_transport_test.dart | 168 +++++ .../network/routing_transport_test.mocks.dart | 545 ++++++++++++++ .../src/network/websocket_transport_test.dart | 145 +++- .../websocket_transport_test.mocks.dart | 675 ++++++++++++------ 12 files changed, 1401 insertions(+), 402 deletions(-) create mode 100644 packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.dart create mode 100644 packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.mocks.dart diff --git a/packages/firebase_data_connect/firebase_data_connect/lib/firebase_data_connect.dart b/packages/firebase_data_connect/firebase_data_connect/lib/firebase_data_connect.dart index 6221ed1ca4af..bbafd64e6c2c 100644 --- a/packages/firebase_data_connect/firebase_data_connect/lib/firebase_data_connect.dart +++ b/packages/firebase_data_connect/firebase_data_connect/lib/firebase_data_connect.dart @@ -35,7 +35,7 @@ export 'src/core/ref.dart' QueryRef, QueryResult, DataSource; -export 'src/firebase_data_connect.dart'; +export 'src/firebase_data_connect.dart' hide RoutingTransport; export 'src/optional.dart' show Optional, diff --git a/packages/firebase_data_connect/firebase_data_connect/lib/src/firebase_data_connect.dart b/packages/firebase_data_connect/firebase_data_connect/lib/src/firebase_data_connect.dart index 165b6f5d62fb..56d4475e31e7 100644 --- a/packages/firebase_data_connect/firebase_data_connect/lib/src/firebase_data_connect.dart +++ b/packages/firebase_data_connect/firebase_data_connect/lib/src/firebase_data_connect.dart @@ -19,6 +19,7 @@ import 'package:firebase_core_platform_interface/firebase_core_platform_interfac import 'package:firebase_data_connect/src/common/common_library.dart'; import 'package:firebase_data_connect/src/core/ref.dart'; import 'package:flutter/foundation.dart'; +import 'package:meta/meta.dart'; import './network/rest_library.dart'; import './network/transport_library.dart'; @@ -116,7 +117,7 @@ class FirebaseDataConnect extends FirebasePlugin { appCheck, auth, ); - transport = _RoutingTransport(rest, ws); + transport = RoutingTransport(rest, ws); } @visibleForTesting @@ -240,8 +241,12 @@ class FirebaseDataConnect extends FirebasePlugin { } } -class _RoutingTransport implements DataConnectTransport { - _RoutingTransport(this.rest, this.websocket); +/// @nodoc +@internal +// TODO: Move RoutingTransport to its own file under src/network/ to avoid exposing it publicly +// and hiding it in exports. +class RoutingTransport implements DataConnectTransport { + RoutingTransport(this.rest, this.websocket); final RestTransport rest; final WebSocketTransport websocket; @@ -294,7 +299,7 @@ class _RoutingTransport implements DataConnectTransport { Variables? vars, String? token, ) { - if (websocket.isConnected) { + if (websocket.isConnected && websocket.hasActiveSubscriptions) { return websocket.invokeMutation( operationId, queryName, deserializer, serializer, vars, token); } @@ -311,7 +316,7 @@ class _RoutingTransport implements DataConnectTransport { Variables? vars, String? token, ) { - if (websocket.isConnected) { + if (websocket.isConnected && websocket.hasActiveSubscriptions) { return websocket.invokeQuery( operationId, queryName, deserializer, serialize, vars, token); } diff --git a/packages/firebase_data_connect/firebase_data_connect/lib/src/network/websocket_transport.dart b/packages/firebase_data_connect/firebase_data_connect/lib/src/network/websocket_transport.dart index 9daf48cbcb08..dfc7a94a1114 100644 --- a/packages/firebase_data_connect/firebase_data_connect/lib/src/network/websocket_transport.dart +++ b/packages/firebase_data_connect/firebase_data_connect/lib/src/network/websocket_transport.dart @@ -54,7 +54,8 @@ class WebSocketTransport implements DataConnectTransport { this.sdkType, this.appCheck, [ this.auth, - ]) { + @visibleForTesting WebSocketChannel Function(Uri)? connectWebSocket, + ]) : _connectWebSocket = connectWebSocket ?? WebSocketChannel.connect { final protocol = (transportOptions.isSecure ?? true) ? 'wss' : 'ws'; final host = transportOptions.host; final port = transportOptions.port ?? 443; @@ -94,6 +95,7 @@ class WebSocketTransport implements DataConnectTransport { }); } + final WebSocketChannel Function(Uri) _connectWebSocket; FirebaseAuth? auth; String? _currentUid; // ignore: unused_field @@ -184,16 +186,39 @@ class WebSocketTransport implements DataConnectTransport { /// vetoes any reconnect for the operation that was still being set up. int _pendingOperationSetups = 0; + static const Duration _idleDisconnectTimeout = Duration(seconds: 15); + Timer? _idleDisconnectTimer; + void _checkIdleAndDisconnect() { - if (_pendingOperationSetups > 0) return; + if (_pendingOperationSetups > 0) { + _cancelIdleDisconnectTimer(); + return; + } if (_streamListeners.isEmpty && _unaryListeners.isEmpty) { - _isExpectedDisconnect = true; - _disconnect(); - _releaseWebSocketTransport(); - _clearState(); + _scheduleIdleDisconnect(); + } else { + _cancelIdleDisconnectTimer(); } } + void _scheduleIdleDisconnect() { + if (_idleDisconnectTimer != null) return; // Already scheduled + _idleDisconnectTimer = Timer(_idleDisconnectTimeout, () { + _idleDisconnectTimer = null; + if (_streamListeners.isEmpty && _unaryListeners.isEmpty && _pendingOperationSetups == 0) { + _isExpectedDisconnect = true; + _disconnect(); + _releaseWebSocketTransport(); + _clearState(); + } + }); + } + + void _cancelIdleDisconnectTimer() { + _idleDisconnectTimer?.cancel(); + _idleDisconnectTimer = null; + } + /// Re-establishes the connection on behalf of operations that are already /// registered. /// @@ -284,6 +309,9 @@ class WebSocketTransport implements DataConnectTransport { bool get isConnected => _channel != null; + /// Returns true if there are active stream listeners. + bool get hasActiveSubscriptions => _streamListeners.isNotEmpty; + @visibleForTesting Map buildHeaders(String? authToken, String? appCheckToken) => _buildHeaders(authToken, appCheckToken); @@ -307,6 +335,7 @@ class WebSocketTransport implements DataConnectTransport { Future? _connectionFuture; Future _ensureConnected(String? authToken) { + _cancelIdleDisconnectTimer(); if (_channel != null) return Future.value(); if (_connectionFuture != null) return _connectionFuture!; _connectionFuture = _doConnect(authToken).whenComplete(() { @@ -331,7 +360,7 @@ class WebSocketTransport implements DataConnectTransport { // `done`/`error` from it cannot clobber the channel we are about to open. unawaited(_channelSubscription?.cancel()); - final channel = WebSocketChannel.connect(Uri.parse(_url)); + final channel = _connectWebSocket(Uri.parse(_url)); _channel = channel; _channelSubscription = channel.stream.listen( _onMessage, @@ -584,6 +613,7 @@ class WebSocketTransport implements DataConnectTransport { // Ignore events from a socket that is no longer the active one. if (!identical(_channel, channel)) return; developer.log('WebSocket error: $error'); + _cancelIdleDisconnectTimer(); _channel = null; _isReconnecting = false; _scheduleReconnect(); @@ -602,6 +632,7 @@ class WebSocketTransport implements DataConnectTransport { void disconnect() { _isExpectedDisconnect = true; + _cancelIdleDisconnectTimer(); _disconnect(); _releaseWebSocketTransport(); } @@ -614,6 +645,7 @@ class WebSocketTransport implements DataConnectTransport { // A `done` from a socket we already replaced must not null out the current // channel: every later `_send` would be dropped on the floor silently. if (!identical(_channel, channel)) return; + _cancelIdleDisconnectTimer(); _channel = null; _isReconnecting = false; if (!_isExpectedDisconnect) { @@ -682,6 +714,7 @@ class WebSocketTransport implements DataConnectTransport { authToken, requestKind, isMutation); } finally { _pendingOperationSetups--; + _checkIdleAndDisconnect(); } return completer.future; } @@ -873,6 +906,7 @@ class WebSocketTransport implements DataConnectTransport { _sendPendingSubscriptions(authToken, appCheckToken); } finally { _pendingOperationSetups--; + _checkIdleAndDisconnect(); } }, onCancel: () { diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.dart index 69f43f9c853f..82440cf71a64 100644 --- a/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.dart +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.dart @@ -36,7 +36,7 @@ import 'package:mockito/annotations.dart'; import 'package:mockito/mockito.dart'; @GenerateNiceMocks([MockSpec(), MockSpec()]) -import '../firebase_data_connect_test.mocks.dart'; +import 'cache_manager_test.mocks.dart'; import '../network/rest_transport_test.mocks.dart'; class MockTransportOptions extends Mock implements TransportOptions {} diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.mocks.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.mocks.dart index 05a303db4353..74d92ec4c1ee 100644 --- a/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.mocks.dart +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/cache/cache_manager_test.mocks.dart @@ -1,17 +1,3 @@ -// Copyright 2026 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - // Mocks generated by Mockito 5.4.6 from annotations // in firebase_data_connect/test/src/cache/cache_manager_test.dart. // Do not manually edit this file. @@ -123,7 +109,7 @@ class MockFirebaseApp extends _i1.Mock implements _i3.FirebaseApp { @override void registerService( - T service, { + T? service, { _i5.Future Function(T)? dispose, }) => super.noSuchMethod( diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.dart index eabf82393de8..2a4d0cce009d 100644 --- a/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.dart +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.dart @@ -22,7 +22,7 @@ import 'package:flutter_test/flutter_test.dart'; import 'package:mockito/annotations.dart'; import 'package:mockito/mockito.dart'; -@GenerateNiceMocks([MockSpec(), MockSpec()]) +@GenerateNiceMocks([MockSpec()]) import 'firebase_data_connect_test.mocks.dart'; class MockFirebaseAuth extends Mock implements FirebaseAuth { @@ -75,24 +75,25 @@ class MockQueryManager extends Mock implements QueryManager {} void main() { group('FirebaseDataConnect', () { - late MockFirebaseApp mockApp; + late DynamicMockFirebaseApp mockApp; late MockFirebaseAuth mockAuth; late MockFirebaseAppCheck mockAppCheck; late MockConnectorConfig mockConnectorConfig; setUp(() { - mockApp = MockFirebaseApp(); mockAuth = MockFirebaseAuth(); mockAppCheck = MockFirebaseAppCheck(); mockConnectorConfig = MockConnectorConfig(); - - when(mockApp.options).thenReturn( - const FirebaseOptions( + mockApp = DynamicMockFirebaseApp( + name: 'default', + options: const FirebaseOptions( apiKey: 'fake_api_key', appId: 'fake_app_id', messagingSenderId: 'fake_messaging_sender_id', projectId: 'fake_project_id', ), + mockAuth: mockAuth, + mockAppCheck: mockAppCheck, ); when(mockConnectorConfig.location).thenReturn('us-central1'); when(mockConnectorConfig.connector).thenReturn('connector'); @@ -181,7 +182,12 @@ void main() { test('instanceFor returns cached instance if available', () { FirebaseDataConnect.cachedInstances.clear(); // Clear cache first - when(mockApp.name).thenReturn('appName'); + mockApp = DynamicMockFirebaseApp( + name: 'appName', + options: mockApp.options, + mockAuth: mockAuth, + mockAppCheck: mockAppCheck, + ); when(mockConnectorConfig.toJson()).thenReturn('connectorConfigStr'); final dataConnect = FirebaseDataConnect( @@ -208,7 +214,12 @@ void main() { test('instanceFor creates new instance if not cached', () { FirebaseDataConnect.cachedInstances.clear(); // Clear cache first - when(mockApp.name).thenReturn('appName'); + mockApp = DynamicMockFirebaseApp( + name: 'appName', + options: mockApp.options, + mockAuth: mockAuth, + mockAppCheck: mockAppCheck, + ); when(mockConnectorConfig.toJson()).thenReturn('connectorConfigStr'); final instance = FirebaseDataConnect.instanceFor( diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.mocks.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.mocks.dart index b4e1b1ed8a00..d9972f0e108c 100644 --- a/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.mocks.dart +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/firebase_data_connect_test.mocks.dart @@ -1,30 +1,11 @@ -// Copyright 2026 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - // Mocks generated by Mockito 5.4.6 from annotations // in firebase_data_connect/test/src/firebase_data_connect_test.dart. // Do not manually edit this file. // ignore_for_file: no_leading_underscores_for_library_prefixes -import 'dart:async' as _i5; - -import 'package:firebase_core/firebase_core.dart' as _i3; -import 'package:firebase_core_platform_interface/firebase_core_platform_interface.dart' - as _i2; -import 'package:firebase_data_connect/src/common/common_library.dart' as _i6; +import 'package:firebase_data_connect/src/common/common_library.dart' as _i2; import 'package:mockito/mockito.dart' as _i1; -import 'package:mockito/src/dummies.dart' as _i4; +import 'package:mockito/src/dummies.dart' as _i3; // ignore_for_file: type=lint // ignore_for_file: avoid_redundant_argument_values @@ -41,113 +22,18 @@ import 'package:mockito/src/dummies.dart' as _i4; // ignore_for_file: subtype_of_sealed_class // ignore_for_file: invalid_use_of_internal_member -class _FakeFirebaseOptions_0 extends _i1.SmartFake - implements _i2.FirebaseOptions { - _FakeFirebaseOptions_0( - Object parent, - Invocation parentInvocation, - ) : super( - parent, - parentInvocation, - ); -} - -/// A class which mocks [FirebaseApp]. -/// -/// See the documentation for Mockito's code generation for more information. -class MockFirebaseApp extends _i1.Mock implements _i3.FirebaseApp { - @override - String get name => (super.noSuchMethod( - Invocation.getter(#name), - returnValue: _i4.dummyValue( - this, - Invocation.getter(#name), - ), - returnValueForMissingStub: _i4.dummyValue( - this, - Invocation.getter(#name), - ), - ) as String); - - @override - _i2.FirebaseOptions get options => (super.noSuchMethod( - Invocation.getter(#options), - returnValue: _FakeFirebaseOptions_0( - this, - Invocation.getter(#options), - ), - returnValueForMissingStub: _FakeFirebaseOptions_0( - this, - Invocation.getter(#options), - ), - ) as _i2.FirebaseOptions); - - @override - bool get isAutomaticDataCollectionEnabled => (super.noSuchMethod( - Invocation.getter(#isAutomaticDataCollectionEnabled), - returnValue: false, - returnValueForMissingStub: false, - ) as bool); - - @override - _i5.Future delete() => (super.noSuchMethod( - Invocation.method( - #delete, - [], - ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); - - @override - _i5.Future setAutomaticDataCollectionEnabled(bool? enabled) => - (super.noSuchMethod( - Invocation.method( - #setAutomaticDataCollectionEnabled, - [enabled], - ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); - - @override - _i5.Future setAutomaticResourceManagementEnabled(bool? enabled) => - (super.noSuchMethod( - Invocation.method( - #setAutomaticResourceManagementEnabled, - [enabled], - ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); - - @override - void registerService( - T service, { - _i5.Future Function(T)? dispose, - }) => - super.noSuchMethod( - Invocation.method( - #registerService, - [service], - {#dispose: dispose}, - ), - returnValueForMissingStub: null, - ); -} - /// A class which mocks [ConnectorConfig]. /// /// See the documentation for Mockito's code generation for more information. -class MockConnectorConfig extends _i1.Mock implements _i6.ConnectorConfig { +class MockConnectorConfig extends _i1.Mock implements _i2.ConnectorConfig { @override String get location => (super.noSuchMethod( Invocation.getter(#location), - returnValue: _i4.dummyValue( + returnValue: _i3.dummyValue( this, Invocation.getter(#location), ), - returnValueForMissingStub: _i4.dummyValue( + returnValueForMissingStub: _i3.dummyValue( this, Invocation.getter(#location), ), @@ -156,11 +42,11 @@ class MockConnectorConfig extends _i1.Mock implements _i6.ConnectorConfig { @override String get connector => (super.noSuchMethod( Invocation.getter(#connector), - returnValue: _i4.dummyValue( + returnValue: _i3.dummyValue( this, Invocation.getter(#connector), ), - returnValueForMissingStub: _i4.dummyValue( + returnValueForMissingStub: _i3.dummyValue( this, Invocation.getter(#connector), ), @@ -169,11 +55,11 @@ class MockConnectorConfig extends _i1.Mock implements _i6.ConnectorConfig { @override String get serviceId => (super.noSuchMethod( Invocation.getter(#serviceId), - returnValue: _i4.dummyValue( + returnValue: _i3.dummyValue( this, Invocation.getter(#serviceId), ), - returnValueForMissingStub: _i4.dummyValue( + returnValueForMissingStub: _i3.dummyValue( this, Invocation.getter(#serviceId), ), @@ -212,14 +98,14 @@ class MockConnectorConfig extends _i1.Mock implements _i6.ConnectorConfig { #toJson, [], ), - returnValue: _i4.dummyValue( + returnValue: _i3.dummyValue( this, Invocation.method( #toJson, [], ), ), - returnValueForMissingStub: _i4.dummyValue( + returnValueForMissingStub: _i3.dummyValue( this, Invocation.method( #toJson, diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/network/rest_transport_test.mocks.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/network/rest_transport_test.mocks.dart index 828b48d4f7e7..4523586d24f4 100644 --- a/packages/firebase_data_connect/firebase_data_connect/test/src/network/rest_transport_test.mocks.dart +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/network/rest_transport_test.mocks.dart @@ -1,17 +1,3 @@ -// Copyright 2026 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - // Mocks generated by Mockito 5.4.6 from annotations // in firebase_data_connect/test/src/network/rest_transport_test.dart. // Do not manually edit this file. @@ -808,6 +794,16 @@ class MockFirebaseAppCheck extends _i1.Mock implements _i10.FirebaseAppCheck { returnValue: _i6.Future.value(), ) as _i6.Future); + @override + _i6.Future<_i11.AppCheckTokenResult?> getTokenResult([bool? forceRefresh]) => + (super.noSuchMethod( + Invocation.method( + #getTokenResult, + [forceRefresh], + ), + returnValue: _i6.Future<_i11.AppCheckTokenResult?>.value(), + ) as _i6.Future<_i11.AppCheckTokenResult?>); + @override _i6.Future setTokenAutoRefreshEnabled( bool? isTokenAutoRefreshEnabled) => diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.dart new file mode 100644 index 000000000000..bcf1d660fbb4 --- /dev/null +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.dart @@ -0,0 +1,168 @@ +// Copyright 2026 Google LLC +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +import 'package:firebase_data_connect/src/common/common_library.dart'; +import 'package:firebase_data_connect/src/firebase_data_connect.dart'; +import 'package:firebase_data_connect/src/network/rest_library.dart'; +import 'package:firebase_data_connect/src/network/transport_library.dart'; +import 'package:flutter_test/flutter_test.dart'; +import 'package:mockito/annotations.dart'; +import 'package:mockito/mockito.dart'; + +import 'routing_transport_test.mocks.dart'; + +@GenerateMocks([RestTransport, WebSocketTransport]) +void main() { + group('RoutingTransport', () { + late MockRestTransport mockRest; + late MockWebSocketTransport mockWS; + late RoutingTransport routingTransport; + + setUp(() { + mockRest = MockRestTransport(); + mockWS = MockWebSocketTransport(); + routingTransport = RoutingTransport(mockRest, mockWS); + }); + + group('invokeQuery', () { + test('should route to WS when connected and has active subscriptions', () async { + when(mockWS.isConnected).thenReturn(true); + when(mockWS.hasActiveSubscriptions).thenReturn(true); + final expectedResponse = ServerResponse({}); + when(mockWS.invokeQuery(any, any, any, any, any, any)) + .thenAnswer((_) => Future.value(expectedResponse)); + + final response = await routingTransport.invokeQuery( + 'opId', + 'queryName', + (json) => json, + null, + null, + 'token', + ); + + expect(response, equals(expectedResponse)); + verify(mockWS.invokeQuery(any, any, any, any, any, any)).called(1); + verifyNever(mockRest.invokeQuery(any, any, any, any, any, any)); + }); + + test('should route to REST when connected but has NO active subscriptions', () async { + when(mockWS.isConnected).thenReturn(true); + when(mockWS.hasActiveSubscriptions).thenReturn(false); + final expectedResponse = ServerResponse({}); + when(mockRest.invokeQuery(any, any, any, any, any, any)) + .thenAnswer((_) => Future.value(expectedResponse)); + + final response = await routingTransport.invokeQuery( + 'opId', + 'queryName', + (json) => json, + null, + null, + 'token', + ); + + expect(response, equals(expectedResponse)); + verify(mockRest.invokeQuery(any, any, any, any, any, any)).called(1); + verifyNever(mockWS.invokeQuery(any, any, any, any, any, any)); + }); + + test('should route to REST when WS is NOT connected', () async { + when(mockWS.isConnected).thenReturn(false); + when(mockWS.hasActiveSubscriptions).thenReturn(false); + final expectedResponse = ServerResponse({}); + when(mockRest.invokeQuery(any, any, any, any, any, any)) + .thenAnswer((_) => Future.value(expectedResponse)); + + final response = await routingTransport.invokeQuery( + 'opId', + 'queryName', + (json) => json, + null, + null, + 'token', + ); + + expect(response, equals(expectedResponse)); + verify(mockRest.invokeQuery(any, any, any, any, any, any)).called(1); + verifyNever(mockWS.invokeQuery(any, any, any, any, any, any)); + }); + }); + + group('invokeMutation', () { + test('should route to WS when connected and has active subscriptions', () async { + when(mockWS.isConnected).thenReturn(true); + when(mockWS.hasActiveSubscriptions).thenReturn(true); + final expectedResponse = ServerResponse({}); + when(mockWS.invokeMutation(any, any, any, any, any, any)) + .thenAnswer((_) => Future.value(expectedResponse)); + + final response = await routingTransport.invokeMutation( + 'opId', + 'mutationName', + (json) => json, + null, + null, + 'token', + ); + + expect(response, equals(expectedResponse)); + verify(mockWS.invokeMutation(any, any, any, any, any, any)).called(1); + verifyNever(mockRest.invokeMutation(any, any, any, any, any, any)); + }); + + test('should route to REST when connected but has NO active subscriptions', () async { + when(mockWS.isConnected).thenReturn(true); + when(mockWS.hasActiveSubscriptions).thenReturn(false); + final expectedResponse = ServerResponse({}); + when(mockRest.invokeMutation(any, any, any, any, any, any)) + .thenAnswer((_) => Future.value(expectedResponse)); + + final response = await routingTransport.invokeMutation( + 'opId', + 'mutationName', + (json) => json, + null, + null, + 'token', + ); + + expect(response, equals(expectedResponse)); + verify(mockRest.invokeMutation(any, any, any, any, any, any)).called(1); + verifyNever(mockWS.invokeMutation(any, any, any, any, any, any)); + }); + + test('should route to REST when WS is NOT connected', () async { + when(mockWS.isConnected).thenReturn(false); + when(mockWS.hasActiveSubscriptions).thenReturn(false); + final expectedResponse = ServerResponse({}); + when(mockRest.invokeMutation(any, any, any, any, any, any)) + .thenAnswer((_) => Future.value(expectedResponse)); + + final response = await routingTransport.invokeMutation( + 'opId', + 'mutationName', + (json) => json, + null, + null, + 'token', + ); + + expect(response, equals(expectedResponse)); + verify(mockRest.invokeMutation(any, any, any, any, any, any)).called(1); + verifyNever(mockWS.invokeMutation(any, any, any, any, any, any)); + }); + }); + }); +} diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.mocks.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.mocks.dart new file mode 100644 index 000000000000..cb2c43ca2d11 --- /dev/null +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/network/routing_transport_test.mocks.dart @@ -0,0 +1,545 @@ +// Mocks generated by Mockito 5.4.6 from annotations +// in firebase_data_connect/test/src/network/routing_transport_test.dart. +// Do not manually edit this file. + +// ignore_for_file: no_leading_underscores_for_library_prefixes +import 'dart:async' as _i7; + +import 'package:firebase_app_check/firebase_app_check.dart' as _i5; +import 'package:firebase_auth/firebase_auth.dart' as _i9; +import 'package:firebase_data_connect/src/common/common_library.dart' as _i2; +import 'package:firebase_data_connect/src/network/rest_library.dart' as _i3; +import 'package:firebase_data_connect/src/network/transport_library.dart' + as _i8; +import 'package:http/http.dart' as _i6; +import 'package:mockito/mockito.dart' as _i1; +import 'package:mockito/src/dummies.dart' as _i4; + +// ignore_for_file: type=lint +// ignore_for_file: avoid_redundant_argument_values +// ignore_for_file: avoid_setters_without_getters +// ignore_for_file: comment_references +// ignore_for_file: deprecated_member_use +// ignore_for_file: deprecated_member_use_from_same_package +// ignore_for_file: implementation_imports +// ignore_for_file: invalid_use_of_visible_for_testing_member +// ignore_for_file: must_be_immutable +// ignore_for_file: prefer_const_constructors +// ignore_for_file: unnecessary_parenthesis +// ignore_for_file: camel_case_types +// ignore_for_file: subtype_of_sealed_class +// ignore_for_file: invalid_use_of_internal_member + +class _FakeTransportOptions_0 extends _i1.SmartFake + implements _i2.TransportOptions { + _FakeTransportOptions_0( + Object parent, + Invocation parentInvocation, + ) : super( + parent, + parentInvocation, + ); +} + +class _FakeDataConnectOptions_1 extends _i1.SmartFake + implements _i2.DataConnectOptions { + _FakeDataConnectOptions_1( + Object parent, + Invocation parentInvocation, + ) : super( + parent, + parentInvocation, + ); +} + +class _FakeServerResponse_2 extends _i1.SmartFake + implements _i2.ServerResponse { + _FakeServerResponse_2( + Object parent, + Invocation parentInvocation, + ) : super( + parent, + parentInvocation, + ); +} + +/// A class which mocks [RestTransport]. +/// +/// See the documentation for Mockito's code generation for more information. +class MockRestTransport extends _i1.Mock implements _i3.RestTransport { + MockRestTransport() { + _i1.throwOnMissingStub(this); + } + + @override + _i2.CallerSDKType get sdkType => (super.noSuchMethod( + Invocation.getter(#sdkType), + returnValue: _i2.CallerSDKType.core, + ) as _i2.CallerSDKType); + + @override + String get url => (super.noSuchMethod( + Invocation.getter(#url), + returnValue: _i4.dummyValue( + this, + Invocation.getter(#url), + ), + ) as String); + + @override + _i2.TransportOptions get transportOptions => (super.noSuchMethod( + Invocation.getter(#transportOptions), + returnValue: _FakeTransportOptions_0( + this, + Invocation.getter(#transportOptions), + ), + ) as _i2.TransportOptions); + + @override + _i2.DataConnectOptions get options => (super.noSuchMethod( + Invocation.getter(#options), + returnValue: _FakeDataConnectOptions_1( + this, + Invocation.getter(#options), + ), + ) as _i2.DataConnectOptions); + + @override + String get appId => (super.noSuchMethod( + Invocation.getter(#appId), + returnValue: _i4.dummyValue( + this, + Invocation.getter(#appId), + ), + ) as String); + + @override + set appCheck(_i5.FirebaseAppCheck? value) => super.noSuchMethod( + Invocation.setter( + #appCheck, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set sdkType(_i2.CallerSDKType? value) => super.noSuchMethod( + Invocation.setter( + #sdkType, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set url(String? value) => super.noSuchMethod( + Invocation.setter( + #url, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set transportOptions(_i2.TransportOptions? value) => super.noSuchMethod( + Invocation.setter( + #transportOptions, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set options(_i2.DataConnectOptions? value) => super.noSuchMethod( + Invocation.setter( + #options, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set appId(String? value) => super.noSuchMethod( + Invocation.setter( + #appId, + value, + ), + returnValueForMissingStub: null, + ); + + @override + void setHttp(_i6.Client? client) => super.noSuchMethod( + Invocation.method( + #setHttp, + [client], + ), + returnValueForMissingStub: null, + ); + + @override + _i7.Future<_i2.ServerResponse> invokeOperation( + String? queryName, + String? endpoint, + _i2.Deserializer? deserializer, + _i2.Serializer? serializer, + Variables? vars, + String? authToken, + ) => + (super.noSuchMethod( + Invocation.method( + #invokeOperation, + [ + queryName, + endpoint, + deserializer, + serializer, + vars, + authToken, + ], + ), + returnValue: _i7.Future<_i2.ServerResponse>.value(_FakeServerResponse_2( + this, + Invocation.method( + #invokeOperation, + [ + queryName, + endpoint, + deserializer, + serializer, + vars, + authToken, + ], + ), + )), + ) as _i7.Future<_i2.ServerResponse>); + + @override + _i7.Future<_i2.ServerResponse> invokeQuery( + String? operationId, + String? queryName, + _i2.Deserializer? deserializer, + _i2.Serializer? serializer, + Variables? vars, + String? token, + ) => + (super.noSuchMethod( + Invocation.method( + #invokeQuery, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + token, + ], + ), + returnValue: _i7.Future<_i2.ServerResponse>.value(_FakeServerResponse_2( + this, + Invocation.method( + #invokeQuery, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + token, + ], + ), + )), + ) as _i7.Future<_i2.ServerResponse>); + + @override + _i7.Future<_i2.ServerResponse> invokeMutation( + String? operationId, + String? queryName, + _i2.Deserializer? deserializer, + _i2.Serializer? serializer, + Variables? vars, + String? token, + ) => + (super.noSuchMethod( + Invocation.method( + #invokeMutation, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + token, + ], + ), + returnValue: _i7.Future<_i2.ServerResponse>.value(_FakeServerResponse_2( + this, + Invocation.method( + #invokeMutation, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + token, + ], + ), + )), + ) as _i7.Future<_i2.ServerResponse>); + + @override + _i7.Stream<_i2.ServerResponse> invokeStreamQuery( + String? operationId, + String? queryName, + _i2.Deserializer? deserializer, + _i2.Serializer? serializer, + Variables? vars, + String? token, + ) => + (super.noSuchMethod( + Invocation.method( + #invokeStreamQuery, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + token, + ], + ), + returnValue: _i7.Stream<_i2.ServerResponse>.empty(), + ) as _i7.Stream<_i2.ServerResponse>); +} + +/// A class which mocks [WebSocketTransport]. +/// +/// See the documentation for Mockito's code generation for more information. +class MockWebSocketTransport extends _i1.Mock + implements _i8.WebSocketTransport { + MockWebSocketTransport() { + _i1.throwOnMissingStub(this); + } + + @override + _i2.CallerSDKType get sdkType => (super.noSuchMethod( + Invocation.getter(#sdkType), + returnValue: _i2.CallerSDKType.core, + ) as _i2.CallerSDKType); + + @override + _i2.TransportOptions get transportOptions => (super.noSuchMethod( + Invocation.getter(#transportOptions), + returnValue: _FakeTransportOptions_0( + this, + Invocation.getter(#transportOptions), + ), + ) as _i2.TransportOptions); + + @override + _i2.DataConnectOptions get options => (super.noSuchMethod( + Invocation.getter(#options), + returnValue: _FakeDataConnectOptions_1( + this, + Invocation.getter(#options), + ), + ) as _i2.DataConnectOptions); + + @override + String get appId => (super.noSuchMethod( + Invocation.getter(#appId), + returnValue: _i4.dummyValue( + this, + Invocation.getter(#appId), + ), + ) as String); + + @override + bool get isConnected => (super.noSuchMethod( + Invocation.getter(#isConnected), + returnValue: false, + ) as bool); + + @override + bool get hasActiveSubscriptions => (super.noSuchMethod( + Invocation.getter(#hasActiveSubscriptions), + returnValue: false, + ) as bool); + + @override + set auth(_i9.FirebaseAuth? value) => super.noSuchMethod( + Invocation.setter( + #auth, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set appCheck(_i5.FirebaseAppCheck? value) => super.noSuchMethod( + Invocation.setter( + #appCheck, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set sdkType(_i2.CallerSDKType? value) => super.noSuchMethod( + Invocation.setter( + #sdkType, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set transportOptions(_i2.TransportOptions? value) => super.noSuchMethod( + Invocation.setter( + #transportOptions, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set options(_i2.DataConnectOptions? value) => super.noSuchMethod( + Invocation.setter( + #options, + value, + ), + returnValueForMissingStub: null, + ); + + @override + set appId(String? value) => super.noSuchMethod( + Invocation.setter( + #appId, + value, + ), + returnValueForMissingStub: null, + ); + + @override + Map buildHeaders( + String? authToken, + String? appCheckToken, + ) => + (super.noSuchMethod( + Invocation.method( + #buildHeaders, + [ + authToken, + appCheckToken, + ], + ), + returnValue: {}, + ) as Map); + + @override + void disconnect() => super.noSuchMethod( + Invocation.method( + #disconnect, + [], + ), + returnValueForMissingStub: null, + ); + + @override + _i7.Future<_i2.ServerResponse> invokeQuery( + String? operationId, + String? queryName, + _i2.Deserializer? deserializer, + _i2.Serializer? serializer, + Variables? vars, + String? authToken, + ) => + (super.noSuchMethod( + Invocation.method( + #invokeQuery, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + authToken, + ], + ), + returnValue: _i7.Future<_i2.ServerResponse>.value(_FakeServerResponse_2( + this, + Invocation.method( + #invokeQuery, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + authToken, + ], + ), + )), + ) as _i7.Future<_i2.ServerResponse>); + + @override + _i7.Future<_i2.ServerResponse> invokeMutation( + String? operationId, + String? queryName, + _i2.Deserializer? deserializer, + _i2.Serializer? serializer, + Variables? vars, + String? authToken, + ) => + (super.noSuchMethod( + Invocation.method( + #invokeMutation, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + authToken, + ], + ), + returnValue: _i7.Future<_i2.ServerResponse>.value(_FakeServerResponse_2( + this, + Invocation.method( + #invokeMutation, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + authToken, + ], + ), + )), + ) as _i7.Future<_i2.ServerResponse>); + + @override + _i7.Stream<_i2.ServerResponse> invokeStreamQuery( + String? operationId, + String? queryName, + _i2.Deserializer? deserializer, + _i2.Serializer? serializer, + Variables? vars, + String? authToken, + ) => + (super.noSuchMethod( + Invocation.method( + #invokeStreamQuery, + [ + operationId, + queryName, + deserializer, + serializer, + vars, + authToken, + ], + ), + returnValue: _i7.Stream<_i2.ServerResponse>.empty(), + ) as _i7.Stream<_i2.ServerResponse>); +} diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.dart index afbbff322873..6e331fd21389 100644 --- a/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.dart +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.dart @@ -20,12 +20,14 @@ import 'package:firebase_auth/firebase_auth.dart'; import 'package:firebase_data_connect/src/common/common_library.dart'; import 'package:firebase_data_connect/src/network/transport_library.dart'; import 'package:flutter_test/flutter_test.dart'; +import 'package:fake_async/fake_async.dart'; import 'package:mockito/annotations.dart'; import 'package:mockito/mockito.dart'; +import 'package:web_socket_channel/web_socket_channel.dart'; import 'websocket_transport_test.mocks.dart'; -@GenerateMocks([FirebaseAuth, User, FirebaseAppCheck]) +@GenerateMocks([FirebaseAuth, User, FirebaseAppCheck, WebSocketChannel, WebSocketSink]) void main() { late WebSocketTransport transport; late MockFirebaseAuth mockAuth; @@ -91,6 +93,147 @@ void main() { }); }); + group('WebSocketTransport Connection Grace Period', () { + late MockWebSocketChannel mockChannel; + late MockWebSocketSink mockSink; + late StreamController channelStreamController; + late int connectCount; + + setUp(() { + mockChannel = MockWebSocketChannel(); + mockSink = MockWebSocketSink(); + channelStreamController = StreamController.broadcast(); + connectCount = 0; + + when(mockChannel.sink).thenReturn(mockSink); + when(mockChannel.stream).thenAnswer((_) => channelStreamController.stream); + when(mockChannel.ready).thenAnswer((_) => Future.value()); + when(mockSink.close()).thenAnswer((_) => Future.value()); + }); + + tearDown(() { + channelStreamController.close(); + }); + + WebSocketTransport createTransport() { + return WebSocketTransport( + TransportOptions('localhost', 8080, false), + DataConnectOptions('proj', 'loc', 'conn', 'serv'), + 'appId', + CallerSDKType.core, + mockAppCheck, + mockAuth, + (uri) { + connectCount++; + return mockChannel; + }, + ); + } + + test('should disconnect after 15 seconds of idleness', () { + fakeAsync((async) { + final t = createTransport(); + + // 1. Establish connection by subscribing + final stream = t.invokeStreamQuery('opId', 'query', (json) => json, null, null, 'token'); + final sub = stream.listen((_) {}); + + // Allow connection to establish (microtasks) + async.flushMicrotasks(); + expect(t.isConnected, isTrue); + expect(connectCount, equals(1)); + + // 2. Unsubscribe to become idle + sub.cancel(); + async.flushMicrotasks(); + + // Verify it is NOT disconnected immediately + expect(t.isConnected, isTrue); + verifyNever(mockSink.close()); + + // 3. Wait 14 seconds (less than 15s timeout) + async.elapse(const Duration(seconds: 14)); + expect(t.isConnected, isTrue); + verifyNever(mockSink.close()); + + // 4. Wait 1 more second (total 15s) + async.elapse(const Duration(seconds: 1)); + // It should disconnect + expect(t.isConnected, isFalse); + verify(mockSink.close()).called(1); + }); + }); + + test('should reuse connection if re-subscribed within 15 seconds', () { + fakeAsync((async) { + final t = createTransport(); + + // 1. Subscribe 1 + final stream1 = t.invokeStreamQuery('opId', 'query', (json) => json, null, null, 'token'); + final sub1 = stream1.listen((_) {}); + async.flushMicrotasks(); + expect(t.isConnected, isTrue); + expect(connectCount, equals(1)); + + // 2. Unsubscribe 1 + sub1.cancel(); + async.flushMicrotasks(); + + // 3. Wait 10 seconds (less than 15s) + async.elapse(const Duration(seconds: 10)); + expect(t.isConnected, isTrue); + + // 4. Subscribe 2 + final stream2 = t.invokeStreamQuery('opId', 'query', (json) => json, null, null, 'token'); + final sub2 = stream2.listen((_) {}); + async.flushMicrotasks(); + + // Verify connection was reused (connectCount is still 1) + expect(t.isConnected, isTrue); + expect(connectCount, equals(1)); + + // Cleanup + sub2.cancel(); + async.elapse(const Duration(seconds: 15)); + }); + }); + + test('should establish new connection if re-subscribed after 15 seconds', () { + fakeAsync((async) { + final t = createTransport(); + + // 1. Subscribe 1 + final stream1 = t.invokeStreamQuery('opId', 'query', (json) => json, null, null, 'token'); + final sub1 = stream1.listen((_) {}); + async.flushMicrotasks(); + expect(t.isConnected, isTrue); + expect(connectCount, equals(1)); + + // 2. Unsubscribe 1 + sub1.cancel(); + async.flushMicrotasks(); + + // 3. Wait 15 seconds -> should disconnect + async.elapse(const Duration(seconds: 15)); + expect(t.isConnected, isFalse); + verify(mockSink.close()).called(1); + + // 4. Subscribe 2 + final stream2 = t.invokeStreamQuery('opId', 'query', (json) => json, null, null, 'token'); + final sub2 = stream2.listen((_) {}); + async.flushMicrotasks(); + + // Verify new connection was established (connectCount is 2) + expect(t.isConnected, isTrue); + expect(connectCount, equals(2)); + + // Cleanup + sub2.cancel(); + async.elapse(const Duration(seconds: 15)); + }); + }); + }); + group('WebSocketTransport URL Validation', () { test('should connect with the correct sticky URL path', () async { final pathCompleter = Completer(); diff --git a/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.mocks.dart b/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.mocks.dart index f73d415a9c22..bebc79d56f60 100644 --- a/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.mocks.dart +++ b/packages/firebase_data_connect/firebase_data_connect/test/src/network/websocket_transport_test.mocks.dart @@ -1,33 +1,22 @@ -// Copyright 2026 Google LLC -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. - // Mocks generated by Mockito 5.4.6 from annotations // in firebase_data_connect/test/src/network/websocket_transport_test.dart. // Do not manually edit this file. // ignore_for_file: no_leading_underscores_for_library_prefixes -import 'dart:async' as _i5; +import 'dart:async' as _i7; -import 'package:firebase_app_check/firebase_app_check.dart' as _i7; +import 'package:async/async.dart' as _i11; +import 'package:firebase_app_check/firebase_app_check.dart' as _i9; import 'package:firebase_app_check_platform_interface/firebase_app_check_platform_interface.dart' - as _i8; + as _i10; import 'package:firebase_auth/firebase_auth.dart' as _i4; import 'package:firebase_auth_platform_interface/firebase_auth_platform_interface.dart' as _i3; import 'package:firebase_core/firebase_core.dart' as _i2; import 'package:mockito/mockito.dart' as _i1; -import 'package:mockito/src/dummies.dart' as _i6; +import 'package:mockito/src/dummies.dart' as _i8; +import 'package:stream_channel/stream_channel.dart' as _i6; +import 'package:web_socket_channel/src/channel.dart' as _i5; // ignore_for_file: type=lint // ignore_for_file: avoid_redundant_argument_values @@ -138,6 +127,27 @@ class _FakeUser_8 extends _i1.SmartFake implements _i4.User { ); } +class _FakeWebSocketSink_9 extends _i1.SmartFake implements _i5.WebSocketSink { + _FakeWebSocketSink_9( + Object parent, + Invocation parentInvocation, + ) : super( + parent, + parentInvocation, + ); +} + +class _FakeStreamChannel_10 extends _i1.SmartFake + implements _i6.StreamChannel { + _FakeStreamChannel_10( + Object parent, + Invocation parentInvocation, + ) : super( + parent, + parentInvocation, + ); +} + /// A class which mocks [FirebaseAuth]. /// /// See the documentation for Mockito's code generation for more information. @@ -189,7 +199,7 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { ) as Map); @override - _i5.Future useAuthEmulator( + _i7.Future useAuthEmulator( String? host, int? port, { bool? automaticHostMapping = true, @@ -203,38 +213,38 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { ], {#automaticHostMapping: automaticHostMapping}, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future applyActionCode(String? code) => (super.noSuchMethod( + _i7.Future applyActionCode(String? code) => (super.noSuchMethod( Invocation.method( #applyActionCode, [code], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i3.ActionCodeInfo> checkActionCode(String? code) => + _i7.Future<_i3.ActionCodeInfo> checkActionCode(String? code) => (super.noSuchMethod( Invocation.method( #checkActionCode, [code], ), - returnValue: _i5.Future<_i3.ActionCodeInfo>.value(_FakeActionCodeInfo_1( + returnValue: _i7.Future<_i3.ActionCodeInfo>.value(_FakeActionCodeInfo_1( this, Invocation.method( #checkActionCode, [code], ), )), - ) as _i5.Future<_i3.ActionCodeInfo>); + ) as _i7.Future<_i3.ActionCodeInfo>); @override - _i5.Future confirmPasswordReset({ + _i7.Future confirmPasswordReset({ required String? code, required String? newPassword, }) => @@ -247,12 +257,12 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #newPassword: newPassword, }, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i4.UserCredential> createUserWithEmailAndPassword({ + _i7.Future<_i4.UserCredential> createUserWithEmailAndPassword({ required String? email, required String? password, }) => @@ -265,7 +275,7 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #password: password, }, ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #createUserWithEmailAndPassword, @@ -276,22 +286,22 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { }, ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> getRedirectResult() => (super.noSuchMethod( + _i7.Future<_i4.UserCredential> getRedirectResult() => (super.noSuchMethod( Invocation.method( #getRedirectResult, [], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #getRedirectResult, [], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override bool isSignInWithEmailLink(String? emailLink) => (super.noSuchMethod( @@ -303,34 +313,34 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { ) as bool); @override - _i5.Stream<_i4.User?> authStateChanges() => (super.noSuchMethod( + _i7.Stream<_i4.User?> authStateChanges() => (super.noSuchMethod( Invocation.method( #authStateChanges, [], ), - returnValue: _i5.Stream<_i4.User?>.empty(), - ) as _i5.Stream<_i4.User?>); + returnValue: _i7.Stream<_i4.User?>.empty(), + ) as _i7.Stream<_i4.User?>); @override - _i5.Stream<_i4.User?> idTokenChanges() => (super.noSuchMethod( + _i7.Stream<_i4.User?> idTokenChanges() => (super.noSuchMethod( Invocation.method( #idTokenChanges, [], ), - returnValue: _i5.Stream<_i4.User?>.empty(), - ) as _i5.Stream<_i4.User?>); + returnValue: _i7.Stream<_i4.User?>.empty(), + ) as _i7.Stream<_i4.User?>); @override - _i5.Stream<_i4.User?> userChanges() => (super.noSuchMethod( + _i7.Stream<_i4.User?> userChanges() => (super.noSuchMethod( Invocation.method( #userChanges, [], ), - returnValue: _i5.Stream<_i4.User?>.empty(), - ) as _i5.Stream<_i4.User?>); + returnValue: _i7.Stream<_i4.User?>.empty(), + ) as _i7.Stream<_i4.User?>); @override - _i5.Future sendPasswordResetEmail({ + _i7.Future sendPasswordResetEmail({ required String? email, _i3.ActionCodeSettings? actionCodeSettings, }) => @@ -343,12 +353,12 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #actionCodeSettings: actionCodeSettings, }, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future sendSignInLinkToEmail({ + _i7.Future sendSignInLinkToEmail({ required String? email, required _i3.ActionCodeSettings? actionCodeSettings, }) => @@ -361,22 +371,22 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #actionCodeSettings: actionCodeSettings, }, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future setLanguageCode(String? languageCode) => (super.noSuchMethod( + _i7.Future setLanguageCode(String? languageCode) => (super.noSuchMethod( Invocation.method( #setLanguageCode, [languageCode], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future setSettings({ + _i7.Future setSettings({ bool? appVerificationDisabledForTesting = false, String? userAccessGroup, String? phoneNumber, @@ -396,71 +406,71 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #forceRecaptchaFlow: forceRecaptchaFlow, }, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future setPersistence(_i3.Persistence? persistence) => + _i7.Future setPersistence(_i3.Persistence? persistence) => (super.noSuchMethod( Invocation.method( #setPersistence, [persistence], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i4.UserCredential> signInAnonymously() => (super.noSuchMethod( + _i7.Future<_i4.UserCredential> signInAnonymously() => (super.noSuchMethod( Invocation.method( #signInAnonymously, [], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #signInAnonymously, [], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> signInWithCredential( + _i7.Future<_i4.UserCredential> signInWithCredential( _i3.AuthCredential? credential) => (super.noSuchMethod( Invocation.method( #signInWithCredential, [credential], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #signInWithCredential, [credential], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> signInWithCustomToken(String? token) => + _i7.Future<_i4.UserCredential> signInWithCustomToken(String? token) => (super.noSuchMethod( Invocation.method( #signInWithCustomToken, [token], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #signInWithCustomToken, [token], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> signInWithEmailAndPassword({ + _i7.Future<_i4.UserCredential> signInWithEmailAndPassword({ required String? email, required String? password, }) => @@ -473,7 +483,7 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #password: password, }, ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #signInWithEmailAndPassword, @@ -484,10 +494,10 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { }, ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> signInWithEmailLink({ + _i7.Future<_i4.UserCredential> signInWithEmailLink({ required String? email, required String? emailLink, }) => @@ -500,7 +510,7 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #emailLink: emailLink, }, ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #signInWithEmailLink, @@ -511,27 +521,27 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { }, ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> signInWithProvider( + _i7.Future<_i4.UserCredential> signInWithProvider( _i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #signInWithProvider, [provider], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #signInWithProvider, [provider], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.ConfirmationResult> signInWithPhoneNumber( + _i7.Future<_i4.ConfirmationResult> signInWithPhoneNumber( String? phoneNumber, [ _i4.RecaptchaVerifier? verifier, ]) => @@ -544,7 +554,7 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { ], ), returnValue: - _i5.Future<_i4.ConfirmationResult>.value(_FakeConfirmationResult_3( + _i7.Future<_i4.ConfirmationResult>.value(_FakeConfirmationResult_3( this, Invocation.method( #signInWithPhoneNumber, @@ -554,53 +564,53 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { ], ), )), - ) as _i5.Future<_i4.ConfirmationResult>); + ) as _i7.Future<_i4.ConfirmationResult>); @override - _i5.Future<_i4.UserCredential> signInWithPopup(_i3.AuthProvider? provider) => + _i7.Future<_i4.UserCredential> signInWithPopup(_i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #signInWithPopup, [provider], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #signInWithPopup, [provider], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future signInWithRedirect(_i3.AuthProvider? provider) => + _i7.Future signInWithRedirect(_i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #signInWithRedirect, [provider], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future verifyPasswordResetCode(String? code) => + _i7.Future verifyPasswordResetCode(String? code) => (super.noSuchMethod( Invocation.method( #verifyPasswordResetCode, [code], ), - returnValue: _i5.Future.value(_i6.dummyValue( + returnValue: _i7.Future.value(_i8.dummyValue( this, Invocation.method( #verifyPasswordResetCode, [code], ), )), - ) as _i5.Future); + ) as _i7.Future); @override - _i5.Future verifyPhoneNumber({ + _i7.Future verifyPhoneNumber({ String? phoneNumber, _i3.PhoneMultiFactorInfo? multiFactorInfo, required _i3.PhoneVerificationCompleted? verificationCompleted, @@ -629,55 +639,55 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { #multiFactorSession: multiFactorSession, }, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future revokeTokenWithAuthorizationCode( + _i7.Future revokeTokenWithAuthorizationCode( String? authorizationCode) => (super.noSuchMethod( Invocation.method( #revokeTokenWithAuthorizationCode, [authorizationCode], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future revokeAccessToken(String? accessToken) => + _i7.Future revokeAccessToken(String? accessToken) => (super.noSuchMethod( Invocation.method( #revokeAccessToken, [accessToken], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future signOut() => (super.noSuchMethod( + _i7.Future signOut() => (super.noSuchMethod( Invocation.method( #signOut, [], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future initializeRecaptchaConfig() => (super.noSuchMethod( + _i7.Future initializeRecaptchaConfig() => (super.noSuchMethod( Invocation.method( #initializeRecaptchaConfig, [], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i3.PasswordValidationStatus> validatePassword( + _i7.Future<_i3.PasswordValidationStatus> validatePassword( _i4.FirebaseAuth? auth, String? password, ) => @@ -689,7 +699,7 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { password, ], ), - returnValue: _i5.Future<_i3.PasswordValidationStatus>.value( + returnValue: _i7.Future<_i3.PasswordValidationStatus>.value( _FakePasswordValidationStatus_4( this, Invocation.method( @@ -700,7 +710,7 @@ class MockFirebaseAuth extends _i1.Mock implements _i4.FirebaseAuth { ], ), )), - ) as _i5.Future<_i3.PasswordValidationStatus>); + ) as _i7.Future<_i3.PasswordValidationStatus>); } /// A class which mocks [User]. @@ -741,7 +751,7 @@ class MockUser extends _i1.Mock implements _i4.User { @override String get uid => (super.noSuchMethod( Invocation.getter(#uid), - returnValue: _i6.dummyValue( + returnValue: _i8.dummyValue( this, Invocation.getter(#uid), ), @@ -757,149 +767,149 @@ class MockUser extends _i1.Mock implements _i4.User { ) as _i4.MultiFactor); @override - _i5.Future delete() => (super.noSuchMethod( + _i7.Future delete() => (super.noSuchMethod( Invocation.method( #delete, [], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future getIdToken([bool? forceRefresh = false]) => + _i7.Future getIdToken([bool? forceRefresh = false]) => (super.noSuchMethod( Invocation.method( #getIdToken, [forceRefresh], ), - returnValue: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i3.IdTokenResult> getIdTokenResult( + _i7.Future<_i3.IdTokenResult> getIdTokenResult( [bool? forceRefresh = false]) => (super.noSuchMethod( Invocation.method( #getIdTokenResult, [forceRefresh], ), - returnValue: _i5.Future<_i3.IdTokenResult>.value(_FakeIdTokenResult_7( + returnValue: _i7.Future<_i3.IdTokenResult>.value(_FakeIdTokenResult_7( this, Invocation.method( #getIdTokenResult, [forceRefresh], ), )), - ) as _i5.Future<_i3.IdTokenResult>); + ) as _i7.Future<_i3.IdTokenResult>); @override - _i5.Future<_i4.UserCredential> linkWithCredential( + _i7.Future<_i4.UserCredential> linkWithCredential( _i3.AuthCredential? credential) => (super.noSuchMethod( Invocation.method( #linkWithCredential, [credential], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #linkWithCredential, [credential], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> linkWithProvider(_i3.AuthProvider? provider) => + _i7.Future<_i4.UserCredential> linkWithProvider(_i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #linkWithProvider, [provider], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #linkWithProvider, [provider], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> reauthenticateWithProvider( + _i7.Future<_i4.UserCredential> reauthenticateWithProvider( _i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #reauthenticateWithProvider, [provider], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #reauthenticateWithProvider, [provider], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future<_i4.UserCredential> reauthenticateWithPopup( + _i7.Future<_i4.UserCredential> reauthenticateWithPopup( _i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #reauthenticateWithPopup, [provider], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #reauthenticateWithPopup, [provider], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future reauthenticateWithRedirect(_i3.AuthProvider? provider) => + _i7.Future reauthenticateWithRedirect(_i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #reauthenticateWithRedirect, [provider], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i4.UserCredential> linkWithPopup(_i3.AuthProvider? provider) => + _i7.Future<_i4.UserCredential> linkWithPopup(_i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #linkWithPopup, [provider], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #linkWithPopup, [provider], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future linkWithRedirect(_i3.AuthProvider? provider) => + _i7.Future linkWithRedirect(_i3.AuthProvider? provider) => (super.noSuchMethod( Invocation.method( #linkWithRedirect, [provider], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i4.ConfirmationResult> linkWithPhoneNumber( + _i7.Future<_i4.ConfirmationResult> linkWithPhoneNumber( String? phoneNumber, [ _i4.RecaptchaVerifier? verifier, ]) => @@ -912,7 +922,7 @@ class MockUser extends _i1.Mock implements _i4.User { ], ), returnValue: - _i5.Future<_i4.ConfirmationResult>.value(_FakeConfirmationResult_3( + _i7.Future<_i4.ConfirmationResult>.value(_FakeConfirmationResult_3( this, Invocation.method( #linkWithPhoneNumber, @@ -922,107 +932,107 @@ class MockUser extends _i1.Mock implements _i4.User { ], ), )), - ) as _i5.Future<_i4.ConfirmationResult>); + ) as _i7.Future<_i4.ConfirmationResult>); @override - _i5.Future<_i4.UserCredential> reauthenticateWithCredential( + _i7.Future<_i4.UserCredential> reauthenticateWithCredential( _i3.AuthCredential? credential) => (super.noSuchMethod( Invocation.method( #reauthenticateWithCredential, [credential], ), - returnValue: _i5.Future<_i4.UserCredential>.value(_FakeUserCredential_2( + returnValue: _i7.Future<_i4.UserCredential>.value(_FakeUserCredential_2( this, Invocation.method( #reauthenticateWithCredential, [credential], ), )), - ) as _i5.Future<_i4.UserCredential>); + ) as _i7.Future<_i4.UserCredential>); @override - _i5.Future reload() => (super.noSuchMethod( + _i7.Future reload() => (super.noSuchMethod( Invocation.method( #reload, [], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future sendEmailVerification( + _i7.Future sendEmailVerification( [_i3.ActionCodeSettings? actionCodeSettings]) => (super.noSuchMethod( Invocation.method( #sendEmailVerification, [actionCodeSettings], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future<_i4.User> unlink(String? providerId) => (super.noSuchMethod( + _i7.Future<_i4.User> unlink(String? providerId) => (super.noSuchMethod( Invocation.method( #unlink, [providerId], ), - returnValue: _i5.Future<_i4.User>.value(_FakeUser_8( + returnValue: _i7.Future<_i4.User>.value(_FakeUser_8( this, Invocation.method( #unlink, [providerId], ), )), - ) as _i5.Future<_i4.User>); + ) as _i7.Future<_i4.User>); @override - _i5.Future updatePassword(String? newPassword) => (super.noSuchMethod( + _i7.Future updatePassword(String? newPassword) => (super.noSuchMethod( Invocation.method( #updatePassword, [newPassword], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future updatePhoneNumber( + _i7.Future updatePhoneNumber( _i3.PhoneAuthCredential? phoneCredential) => (super.noSuchMethod( Invocation.method( #updatePhoneNumber, [phoneCredential], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future updateDisplayName(String? displayName) => + _i7.Future updateDisplayName(String? displayName) => (super.noSuchMethod( Invocation.method( #updateDisplayName, [displayName], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future updatePhotoURL(String? photoURL) => (super.noSuchMethod( + _i7.Future updatePhotoURL(String? photoURL) => (super.noSuchMethod( Invocation.method( #updatePhotoURL, [photoURL], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future updateProfile({ + _i7.Future updateProfile({ String? displayName, String? photoURL, }) => @@ -1035,12 +1045,12 @@ class MockUser extends _i1.Mock implements _i4.User { #photoURL: photoURL, }, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future verifyBeforeUpdateEmail( + _i7.Future verifyBeforeUpdateEmail( String? newEmail, [ _i3.ActionCodeSettings? actionCodeSettings, ]) => @@ -1052,15 +1062,15 @@ class MockUser extends _i1.Mock implements _i4.User { actionCodeSettings, ], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); } /// A class which mocks [FirebaseAppCheck]. /// /// See the documentation for Mockito's code generation for more information. -class MockFirebaseAppCheck extends _i1.Mock implements _i7.FirebaseAppCheck { +class MockFirebaseAppCheck extends _i1.Mock implements _i9.FirebaseAppCheck { MockFirebaseAppCheck() { _i1.throwOnMissingStub(this); } @@ -1075,10 +1085,10 @@ class MockFirebaseAppCheck extends _i1.Mock implements _i7.FirebaseAppCheck { ) as _i2.FirebaseApp); @override - _i5.Stream get onTokenChange => (super.noSuchMethod( + _i7.Stream get onTokenChange => (super.noSuchMethod( Invocation.getter(#onTokenChange), - returnValue: _i5.Stream.empty(), - ) as _i5.Stream); + returnValue: _i7.Stream.empty(), + ) as _i7.Stream); @override set app(_i2.FirebaseApp? value) => super.noSuchMethod( @@ -1096,17 +1106,17 @@ class MockFirebaseAppCheck extends _i1.Mock implements _i7.FirebaseAppCheck { ) as Map); @override - _i5.Future activate({ - _i8.WebProvider? webProvider, - _i8.WebProvider? providerWeb, - _i8.AndroidProvider? androidProvider = _i8.AndroidProvider.playIntegrity, - _i8.AppleProvider? appleProvider = _i8.AppleProvider.deviceCheck, - _i8.AndroidAppCheckProvider? providerAndroid = - const _i8.AndroidPlayIntegrityProvider(), - _i8.AppleAppCheckProvider? providerApple = - const _i8.AppleDeviceCheckProvider(), - _i8.WindowsAppCheckProvider? providerWindows = - const _i8.WindowsDebugProvider(), + _i7.Future activate({ + _i10.WebProvider? webProvider, + _i10.WebProvider? providerWeb, + _i10.AndroidProvider? androidProvider = _i10.AndroidProvider.playIntegrity, + _i10.AppleProvider? appleProvider = _i10.AppleProvider.deviceCheck, + _i10.AndroidAppCheckProvider? providerAndroid = + const _i10.AndroidPlayIntegrityProvider(), + _i10.AppleAppCheckProvider? providerApple = + const _i10.AppleDeviceCheckProvider(), + _i10.WindowsAppCheckProvider? providerWindows = + const _i10.WindowsDebugProvider(), }) => (super.noSuchMethod( Invocation.method( @@ -1122,43 +1132,258 @@ class MockFirebaseAppCheck extends _i1.Mock implements _i7.FirebaseAppCheck { #providerWindows: providerWindows, }, ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future getToken([bool? forceRefresh]) => (super.noSuchMethod( + _i7.Future getToken([bool? forceRefresh]) => (super.noSuchMethod( Invocation.method( #getToken, [forceRefresh], ), - returnValue: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future setTokenAutoRefreshEnabled( + _i7.Future<_i10.AppCheckTokenResult?> getTokenResult([bool? forceRefresh]) => + (super.noSuchMethod( + Invocation.method( + #getTokenResult, + [forceRefresh], + ), + returnValue: _i7.Future<_i10.AppCheckTokenResult?>.value(), + ) as _i7.Future<_i10.AppCheckTokenResult?>); + + @override + _i7.Future setTokenAutoRefreshEnabled( bool? isTokenAutoRefreshEnabled) => (super.noSuchMethod( Invocation.method( #setTokenAutoRefreshEnabled, [isTokenAutoRefreshEnabled], ), - returnValue: _i5.Future.value(), - returnValueForMissingStub: _i5.Future.value(), - ) as _i5.Future); + returnValue: _i7.Future.value(), + returnValueForMissingStub: _i7.Future.value(), + ) as _i7.Future); @override - _i5.Future getLimitedUseToken() => (super.noSuchMethod( + _i7.Future getLimitedUseToken() => (super.noSuchMethod( Invocation.method( #getLimitedUseToken, [], ), - returnValue: _i5.Future.value(_i6.dummyValue( + returnValue: _i7.Future.value(_i8.dummyValue( this, Invocation.method( #getLimitedUseToken, [], ), )), - ) as _i5.Future); + ) as _i7.Future); +} + +/// A class which mocks [WebSocketChannel]. +/// +/// See the documentation for Mockito's code generation for more information. +class MockWebSocketChannel extends _i1.Mock implements _i5.WebSocketChannel { + MockWebSocketChannel() { + _i1.throwOnMissingStub(this); + } + + @override + _i7.Future get ready => (super.noSuchMethod( + Invocation.getter(#ready), + returnValue: _i7.Future.value(), + ) as _i7.Future); + + @override + _i5.WebSocketSink get sink => (super.noSuchMethod( + Invocation.getter(#sink), + returnValue: _FakeWebSocketSink_9( + this, + Invocation.getter(#sink), + ), + ) as _i5.WebSocketSink); + + @override + _i7.Stream get stream => (super.noSuchMethod( + Invocation.getter(#stream), + returnValue: _i7.Stream.empty(), + ) as _i7.Stream); + + @override + void pipe(_i6.StreamChannel? other) => super.noSuchMethod( + Invocation.method( + #pipe, + [other], + ), + returnValueForMissingStub: null, + ); + + @override + _i6.StreamChannel transform( + _i6.StreamChannelTransformer? transformer) => + (super.noSuchMethod( + Invocation.method( + #transform, + [transformer], + ), + returnValue: _FakeStreamChannel_10( + this, + Invocation.method( + #transform, + [transformer], + ), + ), + ) as _i6.StreamChannel); + + @override + _i6.StreamChannel transformStream( + _i7.StreamTransformer? transformer) => + (super.noSuchMethod( + Invocation.method( + #transformStream, + [transformer], + ), + returnValue: _FakeStreamChannel_10( + this, + Invocation.method( + #transformStream, + [transformer], + ), + ), + ) as _i6.StreamChannel); + + @override + _i6.StreamChannel transformSink( + _i11.StreamSinkTransformer? transformer) => + (super.noSuchMethod( + Invocation.method( + #transformSink, + [transformer], + ), + returnValue: _FakeStreamChannel_10( + this, + Invocation.method( + #transformSink, + [transformer], + ), + ), + ) as _i6.StreamChannel); + + @override + _i6.StreamChannel changeStream( + _i7.Stream Function(_i7.Stream)? change) => + (super.noSuchMethod( + Invocation.method( + #changeStream, + [change], + ), + returnValue: _FakeStreamChannel_10( + this, + Invocation.method( + #changeStream, + [change], + ), + ), + ) as _i6.StreamChannel); + + @override + _i6.StreamChannel changeSink( + _i7.StreamSink Function(_i7.StreamSink)? change) => + (super.noSuchMethod( + Invocation.method( + #changeSink, + [change], + ), + returnValue: _FakeStreamChannel_10( + this, + Invocation.method( + #changeSink, + [change], + ), + ), + ) as _i6.StreamChannel); + + @override + _i6.StreamChannel cast() => (super.noSuchMethod( + Invocation.method( + #cast, + [], + ), + returnValue: _FakeStreamChannel_10( + this, + Invocation.method( + #cast, + [], + ), + ), + ) as _i6.StreamChannel); +} + +/// A class which mocks [WebSocketSink]. +/// +/// See the documentation for Mockito's code generation for more information. +class MockWebSocketSink extends _i1.Mock implements _i5.WebSocketSink { + MockWebSocketSink() { + _i1.throwOnMissingStub(this); + } + + @override + _i7.Future get done => (super.noSuchMethod( + Invocation.getter(#done), + returnValue: _i7.Future.value(), + ) as _i7.Future); + + @override + _i7.Future close([ + int? closeCode, + String? closeReason, + ]) => + (super.noSuchMethod( + Invocation.method( + #close, + [ + closeCode, + closeReason, + ], + ), + returnValue: _i7.Future.value(), + ) as _i7.Future); + + @override + void add(dynamic data) => super.noSuchMethod( + Invocation.method( + #add, + [data], + ), + returnValueForMissingStub: null, + ); + + @override + void addError( + Object? error, [ + StackTrace? stackTrace, + ]) => + super.noSuchMethod( + Invocation.method( + #addError, + [ + error, + stackTrace, + ], + ), + returnValueForMissingStub: null, + ); + + @override + _i7.Future addStream(_i7.Stream? stream) => + (super.noSuchMethod( + Invocation.method( + #addStream, + [stream], + ), + returnValue: _i7.Future.value(), + ) as _i7.Future); }