WIP
This commit is contained in:
parent
d99cfc1873
commit
a6a533efd0
|
@ -1,3 +1,4 @@
|
||||||
|
import 'dart:convert';
|
||||||
import 'dart:developer';
|
import 'dart:developer';
|
||||||
import 'package:flutter/material.dart';
|
import 'package:flutter/material.dart';
|
||||||
import 'package:flutter_bloc/flutter_bloc.dart';
|
import 'package:flutter_bloc/flutter_bloc.dart';
|
||||||
|
@ -5,6 +6,7 @@ import 'package:hub/backend/schema/enums/enums.dart';
|
||||||
import 'package:hub/components/atomic_components/menu_button_item/menu_button_item_widget.dart';
|
import 'package:hub/components/atomic_components/menu_button_item/menu_button_item_widget.dart';
|
||||||
import 'package:hub/components/atomic_components/menu_card_item/menu_card_item.dart';
|
import 'package:hub/components/atomic_components/menu_card_item/menu_card_item.dart';
|
||||||
import 'package:hub/components/molecular_components/menu_item/menu_item.dart';
|
import 'package:hub/components/molecular_components/menu_item/menu_item.dart';
|
||||||
|
import 'package:hub/flutter_flow/custom_functions.dart';
|
||||||
import 'package:hub/flutter_flow/flutter_flow_util.dart';
|
import 'package:hub/flutter_flow/flutter_flow_util.dart';
|
||||||
import 'package:hub/flutter_flow/nav/nav.dart';
|
import 'package:hub/flutter_flow/nav/nav.dart';
|
||||||
import 'package:hub/shared/extensions/dialog_extensions.dart';
|
import 'package:hub/shared/extensions/dialog_extensions.dart';
|
||||||
|
@ -38,10 +40,7 @@ class MenuBloc extends Bloc<MenuEvent, MenuState> {
|
||||||
emit(state.copyWith(menuEntries: entries));
|
emit(state.copyWith(menuEntries: entries));
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
Future<MenuEntry?> addMenuEntry(List<MenuEntry?> entries, IconData icon, String text, Function() action) async {
|
||||||
Future<List<MenuEntry?>> generateMenuEntries() async {
|
|
||||||
List<MenuEntry?> entries = [];
|
|
||||||
Future<MenuEntry?> addMenuEntry(IconData icon, String text, Function() action) async {
|
|
||||||
entries.add(
|
entries.add(
|
||||||
item == MenuItem.button
|
item == MenuItem.button
|
||||||
? MenuButtonWidget(icon: icon, action: action, title: text)
|
? MenuButtonWidget(icon: icon, action: action, title: text)
|
||||||
|
@ -54,28 +53,79 @@ class MenuBloc extends Bloc<MenuEvent, MenuState> {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future<List<MenuEntry?>> generateMenuEntries() async {
|
||||||
|
List<MenuEntry?> entries = [];
|
||||||
|
try {
|
||||||
for (var opt in menuOptions) {
|
for (var opt in menuOptions) {
|
||||||
String? v = await LicenseHelper().g(opt.value);
|
String? licenseValue = await LicenseHelper().g(opt.value);
|
||||||
log('Module: ${opt.value} - License: $v');
|
if (licenseValue != null) {
|
||||||
switch (v) {
|
Map<String, String> licenseMap = await stringToMap(licenseValue);
|
||||||
|
if (opt == Module.aboutProperty) log('AboutProperty: $licenseMap');
|
||||||
|
log('Module: ${opt.value} - License: ${licenseMap['display']}');
|
||||||
|
final String display = licenseMap['display'] ?? 'INVISIVEL';
|
||||||
|
final String startDate = licenseMap['startDate'] ?? '';
|
||||||
|
final String expirationDate = licenseMap['expirationDate'] ?? '';
|
||||||
|
final bool isStarted = await processStartDate(startDate, opt);
|
||||||
|
log('isStarted: $isStarted');
|
||||||
|
final bool isExpired = await processExpirationDate(expirationDate, opt);
|
||||||
|
log('isExpired: $isExpired');
|
||||||
|
if (isStarted && !isExpired) {
|
||||||
|
await processDisplay(display, opt, entries);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
log('Error generating menu entries: $e');
|
||||||
|
}
|
||||||
|
return entries;
|
||||||
|
}
|
||||||
|
|
||||||
|
Future<void> processDisplay(String display, Module opt, List<MenuEntry?> entries) async {
|
||||||
|
try {
|
||||||
|
switch (display) {
|
||||||
case 'VISIVEL':
|
case 'VISIVEL':
|
||||||
await addMenuEntry(opt.icon, opt.name, () async {
|
await addMenuEntry(entries, opt.icon, opt.name, () async {
|
||||||
await nav(opt.route);
|
await nav(opt.route);
|
||||||
});
|
});
|
||||||
continue;
|
break;
|
||||||
case 'DESABILITADO':
|
case 'DESABILITADO':
|
||||||
await addMenuEntry(opt.icon, opt.name, () async {
|
await addMenuEntry(entries, opt.icon, opt.name, () async {
|
||||||
await DialogUnavailable.unavailableFeature(key.currentContext!);
|
await DialogUnavailable.unavailableFeature(key.currentContext!);
|
||||||
});
|
});
|
||||||
continue;
|
break;
|
||||||
case 'INVISIVEL':
|
case 'INVISIVEL':
|
||||||
continue;
|
|
||||||
default:
|
default:
|
||||||
continue;
|
break;
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
log('Error processing display for module ${opt.value}: $e');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return entries;
|
Future<bool> processStartDate(String startDate, Module opt) async {
|
||||||
|
try {
|
||||||
|
if (startDate.isEmpty) return true;
|
||||||
|
final DateTime? start = DateTime.tryParse(startDate);
|
||||||
|
if (start != null) {
|
||||||
|
return DateTime.now().isAfter(start);
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
log('Error processing start date for module ${opt.value}: $e');
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
Future<bool> processExpirationDate(String expirationDate, Module opt) async {
|
||||||
|
try {
|
||||||
|
if (expirationDate.isEmpty) return false;
|
||||||
|
final DateTime? expiration = DateTime.tryParse(expirationDate);
|
||||||
|
if (expiration != null) {
|
||||||
|
return DateTime.now().isAfter(expiration);
|
||||||
|
}
|
||||||
|
} catch (e) {
|
||||||
|
log('Error processing expiration date for module ${opt.value}: $e');
|
||||||
|
}
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
Future nav(String link) async {
|
Future nav(String link) async {
|
||||||
|
@ -88,16 +138,4 @@ class MenuBloc extends Bloc<MenuEvent, MenuState> {
|
||||||
),
|
),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<void> logout() async {
|
|
||||||
// Implement logout logic here
|
|
||||||
}
|
|
||||||
|
|
||||||
Future settings() async {
|
|
||||||
// Implement settings navigation logic here
|
|
||||||
}
|
|
||||||
|
|
||||||
Future about() async {
|
|
||||||
// Implement about navigation logic here
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -33,6 +33,25 @@ String jsonListToStr(List<dynamic> visitorList) {
|
||||||
return result.substring(0, result.length - 1);
|
return result.substring(0, result.length - 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future<Map<String, String>> stringToMap(String v) async {
|
||||||
|
try {
|
||||||
|
return Future.value(Map.fromEntries(
|
||||||
|
v.split(',').map((part) {
|
||||||
|
final keyValue = part.split(':');
|
||||||
|
if (keyValue.length < 2) {
|
||||||
|
throw FormatException('Invalid key-value pair: $part of $v');
|
||||||
|
}
|
||||||
|
final key = keyValue[0].trim();
|
||||||
|
final value = keyValue.length > 1 ? keyValue[1].trim() : '';
|
||||||
|
return MapEntry(key, value);
|
||||||
|
}),
|
||||||
|
));
|
||||||
|
} catch (e) {
|
||||||
|
print('Error parsing string to map: $e');
|
||||||
|
return Future.value({});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
List<dynamic> listStrJsonToJsonList(
|
List<dynamic> listStrJsonToJsonList(
|
||||||
dynamic jsonList,
|
dynamic jsonList,
|
||||||
List<String> strList,
|
List<String> strList,
|
||||||
|
|
|
@ -27,7 +27,7 @@ extension AboutPropertyModulesExtension on AboutPropertyModules {
|
||||||
case AboutPropertyModules.residents:
|
case AboutPropertyModules.residents:
|
||||||
return 'FRE-HUB-RESIDENTS';
|
return 'FRE-HUB-RESIDENTS';
|
||||||
case AboutPropertyModules.petsHistory:
|
case AboutPropertyModules.petsHistory:
|
||||||
return 'FRE-HUB-PETS-HISTORY';
|
return 'FRE-HUB-PETS';
|
||||||
default:
|
default:
|
||||||
return '';
|
return '';
|
||||||
}
|
}
|
||||||
|
@ -85,7 +85,7 @@ class _AboutPropertyPageState extends State<AboutPropertyPage> with SingleTicker
|
||||||
child: Container(
|
child: Container(
|
||||||
color: FlutterFlowTheme.of(context).primaryBackground,
|
color: FlutterFlowTheme.of(context).primaryBackground,
|
||||||
child: MenuComponentWidget(expandable: true, style: MenuView.list_grid, item: MenuItem.button, menuOptions: [
|
child: MenuComponentWidget(expandable: true, style: MenuView.list_grid, item: MenuItem.button, menuOptions: [
|
||||||
Module.pets,
|
Module.petsHistory,
|
||||||
Module.residents,
|
Module.residents,
|
||||||
Module.openedVisits,
|
Module.openedVisits,
|
||||||
Module.vehicles,
|
Module.vehicles,
|
||||||
|
|
|
@ -32,7 +32,7 @@ class DatabaseStorage {
|
||||||
onUpgrade: _onUpgrade,
|
onUpgrade: _onUpgrade,
|
||||||
onDowngrade: _onDowngrade,
|
onDowngrade: _onDowngrade,
|
||||||
);
|
);
|
||||||
await LicenseService().setupLicense(database);
|
await LicenseService().setupLicense(database, false);
|
||||||
isInitialized = true;
|
isInitialized = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -4,6 +4,7 @@ import 'package:flutter/material.dart';
|
||||||
import 'package:hub/flutter_flow/internationalization.dart';
|
import 'package:hub/flutter_flow/internationalization.dart';
|
||||||
import 'package:hub/flutter_flow/nav/nav.dart';
|
import 'package:hub/flutter_flow/nav/nav.dart';
|
||||||
import 'package:hub/shared/helpers/database/database_helper.dart';
|
import 'package:hub/shared/helpers/database/database_helper.dart';
|
||||||
|
import 'package:hub/shared/helpers/storage/base_storage.dart';
|
||||||
import 'package:sqflite/sqflite.dart';
|
import 'package:sqflite/sqflite.dart';
|
||||||
|
|
||||||
enum InactiveModuleKey {
|
enum InactiveModuleKey {
|
||||||
|
@ -11,6 +12,7 @@ enum InactiveModuleKey {
|
||||||
vehicles,
|
vehicles,
|
||||||
openedVisits,
|
openedVisits,
|
||||||
petsHistory,
|
petsHistory,
|
||||||
|
aboutProperty,
|
||||||
}
|
}
|
||||||
|
|
||||||
extension InactiveModuleKeyExtension on InactiveModuleKey {
|
extension InactiveModuleKeyExtension on InactiveModuleKey {
|
||||||
|
@ -24,6 +26,8 @@ extension InactiveModuleKeyExtension on InactiveModuleKey {
|
||||||
return 'FRE-HUB-RESIDENTS';
|
return 'FRE-HUB-RESIDENTS';
|
||||||
case InactiveModuleKey.petsHistory:
|
case InactiveModuleKey.petsHistory:
|
||||||
return 'FRE-HUB-PETS-HISTORY';
|
return 'FRE-HUB-PETS-HISTORY';
|
||||||
|
case InactiveModuleKey.aboutProperty:
|
||||||
|
return 'FRE-HUB-PROPERTY';
|
||||||
default:
|
default:
|
||||||
return '';
|
return '';
|
||||||
}
|
}
|
||||||
|
@ -39,6 +43,7 @@ extension DisabledModuleKeyExtension on DisabledModuleKey {
|
||||||
switch (this) {
|
switch (this) {
|
||||||
case DisabledModuleKey.fastPass:
|
case DisabledModuleKey.fastPass:
|
||||||
return 'FRE-HUB-FASTPASS';
|
return 'FRE-HUB-FASTPASS';
|
||||||
|
|
||||||
default:
|
default:
|
||||||
return '';
|
return '';
|
||||||
}
|
}
|
||||||
|
@ -385,6 +390,7 @@ class LicenseHelper {
|
||||||
|
|
||||||
Future<void> setByKey(final List<String> key, final String display) async {
|
Future<void> setByKey(final List<String> key, final String display) async {
|
||||||
for (var element in key) {
|
for (var element in key) {
|
||||||
|
log('setByKey($element, $display)');
|
||||||
await s(element, {
|
await s(element, {
|
||||||
'display': display,
|
'display': display,
|
||||||
'expirationDate': '',
|
'expirationDate': '',
|
||||||
|
@ -394,12 +400,21 @@ class LicenseHelper {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Future<bool> isNewVersion() async {
|
||||||
|
var response = await DatabaseStorage.database.query(tableLicense, where: 'key = ?', whereArgs: [KeychainStorageKey.isNewVersion.value], columns: ['display']);
|
||||||
|
if (response.isEmpty) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
log('isNewVersion(): ${response.first['display']}');
|
||||||
|
return response.first['display'] == 'true';
|
||||||
|
}
|
||||||
|
|
||||||
Future<String?> g(String key) async {
|
Future<String?> g(String key) async {
|
||||||
var response = await DatabaseStorage.database.query(tableLicense, where: 'key = ?', whereArgs: [key], columns: ['display']);
|
var response = await DatabaseStorage.database.query(tableLicense, where: 'key = ?', whereArgs: [key]);
|
||||||
if (response.isEmpty) {
|
if (response.isEmpty) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
return response.first['display'].toString();
|
return response.first.toString();
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<void> s<T>(String key, T value) async {
|
Future<void> s<T>(String key, T value) async {
|
||||||
|
|
|
@ -19,19 +19,42 @@ class LicenseService {
|
||||||
|
|
||||||
Stream<List<dynamic>> get licenseStream => _licenseSubject.stream;
|
Stream<List<dynamic>> get licenseStream => _licenseSubject.stream;
|
||||||
|
|
||||||
|
Future<void> processLicense() async {
|
||||||
|
if (body['key'] == Module.pets.value && body['display'] == 'VISIVEL') {
|
||||||
|
await LicenseHelper().s(Module.petsHistory.value, body);
|
||||||
|
}
|
||||||
|
final bool isAboutProperty = AboutPropertyModules.values.contains(body['key']);
|
||||||
|
final bool isVisible = body['display'] == 'VISIVEL';
|
||||||
|
log('contains () => ${body['key']} - $isAboutProperty');
|
||||||
|
if (isAboutProperty && isVisible) {
|
||||||
|
await LicenseHelper().s(Module.aboutProperty.value, body);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
Future<void> cleanLicense() async {
|
Future<void> cleanLicense() async {
|
||||||
_licenseSubject.add([]);
|
_licenseSubject.add([]);
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<void> setupLicense(Database database) async {
|
Future<void> setupLicense(Database database, bool isNewVersion) async {
|
||||||
|
log('(B) => license');
|
||||||
|
|
||||||
final List<String> inactiveModuleKey = InactiveModuleKey.values.map((e) => e.value).toList();
|
final List<String> inactiveModuleKey = InactiveModuleKey.values.map((e) => e.value).toList();
|
||||||
final List<String> activeModuleKey = ActiveModuleKey.values.map((e) => e.value).toList();
|
final List<String> activeModuleKey = ActiveModuleKey.values.map((e) => e.value).toList();
|
||||||
|
final List<String> disabledModuleKey = DisabledModuleKey.values.map((e) => e.value).toList();
|
||||||
|
|
||||||
await LicenseHelper().setByKey(inactiveModuleKey, 'INVISIVEL');
|
await LicenseHelper().setByKey(inactiveModuleKey, 'INVISIVEL');
|
||||||
await LicenseHelper().setByKey(activeModuleKey, 'VISIVEL');
|
await LicenseHelper().setByKey(activeModuleKey, 'VISIVEL');
|
||||||
|
if (isNewVersion == true) {
|
||||||
|
await LicenseHelper().setByKey(disabledModuleKey, 'VISIVEL');
|
||||||
|
await LicenseHelper().setByKey([Module.aboutProperty.value], 'VISIVEL');
|
||||||
|
} else {
|
||||||
|
await LicenseHelper().setByKey(disabledModuleKey, 'DESABILITADO');
|
||||||
|
}
|
||||||
_licenseSubject.add([...activeModuleKey]);
|
_licenseSubject.add([...activeModuleKey]);
|
||||||
}
|
}
|
||||||
|
|
||||||
Future<bool> fetchLicenses() async {
|
Future<bool> fetchLicenses(bool isNewVersion) async {
|
||||||
|
log('(A) => license');
|
||||||
try {
|
try {
|
||||||
log('Obtendo licenças...');
|
log('Obtendo licenças...');
|
||||||
final response = await PhpGroup.getLicense();
|
final response = await PhpGroup.getLicense();
|
||||||
|
@ -49,7 +72,7 @@ class LicenseService {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (responseBody == []) {
|
if (responseBody == []) {
|
||||||
await setupLicense(DatabaseStorage.database);
|
await setupLicense(DatabaseStorage.database, isNewVersion);
|
||||||
_licenseSubject.add([]);
|
_licenseSubject.add([]);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -63,7 +86,7 @@ class LicenseService {
|
||||||
return true;
|
return true;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
log('Erro ao obter licenças: $e');
|
log('Erro ao obter licenças: $e');
|
||||||
await setupLicense(DatabaseStorage.database);
|
await setupLicense(DatabaseStorage.database, isNewVersion);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -73,16 +96,8 @@ class LicenseService {
|
||||||
}
|
}
|
||||||
|
|
||||||
static Future<void> _saveModule(final dynamic body) async {
|
static Future<void> _saveModule(final dynamic body) async {
|
||||||
if (body is Map<String, dynamic>) {
|
if (body is! Map<String, dynamic>) return;
|
||||||
log('Salvando módulo: ${body.toString()}');
|
log('Salvando módulo: ${body.toString()}');
|
||||||
await LicenseHelper().s(body['key'], body);
|
await LicenseHelper().s(body['key'], body);
|
||||||
log('body[key]: ${body['key']}');
|
|
||||||
if (body['key'] == Module.pets.value) if (body['display'] == 'VISIVEL') {
|
|
||||||
await LicenseHelper().s(Module.petsHistory.value, body);
|
|
||||||
}
|
|
||||||
if (AboutPropertyModules.values.any((e) => e.value == body['key']) && body['display'] == 'VISIVEL') {
|
|
||||||
await LicenseHelper().s(Module.aboutProperty.value, body);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -153,13 +153,11 @@ class LocalizationService {
|
||||||
return false;
|
return false;
|
||||||
} else {
|
} else {
|
||||||
final bool isNewVersion = await _updateStorageUtil(response.jsonBody);
|
final bool isNewVersion = await _updateStorageUtil(response.jsonBody);
|
||||||
|
await LicenseService().setupLicense(DatabaseStorage.database, isNewVersion);
|
||||||
if (isNewVersion) {
|
if (isNewVersion) {
|
||||||
return await LicenseService().fetchLicenses();
|
log('(A) => isNewVersion: $isNewVersion');
|
||||||
} else {
|
return await LicenseService().fetchLicenses(isNewVersion);
|
||||||
await LicenseService().setupLicense(DatabaseStorage.database);
|
|
||||||
}
|
}
|
||||||
log('() => isNewVersion: $isNewVersion');
|
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
} catch (e, s) {
|
} catch (e, s) {
|
||||||
|
|
Loading…
Reference in New Issue