From d0014e5cc9f73998e5a0d801bf17f08980442beb Mon Sep 17 00:00:00 2001 From: KoiFresh Date: Wed, 23 Aug 2023 00:27:56 +0200 Subject: [PATCH 1/5] feat: add passcode to home --- lib/blocs/home_add_view_bloc.dart | 10 +--------- lib/blocs/home_view_bloc.dart | 31 +++++++++++++++++++++++++++++++ lib/models/home.dart | 13 ++++++++++--- lib/states/home_add_state.dart | 11 +++++------ lib/states/home_state.dart | 2 ++ lib/views/call_view.dart | 25 +++++++++++++++++++++++-- lib/views/home_add_view.dart | 15 +++++++++++---- 7 files changed, 83 insertions(+), 24 deletions(-) diff --git a/lib/blocs/home_add_view_bloc.dart b/lib/blocs/home_add_view_bloc.dart index f44a731..bae2bde 100644 --- a/lib/blocs/home_add_view_bloc.dart +++ b/lib/blocs/home_add_view_bloc.dart @@ -42,19 +42,10 @@ class HomeAddViewBloc extends Bloc { "Please enter a channel prefix within format 'com.dieklingel/main/prefix/'"; } - String? signError; - RegExp signRegex = RegExp( - r'^[A-Za-z]+$', - ); - if (!signRegex.hasMatch(event.sign)) { - signError = "Please enter a sign within the format 'mysign'"; - } - HomeAddFormErrorState errorState = HomeAddFormErrorState( nameError: nameError, serverError: serverError, channelError: channelError, - signError: signError, ); if (errorState.hasError) { emit(errorState); @@ -71,6 +62,7 @@ class HomeAddViewBloc extends Bloc { home.uri = uri; home.username = event.username; home.password = event.password; + home.passcode = event.passcode; emit(HomeAddLoadingState()); final client = MqttClient(home.uri); diff --git a/lib/blocs/home_view_bloc.dart b/lib/blocs/home_view_bloc.dart index e2ffe06..ae08ef3 100644 --- a/lib/blocs/home_view_bloc.dart +++ b/lib/blocs/home_view_bloc.dart @@ -1,9 +1,12 @@ import 'dart:async'; import 'package:dieklingel_app/models/hive_home.dart'; +import 'package:dieklingel_app/models/request.dart'; import 'package:dieklingel_app/repositories/home_repository.dart'; import 'package:dieklingel_app/states/home_state.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; +import 'package:mqtt/mqtt.dart'; +import 'package:path/path.dart' as path; class HomeViewBloc extends Bloc { final HomeRepository homeRepository; @@ -11,6 +14,7 @@ class HomeViewBloc extends Bloc { HomeViewBloc(this.homeRepository) : super(HomeState()) { on(_onSelected); on(_onRefresh); + on(_onUnlock); add(HomeRefresh()); } @@ -39,4 +43,31 @@ class HomeViewBloc extends Bloc { ); } } + + Future _onUnlock(HomeUnlock event, Emitter emit) async { + HiveHome? home = homeRepository.selected; + if (home == null) { + return; + } + + MqttClient client = MqttClient(home.uri); + try { + await client.connect( + username: home.username ?? "", + password: home.password ?? "", + ); + } catch (e) { + print("error ${e.toString()}"); + return; + } + + await client.publish( + path.normalize("./${home.uri.path}/actions/execute"), + Request.withJsonBody("GET", { + "pattern": "unlock", + "environment": { + "PASSCODE": home.passcode, + } + }).toJsonString()); + } } diff --git a/lib/models/home.dart b/lib/models/home.dart index 89a0738..2f82fcc 100644 --- a/lib/models/home.dart +++ b/lib/models/home.dart @@ -3,12 +3,14 @@ class Home { Uri uri; String? username; String? password; + String? passcode; Home({ required this.name, required this.uri, this.username, this.password, + this.passcode, }); factory Home.fromMap(Map map) { @@ -24,6 +26,7 @@ class Home { uri: Uri.parse(map["uri"]), username: map["username"], password: map["password"], + passcode: map["passcode"], ); } @@ -33,6 +36,7 @@ class Home { "uri": uri.toString(), "username": username, "password": password, + "passcode": passcode, }; } @@ -45,12 +49,14 @@ class Home { Uri? uri, String? username, String? password, + String? passcode, }) => Home( name: name ?? this.name, uri: uri ?? this.uri, username: username ?? this.username, - password: this.password, + password: password ?? this.password, + passcode: passcode ?? this.passcode, ); @override @@ -61,11 +67,12 @@ class Home { return name == other.name && uri == other.uri && username == other.username && - password == other.password; + password == other.password && + passcode == other.passcode; } @override - int get hashCode => Object.hash(name, uri, username, password); + int get hashCode => Object.hash(name, uri, username, password, passcode); @override String toString() { diff --git a/lib/states/home_add_state.dart b/lib/states/home_add_state.dart index 3d28aaa..6809664 100644 --- a/lib/states/home_add_state.dart +++ b/lib/states/home_add_state.dart @@ -9,6 +9,7 @@ class HomeAddInitialState extends HomeAddState { final String password; final String channel; final String sign; + final String passcode; HomeAddInitialState({ required this.name, @@ -17,6 +18,7 @@ class HomeAddInitialState extends HomeAddState { required this.password, required this.channel, required this.sign, + required this.passcode, }); } @@ -32,20 +34,15 @@ class HomeAddFormErrorState extends HomeAddState { final String? nameError; final String? serverError; final String? channelError; - final String? signError; bool get hasError { - return nameError != null || - serverError != null || - channelError != null || - signError != null; + return nameError != null || serverError != null || channelError != null; } HomeAddFormErrorState({ this.nameError, this.serverError, this.channelError, - this.signError, }); } @@ -109,6 +106,7 @@ class HomeAddSubmit extends HomeAddEvent { final String password; final String channel; final String sign; + final String passcode; HomeAddSubmit({ required this.name, @@ -117,6 +115,7 @@ class HomeAddSubmit extends HomeAddEvent { required this.password, required this.channel, required this.sign, + required this.passcode, this.home, }); } diff --git a/lib/states/home_state.dart b/lib/states/home_state.dart index 44047fb..bcdc499 100644 --- a/lib/states/home_state.dart +++ b/lib/states/home_state.dart @@ -21,3 +21,5 @@ class HomeSelected extends HomeEvent { } class HomeRefresh extends HomeEvent {} + +class HomeUnlock extends HomeEvent {} diff --git a/lib/views/call_view.dart b/lib/views/call_view.dart index fc99cf9..cf79520 100644 --- a/lib/views/call_view.dart +++ b/lib/views/call_view.dart @@ -1,7 +1,9 @@ import 'package:dieklingel_app/blocs/call_view_bloc.dart'; +import 'package:dieklingel_app/blocs/home_view_bloc.dart'; import 'package:dieklingel_app/components/icon_builder.dart'; import 'package:dieklingel_app/components/map_builder.dart'; import 'package:dieklingel_app/states/call_state.dart'; +import 'package:dieklingel_app/states/home_state.dart'; import 'package:dieklingel_app/utils/microphone_state.dart'; import 'package:dieklingel_app/utils/speaker_state.dart'; import 'package:flutter/cupertino.dart'; @@ -127,13 +129,32 @@ class _Toolbar extends StatelessWidget { } : null, ), - const _ToolbarButton( - icon: Icon( + _ToolbarButton( + icon: const Icon( CupertinoIcons.lock_fill, color: Colors.white, size: 30, ), color: Colors.amber, + onPressed: () { + context.read().add(HomeUnlock()); + showCupertinoDialog( + context: context, + builder: (BuildContext context) { + Future.delayed(const Duration(milliseconds: 600), () { + Navigator.of(context).pop(); + }); + + return Center( + child: Icon( + CupertinoIcons.lock_open_fill, + size: 150, + color: Colors.green.shade400, + ), + ); + }, + ); + }, ), ]; } diff --git a/lib/views/home_add_view.dart b/lib/views/home_add_view.dart index 3a75a26..04cea56 100644 --- a/lib/views/home_add_view.dart +++ b/lib/views/home_add_view.dart @@ -29,6 +29,7 @@ class _HomeAddView extends State { : path.normalize("./${widget.home!.uri.path}"), ); late final _sign = TextEditingController(text: widget.home?.uri.fragment); + late final _passcode = TextEditingController(text: widget.home?.passcode); @override Widget build(BuildContext context) { @@ -81,6 +82,7 @@ class _HomeAddView extends State { password: _password.text, channel: _channel.text, sign: _sign.text, + passcode: _passcode.text, ), ); }, @@ -140,13 +142,18 @@ class _HomeAddView extends State { ), CupertinoTextFormFieldRow( prefix: const Text("Sign"), - validator: (value) => state is HomeAddFormErrorState - ? state.signError - : null, - autovalidateMode: AutovalidateMode.always, controller: _sign, ) ], + ), + CupertinoFormSection.insetGrouped( + header: const Text("Doorunit"), + children: [ + CupertinoTextFormFieldRow( + prefix: const Text("Passcode"), + controller: _passcode, + ), + ], ) ], ), From 2db62a3712621e60a2e7eea3858b6c17d52a2f03 Mon Sep 17 00:00:00 2001 From: KoiFresh Date: Thu, 24 Aug 2023 20:32:51 +0200 Subject: [PATCH 2/5] fix: hangup connection --- lib/blocs/call_view_bloc.dart | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/lib/blocs/call_view_bloc.dart b/lib/blocs/call_view_bloc.dart index fcc37d9..f837911 100644 --- a/lib/blocs/call_view_bloc.dart +++ b/lib/blocs/call_view_bloc.dart @@ -57,6 +57,7 @@ class CallViewBloc extends Bloc { username: home.username ?? "", password: home.password ?? "", ); + this.client = client; } on mqtt.NoConnectionException catch (exception) { emit(CallCancelState(exception.toString())); return; @@ -197,11 +198,9 @@ class CallViewBloc extends Bloc { await rtcclient?.dispose(); rtcclient = null; - client?.publish( + await client?.publish( path.normalize("./${home.uri.path}/rtc/connections/close/$uuid"), - jsonEncode( - Request("GET", ""), - ), + Request("GET", "").toJsonString(), ); candidateSub?.cancel(); candidateSub = null; From 687740bac0b9c65c423c113f190d53e0142e1895 Mon Sep 17 00:00:00 2001 From: KoiFresh Date: Thu, 24 Aug 2023 20:35:19 +0200 Subject: [PATCH 3/5] release v.1.2.3+1 --- pubspec.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pubspec.yaml b/pubspec.yaml index c2cf443..817f0ba 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -15,7 +15,7 @@ publish_to: "none" # Remove this line if you wish to publish to pub.dev # In iOS, build-name is used as CFBundleShortVersionString while build-number used as CFBundleVersion. # Read more about iOS versioning at # https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html -version: 1.2.2+1 +version: 1.2.3+1 environment: sdk: ">=2.18.6 <3.7.11" From d6afe53d193626b9bece9c6c3cfd4324b324d363 Mon Sep 17 00:00:00 2001 From: KoiFresh Date: Fri, 25 Aug 2023 10:47:05 +0200 Subject: [PATCH 4/5] fix: catch MediaStream open exception --- lib/utils/media_ressource.dart | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/lib/utils/media_ressource.dart b/lib/utils/media_ressource.dart index 19b4fd0..8b3ccfd 100644 --- a/lib/utils/media_ressource.dart +++ b/lib/utils/media_ressource.dart @@ -13,7 +13,11 @@ class MediaRessource { 'audio': audio, 'video': video, }; - _stream = await navigator.mediaDevices.getUserMedia(constraints); + try { + _stream = await navigator.mediaDevices.getUserMedia(constraints); + } catch (e) { + // TODO: noting stream is empty + } return _stream; } From 82e14b0ed0ea5cc7d43577615b90e816e8cbc973 Mon Sep 17 00:00:00 2001 From: KoiFresh Date: Fri, 25 Aug 2023 12:06:26 +0200 Subject: [PATCH 5/5] feat: obscure unlock text --- lib/views/home_add_view.dart | 1 + 1 file changed, 1 insertion(+) diff --git a/lib/views/home_add_view.dart b/lib/views/home_add_view.dart index 04cea56..f0c59c4 100644 --- a/lib/views/home_add_view.dart +++ b/lib/views/home_add_view.dart @@ -151,6 +151,7 @@ class _HomeAddView extends State { children: [ CupertinoTextFormFieldRow( prefix: const Text("Passcode"), + obscureText: true, controller: _passcode, ), ],