Store generated wallet; Access it with PIN validation
This commit is contained in:
parent
b5fc4d1b0b
commit
0a42a17cdd
|
@ -1,4 +1,5 @@
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:qrscan/qrscan.dart' as scanner;
|
import 'package:qrscan/qrscan.dart' as scanner;
|
||||||
import 'package:gecko/ui/generateWallets.dart';
|
import 'package:gecko/ui/generateWallets.dart';
|
||||||
import 'package:gecko/ui/historyWallets.dart';
|
import 'package:gecko/ui/historyWallets.dart';
|
||||||
|
@ -75,7 +76,6 @@ class _HomeScreenState extends State<HomeScreen> {
|
||||||
|
|
||||||
@override
|
@override
|
||||||
void initState() {
|
void initState() {
|
||||||
// TODO: implement initState
|
|
||||||
super.initState();
|
super.initState();
|
||||||
_scrollController = ScrollController();
|
_scrollController = ScrollController();
|
||||||
_scrollController.addListener(_scrollListener);
|
_scrollController.addListener(_scrollListener);
|
||||||
|
@ -274,10 +274,12 @@ class _HomeScreenState extends State<HomeScreen> {
|
||||||
barcode = await scanner.scan();
|
barcode = await scanner.scan();
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
print(e);
|
print(e);
|
||||||
await sentry.Sentry.captureException(
|
if (kReleaseMode) {
|
||||||
e,
|
await sentry.Sentry.captureException(
|
||||||
stackTrace: stack,
|
e,
|
||||||
);
|
stackTrace: stack,
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
// this._outputPubkey.text = "";
|
// this._outputPubkey.text = "";
|
||||||
if (barcode != null) {
|
if (barcode != null) {
|
||||||
|
|
|
@ -3,17 +3,24 @@ import 'package:flutter/material.dart';
|
||||||
import 'home.dart';
|
import 'home.dart';
|
||||||
import 'package:graphql_flutter/graphql_flutter.dart';
|
import 'package:graphql_flutter/graphql_flutter.dart';
|
||||||
import 'package:sentry_flutter/sentry_flutter.dart';
|
import 'package:sentry_flutter/sentry_flutter.dart';
|
||||||
|
import 'package:flutter/foundation.dart';
|
||||||
|
|
||||||
// void main() => runApp(Gecko());
|
// void main() => runApp(Gecko());
|
||||||
|
|
||||||
Future<void> main() async {
|
Future<void> main() async {
|
||||||
await SentryFlutter.init(
|
if (kReleaseMode) {
|
||||||
(options) {
|
print('Release');
|
||||||
options.dsn =
|
await SentryFlutter.init(
|
||||||
'https://c09587b46eaa42e8b9fda28d838ed180@o496840.ingest.sentry.io/5572110';
|
(options) {
|
||||||
},
|
options.dsn =
|
||||||
appRunner: () => runApp(Gecko()),
|
'https://c09587b46eaa42e8b9fda28d838ed180@o496840.ingest.sentry.io/5572110';
|
||||||
);
|
},
|
||||||
|
appRunner: () => runApp(Gecko()),
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
print('Debug');
|
||||||
|
runApp(Gecko());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class Gecko extends StatelessWidget {
|
class Gecko extends StatelessWidget {
|
||||||
|
|
|
@ -1,6 +1,10 @@
|
||||||
|
import 'package:flutter/foundation.dart';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:dubp/dubp.dart';
|
import 'package:dubp/dubp.dart';
|
||||||
import 'package:sentry/sentry.dart' as sentry;
|
import 'package:sentry/sentry.dart' as sentry;
|
||||||
|
import 'dart:io';
|
||||||
|
import 'package:path_provider/path_provider.dart';
|
||||||
|
import 'package:pin_code_fields/pin_code_fields.dart';
|
||||||
|
|
||||||
class GenerateWalletScreen extends StatefulWidget {
|
class GenerateWalletScreen extends StatefulWidget {
|
||||||
@override
|
@override
|
||||||
|
@ -17,6 +21,8 @@ class _GenerateWalletScreen extends State<GenerateWalletScreen> {
|
||||||
TextEditingController _pubkey = new TextEditingController();
|
TextEditingController _pubkey = new TextEditingController();
|
||||||
TextEditingController _dewif = new TextEditingController();
|
TextEditingController _dewif = new TextEditingController();
|
||||||
TextEditingController _pin = new TextEditingController();
|
TextEditingController _pin = new TextEditingController();
|
||||||
|
TextEditingController _enterPin = new TextEditingController();
|
||||||
|
String validPin = 'NO PIN';
|
||||||
|
|
||||||
@override
|
@override
|
||||||
Widget build(BuildContext context) {
|
Widget build(BuildContext context) {
|
||||||
|
@ -59,9 +65,32 @@ class _GenerateWalletScreen extends State<GenerateWalletScreen> {
|
||||||
fontSize: 20.0,
|
fontSize: 20.0,
|
||||||
color: Colors.black,
|
color: Colors.black,
|
||||||
fontWeight: FontWeight.bold)),
|
fontWeight: FontWeight.bold)),
|
||||||
|
SizedBox(height: 12),
|
||||||
new RaisedButton(
|
new RaisedButton(
|
||||||
onPressed: () => generateMnemonic(),
|
onPressed: () => generateMnemonic(),
|
||||||
child: Text('Générer un wallet', style: TextStyle(fontSize: 20))),
|
child: Text('Générer un wallet', style: TextStyle(fontSize: 20))),
|
||||||
|
SizedBox(height: 20),
|
||||||
|
TextField(
|
||||||
|
controller: this._enterPin,
|
||||||
|
onChanged: (validPin) {
|
||||||
|
this.validPin = validPin ?? 'NO PIN';
|
||||||
|
print('PIN: ' + this.validPin);
|
||||||
|
},
|
||||||
|
maxLines: 1,
|
||||||
|
textAlign: TextAlign.center,
|
||||||
|
decoration: InputDecoration(
|
||||||
|
hintText: 'Tappez votre code PIN',
|
||||||
|
hintStyle: TextStyle(fontSize: 15),
|
||||||
|
contentPadding: EdgeInsets.symmetric(horizontal: 7, vertical: 15),
|
||||||
|
),
|
||||||
|
style: TextStyle(
|
||||||
|
fontSize: 20.0,
|
||||||
|
color: Colors.black,
|
||||||
|
fontWeight: FontWeight.bold)),
|
||||||
|
SizedBox(height: 12),
|
||||||
|
new RaisedButton(
|
||||||
|
onPressed: () => readLocalWallet(this.validPin.toUpperCase()),
|
||||||
|
child: Text('Lire le wallet local', style: TextStyle(fontSize: 20))),
|
||||||
]));
|
]));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -71,26 +100,31 @@ class _GenerateWalletScreen extends State<GenerateWalletScreen> {
|
||||||
generatedMnemonic = await DubpRust.genMnemonic(language: Language.french);
|
generatedMnemonic = await DubpRust.genMnemonic(language: Language.french);
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
print(e);
|
print(e);
|
||||||
await sentry.Sentry.captureException(
|
if (kReleaseMode) {
|
||||||
e,
|
await sentry.Sentry.captureException(
|
||||||
stackTrace: stack,
|
e,
|
||||||
);
|
stackTrace: stack,
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
generateWallet(generatedMnemonic);
|
generateWallet(generatedMnemonic);
|
||||||
}
|
}
|
||||||
|
|
||||||
Future generateWallet(generatedMnemonic) async {
|
Future generateWallet(generatedMnemonic) async {
|
||||||
|
final walletFile = await _localWallet;
|
||||||
NewWallet newWallet;
|
NewWallet newWallet;
|
||||||
try {
|
try {
|
||||||
newWallet = await DubpRust.genWalletFromMnemonic(
|
newWallet = await DubpRust.genWalletFromMnemonic(
|
||||||
language: Language.french, mnemonic: generatedMnemonic);
|
language: Language.french, mnemonic: generatedMnemonic);
|
||||||
} catch (e, stack) {
|
} catch (e, stack) {
|
||||||
print(e);
|
print(e);
|
||||||
await sentry.Sentry.captureException(
|
if (kReleaseMode) {
|
||||||
e,
|
await sentry.Sentry.captureException(
|
||||||
stackTrace: stack,
|
e,
|
||||||
);
|
stackTrace: stack,
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
setState(() {
|
setState(() {
|
||||||
|
@ -99,5 +133,80 @@ class _GenerateWalletScreen extends State<GenerateWalletScreen> {
|
||||||
this._dewif.text = newWallet.dewif;
|
this._dewif.text = newWallet.dewif;
|
||||||
this._pin.text = newWallet.pin;
|
this._pin.text = newWallet.pin;
|
||||||
});
|
});
|
||||||
|
|
||||||
|
return walletFile.writeAsString('${newWallet.dewif}');
|
||||||
|
}
|
||||||
|
|
||||||
|
Future getPubkeyFromDewif(_dewif, _pin) async {
|
||||||
|
String _pubkey;
|
||||||
|
RegExp regExp = new RegExp(
|
||||||
|
r'^[A-Z0-9]+$',
|
||||||
|
caseSensitive: false,
|
||||||
|
multiLine: false,
|
||||||
|
);
|
||||||
|
|
||||||
|
if (regExp.hasMatch(_pin) == true && _pin.length == 6) {
|
||||||
|
print("Le format du code PIN est correct.");
|
||||||
|
} else {
|
||||||
|
print('Format de code PIN invalide');
|
||||||
|
return 'false';
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
_pubkey = await DubpRust.getDewifPublicKey(dewif: _dewif, pin: _pin);
|
||||||
|
setState(() {
|
||||||
|
this._pubkey.text = _pubkey;
|
||||||
|
});
|
||||||
|
|
||||||
|
return _pubkey;
|
||||||
|
} catch (e, stack) {
|
||||||
|
print('Bad PIN code !');
|
||||||
|
print(e);
|
||||||
|
if (kReleaseMode) {
|
||||||
|
await sentry.Sentry.captureException(
|
||||||
|
e,
|
||||||
|
stackTrace: stack,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
return 'false';
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Future readLocalWallet(String _pin) async {
|
||||||
|
// print(pin);
|
||||||
|
try {
|
||||||
|
final file = await _localWallet;
|
||||||
|
String _localDewif = await file.readAsString();
|
||||||
|
String _localPubkey;
|
||||||
|
|
||||||
|
// _localPubkey = await getPubkeyFromDewif(_localDewif, _pin)?
|
||||||
|
|
||||||
|
if ((_localPubkey = await getPubkeyFromDewif(_localDewif, _pin)) !=
|
||||||
|
'false') {
|
||||||
|
setState(() {
|
||||||
|
this._mnemonic.text = '';
|
||||||
|
this._pubkey.text = _localPubkey;
|
||||||
|
this._dewif.text = _localDewif;
|
||||||
|
this._pin.text = _pin;
|
||||||
|
});
|
||||||
|
|
||||||
|
return _localDewif;
|
||||||
|
} else {
|
||||||
|
throw 'Bad pubkey';
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
print('ERROR READING FILE: $e');
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
Future<String> get _localPath async {
|
||||||
|
final directory = await getApplicationDocumentsDirectory();
|
||||||
|
|
||||||
|
return directory.path;
|
||||||
|
}
|
||||||
|
|
||||||
|
Future<File> get _localWallet async {
|
||||||
|
final path = await _localPath;
|
||||||
|
return File('$path/wallet.dewif');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,6 +19,10 @@ import 'package:truncate/truncate.dart';
|
||||||
// }
|
// }
|
||||||
|
|
||||||
class HistoryListView extends StatelessWidget {
|
class HistoryListView extends StatelessWidget {
|
||||||
|
// const String({this.isPubkey});
|
||||||
|
// final PubkeyCallBack isPubkey;
|
||||||
|
// GlobalKey<MyState> _myKey = GlobalKey();
|
||||||
|
|
||||||
const HistoryListView(
|
const HistoryListView(
|
||||||
{Key key,
|
{Key key,
|
||||||
@required ScrollController scrollController,
|
@required ScrollController scrollController,
|
||||||
|
@ -55,12 +59,12 @@ class HistoryListView extends StatelessWidget {
|
||||||
leading: Text(repository[3].toString()),
|
leading: Text(repository[3].toString()),
|
||||||
title: Text(repository[1].toString() +
|
title: Text(repository[1].toString() +
|
||||||
'\n' +
|
'\n' +
|
||||||
truncate(repository[2].toString(), 17,
|
truncate(repository[2], 17,
|
||||||
omission: "...", position: TruncatePosition.end)),
|
omission: "...", position: TruncatePosition.end)),
|
||||||
subtitle: Text(repository[5].toString()),
|
subtitle: Text(repository[5]),
|
||||||
dense: true,
|
dense: true,
|
||||||
// enabled: _act == 2,
|
// enabled: _act == 2,
|
||||||
onTap: () {/* TODO: Load this history */}),
|
onTap: () {/* TODO: Load this history: repository[2] */}),
|
||||||
if (historyData.isLoading)
|
if (historyData.isLoading)
|
||||||
Row(
|
Row(
|
||||||
mainAxisAlignment: MainAxisAlignment.center,
|
mainAxisAlignment: MainAxisAlignment.center,
|
||||||
|
@ -80,3 +84,5 @@ class HistoryListView extends StatelessWidget {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// typedef PubkeyCallBack = void Function(String pubkey);
|
56
pubspec.lock
56
pubspec.lock
|
@ -21,42 +21,42 @@ packages:
|
||||||
name: async
|
name: async
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.5.0-nullsafety.1"
|
version: "2.5.0-nullsafety.3"
|
||||||
boolean_selector:
|
boolean_selector:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: boolean_selector
|
name: boolean_selector
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.0-nullsafety.1"
|
version: "2.1.0-nullsafety.3"
|
||||||
characters:
|
characters:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: characters
|
name: characters
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.1.0-nullsafety.3"
|
version: "1.1.0-nullsafety.5"
|
||||||
charcode:
|
charcode:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: charcode
|
name: charcode
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.2.0-nullsafety.1"
|
version: "1.2.0-nullsafety.3"
|
||||||
clock:
|
clock:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: clock
|
name: clock
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.1.0-nullsafety.1"
|
version: "1.1.0-nullsafety.3"
|
||||||
collection:
|
collection:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: collection
|
name: collection
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.15.0-nullsafety.3"
|
version: "1.15.0-nullsafety.5"
|
||||||
connectivity:
|
connectivity:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -112,7 +112,7 @@ packages:
|
||||||
name: fake_async
|
name: fake_async
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.2.0-nullsafety.1"
|
version: "1.2.0-nullsafety.3"
|
||||||
ffi:
|
ffi:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -282,20 +282,27 @@ packages:
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.0.3"
|
version: "2.0.3"
|
||||||
|
js:
|
||||||
|
dependency: transitive
|
||||||
|
description:
|
||||||
|
name: js
|
||||||
|
url: "https://pub.dartlang.org"
|
||||||
|
source: hosted
|
||||||
|
version: "0.6.3-nullsafety.3"
|
||||||
matcher:
|
matcher:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: matcher
|
name: matcher
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.12.10-nullsafety.1"
|
version: "0.12.10-nullsafety.3"
|
||||||
meta:
|
meta:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: meta
|
name: meta
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.3.0-nullsafety.3"
|
version: "1.3.0-nullsafety.6"
|
||||||
nested:
|
nested:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -323,9 +330,9 @@ packages:
|
||||||
name: path
|
name: path
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.8.0-nullsafety.1"
|
version: "1.8.0-nullsafety.3"
|
||||||
path_provider:
|
path_provider:
|
||||||
dependency: transitive
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
name: path_provider
|
name: path_provider
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
|
@ -387,6 +394,13 @@ packages:
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "3.1.0"
|
version: "3.1.0"
|
||||||
|
pin_code_fields:
|
||||||
|
dependency: "direct main"
|
||||||
|
description:
|
||||||
|
name: pin_code_fields
|
||||||
|
url: "https://pub.dartlang.org"
|
||||||
|
source: hosted
|
||||||
|
version: "6.0.2"
|
||||||
platform:
|
platform:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -454,42 +468,42 @@ packages:
|
||||||
name: source_span
|
name: source_span
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.8.0-nullsafety.2"
|
version: "1.8.0-nullsafety.4"
|
||||||
stack_trace:
|
stack_trace:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: stack_trace
|
name: stack_trace
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.10.0-nullsafety.1"
|
version: "1.10.0-nullsafety.6"
|
||||||
stream_channel:
|
stream_channel:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: stream_channel
|
name: stream_channel
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.0-nullsafety.1"
|
version: "2.1.0-nullsafety.3"
|
||||||
string_scanner:
|
string_scanner:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: string_scanner
|
name: string_scanner
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.1.0-nullsafety.1"
|
version: "1.1.0-nullsafety.3"
|
||||||
term_glyph:
|
term_glyph:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: term_glyph
|
name: term_glyph
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.2.0-nullsafety.1"
|
version: "1.2.0-nullsafety.3"
|
||||||
test_api:
|
test_api:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
name: test_api
|
name: test_api
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "0.2.19-nullsafety.2"
|
version: "0.2.19-nullsafety.6"
|
||||||
truncate:
|
truncate:
|
||||||
dependency: "direct main"
|
dependency: "direct main"
|
||||||
description:
|
description:
|
||||||
|
@ -503,7 +517,7 @@ packages:
|
||||||
name: typed_data
|
name: typed_data
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "1.3.0-nullsafety.3"
|
version: "1.3.0-nullsafety.5"
|
||||||
uuid:
|
uuid:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -524,7 +538,7 @@ packages:
|
||||||
name: vector_math
|
name: vector_math
|
||||||
url: "https://pub.dartlang.org"
|
url: "https://pub.dartlang.org"
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.1.0-nullsafety.3"
|
version: "2.1.0-nullsafety.5"
|
||||||
websocket:
|
websocket:
|
||||||
dependency: transitive
|
dependency: transitive
|
||||||
description:
|
description:
|
||||||
|
@ -561,5 +575,5 @@ packages:
|
||||||
source: hosted
|
source: hosted
|
||||||
version: "2.2.1"
|
version: "2.2.1"
|
||||||
sdks:
|
sdks:
|
||||||
dart: ">=2.10.0-110 <2.11.0"
|
dart: ">=2.12.0-0.0 <3.0.0"
|
||||||
flutter: ">=1.17.0 <2.0.0"
|
flutter: ">=1.22.0 <2.0.0"
|
||||||
|
|
|
@ -34,6 +34,8 @@ dependencies:
|
||||||
provider: ^4.3.2+3
|
provider: ^4.3.2+3
|
||||||
truncate: ^2.1.2
|
truncate: ^2.1.2
|
||||||
sentry_flutter: ^4.0.1
|
sentry_flutter: ^4.0.1
|
||||||
|
path_provider: ^1.6.24
|
||||||
|
pin_code_fields: ^6.0.2
|
||||||
|
|
||||||
|
|
||||||
flutter_icons:
|
flutter_icons:
|
||||||
|
|
Loading…
Reference in New Issue