payin fixes , allowance setup device step modified , sca pin 2fa added, provisioning changes

This commit is contained in:
2026-02-19 14:56:05 +01:00
parent 2ba83a22ac
commit 722c978674
46 changed files with 593 additions and 232 deletions

View File

@@ -0,0 +1,31 @@
Extension Discovery Cache
=========================
This folder is used by `package:extension_discovery` to cache lists of
packages that contains extensions for other packages.
DO NOT USE THIS FOLDER
----------------------
* Do not read (or rely) the contents of this folder.
* Do write to this folder.
If you're interested in the lists of extensions stored in this folder use the
API offered by package `extension_discovery` to get this information.
If this package doesn't work for your use-case, then don't try to read the
contents of this folder. It may change, and will not remain stable.
Use package `extension_discovery`
---------------------------------
If you want to access information from this folder.
Feel free to delete this folder
-------------------------------
Files in this folder act as a cache, and the cache is discarded if the files
are older than the modification time of `.dart_tool/package_config.json`.
Hence, it should never be necessary to clear this cache manually, if you find a
need to do please file a bug.

View File

@@ -0,0 +1 @@
{"version":2,"entries":[{"package":"design_system","rootUri":"../../../packages/design_system/","packageUri":"lib/"},{"package":"flutter_treezor_entrust_sdk_bridge","rootUri":"../../../packages/flutter_treezor_entrust_sdk_bridge/","packageUri":"lib/"},{"package":"fonts","rootUri":"../../../packages/fonts/","packageUri":"lib/"},{"package":"sca_treezor","rootUri":"../../../packages/sca_treezor/","packageUri":"lib/"},{"package":"sf_infrastructure","rootUri":"../../../packages/sf_infrastructure/","packageUri":"lib/"},{"package":"sf_localizations","rootUri":"../../../packages/sf_localizations/","packageUri":"lib/"},{"package":"sf_shared","rootUri":"../../../packages/sf_shared/","packageUri":"lib/"},{"package":"utils","rootUri":"../../../packages/utils/","packageUri":"lib/"},{"package":"activity","rootUri":"../","packageUri":"lib/"}]}

View File

@@ -206,7 +206,6 @@ class ActivityScreen extends ConsumerWidget {
const Center(child: CircularProgressIndicator()),
error: (_, __) => const SizedBox.shrink(),
data: (balance) => WalletBalanceBlock(
max: balance.totalBalance,
value: balance.availableBalance,
savings: balance.allocatedBalance,
),

View File

@@ -121,9 +121,10 @@ class DeviceSetupScreen extends ConsumerWidget {
vm.setError('');
showTopSnackbar(
context,
message: context.translate(I18n.deviceSetup_paymentSuccess),
message: context.translate(I18n.deviceSetup_cardRegistered),
type: MessageType.success,
);
navigationContract.pushTo(AppRoutes.dashboardHome);
} else {
showTopSnackbar(
context,
@@ -146,7 +147,7 @@ class DeviceSetupScreen extends ConsumerWidget {
case AddKidStep.intro:
return I18n.deviceSetup_start;
case AddKidStep.allowance:
return I18n.deviceSetup_giveFirstAllowance;
return I18n.deviceSetup_addCreditCard;
default:
return I18n.continueKey;
}

View File

@@ -33,7 +33,7 @@ class DeviceSetupViewModel extends Notifier<DeviceSetupViewState> {
@override
DeviceSetupViewState build() {
final initial = DeviceSetupViewState(id: const Uuid().v4(), step: AddKidStep.allowance); // TODO: revert to default (intro)
final initial = DeviceSetupViewState(id: const Uuid().v4());
_initControllers(initial);
_addListeners();

View File

@@ -1,15 +1,13 @@
import 'package:auth/src/features/device_setup/presentation/state/device_setup_view_model.dart';
import 'package:design_system/design_system.dart';
import 'package:flutter/material.dart';
import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:sf_localizations/sf_localizations.dart';
class AllowanceStepScreen extends ConsumerWidget {
const AllowanceStepScreen({super.key});
@override
Widget build(BuildContext context, WidgetRef ref) {
final vm = ref.read(deviceSetupViewModelProvider.notifier);
return SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.symmetric(horizontal: 24),
@@ -19,31 +17,19 @@ class AllowanceStepScreen extends ConsumerWidget {
children: [
const SizedBox(height: 30),
Text(
'¡Dale su primera paga!',
context.translate(I18n.deviceSetup_addCreditCard_title),
style: const TextStyle(fontSize: 30, fontWeight: FontWeight.bold),
textAlign: TextAlign.center,
),
const SizedBox(height: 20),
Text(
'Enséñales a gestionar su dinero recargando su reloj',
context.translate(I18n.deviceSetup_addCreditCard_subtitle),
style: const TextStyle(fontSize: 18),
textAlign: TextAlign.center,
),
const SizedBox(height: 30),
CustomTextField(
label: 'Cantidad de dinero de la paga',
hint: '0',
controller: vm.allowanceAmountController,
keyboardType: TextInputType.number,
),
const SizedBox(height: 12),
Text(
'Cantidad mínima: 10 euros',
style: const TextStyle(fontSize: 14, fontWeight: FontWeight.w500),
),
const SizedBox(height: 24),
Text(
'Por seguridad sólo se puede disponer de un máximo de 150€ por wallet',
context.translate(I18n.deviceSetup_addCreditCard_info),
style: const TextStyle(fontSize: 14),
textAlign: TextAlign.center,
),

View File

@@ -42,8 +42,10 @@ class SCATreezorScreen extends ConsumerWidget {
: state.isProvisioned
? ScaPinView(
title: state.isFirstConnectionDone
? 'Introduce tu PIN para conectar'
: 'Crea tu PIN para conectar tu wallet',
? context.translate(I18n.scaPinEnter)
: state.isConfirmingPin
? context.translate(I18n.scaPinConfirm)
: context.translate(I18n.scaPinCreate),
pin: state.pin,
isProcessing: state.isConnecting || state.isSigning,
processingText: state.isConnecting
@@ -58,7 +60,13 @@ class SCATreezorScreen extends ConsumerWidget {
final success = await vm.connectAndSignJwtSca();
if (!context.mounted) return;
if (success) {
navigationContract.goTo(AppRoutes.deviceSetup);
final hasChildren = await vm.hasChildren();
if (!context.mounted) return;
if (hasChildren) {
navigationContract.goTo(AppRoutes.dashboardHome);
} else {
navigationContract.goTo(AppRoutes.deviceSetup);
}
}
},
)
@@ -69,29 +77,75 @@ class SCATreezorScreen extends ConsumerWidget {
}
}
class _ProvisioningBody extends StatelessWidget {
class _ProvisioningBody extends ConsumerWidget {
final SCATreezorViewState state;
final SCATreezorViewModel vm;
const _ProvisioningBody({required this.state, required this.vm});
@override
Widget build(BuildContext context) {
return Column(
mainAxisSize: MainAxisSize.min,
children: [
const SizedBox(height: 16),
if (state.isProvisioning) ...[
const CircularProgressIndicator(),
const SizedBox(height: 8),
const Text('Provisionando...'),
] else ...[
ElevatedButton(
onPressed: vm.provisionWallet,
child: const Text('Provisionar (manual)'),
Widget build(BuildContext context, WidgetRef ref) {
final theme = ref.watch(themePortProvider);
if (state.isProvisioning) {
return const Column(
mainAxisSize: MainAxisSize.min,
children: [
SizedBox(height: 16),
CircularProgressIndicator(),
SizedBox(height: 8),
Text('Provisionando...'),
],
);
}
return Padding(
padding: const EdgeInsets.symmetric(horizontal: 24),
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
Icon(
Icons.warning_amber_rounded,
size: 48,
color: Colors.orange,
),
const SizedBox(height: 16),
Text(
context.translate(I18n.scaProvisioningFailed),
textAlign: TextAlign.center,
style: const TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold,
),
),
const SizedBox(height: 16),
Container(
padding: const EdgeInsets.all(16),
decoration: BoxDecoration(
color: Colors.orange.withValues(alpha: 0.1),
borderRadius: BorderRadius.circular(12),
),
child: Row(
children: [
const Icon(Icons.info_outline, color: Colors.orange),
const SizedBox(width: 12),
Expanded(
child: Text(
context.translate(I18n.scaProvisioningWarning),
style: const TextStyle(fontSize: 14),
),
),
],
),
),
const SizedBox(height: 24),
PrimaryButton(
onPressed: vm.retryProvisioning,
text: context.translate(I18n.scaProvisioningRetry),
color: theme.getColorFor(ThemeCode.buttonPrimary),
),
],
],
),
);
}
}

View File

@@ -104,7 +104,7 @@ class SCATreezorViewModel extends Notifier<SCATreezorViewState> {
final code = state.activationCode.trim();
if (code.isEmpty) {
state = state.copyWith(isLoading: false);
state = state.copyWith(isLoading: false, provisioningFailed: true);
return;
}
@@ -177,8 +177,45 @@ class SCATreezorViewModel extends Notifier<SCATreezorViewState> {
} catch (e) {
state = state.copyWith(
isProvisioning: false,
provisioningFailed: true,
success: false,
errorMessage: '❌ Error en provisioning: $e',
errorMessage: e.toString(),
);
}
}
Future<void> retryProvisioning() async {
state = state.copyWith(
isLoading: true,
provisioningFailed: false,
errorMessage: '',
);
try {
final treezorRepo = ref.read(treezorRepositoryProvider);
final wallets = await treezorRepo.getScaWallets();
if (!ref.mounted) return;
for (final wallet in wallets) {
if (wallet.status == 'DELETED') continue;
try {
await treezorRepo.deleteScaWallet(scaWalletId: wallet.id);
} catch (_) {}
}
if (!ref.mounted) return;
await clearLocalFlags();
await treezorRepo.resetScaWallets();
if (!ref.mounted) return;
await _bootstrap();
} catch (e) {
if (!ref.mounted) return;
state = state.copyWith(
isLoading: false,
provisioningFailed: true,
errorMessage: e.toString(),
);
}
}
@@ -317,6 +354,28 @@ class SCATreezorViewModel extends Notifier<SCATreezorViewState> {
Future<bool> connectAndSignJwtSca() async {
if (state.isConnecting || state.isSigning) return false;
if (!state.isFirstConnectionDone && !state.isConfirmingPin) {
state = state.copyWith(
firstPin: state.pin,
pin: '',
isConfirmingPin: true,
errorMessage: '',
);
return false;
}
if (!state.isFirstConnectionDone && state.isConfirmingPin) {
if (state.pin != state.firstPin) {
state = state.copyWith(
pin: '',
firstPin: '',
isConfirmingPin: false,
errorMessage: I18n.errorPinMismatch,
);
return false;
}
}
final connected = await connectWithPin();
if (!connected) return false;
@@ -332,15 +391,23 @@ class SCATreezorViewModel extends Notifier<SCATreezorViewState> {
if (paymentProfile.paymentWalletId == null ||
paymentProfile.paymentWalletId!.isEmpty) {
await _authRepository.createWallet();
// tengo que coger la walletId de createWallet y pasarlo savePaymentProfileId
await _sessionLocal.savePaymentProfileId(paymentProfile.paymentWalletId!);
}
// remove this when the backend starts returning the walletId on getUserInfo or getPaymentProfile
await _sessionLocal.savePaymentProfileId(paymentProfile.paymentWalletId!);
return state.lastSignature.isNotEmpty;
}
Future<bool> hasChildren() async {
try {
final userRepository = ref.read(userRepositoryProvider);
final children = await userRepository.getChildProfiles();
return children.isNotEmpty;
} catch (_) {
return false;
}
}
String _sanitizeActivationCode(String code) {
if (code.startsWith('0x')) return code.substring(2);
return code;

View File

@@ -14,8 +14,11 @@ abstract class SCATreezorViewState with _$SCATreezorViewState {
@Default(false) bool isProvisioning,
@Default(false) bool isProvisioned,
@Default(false) bool provisioningFailed,
@Default(false) bool isFirstConnectionDone,
@Default(false) bool isConfirmingPin,
@Default('') String firstPin,
@Default(false) bool isConnecting,
@Default(false) bool isConnected,
@Default('') String pin,

View File

@@ -14,7 +14,7 @@ T _$identity<T>(T value) => value;
/// @nodoc
mixin _$SCATreezorViewState {
String get activationCode; String get errorMessage; bool get isCreated; bool get isLoading; bool get isProvisioning; bool get isProvisioned; bool get isFirstConnectionDone; bool get isConnecting; bool get isConnected; String get pin; bool get isSigning; String get lastSignature; bool get success; String get walletId; String get walletStatus;
String get activationCode; String get errorMessage; bool get isCreated; bool get isLoading; bool get isProvisioning; bool get isProvisioned; bool get provisioningFailed; bool get isFirstConnectionDone; bool get isConfirmingPin; String get firstPin; bool get isConnecting; bool get isConnected; String get pin; bool get isSigning; String get lastSignature; bool get success; String get walletId; String get walletStatus;
/// Create a copy of SCATreezorViewState
/// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false)
@@ -25,16 +25,16 @@ $SCATreezorViewStateCopyWith<SCATreezorViewState> get copyWith => _$SCATreezorVi
@override
bool operator ==(Object other) {
return identical(this, other) || (other.runtimeType == runtimeType&&other is SCATreezorViewState&&(identical(other.activationCode, activationCode) || other.activationCode == activationCode)&&(identical(other.errorMessage, errorMessage) || other.errorMessage == errorMessage)&&(identical(other.isCreated, isCreated) || other.isCreated == isCreated)&&(identical(other.isLoading, isLoading) || other.isLoading == isLoading)&&(identical(other.isProvisioning, isProvisioning) || other.isProvisioning == isProvisioning)&&(identical(other.isProvisioned, isProvisioned) || other.isProvisioned == isProvisioned)&&(identical(other.isFirstConnectionDone, isFirstConnectionDone) || other.isFirstConnectionDone == isFirstConnectionDone)&&(identical(other.isConnecting, isConnecting) || other.isConnecting == isConnecting)&&(identical(other.isConnected, isConnected) || other.isConnected == isConnected)&&(identical(other.pin, pin) || other.pin == pin)&&(identical(other.isSigning, isSigning) || other.isSigning == isSigning)&&(identical(other.lastSignature, lastSignature) || other.lastSignature == lastSignature)&&(identical(other.success, success) || other.success == success)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.walletStatus, walletStatus) || other.walletStatus == walletStatus));
return identical(this, other) || (other.runtimeType == runtimeType&&other is SCATreezorViewState&&(identical(other.activationCode, activationCode) || other.activationCode == activationCode)&&(identical(other.errorMessage, errorMessage) || other.errorMessage == errorMessage)&&(identical(other.isCreated, isCreated) || other.isCreated == isCreated)&&(identical(other.isLoading, isLoading) || other.isLoading == isLoading)&&(identical(other.isProvisioning, isProvisioning) || other.isProvisioning == isProvisioning)&&(identical(other.isProvisioned, isProvisioned) || other.isProvisioned == isProvisioned)&&(identical(other.provisioningFailed, provisioningFailed) || other.provisioningFailed == provisioningFailed)&&(identical(other.isFirstConnectionDone, isFirstConnectionDone) || other.isFirstConnectionDone == isFirstConnectionDone)&&(identical(other.isConfirmingPin, isConfirmingPin) || other.isConfirmingPin == isConfirmingPin)&&(identical(other.firstPin, firstPin) || other.firstPin == firstPin)&&(identical(other.isConnecting, isConnecting) || other.isConnecting == isConnecting)&&(identical(other.isConnected, isConnected) || other.isConnected == isConnected)&&(identical(other.pin, pin) || other.pin == pin)&&(identical(other.isSigning, isSigning) || other.isSigning == isSigning)&&(identical(other.lastSignature, lastSignature) || other.lastSignature == lastSignature)&&(identical(other.success, success) || other.success == success)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.walletStatus, walletStatus) || other.walletStatus == walletStatus));
}
@override
int get hashCode => Object.hash(runtimeType,activationCode,errorMessage,isCreated,isLoading,isProvisioning,isProvisioned,isFirstConnectionDone,isConnecting,isConnected,pin,isSigning,lastSignature,success,walletId,walletStatus);
int get hashCode => Object.hash(runtimeType,activationCode,errorMessage,isCreated,isLoading,isProvisioning,isProvisioned,provisioningFailed,isFirstConnectionDone,isConfirmingPin,firstPin,isConnecting,isConnected,pin,isSigning,lastSignature,success,walletId,walletStatus);
@override
String toString() {
return 'SCATreezorViewState(activationCode: $activationCode, errorMessage: $errorMessage, isCreated: $isCreated, isLoading: $isLoading, isProvisioning: $isProvisioning, isProvisioned: $isProvisioned, isFirstConnectionDone: $isFirstConnectionDone, isConnecting: $isConnecting, isConnected: $isConnected, pin: $pin, isSigning: $isSigning, lastSignature: $lastSignature, success: $success, walletId: $walletId, walletStatus: $walletStatus)';
return 'SCATreezorViewState(activationCode: $activationCode, errorMessage: $errorMessage, isCreated: $isCreated, isLoading: $isLoading, isProvisioning: $isProvisioning, isProvisioned: $isProvisioned, provisioningFailed: $provisioningFailed, isFirstConnectionDone: $isFirstConnectionDone, isConfirmingPin: $isConfirmingPin, firstPin: $firstPin, isConnecting: $isConnecting, isConnected: $isConnected, pin: $pin, isSigning: $isSigning, lastSignature: $lastSignature, success: $success, walletId: $walletId, walletStatus: $walletStatus)';
}
@@ -45,7 +45,7 @@ abstract mixin class $SCATreezorViewStateCopyWith<$Res> {
factory $SCATreezorViewStateCopyWith(SCATreezorViewState value, $Res Function(SCATreezorViewState) _then) = _$SCATreezorViewStateCopyWithImpl;
@useResult
$Res call({
String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool isFirstConnectionDone, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus
String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool provisioningFailed, bool isFirstConnectionDone, bool isConfirmingPin, String firstPin, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus
});
@@ -62,7 +62,7 @@ class _$SCATreezorViewStateCopyWithImpl<$Res>
/// Create a copy of SCATreezorViewState
/// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @override $Res call({Object? activationCode = null,Object? errorMessage = null,Object? isCreated = null,Object? isLoading = null,Object? isProvisioning = null,Object? isProvisioned = null,Object? isFirstConnectionDone = null,Object? isConnecting = null,Object? isConnected = null,Object? pin = null,Object? isSigning = null,Object? lastSignature = null,Object? success = null,Object? walletId = null,Object? walletStatus = null,}) {
@pragma('vm:prefer-inline') @override $Res call({Object? activationCode = null,Object? errorMessage = null,Object? isCreated = null,Object? isLoading = null,Object? isProvisioning = null,Object? isProvisioned = null,Object? provisioningFailed = null,Object? isFirstConnectionDone = null,Object? isConfirmingPin = null,Object? firstPin = null,Object? isConnecting = null,Object? isConnected = null,Object? pin = null,Object? isSigning = null,Object? lastSignature = null,Object? success = null,Object? walletId = null,Object? walletStatus = null,}) {
return _then(_self.copyWith(
activationCode: null == activationCode ? _self.activationCode : activationCode // ignore: cast_nullable_to_non_nullable
as String,errorMessage: null == errorMessage ? _self.errorMessage : errorMessage // ignore: cast_nullable_to_non_nullable
@@ -70,8 +70,11 @@ as String,isCreated: null == isCreated ? _self.isCreated : isCreated // ignore:
as bool,isLoading: null == isLoading ? _self.isLoading : isLoading // ignore: cast_nullable_to_non_nullable
as bool,isProvisioning: null == isProvisioning ? _self.isProvisioning : isProvisioning // ignore: cast_nullable_to_non_nullable
as bool,isProvisioned: null == isProvisioned ? _self.isProvisioned : isProvisioned // ignore: cast_nullable_to_non_nullable
as bool,provisioningFailed: null == provisioningFailed ? _self.provisioningFailed : provisioningFailed // ignore: cast_nullable_to_non_nullable
as bool,isFirstConnectionDone: null == isFirstConnectionDone ? _self.isFirstConnectionDone : isFirstConnectionDone // ignore: cast_nullable_to_non_nullable
as bool,isConnecting: null == isConnecting ? _self.isConnecting : isConnecting // ignore: cast_nullable_to_non_nullable
as bool,isConfirmingPin: null == isConfirmingPin ? _self.isConfirmingPin : isConfirmingPin // ignore: cast_nullable_to_non_nullable
as bool,firstPin: null == firstPin ? _self.firstPin : firstPin // ignore: cast_nullable_to_non_nullable
as String,isConnecting: null == isConnecting ? _self.isConnecting : isConnecting // ignore: cast_nullable_to_non_nullable
as bool,isConnected: null == isConnected ? _self.isConnected : isConnected // ignore: cast_nullable_to_non_nullable
as bool,pin: null == pin ? _self.pin : pin // ignore: cast_nullable_to_non_nullable
as String,isSigning: null == isSigning ? _self.isSigning : isSigning // ignore: cast_nullable_to_non_nullable
@@ -164,10 +167,10 @@ return $default(_that);case _:
/// }
/// ```
@optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool isFirstConnectionDone, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus)? $default,{required TResult orElse(),}) {final _that = this;
@optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool provisioningFailed, bool isFirstConnectionDone, bool isConfirmingPin, String firstPin, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus)? $default,{required TResult orElse(),}) {final _that = this;
switch (_that) {
case _SCATreezorViewState() when $default != null:
return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.isLoading,_that.isProvisioning,_that.isProvisioned,_that.isFirstConnectionDone,_that.isConnecting,_that.isConnected,_that.pin,_that.isSigning,_that.lastSignature,_that.success,_that.walletId,_that.walletStatus);case _:
return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.isLoading,_that.isProvisioning,_that.isProvisioned,_that.provisioningFailed,_that.isFirstConnectionDone,_that.isConfirmingPin,_that.firstPin,_that.isConnecting,_that.isConnected,_that.pin,_that.isSigning,_that.lastSignature,_that.success,_that.walletId,_that.walletStatus);case _:
return orElse();
}
@@ -185,10 +188,10 @@ return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.is
/// }
/// ```
@optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool isFirstConnectionDone, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus) $default,) {final _that = this;
@optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool provisioningFailed, bool isFirstConnectionDone, bool isConfirmingPin, String firstPin, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus) $default,) {final _that = this;
switch (_that) {
case _SCATreezorViewState():
return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.isLoading,_that.isProvisioning,_that.isProvisioned,_that.isFirstConnectionDone,_that.isConnecting,_that.isConnected,_that.pin,_that.isSigning,_that.lastSignature,_that.success,_that.walletId,_that.walletStatus);case _:
return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.isLoading,_that.isProvisioning,_that.isProvisioned,_that.provisioningFailed,_that.isFirstConnectionDone,_that.isConfirmingPin,_that.firstPin,_that.isConnecting,_that.isConnected,_that.pin,_that.isSigning,_that.lastSignature,_that.success,_that.walletId,_that.walletStatus);case _:
throw StateError('Unexpected subclass');
}
@@ -205,10 +208,10 @@ return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.is
/// }
/// ```
@optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool isFirstConnectionDone, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus)? $default,) {final _that = this;
@optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool provisioningFailed, bool isFirstConnectionDone, bool isConfirmingPin, String firstPin, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus)? $default,) {final _that = this;
switch (_that) {
case _SCATreezorViewState() when $default != null:
return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.isLoading,_that.isProvisioning,_that.isProvisioned,_that.isFirstConnectionDone,_that.isConnecting,_that.isConnected,_that.pin,_that.isSigning,_that.lastSignature,_that.success,_that.walletId,_that.walletStatus);case _:
return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.isLoading,_that.isProvisioning,_that.isProvisioned,_that.provisioningFailed,_that.isFirstConnectionDone,_that.isConfirmingPin,_that.firstPin,_that.isConnecting,_that.isConnected,_that.pin,_that.isSigning,_that.lastSignature,_that.success,_that.walletId,_that.walletStatus);case _:
return null;
}
@@ -220,7 +223,7 @@ return $default(_that.activationCode,_that.errorMessage,_that.isCreated,_that.is
class _SCATreezorViewState extends SCATreezorViewState {
const _SCATreezorViewState({this.activationCode = '', this.errorMessage = '', this.isCreated = false, this.isLoading = false, this.isProvisioning = false, this.isProvisioned = false, this.isFirstConnectionDone = false, this.isConnecting = false, this.isConnected = false, this.pin = '', this.isSigning = false, this.lastSignature = '', this.success = false, this.walletId = '', this.walletStatus = ''}): super._();
const _SCATreezorViewState({this.activationCode = '', this.errorMessage = '', this.isCreated = false, this.isLoading = false, this.isProvisioning = false, this.isProvisioned = false, this.provisioningFailed = false, this.isFirstConnectionDone = false, this.isConfirmingPin = false, this.firstPin = '', this.isConnecting = false, this.isConnected = false, this.pin = '', this.isSigning = false, this.lastSignature = '', this.success = false, this.walletId = '', this.walletStatus = ''}): super._();
@override@JsonKey() final String activationCode;
@@ -229,7 +232,10 @@ class _SCATreezorViewState extends SCATreezorViewState {
@override@JsonKey() final bool isLoading;
@override@JsonKey() final bool isProvisioning;
@override@JsonKey() final bool isProvisioned;
@override@JsonKey() final bool provisioningFailed;
@override@JsonKey() final bool isFirstConnectionDone;
@override@JsonKey() final bool isConfirmingPin;
@override@JsonKey() final String firstPin;
@override@JsonKey() final bool isConnecting;
@override@JsonKey() final bool isConnected;
@override@JsonKey() final String pin;
@@ -249,16 +255,16 @@ _$SCATreezorViewStateCopyWith<_SCATreezorViewState> get copyWith => __$SCATreezo
@override
bool operator ==(Object other) {
return identical(this, other) || (other.runtimeType == runtimeType&&other is _SCATreezorViewState&&(identical(other.activationCode, activationCode) || other.activationCode == activationCode)&&(identical(other.errorMessage, errorMessage) || other.errorMessage == errorMessage)&&(identical(other.isCreated, isCreated) || other.isCreated == isCreated)&&(identical(other.isLoading, isLoading) || other.isLoading == isLoading)&&(identical(other.isProvisioning, isProvisioning) || other.isProvisioning == isProvisioning)&&(identical(other.isProvisioned, isProvisioned) || other.isProvisioned == isProvisioned)&&(identical(other.isFirstConnectionDone, isFirstConnectionDone) || other.isFirstConnectionDone == isFirstConnectionDone)&&(identical(other.isConnecting, isConnecting) || other.isConnecting == isConnecting)&&(identical(other.isConnected, isConnected) || other.isConnected == isConnected)&&(identical(other.pin, pin) || other.pin == pin)&&(identical(other.isSigning, isSigning) || other.isSigning == isSigning)&&(identical(other.lastSignature, lastSignature) || other.lastSignature == lastSignature)&&(identical(other.success, success) || other.success == success)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.walletStatus, walletStatus) || other.walletStatus == walletStatus));
return identical(this, other) || (other.runtimeType == runtimeType&&other is _SCATreezorViewState&&(identical(other.activationCode, activationCode) || other.activationCode == activationCode)&&(identical(other.errorMessage, errorMessage) || other.errorMessage == errorMessage)&&(identical(other.isCreated, isCreated) || other.isCreated == isCreated)&&(identical(other.isLoading, isLoading) || other.isLoading == isLoading)&&(identical(other.isProvisioning, isProvisioning) || other.isProvisioning == isProvisioning)&&(identical(other.isProvisioned, isProvisioned) || other.isProvisioned == isProvisioned)&&(identical(other.provisioningFailed, provisioningFailed) || other.provisioningFailed == provisioningFailed)&&(identical(other.isFirstConnectionDone, isFirstConnectionDone) || other.isFirstConnectionDone == isFirstConnectionDone)&&(identical(other.isConfirmingPin, isConfirmingPin) || other.isConfirmingPin == isConfirmingPin)&&(identical(other.firstPin, firstPin) || other.firstPin == firstPin)&&(identical(other.isConnecting, isConnecting) || other.isConnecting == isConnecting)&&(identical(other.isConnected, isConnected) || other.isConnected == isConnected)&&(identical(other.pin, pin) || other.pin == pin)&&(identical(other.isSigning, isSigning) || other.isSigning == isSigning)&&(identical(other.lastSignature, lastSignature) || other.lastSignature == lastSignature)&&(identical(other.success, success) || other.success == success)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.walletStatus, walletStatus) || other.walletStatus == walletStatus));
}
@override
int get hashCode => Object.hash(runtimeType,activationCode,errorMessage,isCreated,isLoading,isProvisioning,isProvisioned,isFirstConnectionDone,isConnecting,isConnected,pin,isSigning,lastSignature,success,walletId,walletStatus);
int get hashCode => Object.hash(runtimeType,activationCode,errorMessage,isCreated,isLoading,isProvisioning,isProvisioned,provisioningFailed,isFirstConnectionDone,isConfirmingPin,firstPin,isConnecting,isConnected,pin,isSigning,lastSignature,success,walletId,walletStatus);
@override
String toString() {
return 'SCATreezorViewState(activationCode: $activationCode, errorMessage: $errorMessage, isCreated: $isCreated, isLoading: $isLoading, isProvisioning: $isProvisioning, isProvisioned: $isProvisioned, isFirstConnectionDone: $isFirstConnectionDone, isConnecting: $isConnecting, isConnected: $isConnected, pin: $pin, isSigning: $isSigning, lastSignature: $lastSignature, success: $success, walletId: $walletId, walletStatus: $walletStatus)';
return 'SCATreezorViewState(activationCode: $activationCode, errorMessage: $errorMessage, isCreated: $isCreated, isLoading: $isLoading, isProvisioning: $isProvisioning, isProvisioned: $isProvisioned, provisioningFailed: $provisioningFailed, isFirstConnectionDone: $isFirstConnectionDone, isConfirmingPin: $isConfirmingPin, firstPin: $firstPin, isConnecting: $isConnecting, isConnected: $isConnected, pin: $pin, isSigning: $isSigning, lastSignature: $lastSignature, success: $success, walletId: $walletId, walletStatus: $walletStatus)';
}
@@ -269,7 +275,7 @@ abstract mixin class _$SCATreezorViewStateCopyWith<$Res> implements $SCATreezorV
factory _$SCATreezorViewStateCopyWith(_SCATreezorViewState value, $Res Function(_SCATreezorViewState) _then) = __$SCATreezorViewStateCopyWithImpl;
@override @useResult
$Res call({
String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool isFirstConnectionDone, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus
String activationCode, String errorMessage, bool isCreated, bool isLoading, bool isProvisioning, bool isProvisioned, bool provisioningFailed, bool isFirstConnectionDone, bool isConfirmingPin, String firstPin, bool isConnecting, bool isConnected, String pin, bool isSigning, String lastSignature, bool success, String walletId, String walletStatus
});
@@ -286,7 +292,7 @@ class __$SCATreezorViewStateCopyWithImpl<$Res>
/// Create a copy of SCATreezorViewState
/// with the given fields replaced by the non-null parameter values.
@override @pragma('vm:prefer-inline') $Res call({Object? activationCode = null,Object? errorMessage = null,Object? isCreated = null,Object? isLoading = null,Object? isProvisioning = null,Object? isProvisioned = null,Object? isFirstConnectionDone = null,Object? isConnecting = null,Object? isConnected = null,Object? pin = null,Object? isSigning = null,Object? lastSignature = null,Object? success = null,Object? walletId = null,Object? walletStatus = null,}) {
@override @pragma('vm:prefer-inline') $Res call({Object? activationCode = null,Object? errorMessage = null,Object? isCreated = null,Object? isLoading = null,Object? isProvisioning = null,Object? isProvisioned = null,Object? provisioningFailed = null,Object? isFirstConnectionDone = null,Object? isConfirmingPin = null,Object? firstPin = null,Object? isConnecting = null,Object? isConnected = null,Object? pin = null,Object? isSigning = null,Object? lastSignature = null,Object? success = null,Object? walletId = null,Object? walletStatus = null,}) {
return _then(_SCATreezorViewState(
activationCode: null == activationCode ? _self.activationCode : activationCode // ignore: cast_nullable_to_non_nullable
as String,errorMessage: null == errorMessage ? _self.errorMessage : errorMessage // ignore: cast_nullable_to_non_nullable
@@ -294,8 +300,11 @@ as String,isCreated: null == isCreated ? _self.isCreated : isCreated // ignore:
as bool,isLoading: null == isLoading ? _self.isLoading : isLoading // ignore: cast_nullable_to_non_nullable
as bool,isProvisioning: null == isProvisioning ? _self.isProvisioning : isProvisioning // ignore: cast_nullable_to_non_nullable
as bool,isProvisioned: null == isProvisioned ? _self.isProvisioned : isProvisioned // ignore: cast_nullable_to_non_nullable
as bool,provisioningFailed: null == provisioningFailed ? _self.provisioningFailed : provisioningFailed // ignore: cast_nullable_to_non_nullable
as bool,isFirstConnectionDone: null == isFirstConnectionDone ? _self.isFirstConnectionDone : isFirstConnectionDone // ignore: cast_nullable_to_non_nullable
as bool,isConnecting: null == isConnecting ? _self.isConnecting : isConnecting // ignore: cast_nullable_to_non_nullable
as bool,isConfirmingPin: null == isConfirmingPin ? _self.isConfirmingPin : isConfirmingPin // ignore: cast_nullable_to_non_nullable
as bool,firstPin: null == firstPin ? _self.firstPin : firstPin // ignore: cast_nullable_to_non_nullable
as String,isConnecting: null == isConnecting ? _self.isConnecting : isConnecting // ignore: cast_nullable_to_non_nullable
as bool,isConnected: null == isConnected ? _self.isConnected : isConnected // ignore: cast_nullable_to_non_nullable
as bool,pin: null == pin ? _self.pin : pin // ignore: cast_nullable_to_non_nullable
as String,isSigning: null == isSigning ? _self.isSigning : isSigning // ignore: cast_nullable_to_non_nullable

View File

@@ -99,6 +99,7 @@ class DepositViewModel extends Notifier<DepositViewState> {
);
if (!ref.mounted) return;
ref.read(childDataProvider(childId).notifier).load();
state = state.copyWith(isSubmitting: false, success: true);
} catch (e) {
if (!ref.mounted) return;

View File

@@ -91,6 +91,7 @@ class ExtractViewModel extends Notifier<ExtractViewState> {
);
if (!ref.mounted) return;
ref.read(childDataProvider(childId).notifier).load();
state = state.copyWith(isSubmitting: false, success: true);
} catch (e) {
if (!ref.mounted) return;

View File

@@ -35,20 +35,32 @@ class HomeScreen extends ConsumerWidget {
margin: EdgeInsets.all(30),
child: Column(
children: [
Align(
alignment: Alignment.topLeft,
child: Text.rich(
TextSpan(
text: context.translate(I18n.homeGreeting),
style: TextStyle(fontSize: 25),
children: <TextSpan>[
Row(
children: [
Expanded(
child: Text.rich(
TextSpan(
text: viewState.userName,
style: TextStyle(fontWeight: FontWeight.w500),
text: context.translate(I18n.homeGreeting),
style: TextStyle(fontSize: 25),
children: <TextSpan>[
TextSpan(
text: viewState.userName,
style: TextStyle(fontWeight: FontWeight.w500),
),
],
),
],
),
),
),
IconButton(
onPressed: () =>
navigationContract.pushTo(AppRoutes.deviceSetup),
icon: Icon(
Icons.person_add_outlined,
color: theme.getColorFor(ThemeCode.textPrimary),
),
tooltip: context.translate(I18n.homeAddAnotherKid),
),
],
),
_buildWalletsList(context, viewState.children, viewState.childWallets, viewState.childDevices, ref),
Align(
@@ -67,7 +79,6 @@ class HomeScreen extends ConsumerWidget {
),
if (balance != null)
WalletBalanceBlock(
max: balance.totalBalance,
value: balance.availableBalance,
savings: balance.allocatedBalance,
),

View File

@@ -411,15 +411,17 @@ class PayoutScreen extends ConsumerWidget {
return Column(
children: [
Expanded(
child: ScaPinView(
title: context.translate(I18n.payoutPinTitle),
pin: viewState.pin,
isProcessing: viewState.isSigning,
canSubmit: viewModel.canSubmitPin,
onDigitPressed: viewModel.onDigitPressed,
onBackspacePressed: viewModel.onBackspacePressed,
onClearPin: viewModel.onClearPin,
onSubmit: () => viewModel.onPinSubmit(),
child: SingleChildScrollView(
child: ScaPinView(
title: context.translate(I18n.payoutPinTitle),
pin: viewState.pin,
isProcessing: viewState.isSigning,
canSubmit: viewModel.canSubmitPin,
onDigitPressed: viewModel.onDigitPressed,
onBackspacePressed: viewModel.onBackspacePressed,
onClearPin: viewModel.onClearPin,
onSubmit: () => viewModel.onPinSubmit(),
),
),
),
SafeArea(

View File

@@ -274,7 +274,8 @@ class PayoutViewModel extends Notifier<PayoutViewState> {
final beneficiary = state.selectedBeneficiary;
if (beneficiary == null) return;
state = state.copyWith(isSubmitting: true, errorMessage: '', pin: '');
final pin = state.pin;
state = state.copyWith(isSigning: true, errorMessage: '', pin: '');
try {
final treezorRepo = ref.read(treezorRepositoryProvider);
@@ -284,11 +285,31 @@ class PayoutViewModel extends Notifier<PayoutViewState> {
if (!ref.mounted) return;
final url = 'https://savefamily.sandbox.treezor.co/v1/payouts';
final scaProof = await _signatureService.generateJwsWithPin(
message: '',
input: jsonEncode({
'url': url,
'body': {
'walletId': state.walletId,
'amount': amount,
'currency': 'EUR',
'beneficiaryId': beneficiary.id,
'beneficiaryValidationId': beneficiaryValidationId,
},
}),
pin: pin,
);
if (!ref.mounted) return;
state = state.copyWith(isSigning: false, isSubmitting: true);
await treezorRepo.walletTransfer(
walletId: state.walletId,
beneficiaryId: beneficiary.id,
beneficiaryValidationId: beneficiaryValidationId,
amount: amount,
scaProof: scaProof,
);
if (!ref.mounted) return;
@@ -296,6 +317,7 @@ class PayoutViewModel extends Notifier<PayoutViewState> {
} catch (e) {
if (!ref.mounted) return;
state = state.copyWith(
isSigning: false,
isSubmitting: false,
pin: '',
errorMessage: e.toString(),

View File

@@ -78,7 +78,6 @@ class ProfileScreen extends ConsumerWidget {
),
if (balance != null)
WalletBalanceBlock(
max: balance.totalBalance,
value: balance.availableBalance,
savings: balance.allocatedBalance,
),

View File

@@ -7,6 +7,6 @@
<versions>
<version>2.6.4</version>
</versions>
<lastUpdated>20260217000000</lastUpdated>
<lastUpdated>20260219000000</lastUpdated>
</versioning>
</metadata>

View File

@@ -1 +1 @@
087d0596a6fa922f247041831d62884c
d23803d2649c8b4a6df651aa4cfb8ffb

View File

@@ -1 +1 @@
a0dfee636080915f528e7f6c5d22c87e3e4a1154
b31ec93b3eddc91940c6dd58979739a17238a442

File diff suppressed because one or more lines are too long

View File

@@ -4,20 +4,20 @@
_PayinResponseModel _$PayinResponseModelFromJson(Map<String, dynamic> json) =>
_PayinResponseModel(
state: json['state'] as String,
status: json['status'] as String,
forwardUrl: json['forwardUrl'] as String?,
transactionReference: json['transactionReference'] as String,
capturedAmount: (json['capturedAmount'] as num).toDouble(),
orderId: json['orderId'] as String,
payinId: json['payinId'] as String,
payinStatus: json['payinStatus'] as String,
informationStatus: json['informationStatus'] as String? ?? '',
walletId: json['walletId'] as String? ?? '',
amount: json['amount'] as String? ?? '',
currency: json['currency'] as String? ?? '',
);
Map<String, dynamic> _$PayinResponseModelToJson(_PayinResponseModel instance) =>
<String, dynamic>{
'state': instance.state,
'status': instance.status,
'forwardUrl': instance.forwardUrl,
'transactionReference': instance.transactionReference,
'capturedAmount': instance.capturedAmount,
'orderId': instance.orderId,
'payinId': instance.payinId,
'payinStatus': instance.payinStatus,
'informationStatus': instance.informationStatus,
'walletId': instance.walletId,
'amount': instance.amount,
'currency': instance.currency,
};

View File

@@ -0,0 +1,31 @@
Extension Discovery Cache
=========================
This folder is used by `package:extension_discovery` to cache lists of
packages that contains extensions for other packages.
DO NOT USE THIS FOLDER
----------------------
* Do not read (or rely) the contents of this folder.
* Do write to this folder.
If you're interested in the lists of extensions stored in this folder use the
API offered by package `extension_discovery` to get this information.
If this package doesn't work for your use-case, then don't try to read the
contents of this folder. It may change, and will not remain stable.
Use package `extension_discovery`
---------------------------------
If you want to access information from this folder.
Feel free to delete this folder
-------------------------------
Files in this folder act as a cache, and the cache is discarded if the files
are older than the modification time of `.dart_tool/package_config.json`.
Hence, it should never be necessary to clear this cache manually, if you find a
need to do please file a bug.

View File

@@ -0,0 +1 @@
{"version":2,"entries":[{"package":"design_system","rootUri":"../../design_system/","packageUri":"lib/"},{"package":"fonts","rootUri":"../../fonts/","packageUri":"lib/"},{"package":"navigation","rootUri":"../../navigation/","packageUri":"lib/"},{"package":"sf_infrastructure","rootUri":"../../sf_infrastructure/","packageUri":"lib/"},{"package":"sf_localizations","rootUri":"../../sf_localizations/","packageUri":"lib/"},{"package":"utils","rootUri":"../../utils/","packageUri":"lib/"},{"package":"payments","rootUri":"../","packageUri":"lib/"}]}

View File

@@ -1,4 +1,5 @@
import 'package:dio/dio.dart';
import 'package:flutter/foundation.dart';
import 'package:payments/src/core/data/models/payin_response_model.dart';
import 'package:payments/src/core/data/models/payment_card_model.dart';
import 'package:payments/src/core/data/models/topup_cards_response_model.dart';
@@ -75,7 +76,10 @@ class HiPayRemoteDatasourceImpl implements HiPayRemoteDatasource {
}
@override
Future<PayinResponseModel> payin({required String topupCardId, required double amount}) async {
Future<PayinResponseModel> payin({
required String topupCardId,
required double amount,
}) async {
try {
final response = await _repository.post<Map<String, dynamic>>(
'/payments/topup-cards/$topupCardId/payin',
@@ -83,6 +87,7 @@ class HiPayRemoteDatasourceImpl implements HiPayRemoteDatasource {
);
final data = response.data;
debugPrint('[payin] status: ${response.statusCode} response: $data');
if (data == null || data.isEmpty) {
throw Exception('Empty response from payin');
}

View File

@@ -7,12 +7,12 @@ part 'payin_response_model.g.dart';
@freezed
abstract class PayinResponseModel with _$PayinResponseModel {
const factory PayinResponseModel({
required String state,
required String status,
String? forwardUrl,
required String transactionReference,
required double capturedAmount,
required String orderId,
required String payinId,
required String payinStatus,
@Default('') String informationStatus,
@Default('') String walletId,
@Default('') String amount,
@Default('') String currency,
}) = _PayinResponseModel;
factory PayinResponseModel.fromJson(Map<String, dynamic> json) =>
@@ -22,11 +22,12 @@ abstract class PayinResponseModel with _$PayinResponseModel {
extension PayinResponseModelMapper on PayinResponseModel {
PayinResponseEntity toEntity() {
return PayinResponseEntity(
state: state,
status: status,
transactionReference: transactionReference,
capturedAmount: capturedAmount,
orderId: orderId,
payinId: payinId,
payinStatus: payinStatus,
informationStatus: informationStatus,
walletId: walletId,
amount: amount,
currency: currency,
);
}
}

View File

@@ -15,7 +15,7 @@ T _$identity<T>(T value) => value;
/// @nodoc
mixin _$PayinResponseModel {
String get state; String get status; String? get forwardUrl; String get transactionReference; double get capturedAmount; String get orderId;
String get payinId; String get payinStatus; String get informationStatus; String get walletId; String get amount; String get currency;
/// Create a copy of PayinResponseModel
/// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false)
@@ -28,16 +28,16 @@ $PayinResponseModelCopyWith<PayinResponseModel> get copyWith => _$PayinResponseM
@override
bool operator ==(Object other) {
return identical(this, other) || (other.runtimeType == runtimeType&&other is PayinResponseModel&&(identical(other.state, state) || other.state == state)&&(identical(other.status, status) || other.status == status)&&(identical(other.forwardUrl, forwardUrl) || other.forwardUrl == forwardUrl)&&(identical(other.transactionReference, transactionReference) || other.transactionReference == transactionReference)&&(identical(other.capturedAmount, capturedAmount) || other.capturedAmount == capturedAmount)&&(identical(other.orderId, orderId) || other.orderId == orderId));
return identical(this, other) || (other.runtimeType == runtimeType&&other is PayinResponseModel&&(identical(other.payinId, payinId) || other.payinId == payinId)&&(identical(other.payinStatus, payinStatus) || other.payinStatus == payinStatus)&&(identical(other.informationStatus, informationStatus) || other.informationStatus == informationStatus)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.amount, amount) || other.amount == amount)&&(identical(other.currency, currency) || other.currency == currency));
}
@JsonKey(includeFromJson: false, includeToJson: false)
@override
int get hashCode => Object.hash(runtimeType,state,status,forwardUrl,transactionReference,capturedAmount,orderId);
int get hashCode => Object.hash(runtimeType,payinId,payinStatus,informationStatus,walletId,amount,currency);
@override
String toString() {
return 'PayinResponseModel(state: $state, status: $status, forwardUrl: $forwardUrl, transactionReference: $transactionReference, capturedAmount: $capturedAmount, orderId: $orderId)';
return 'PayinResponseModel(payinId: $payinId, payinStatus: $payinStatus, informationStatus: $informationStatus, walletId: $walletId, amount: $amount, currency: $currency)';
}
@@ -48,7 +48,7 @@ abstract mixin class $PayinResponseModelCopyWith<$Res> {
factory $PayinResponseModelCopyWith(PayinResponseModel value, $Res Function(PayinResponseModel) _then) = _$PayinResponseModelCopyWithImpl;
@useResult
$Res call({
String state, String status, String? forwardUrl, String transactionReference, double capturedAmount, String orderId
String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency
});
@@ -65,14 +65,14 @@ class _$PayinResponseModelCopyWithImpl<$Res>
/// Create a copy of PayinResponseModel
/// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @override $Res call({Object? state = null,Object? status = null,Object? forwardUrl = freezed,Object? transactionReference = null,Object? capturedAmount = null,Object? orderId = null,}) {
@pragma('vm:prefer-inline') @override $Res call({Object? payinId = null,Object? payinStatus = null,Object? informationStatus = null,Object? walletId = null,Object? amount = null,Object? currency = null,}) {
return _then(_self.copyWith(
state: null == state ? _self.state : state // ignore: cast_nullable_to_non_nullable
as String,status: null == status ? _self.status : status // ignore: cast_nullable_to_non_nullable
as String,forwardUrl: freezed == forwardUrl ? _self.forwardUrl : forwardUrl // ignore: cast_nullable_to_non_nullable
as String?,transactionReference: null == transactionReference ? _self.transactionReference : transactionReference // ignore: cast_nullable_to_non_nullable
as String,capturedAmount: null == capturedAmount ? _self.capturedAmount : capturedAmount // ignore: cast_nullable_to_non_nullable
as double,orderId: null == orderId ? _self.orderId : orderId // ignore: cast_nullable_to_non_nullable
payinId: null == payinId ? _self.payinId : payinId // ignore: cast_nullable_to_non_nullable
as String,payinStatus: null == payinStatus ? _self.payinStatus : payinStatus // ignore: cast_nullable_to_non_nullable
as String,informationStatus: null == informationStatus ? _self.informationStatus : informationStatus // ignore: cast_nullable_to_non_nullable
as String,walletId: null == walletId ? _self.walletId : walletId // ignore: cast_nullable_to_non_nullable
as String,amount: null == amount ? _self.amount : amount // ignore: cast_nullable_to_non_nullable
as String,currency: null == currency ? _self.currency : currency // ignore: cast_nullable_to_non_nullable
as String,
));
}
@@ -158,10 +158,10 @@ return $default(_that);case _:
/// }
/// ```
@optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String state, String status, String? forwardUrl, String transactionReference, double capturedAmount, String orderId)? $default,{required TResult orElse(),}) {final _that = this;
@optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency)? $default,{required TResult orElse(),}) {final _that = this;
switch (_that) {
case _PayinResponseModel() when $default != null:
return $default(_that.state,_that.status,_that.forwardUrl,_that.transactionReference,_that.capturedAmount,_that.orderId);case _:
return $default(_that.payinId,_that.payinStatus,_that.informationStatus,_that.walletId,_that.amount,_that.currency);case _:
return orElse();
}
@@ -179,10 +179,10 @@ return $default(_that.state,_that.status,_that.forwardUrl,_that.transactionRefer
/// }
/// ```
@optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String state, String status, String? forwardUrl, String transactionReference, double capturedAmount, String orderId) $default,) {final _that = this;
@optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency) $default,) {final _that = this;
switch (_that) {
case _PayinResponseModel():
return $default(_that.state,_that.status,_that.forwardUrl,_that.transactionReference,_that.capturedAmount,_that.orderId);case _:
return $default(_that.payinId,_that.payinStatus,_that.informationStatus,_that.walletId,_that.amount,_that.currency);case _:
throw StateError('Unexpected subclass');
}
@@ -199,10 +199,10 @@ return $default(_that.state,_that.status,_that.forwardUrl,_that.transactionRefer
/// }
/// ```
@optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String state, String status, String? forwardUrl, String transactionReference, double capturedAmount, String orderId)? $default,) {final _that = this;
@optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency)? $default,) {final _that = this;
switch (_that) {
case _PayinResponseModel() when $default != null:
return $default(_that.state,_that.status,_that.forwardUrl,_that.transactionReference,_that.capturedAmount,_that.orderId);case _:
return $default(_that.payinId,_that.payinStatus,_that.informationStatus,_that.walletId,_that.amount,_that.currency);case _:
return null;
}
@@ -214,15 +214,15 @@ return $default(_that.state,_that.status,_that.forwardUrl,_that.transactionRefer
@JsonSerializable()
class _PayinResponseModel implements PayinResponseModel {
const _PayinResponseModel({required this.state, required this.status, this.forwardUrl, required this.transactionReference, required this.capturedAmount, required this.orderId});
const _PayinResponseModel({required this.payinId, required this.payinStatus, this.informationStatus = '', this.walletId = '', this.amount = '', this.currency = ''});
factory _PayinResponseModel.fromJson(Map<String, dynamic> json) => _$PayinResponseModelFromJson(json);
@override final String state;
@override final String status;
@override final String? forwardUrl;
@override final String transactionReference;
@override final double capturedAmount;
@override final String orderId;
@override final String payinId;
@override final String payinStatus;
@override@JsonKey() final String informationStatus;
@override@JsonKey() final String walletId;
@override@JsonKey() final String amount;
@override@JsonKey() final String currency;
/// Create a copy of PayinResponseModel
/// with the given fields replaced by the non-null parameter values.
@@ -237,16 +237,16 @@ Map<String, dynamic> toJson() {
@override
bool operator ==(Object other) {
return identical(this, other) || (other.runtimeType == runtimeType&&other is _PayinResponseModel&&(identical(other.state, state) || other.state == state)&&(identical(other.status, status) || other.status == status)&&(identical(other.forwardUrl, forwardUrl) || other.forwardUrl == forwardUrl)&&(identical(other.transactionReference, transactionReference) || other.transactionReference == transactionReference)&&(identical(other.capturedAmount, capturedAmount) || other.capturedAmount == capturedAmount)&&(identical(other.orderId, orderId) || other.orderId == orderId));
return identical(this, other) || (other.runtimeType == runtimeType&&other is _PayinResponseModel&&(identical(other.payinId, payinId) || other.payinId == payinId)&&(identical(other.payinStatus, payinStatus) || other.payinStatus == payinStatus)&&(identical(other.informationStatus, informationStatus) || other.informationStatus == informationStatus)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.amount, amount) || other.amount == amount)&&(identical(other.currency, currency) || other.currency == currency));
}
@JsonKey(includeFromJson: false, includeToJson: false)
@override
int get hashCode => Object.hash(runtimeType,state,status,forwardUrl,transactionReference,capturedAmount,orderId);
int get hashCode => Object.hash(runtimeType,payinId,payinStatus,informationStatus,walletId,amount,currency);
@override
String toString() {
return 'PayinResponseModel(state: $state, status: $status, forwardUrl: $forwardUrl, transactionReference: $transactionReference, capturedAmount: $capturedAmount, orderId: $orderId)';
return 'PayinResponseModel(payinId: $payinId, payinStatus: $payinStatus, informationStatus: $informationStatus, walletId: $walletId, amount: $amount, currency: $currency)';
}
@@ -257,7 +257,7 @@ abstract mixin class _$PayinResponseModelCopyWith<$Res> implements $PayinRespons
factory _$PayinResponseModelCopyWith(_PayinResponseModel value, $Res Function(_PayinResponseModel) _then) = __$PayinResponseModelCopyWithImpl;
@override @useResult
$Res call({
String state, String status, String? forwardUrl, String transactionReference, double capturedAmount, String orderId
String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency
});
@@ -274,14 +274,14 @@ class __$PayinResponseModelCopyWithImpl<$Res>
/// Create a copy of PayinResponseModel
/// with the given fields replaced by the non-null parameter values.
@override @pragma('vm:prefer-inline') $Res call({Object? state = null,Object? status = null,Object? forwardUrl = freezed,Object? transactionReference = null,Object? capturedAmount = null,Object? orderId = null,}) {
@override @pragma('vm:prefer-inline') $Res call({Object? payinId = null,Object? payinStatus = null,Object? informationStatus = null,Object? walletId = null,Object? amount = null,Object? currency = null,}) {
return _then(_PayinResponseModel(
state: null == state ? _self.state : state // ignore: cast_nullable_to_non_nullable
as String,status: null == status ? _self.status : status // ignore: cast_nullable_to_non_nullable
as String,forwardUrl: freezed == forwardUrl ? _self.forwardUrl : forwardUrl // ignore: cast_nullable_to_non_nullable
as String?,transactionReference: null == transactionReference ? _self.transactionReference : transactionReference // ignore: cast_nullable_to_non_nullable
as String,capturedAmount: null == capturedAmount ? _self.capturedAmount : capturedAmount // ignore: cast_nullable_to_non_nullable
as double,orderId: null == orderId ? _self.orderId : orderId // ignore: cast_nullable_to_non_nullable
payinId: null == payinId ? _self.payinId : payinId // ignore: cast_nullable_to_non_nullable
as String,payinStatus: null == payinStatus ? _self.payinStatus : payinStatus // ignore: cast_nullable_to_non_nullable
as String,informationStatus: null == informationStatus ? _self.informationStatus : informationStatus // ignore: cast_nullable_to_non_nullable
as String,walletId: null == walletId ? _self.walletId : walletId // ignore: cast_nullable_to_non_nullable
as String,amount: null == amount ? _self.amount : amount // ignore: cast_nullable_to_non_nullable
as String,currency: null == currency ? _self.currency : currency // ignore: cast_nullable_to_non_nullable
as String,
));
}

View File

@@ -8,20 +8,20 @@ part of 'payin_response_model.dart';
_PayinResponseModel _$PayinResponseModelFromJson(Map<String, dynamic> json) =>
_PayinResponseModel(
state: json['state'] as String,
status: json['status'] as String,
forwardUrl: json['forwardUrl'] as String?,
transactionReference: json['transactionReference'] as String,
capturedAmount: (json['capturedAmount'] as num).toDouble(),
orderId: json['orderId'] as String,
payinId: json['payinId'] as String,
payinStatus: json['payinStatus'] as String,
informationStatus: json['informationStatus'] as String? ?? '',
walletId: json['walletId'] as String? ?? '',
amount: json['amount'] as String? ?? '',
currency: json['currency'] as String? ?? '',
);
Map<String, dynamic> _$PayinResponseModelToJson(_PayinResponseModel instance) =>
<String, dynamic>{
'state': instance.state,
'status': instance.status,
'forwardUrl': instance.forwardUrl,
'transactionReference': instance.transactionReference,
'capturedAmount': instance.capturedAmount,
'orderId': instance.orderId,
'payinId': instance.payinId,
'payinStatus': instance.payinStatus,
'informationStatus': instance.informationStatus,
'walletId': instance.walletId,
'amount': instance.amount,
'currency': instance.currency,
};

View File

@@ -5,10 +5,11 @@ part 'payin_response_entity.freezed.dart';
@freezed
abstract class PayinResponseEntity with _$PayinResponseEntity {
const factory PayinResponseEntity({
required String state,
required String status,
required String transactionReference,
required double capturedAmount,
required String orderId,
required String payinId,
required String payinStatus,
@Default('') String informationStatus,
@Default('') String walletId,
@Default('') String amount,
@Default('') String currency,
}) = _PayinResponseEntity;
}

View File

@@ -14,7 +14,7 @@ T _$identity<T>(T value) => value;
/// @nodoc
mixin _$PayinResponseEntity {
String get state; String get status; String get transactionReference; double get capturedAmount; String get orderId;
String get payinId; String get payinStatus; String get informationStatus; String get walletId; String get amount; String get currency;
/// Create a copy of PayinResponseEntity
/// with the given fields replaced by the non-null parameter values.
@JsonKey(includeFromJson: false, includeToJson: false)
@@ -25,16 +25,16 @@ $PayinResponseEntityCopyWith<PayinResponseEntity> get copyWith => _$PayinRespons
@override
bool operator ==(Object other) {
return identical(this, other) || (other.runtimeType == runtimeType&&other is PayinResponseEntity&&(identical(other.state, state) || other.state == state)&&(identical(other.status, status) || other.status == status)&&(identical(other.transactionReference, transactionReference) || other.transactionReference == transactionReference)&&(identical(other.capturedAmount, capturedAmount) || other.capturedAmount == capturedAmount)&&(identical(other.orderId, orderId) || other.orderId == orderId));
return identical(this, other) || (other.runtimeType == runtimeType&&other is PayinResponseEntity&&(identical(other.payinId, payinId) || other.payinId == payinId)&&(identical(other.payinStatus, payinStatus) || other.payinStatus == payinStatus)&&(identical(other.informationStatus, informationStatus) || other.informationStatus == informationStatus)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.amount, amount) || other.amount == amount)&&(identical(other.currency, currency) || other.currency == currency));
}
@override
int get hashCode => Object.hash(runtimeType,state,status,transactionReference,capturedAmount,orderId);
int get hashCode => Object.hash(runtimeType,payinId,payinStatus,informationStatus,walletId,amount,currency);
@override
String toString() {
return 'PayinResponseEntity(state: $state, status: $status, transactionReference: $transactionReference, capturedAmount: $capturedAmount, orderId: $orderId)';
return 'PayinResponseEntity(payinId: $payinId, payinStatus: $payinStatus, informationStatus: $informationStatus, walletId: $walletId, amount: $amount, currency: $currency)';
}
@@ -45,7 +45,7 @@ abstract mixin class $PayinResponseEntityCopyWith<$Res> {
factory $PayinResponseEntityCopyWith(PayinResponseEntity value, $Res Function(PayinResponseEntity) _then) = _$PayinResponseEntityCopyWithImpl;
@useResult
$Res call({
String state, String status, String transactionReference, double capturedAmount, String orderId
String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency
});
@@ -62,13 +62,14 @@ class _$PayinResponseEntityCopyWithImpl<$Res>
/// Create a copy of PayinResponseEntity
/// with the given fields replaced by the non-null parameter values.
@pragma('vm:prefer-inline') @override $Res call({Object? state = null,Object? status = null,Object? transactionReference = null,Object? capturedAmount = null,Object? orderId = null,}) {
@pragma('vm:prefer-inline') @override $Res call({Object? payinId = null,Object? payinStatus = null,Object? informationStatus = null,Object? walletId = null,Object? amount = null,Object? currency = null,}) {
return _then(_self.copyWith(
state: null == state ? _self.state : state // ignore: cast_nullable_to_non_nullable
as String,status: null == status ? _self.status : status // ignore: cast_nullable_to_non_nullable
as String,transactionReference: null == transactionReference ? _self.transactionReference : transactionReference // ignore: cast_nullable_to_non_nullable
as String,capturedAmount: null == capturedAmount ? _self.capturedAmount : capturedAmount // ignore: cast_nullable_to_non_nullable
as double,orderId: null == orderId ? _self.orderId : orderId // ignore: cast_nullable_to_non_nullable
payinId: null == payinId ? _self.payinId : payinId // ignore: cast_nullable_to_non_nullable
as String,payinStatus: null == payinStatus ? _self.payinStatus : payinStatus // ignore: cast_nullable_to_non_nullable
as String,informationStatus: null == informationStatus ? _self.informationStatus : informationStatus // ignore: cast_nullable_to_non_nullable
as String,walletId: null == walletId ? _self.walletId : walletId // ignore: cast_nullable_to_non_nullable
as String,amount: null == amount ? _self.amount : amount // ignore: cast_nullable_to_non_nullable
as String,currency: null == currency ? _self.currency : currency // ignore: cast_nullable_to_non_nullable
as String,
));
}
@@ -154,10 +155,10 @@ return $default(_that);case _:
/// }
/// ```
@optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String state, String status, String transactionReference, double capturedAmount, String orderId)? $default,{required TResult orElse(),}) {final _that = this;
@optionalTypeArgs TResult maybeWhen<TResult extends Object?>(TResult Function( String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency)? $default,{required TResult orElse(),}) {final _that = this;
switch (_that) {
case _PayinResponseEntity() when $default != null:
return $default(_that.state,_that.status,_that.transactionReference,_that.capturedAmount,_that.orderId);case _:
return $default(_that.payinId,_that.payinStatus,_that.informationStatus,_that.walletId,_that.amount,_that.currency);case _:
return orElse();
}
@@ -175,10 +176,10 @@ return $default(_that.state,_that.status,_that.transactionReference,_that.captur
/// }
/// ```
@optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String state, String status, String transactionReference, double capturedAmount, String orderId) $default,) {final _that = this;
@optionalTypeArgs TResult when<TResult extends Object?>(TResult Function( String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency) $default,) {final _that = this;
switch (_that) {
case _PayinResponseEntity():
return $default(_that.state,_that.status,_that.transactionReference,_that.capturedAmount,_that.orderId);case _:
return $default(_that.payinId,_that.payinStatus,_that.informationStatus,_that.walletId,_that.amount,_that.currency);case _:
throw StateError('Unexpected subclass');
}
@@ -195,10 +196,10 @@ return $default(_that.state,_that.status,_that.transactionReference,_that.captur
/// }
/// ```
@optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String state, String status, String transactionReference, double capturedAmount, String orderId)? $default,) {final _that = this;
@optionalTypeArgs TResult? whenOrNull<TResult extends Object?>(TResult? Function( String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency)? $default,) {final _that = this;
switch (_that) {
case _PayinResponseEntity() when $default != null:
return $default(_that.state,_that.status,_that.transactionReference,_that.capturedAmount,_that.orderId);case _:
return $default(_that.payinId,_that.payinStatus,_that.informationStatus,_that.walletId,_that.amount,_that.currency);case _:
return null;
}
@@ -210,14 +211,15 @@ return $default(_that.state,_that.status,_that.transactionReference,_that.captur
class _PayinResponseEntity implements PayinResponseEntity {
const _PayinResponseEntity({required this.state, required this.status, required this.transactionReference, required this.capturedAmount, required this.orderId});
const _PayinResponseEntity({required this.payinId, required this.payinStatus, this.informationStatus = '', this.walletId = '', this.amount = '', this.currency = ''});
@override final String state;
@override final String status;
@override final String transactionReference;
@override final double capturedAmount;
@override final String orderId;
@override final String payinId;
@override final String payinStatus;
@override@JsonKey() final String informationStatus;
@override@JsonKey() final String walletId;
@override@JsonKey() final String amount;
@override@JsonKey() final String currency;
/// Create a copy of PayinResponseEntity
/// with the given fields replaced by the non-null parameter values.
@@ -229,16 +231,16 @@ _$PayinResponseEntityCopyWith<_PayinResponseEntity> get copyWith => __$PayinResp
@override
bool operator ==(Object other) {
return identical(this, other) || (other.runtimeType == runtimeType&&other is _PayinResponseEntity&&(identical(other.state, state) || other.state == state)&&(identical(other.status, status) || other.status == status)&&(identical(other.transactionReference, transactionReference) || other.transactionReference == transactionReference)&&(identical(other.capturedAmount, capturedAmount) || other.capturedAmount == capturedAmount)&&(identical(other.orderId, orderId) || other.orderId == orderId));
return identical(this, other) || (other.runtimeType == runtimeType&&other is _PayinResponseEntity&&(identical(other.payinId, payinId) || other.payinId == payinId)&&(identical(other.payinStatus, payinStatus) || other.payinStatus == payinStatus)&&(identical(other.informationStatus, informationStatus) || other.informationStatus == informationStatus)&&(identical(other.walletId, walletId) || other.walletId == walletId)&&(identical(other.amount, amount) || other.amount == amount)&&(identical(other.currency, currency) || other.currency == currency));
}
@override
int get hashCode => Object.hash(runtimeType,state,status,transactionReference,capturedAmount,orderId);
int get hashCode => Object.hash(runtimeType,payinId,payinStatus,informationStatus,walletId,amount,currency);
@override
String toString() {
return 'PayinResponseEntity(state: $state, status: $status, transactionReference: $transactionReference, capturedAmount: $capturedAmount, orderId: $orderId)';
return 'PayinResponseEntity(payinId: $payinId, payinStatus: $payinStatus, informationStatus: $informationStatus, walletId: $walletId, amount: $amount, currency: $currency)';
}
@@ -249,7 +251,7 @@ abstract mixin class _$PayinResponseEntityCopyWith<$Res> implements $PayinRespon
factory _$PayinResponseEntityCopyWith(_PayinResponseEntity value, $Res Function(_PayinResponseEntity) _then) = __$PayinResponseEntityCopyWithImpl;
@override @useResult
$Res call({
String state, String status, String transactionReference, double capturedAmount, String orderId
String payinId, String payinStatus, String informationStatus, String walletId, String amount, String currency
});
@@ -266,13 +268,14 @@ class __$PayinResponseEntityCopyWithImpl<$Res>
/// Create a copy of PayinResponseEntity
/// with the given fields replaced by the non-null parameter values.
@override @pragma('vm:prefer-inline') $Res call({Object? state = null,Object? status = null,Object? transactionReference = null,Object? capturedAmount = null,Object? orderId = null,}) {
@override @pragma('vm:prefer-inline') $Res call({Object? payinId = null,Object? payinStatus = null,Object? informationStatus = null,Object? walletId = null,Object? amount = null,Object? currency = null,}) {
return _then(_PayinResponseEntity(
state: null == state ? _self.state : state // ignore: cast_nullable_to_non_nullable
as String,status: null == status ? _self.status : status // ignore: cast_nullable_to_non_nullable
as String,transactionReference: null == transactionReference ? _self.transactionReference : transactionReference // ignore: cast_nullable_to_non_nullable
as String,capturedAmount: null == capturedAmount ? _self.capturedAmount : capturedAmount // ignore: cast_nullable_to_non_nullable
as double,orderId: null == orderId ? _self.orderId : orderId // ignore: cast_nullable_to_non_nullable
payinId: null == payinId ? _self.payinId : payinId // ignore: cast_nullable_to_non_nullable
as String,payinStatus: null == payinStatus ? _self.payinStatus : payinStatus // ignore: cast_nullable_to_non_nullable
as String,informationStatus: null == informationStatus ? _self.informationStatus : informationStatus // ignore: cast_nullable_to_non_nullable
as String,walletId: null == walletId ? _self.walletId : walletId // ignore: cast_nullable_to_non_nullable
as String,amount: null == amount ? _self.amount : amount // ignore: cast_nullable_to_non_nullable
as String,currency: null == currency ? _self.currency : currency // ignore: cast_nullable_to_non_nullable
as String,
));
}

View File

@@ -160,6 +160,11 @@
"deviceSetup_giveFirstAllowance": "Gib das erste Taschengeld",
"deviceSetup_paymentCancelled": "Die Zahlung wurde abgebrochen. Bitte versuche es erneut.",
"deviceSetup_skipAndConfigureLater": "Überspringen und später konfigurieren",
"deviceSetup_addCreditCard": "Kreditkarte hinzufügen",
"deviceSetup_addCreditCard_title": "Füge deine Kreditkarte hinzu!",
"deviceSetup_addCreditCard_subtitle": "Registriere deine Karte, um Einzahlungen auf das Konto deines Kindes zu machen",
"deviceSetup_addCreditCard_info": "Du kannst Einzahlungen vornehmen und das Taschengeld über die App verwalten",
"deviceSetup_cardRegistered": "Karte erfolgreich registriert!",
"deviceSetup_paymentSuccess": "Zahlung erfolgreich abgeschlossen!",
"deviceSetup_scanQr": "QR scannen",
"deviceSetup_scanQr_hint": "Richte den QR-Code innerhalb des Rahmens aus",
@@ -182,6 +187,13 @@
"errorWalletNotProvisioned": "Wallet ist noch nicht provisioniert",
"errorPinLength": "Die PIN muss {length} Ziffern haben",
"errorWalletConnectFirst": "Verbinde zuerst die Wallet",
"errorPinMismatch": "PINs stimmen nicht überein, bitte versuche es erneut",
"scaPinCreate": "Erstelle deine 6-stellige PIN",
"scaPinConfirm": "Bestätige deine PIN",
"scaPinEnter": "Gib deine PIN ein",
"scaProvisioningFailed": "Aktivierung fehlgeschlagen",
"scaProvisioningWarning": "Beim erneuten Versuch wird der Zugang auf anderen Geräten deaktiviert. Nur ein Zugang pro Benutzer ist erlaubt.",
"scaProvisioningRetry": "Aktivierung erneut versuchen",
"errorLoadingData": "Fehler beim Laden der Daten",
"retry": "Erneut versuchen",

View File

@@ -160,6 +160,11 @@
"deviceSetup_giveFirstAllowance": "Give their first allowance",
"deviceSetup_paymentCancelled": "Payment was cancelled. Please try again.",
"deviceSetup_skipAndConfigureLater": "Skip and configure later",
"deviceSetup_addCreditCard": "Add credit card",
"deviceSetup_addCreditCard_title": "Add your credit card!",
"deviceSetup_addCreditCard_subtitle": "Register your card to make deposits to your child's account",
"deviceSetup_addCreditCard_info": "You'll be able to make deposits and manage allowances from the app",
"deviceSetup_cardRegistered": "Card registered successfully!",
"deviceSetup_paymentSuccess": "Payment completed successfully!",
"deviceSetup_scanQr": "Scan QR",
"deviceSetup_scanQr_hint": "Center the QR inside the frame",
@@ -182,6 +187,13 @@
"errorWalletNotProvisioned": "Wallet is not provisioned yet",
"errorPinLength": "PIN must be {length} digits",
"errorWalletConnectFirst": "Connect the wallet first",
"errorPinMismatch": "PINs do not match, please try again",
"scaPinCreate": "Create your 6-digit PIN",
"scaPinConfirm": "Confirm your PIN",
"scaPinEnter": "Enter your PIN",
"scaProvisioningFailed": "Activation failed",
"scaProvisioningWarning": "Retrying will disable access on any other device. Only one access per user is allowed.",
"scaProvisioningRetry": "Retry activation",
"errorLoadingData": "Error loading data",
"retry": "Retry",

View File

@@ -160,6 +160,11 @@
"deviceSetup_giveFirstAllowance": "Dale su primera paga",
"deviceSetup_paymentCancelled": "El pago fue cancelado. Inténtalo de nuevo.",
"deviceSetup_skipAndConfigureLater": "Saltar y configurar más tarde",
"deviceSetup_addCreditCard": "Agregar tarjeta de crédito",
"deviceSetup_addCreditCard_title": "¡Añade tu tarjeta de crédito!",
"deviceSetup_addCreditCard_subtitle": "Registra tu tarjeta para poder realizar ingresos en la cuenta de tu peque",
"deviceSetup_addCreditCard_info": "Podrás hacer ingresos y gestionar las pagas desde la app",
"deviceSetup_cardRegistered": "¡Tarjeta registrada con éxito!",
"deviceSetup_paymentSuccess": "¡Pago realizado con éxito!",
"deviceSetup_scanQr": "Escanear QR",
"deviceSetup_scanQr_hint": "Centra el QR dentro del recuadro",
@@ -182,6 +187,13 @@
"errorWalletNotProvisioned": "No está provisionado aún",
"errorPinLength": "El PIN debe tener {length} dígitos",
"errorWalletConnectFirst": "Conecta la wallet primero",
"errorPinMismatch": "Los PIN no coinciden, inténtalo de nuevo",
"scaPinCreate": "Crea tu PIN de 6 dígitos",
"scaPinConfirm": "Confirma tu PIN",
"scaPinEnter": "Introduce tu PIN",
"scaProvisioningFailed": "Error en la activación",
"scaProvisioningWarning": "Al reintentar se desactivará el acceso en cualquier otro dispositivo. Solo se permite un acceso por usuario.",
"scaProvisioningRetry": "Reintentar activación",
"errorLoadingData": "Error al cargar datos",
"retry": "Reintentar",

View File

@@ -160,6 +160,11 @@
"deviceSetup_giveFirstAllowance": "Donner sa première allocation",
"deviceSetup_paymentCancelled": "Le paiement a été annulé. Veuillez réessayer.",
"deviceSetup_skipAndConfigureLater": "Passer et configurer plus tard",
"deviceSetup_addCreditCard": "Ajouter une carte de crédit",
"deviceSetup_addCreditCard_title": "Ajoutez votre carte de crédit !",
"deviceSetup_addCreditCard_subtitle": "Enregistrez votre carte pour effectuer des versements sur le compte de votre enfant",
"deviceSetup_addCreditCard_info": "Vous pourrez faire des versements et gérer les allocations depuis l'application",
"deviceSetup_cardRegistered": "Carte enregistrée avec succès !",
"deviceSetup_paymentSuccess": "Paiement effectué avec succès !",
"deviceSetup_scanQr": "Scanner le QR",
"deviceSetup_scanQr_hint": "Place le QR au centre du cadre",
@@ -182,6 +187,13 @@
"errorWalletNotProvisioned": "Le portefeuille n'est pas encore provisionné",
"errorPinLength": "Le PIN doit contenir {length} chiffres",
"errorWalletConnectFirst": "Connectez d'abord le portefeuille",
"errorPinMismatch": "Les PIN ne correspondent pas, veuillez réessayer",
"scaPinCreate": "Créez votre PIN à 6 chiffres",
"scaPinConfirm": "Confirmez votre PIN",
"scaPinEnter": "Entrez votre PIN",
"scaProvisioningFailed": "Échec de l'activation",
"scaProvisioningWarning": "En réessayant, l'accès sera désactivé sur tout autre appareil. Un seul accès par utilisateur est autorisé.",
"scaProvisioningRetry": "Réessayer l'activation",
"errorLoadingData": "Erreur lors du chargement des données",
"retry": "Réessayer",

View File

@@ -160,6 +160,11 @@
"deviceSetup_giveFirstAllowance": "Dagli la sua prima paghetta",
"deviceSetup_paymentCancelled": "Il pagamento è stato annullato. Riprova.",
"deviceSetup_skipAndConfigureLater": "Salta e configura più tardi",
"deviceSetup_addCreditCard": "Aggiungi carta di credito",
"deviceSetup_addCreditCard_title": "Aggiungi la tua carta di credito!",
"deviceSetup_addCreditCard_subtitle": "Registra la tua carta per poter effettuare versamenti sul conto del tuo bambino",
"deviceSetup_addCreditCard_info": "Potrai fare versamenti e gestire le paghette dall'app",
"deviceSetup_cardRegistered": "Carta registrata con successo!",
"deviceSetup_paymentSuccess": "Pagamento completato con successo!",
"deviceSetup_scanQr": "Scansiona QR",
"deviceSetup_scanQr_hint": "Centra il QR all'interno del riquadro",
@@ -182,6 +187,13 @@
"errorWalletNotProvisioned": "Il portafoglio non è ancora provisionato",
"errorPinLength": "Il PIN deve avere {length} cifre",
"errorWalletConnectFirst": "Connetti prima il portafoglio",
"errorPinMismatch": "I PIN non corrispondono, riprova",
"scaPinCreate": "Crea il tuo PIN a 6 cifre",
"scaPinConfirm": "Conferma il tuo PIN",
"scaPinEnter": "Inserisci il tuo PIN",
"scaProvisioningFailed": "Attivazione fallita",
"scaProvisioningWarning": "Riprovando si disattiverà l'accesso su qualsiasi altro dispositivo. È consentito un solo accesso per utente.",
"scaProvisioningRetry": "Riprova attivazione",
"errorLoadingData": "Errore durante il caricamento dei dati",
"retry": "Riprova",

View File

@@ -160,6 +160,11 @@
"deviceSetup_giveFirstAllowance": "Dá-lhe a primeira mesada",
"deviceSetup_paymentCancelled": "O pagamento foi cancelado. Tente novamente.",
"deviceSetup_skipAndConfigureLater": "Pular e configurar mais tarde",
"deviceSetup_addCreditCard": "Adicionar cartão de crédito",
"deviceSetup_addCreditCard_title": "Adiciona o teu cartão de crédito!",
"deviceSetup_addCreditCard_subtitle": "Regista o teu cartão para poderes fazer depósitos na conta do teu filho",
"deviceSetup_addCreditCard_info": "Poderás fazer depósitos e gerir as mesadas a partir da app",
"deviceSetup_cardRegistered": "Cartão registado com sucesso!",
"deviceSetup_paymentSuccess": "Pagamento realizado com sucesso!",
"deviceSetup_scanQr": "Digitalizar QR",
"deviceSetup_scanQr_hint": "Centraliza o QR dentro da moldura",
@@ -182,6 +187,13 @@
"errorWalletNotProvisioned": "A carteira ainda não está provisionada",
"errorPinLength": "O PIN deve ter {length} dígitos",
"errorWalletConnectFirst": "Conecta a carteira primeiro",
"errorPinMismatch": "Os PINs não coincidem, tente novamente",
"scaPinCreate": "Cria o teu PIN de 6 dígitos",
"scaPinConfirm": "Confirma o teu PIN",
"scaPinEnter": "Introduz o teu PIN",
"scaProvisioningFailed": "Falha na ativação",
"scaProvisioningWarning": "Ao tentar novamente, o acesso será desativado em qualquer outro dispositivo. Apenas um acesso por utilizador é permitido.",
"scaProvisioningRetry": "Tentar ativação novamente",
"errorLoadingData": "Erro ao carregar dados",
"retry": "Tentar novamente",

View File

@@ -232,6 +232,13 @@ class I18n {
static const String errorWalletNotProvisioned = 'errorWalletNotProvisioned';
static const String errorPinLength = 'errorPinLength';
static const String errorWalletConnectFirst = 'errorWalletConnectFirst';
static const String errorPinMismatch = 'errorPinMismatch';
static const String scaPinCreate = 'scaPinCreate';
static const String scaPinConfirm = 'scaPinConfirm';
static const String scaPinEnter = 'scaPinEnter';
static const String scaProvisioningFailed = 'scaProvisioningFailed';
static const String scaProvisioningWarning = 'scaProvisioningWarning';
static const String scaProvisioningRetry = 'scaProvisioningRetry';
static const String errorLoadingData = 'errorLoadingData';
static const String retry = 'retry';
static const String walletTitle = 'walletTitle';
@@ -454,6 +461,13 @@ class I18n {
static const String statementCurrentMonthError = 'statementCurrentMonthError';
static const String download = 'download';
// Device Setup - Add Credit Card
static const String deviceSetup_addCreditCard = 'deviceSetup_addCreditCard';
static const String deviceSetup_addCreditCard_title = 'deviceSetup_addCreditCard_title';
static const String deviceSetup_addCreditCard_subtitle = 'deviceSetup_addCreditCard_subtitle';
static const String deviceSetup_addCreditCard_info = 'deviceSetup_addCreditCard_info';
static const String deviceSetup_cardRegistered = 'deviceSetup_cardRegistered';
// Payin
static const String payinSelectCard = 'payinSelectCard';
static const String payinNoCards = 'payinNoCards';

View File

@@ -9,6 +9,8 @@ import 'package:sf_shared/src/data/models/wallet_transaction_model.dart';
abstract class TreezorRemoteDatasource {
Future<ScaWalletsResponseModel> scaWallets();
Future<List<ScaWalletItemModel>> getScaWallets();
Future<bool> sendJWSSesion({required String jws});
Future<PaymentProfileResponseModel> getPaymentProfile({
@@ -37,6 +39,7 @@ abstract class TreezorRemoteDatasource {
required int beneficiaryId,
required String beneficiaryValidationId,
required double amount,
required String scaProof,
});
Future<List<PayoutBeneficiaryModel>> getPayoutBeneficiaries();

View File

@@ -46,6 +46,30 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
}
}
@override
Future<List<ScaWalletItemModel>> getScaWallets() async {
try {
final response = await _repository.get<Map<String, dynamic>>(
'/treezor/sca-wallets',
);
final data = response.data;
if (data == null) return [];
final items = data['item'];
if (items is List) {
return items
.cast<Map<String, dynamic>>()
.map(ScaWalletItemModel.fromJson)
.toList();
}
return [];
} on DioException catch (error) {
throw _mapDioError(error, defaultMessage: 'Error fetching SCA wallets');
}
}
@override
Future<bool> sendJWSSesion({required String jws}) async {
try {
@@ -140,12 +164,11 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
);
}
}
@override
Future<void> deleteScaWallet({required String scaWalletId}) async {
try {
await _repository.delete<void>(
'/treezor/sca-wallets/$scaWalletId',
);
await _repository.delete<void>('/treezor/sca-wallets/$scaWalletId');
} on DioException catch (error) {
throw _mapDioError(
error,
@@ -215,6 +238,7 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
required int beneficiaryId,
required String beneficiaryValidationId,
required double amount,
required String scaProof,
}) async {
try {
await _repository.post<void>(
@@ -224,13 +248,11 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
'target': beneficiaryId,
'beneficiaryValidationId': beneficiaryValidationId,
'amount': amount,
'scaProof': scaProof,
},
);
} on DioException catch (error) {
throw _mapDioError(
error,
defaultMessage: 'Error in /wallets/transfer',
);
throw _mapDioError(error, defaultMessage: 'Error in /wallets/transfer');
}
}
@@ -247,16 +269,12 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
.map((json) => PayoutBeneficiaryModel.fromJson(json))
.toList();
} on DioException catch (error) {
throw _mapDioError(
error,
defaultMessage: 'Error fetching beneficiaries',
);
throw _mapDioError(error, defaultMessage: 'Error fetching beneficiaries');
}
}
@override
Future<ChildWalletModel> getChildWallet({
required String walletId,
}) async {
Future<ChildWalletModel> getChildWallet({required String walletId}) async {
try {
final response = await _repository.get<Map<String, dynamic>>(
'/wallets/$walletId',
@@ -270,12 +288,10 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
final parsed = ChildWalletResponseModel.fromJson(data);
return parsed.item;
} on DioException catch (error) {
throw _mapDioError(
error,
defaultMessage: 'Error in /wallets/$walletId',
);
throw _mapDioError(error, defaultMessage: 'Error in /wallets/$walletId');
}
}
@override
Future<void> walletMove({
required String walletId,
@@ -323,7 +339,9 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
);
final data = response.data;
if (data == null || data['item'] == null) {
throw Exception('Empty response from /wallets/$walletId/account-details');
throw Exception(
'Empty response from /wallets/$walletId/account-details',
);
}
return (data['item'] as Map<String, dynamic>)['link'] as String;
} on DioException catch (error) {
@@ -347,7 +365,9 @@ class TreezorRemoteDatasourceImpl implements TreezorRemoteDatasource {
);
final data = response.data;
if (data == null || data['item'] == null) {
throw Exception('Empty response from /wallets/$walletId/account-statement');
throw Exception(
'Empty response from /wallets/$walletId/account-statement',
);
}
return (data['item'] as Map<String, dynamic>)['link'] as String;
} on DioException catch (error) {

View File

@@ -19,7 +19,7 @@ abstract class ScaWalletItemModel with _$ScaWalletItemModel {
const factory ScaWalletItemModel({
required String id,
required String status,
required String activationCode,
@Default('') String activationCode,
}) = _ScaWalletItemModel;
factory ScaWalletItemModel.fromJson(Map<String, dynamic> json) =>

View File

@@ -495,12 +495,12 @@ return $default(_that.id,_that.status,_that.activationCode);case _:
@JsonSerializable()
class _ScaWalletItemModel implements ScaWalletItemModel {
const _ScaWalletItemModel({required this.id, required this.status, required this.activationCode});
const _ScaWalletItemModel({required this.id, required this.status, this.activationCode = ''});
factory _ScaWalletItemModel.fromJson(Map<String, dynamic> json) => _$ScaWalletItemModelFromJson(json);
@override final String id;
@override final String status;
@override final String activationCode;
@override@JsonKey() final String activationCode;
/// Create a copy of ScaWalletItemModel
/// with the given fields replaced by the non-null parameter values.

View File

@@ -21,7 +21,7 @@ _ScaWalletItemModel _$ScaWalletItemModelFromJson(Map<String, dynamic> json) =>
_ScaWalletItemModel(
id: json['id'] as String,
status: json['status'] as String,
activationCode: json['activationCode'] as String,
activationCode: json['activationCode'] as String? ?? '',
);
Map<String, dynamic> _$ScaWalletItemModelToJson(_ScaWalletItemModel instance) =>

View File

@@ -57,6 +57,18 @@ class TreezorRepositoryImpl implements TreezorRepository {
return model.toEntity();
}
@override
Future<List<ScaWalletItemEntity>> getScaWallets() async {
final models = await _remote.getScaWallets();
return models
.map((m) => ScaWalletItemEntity(
id: m.id,
status: m.status,
activationCode: m.activationCode,
))
.toList();
}
@override
Future<void> resetScaWallets() {
return _local.clearScaWallets();
@@ -130,12 +142,14 @@ class TreezorRepositoryImpl implements TreezorRepository {
required int beneficiaryId,
required String beneficiaryValidationId,
required double amount,
required String scaProof,
}) async {
await _remote.walletTransfer(
walletId: walletId,
beneficiaryId: beneficiaryId,
beneficiaryValidationId: beneficiaryValidationId,
amount: amount,
scaProof: scaProof,
);
}

View File

@@ -15,6 +15,6 @@ abstract class ScaWalletItemEntity with _$ScaWalletItemEntity {
const factory ScaWalletItemEntity({
required String id,
required String status,
required String activationCode,
@Default('') String activationCode,
}) = _ScaWalletItemEntity;
}

View File

@@ -486,12 +486,12 @@ return $default(_that.id,_that.status,_that.activationCode);case _:
class _ScaWalletItemEntity implements ScaWalletItemEntity {
const _ScaWalletItemEntity({required this.id, required this.status, required this.activationCode});
const _ScaWalletItemEntity({required this.id, required this.status, this.activationCode = ''});
@override final String id;
@override final String status;
@override final String activationCode;
@override@JsonKey() final String activationCode;
/// Create a copy of ScaWalletItemEntity
/// with the given fields replaced by the non-null parameter values.

View File

@@ -9,6 +9,8 @@ import '../entities/wallet_transaction_entity.dart';
abstract class TreezorRepository {
Future<ScaWalletsResponseEntity> scaWallets({bool forceRefresh});
Future<List<ScaWalletItemEntity>> getScaWallets();
Future<void> resetScaWallets();
Future<bool> sendJWSSesion({required String jws});
@@ -37,6 +39,7 @@ abstract class TreezorRepository {
required int beneficiaryId,
required String beneficiaryValidationId,
required double amount,
required String scaProof,
});
Future<List<PayoutBeneficiaryEntity>> getPayoutBeneficiaries();

View File

@@ -4,14 +4,14 @@ import 'package:flutter_riverpod/flutter_riverpod.dart';
import 'package:sf_localizations/sf_localizations.dart';
class WalletBalanceBlock extends ConsumerWidget {
final double max;
static const double _maxBalance = 150.0;
final double value;
final double savings;
final double savingsPlan;
const WalletBalanceBlock({
super.key,
required this.max,
required this.value,
required this.savings,
this.savingsPlan = 30.0,
@@ -40,7 +40,7 @@ class WalletBalanceBlock extends ConsumerWidget {
MoneyText(
text: context.translate(
I18n.walletTotal,
args: {'amount': '$max'},
args: {'amount': '$value'},
),
size: 26,
secondarySize: 16,
@@ -59,7 +59,7 @@ class WalletBalanceBlock extends ConsumerWidget {
// textColor: theme.getColorFor(ThemeCode.textPrimary),
// ),
ProgressBar(
max: max,
max: _maxBalance,
value: value,
height: 83,
textSize: 40,
@@ -68,6 +68,12 @@ class WalletBalanceBlock extends ConsumerWidget {
foregroundColor: theme.getColorFor(ThemeCode.buttonPrimary),
textColor: theme.getColorFor(ThemeCode.textSecondary),
),
Center(
child: Text(
'${value.toStringAsFixed(2)}\u20AC / ${_maxBalance.toStringAsFixed(0)}\u20AC',
style: TextStyle(fontWeight: FontWeight.w600, fontSize: 16),
),
),
Center(child: Text(context.translate(I18n.walletAvailable))),
],
),