diff --git a/.metadata b/.metadata index faf7aba..9c3a509 100644 --- a/.metadata +++ b/.metadata @@ -4,7 +4,7 @@ # This file should be version controlled and should not be manually edited. version: - revision: "8495dee1fd4aacbe9de707e7581203232f591b2f" + revision: "d8a9f9a52e5af486f80d932e838ee93861ffd863" channel: "stable" project_type: app @@ -13,17 +13,11 @@ project_type: app migration: platforms: - platform: root - create_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f - base_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f + create_revision: d8a9f9a52e5af486f80d932e838ee93861ffd863 + base_revision: d8a9f9a52e5af486f80d932e838ee93861ffd863 - platform: android - create_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f - base_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f - - platform: ios - create_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f - base_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f - - platform: macos - create_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f - base_revision: 8495dee1fd4aacbe9de707e7581203232f591b2f + create_revision: d8a9f9a52e5af486f80d932e838ee93861ffd863 + base_revision: d8a9f9a52e5af486f80d932e838ee93861ffd863 # User provided section diff --git a/android/app/src/main/java/io/flutter/plugins/facediscern/database/DatabaseHelper.java b/android/app/src/main/java/io/flutter/plugins/facediscern/database/DatabaseHelper.java index 75b48d8..07ed681 100644 --- a/android/app/src/main/java/io/flutter/plugins/facediscern/database/DatabaseHelper.java +++ b/android/app/src/main/java/io/flutter/plugins/facediscern/database/DatabaseHelper.java @@ -15,7 +15,7 @@ public class DatabaseHelper extends SQLiteOpenHelper { private static final String DATABASE_PATH = "pj_cashier/database"; private static final String DATABASE_NAME = "cash_register.db"; - private static final int DATABASE_VERSION = 3; + private static final int DATABASE_VERSION = 5; public DatabaseHelper(Context context) { super(context, getCustomDatabasePath(context), null, DATABASE_VERSION); diff --git a/lib/common/api/wallet_api.dart b/lib/common/api/wallet_api.dart index 9bdb9ed..b15cc8a 100644 --- a/lib/common/api/wallet_api.dart +++ b/lib/common/api/wallet_api.dart @@ -1,6 +1,18 @@ import 'package:pj_supermarket_cloud/common/index.dart'; abstract class WalletApi { + /// 优惠列表 + static Future?> getDiscountsListByUserId( + dynamic params, + ) async { + final res = await HttpManage().dio.get( + "/wallet/wallet-setting/ad/get-discounts-list", + queryParameters: params, + ); + if (res.data == null) return null; + return (res.data as List).map((e) => DiscountsItem.fromJson(e)).toList(); + } + /// 支付配置 static Future getPaySetting() async { final res = await HttpManage().dio.get( diff --git a/lib/common/models/database/database_enum_models.dart b/lib/common/models/database/database_enum_models.dart index 7d5574c..a10f161 100644 --- a/lib/common/models/database/database_enum_models.dart +++ b/lib/common/models/database/database_enum_models.dart @@ -183,3 +183,16 @@ enum ProductNature implements BaseEnum { const ProductNature(this.code, this.title); } + +/// 优惠类型 +enum DiscountsType implements BaseEnum { + JZ_DISCOUNT("1", "9折优惠"), + ; + + @override + final String code; + @override + final String title; + + const DiscountsType(this.code, this.title); +} diff --git a/lib/common/services/database/database.dart b/lib/common/services/database/database.dart index 2617ae7..dca2e66 100644 --- a/lib/common/services/database/database.dart +++ b/lib/common/services/database/database.dart @@ -1,7 +1,9 @@ import 'dart:async'; +import 'dart:io'; import 'package:floor/floor.dart'; import 'package:pj_supermarket_cloud/common/index.dart'; +import 'package:pj_supermarket_cloud/common/services/database/databaseMigration.dart'; import 'package:sqflite/sqflite.dart' as sqflite; @@ -32,11 +34,13 @@ const typeConverters = [ SysTypeConverter, PrintStatusConverter, SupermarketNatureConverter, + DiscountsTypeConverter, + ListDiscountsConverter, ListIntConverter, BoolConverter, ]; -@Database(version: 3, entities: entities) +@Database(version: 5, entities: entities) @TypeConverters(typeConverters) abstract class AppDatabase extends FloorDatabase { BroadcastDao get getBroadcastDao; @@ -53,130 +57,11 @@ abstract class AppDatabase extends FloorDatabase { FaceDao get getFaceDao; SettingDao get getSettingDao; - // 获取数据库迁移列表 - static List _getDatabaseMigrations() { - return [ - // 从版本1到版本2的迁移:添加productNamePy字段 - Migration(1, 2, (database) async { - // 先检查列是否存在,不存在才添加 - final result = await database.rawQuery( - "PRAGMA table_info(supermarket_spu)", - ); - bool columnExists = false; - for (var column in result) { - if (column['name'] == 'productNamePy') { - columnExists = true; - break; - } - } - - if (!columnExists) { - await database.execute( - 'ALTER TABLE supermarket_spu ADD COLUMN productNamePy TEXT'); - } - }), - Migration(2, 3, (database) async { - // 如果表不存在则创建,存在则校验列并补齐缺失项 - final tables = await database.rawQuery( - "SELECT name FROM sqlite_master WHERE type='table' AND name='order_hold_bill'", - ); - if (tables.isEmpty) { - await database.execute(''' - CREATE TABLE IF NOT EXISTS order_hold_bill ( - id INTEGER PRIMARY KEY AUTOINCREMENT, - sysType TEXT NOT NULL, - carListJson TEXT, - userJson TEXT, - price INTEGER DEFAULT 0 NOT NULL, - extraPrice INTEGER DEFAULT 0 NOT NULL, - payPrice INTEGER DEFAULT 0 NOT NULL, - createTime TEXT NOT NULL - ) - '''); - await database.execute( - "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_sysType ON order_hold_bill(sysType)", - ); - await database.execute( - "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_createTime ON order_hold_bill(createTime)", - ); - } else { - final columns = - await database.rawQuery("PRAGMA table_info(order_hold_bill)"); - bool hasSysType = false; - bool hasCarListJson = false; - bool hasOrderListJson = false; - bool hasUserJson = false; - bool hasPrice = false; - bool hasExtraPrice = false; - bool hasPayPrice = false; - bool hasCreateTime = false; - for (final c in columns) { - final name = c['name']; - if (name == 'sysType') hasSysType = true; - if (name == 'carListJson') hasCarListJson = true; - if (name == 'orderListJson') hasOrderListJson = true; - if (name == 'userJson') hasUserJson = true; - if (name == 'price') hasPrice = true; - if (name == 'extraPrice') hasExtraPrice = true; - if (name == 'payPrice') hasPayPrice = true; - if (name == 'createTime') hasCreateTime = true; - } - if (!hasSysType) { - await database.execute( - 'ALTER TABLE order_hold_bill ADD COLUMN sysType TEXT', - ); - } - if (!hasCarListJson) { - await database.execute( - 'ALTER TABLE order_hold_bill ADD COLUMN carListJson TEXT', - ); - if (hasOrderListJson) { - // 旧列迁移到新列 - await database.execute( - "UPDATE order_hold_bill SET carListJson = orderListJson WHERE carListJson IS NULL", - ); - } - } - if (!hasUserJson) { - await database.execute( - 'ALTER TABLE order_hold_bill ADD COLUMN userJson TEXT', - ); - } - if (!hasPrice) { - await database.execute( - 'ALTER TABLE order_hold_bill ADD COLUMN price INTEGER DEFAULT 0 NOT NULL', - ); - } - if (!hasExtraPrice) { - await database.execute( - 'ALTER TABLE order_hold_bill ADD COLUMN extraPrice INTEGER DEFAULT 0 NOT NULL', - ); - } - if (!hasPayPrice) { - await database.execute( - 'ALTER TABLE order_hold_bill ADD COLUMN payPrice INTEGER DEFAULT 0 NOT NULL', - ); - } - if (!hasCreateTime) { - await database.execute( - 'ALTER TABLE order_hold_bill ADD COLUMN createTime TEXT DEFAULT "" NOT NULL', - ); - } - await database.execute( - "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_sysType ON order_hold_bill(sysType)", - ); - await database.execute( - "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_createTime ON order_hold_bill(createTime)", - ); - } - }), - ]; - } - static Future getDataBase() async { final dbPath = await AppFileTool.getDatabasePath(); + final name = "$dbPath/${Constants.databaseName}"; final dataBase = await $FloorAppDatabase - .databaseBuilder("$dbPath/${Constants.databaseName}") + .databaseBuilder(name) .addCallback( Callback( onCreate: (database, version) async { @@ -190,7 +75,7 @@ abstract class AppDatabase extends FloorDatabase { }, ), ) - .addMigrations(_getDatabaseMigrations()) + .addMigrations(DatabaseMigration.getDatabaseMigrations()) .build(); return dataBase; } diff --git a/lib/common/services/database/database.g.dart b/lib/common/services/database/database.g.dart index 839a290..99e9c73 100644 --- a/lib/common/services/database/database.g.dart +++ b/lib/common/services/database/database.g.dart @@ -104,7 +104,7 @@ class _$AppDatabase extends AppDatabase { Callback? callback, ]) async { final databaseOptions = sqflite.OpenDatabaseOptions( - version: 3, + version: 5, onConfigure: (database) async { await database.execute('PRAGMA foreign_keys = ON'); await callback?.onConfigure?.call(database); @@ -140,7 +140,7 @@ class _$AppDatabase extends AppDatabase { await database.execute( 'CREATE TABLE IF NOT EXISTS `print_history` (`id` INTEGER PRIMARY KEY AUTOINCREMENT, `orderId` TEXT NOT NULL, `serviceOrderId` TEXT NOT NULL, `servicePrintId` TEXT NOT NULL, `invoiceUrl` TEXT NOT NULL, `status` TEXT NOT NULL, `printTime` TEXT, `syncTime` TEXT, `createTime` TEXT NOT NULL)'); await database.execute( - 'CREATE TABLE IF NOT EXISTS `user_record` (`id` INTEGER PRIMARY KEY AUTOINCREMENT, `userId` TEXT NOT NULL, `nickname` TEXT NOT NULL, `mobile` TEXT, `avatar` TEXT, `walletCardNumber` TEXT, `walletId` TEXT, `walletTypeId` TEXT, `walletBalance` INTEGER, `canteenId` TEXT, `createTime` TEXT, `updateTime` TEXT)'); + 'CREATE TABLE IF NOT EXISTS `user_record` (`id` INTEGER PRIMARY KEY AUTOINCREMENT, `userId` TEXT NOT NULL, `nickname` TEXT NOT NULL, `mobile` TEXT, `avatar` TEXT, `walletCardNumber` TEXT, `walletId` TEXT, `walletTypeId` TEXT, `walletBalance` INTEGER, `canteenId` TEXT, `discountsList` TEXT, `discountsUpdateTime` TEXT, `createTime` TEXT, `updateTime` TEXT)'); await database.execute( 'CREATE TABLE IF NOT EXISTS `face` (`id` INTEGER PRIMARY KEY AUTOINCREMENT, `userId` TEXT NOT NULL, `sampleId` TEXT NOT NULL, `userName` TEXT NOT NULL, `deptId` TEXT, `deptName` TEXT, `imagePath` TEXT NOT NULL, `path` TEXT, `faceModel` TEXT, `createTime` TEXT, `updateTime` TEXT)'); await database.execute( @@ -1504,6 +1504,10 @@ class _$UserDao extends UserDao { 'walletTypeId': item.walletTypeId, 'walletBalance': item.walletBalance, 'canteenId': item.canteenId, + 'discountsList': + _listDiscountsConverter.encode(item.discountsList), + 'discountsUpdateTime': + _dateTimeEmptyConverter.encode(item.discountsUpdateTime), 'createTime': _dateTimeEmptyConverter.encode(item.createTime), 'updateTime': _dateTimeEmptyConverter.encode(item.updateTime) }), @@ -1522,6 +1526,10 @@ class _$UserDao extends UserDao { 'walletTypeId': item.walletTypeId, 'walletBalance': item.walletBalance, 'canteenId': item.canteenId, + 'discountsList': + _listDiscountsConverter.encode(item.discountsList), + 'discountsUpdateTime': + _dateTimeEmptyConverter.encode(item.discountsUpdateTime), 'createTime': _dateTimeEmptyConverter.encode(item.createTime), 'updateTime': _dateTimeEmptyConverter.encode(item.updateTime) }), @@ -1540,6 +1548,10 @@ class _$UserDao extends UserDao { 'walletTypeId': item.walletTypeId, 'walletBalance': item.walletBalance, 'canteenId': item.canteenId, + 'discountsList': + _listDiscountsConverter.encode(item.discountsList), + 'discountsUpdateTime': + _dateTimeEmptyConverter.encode(item.discountsUpdateTime), 'createTime': _dateTimeEmptyConverter.encode(item.createTime), 'updateTime': _dateTimeEmptyConverter.encode(item.updateTime) }); @@ -1946,5 +1958,7 @@ final _orderPayTypeConverter = OrderPayTypeConverter(); final _sysTypeConverter = SysTypeConverter(); final _printStatusConverter = PrintStatusConverter(); final _supermarketNatureConverter = SupermarketNatureConverter(); +final _discountsTypeConverter = DiscountsTypeConverter(); +final _listDiscountsConverter = ListDiscountsConverter(); final _listIntConverter = ListIntConverter(); final _boolConverter = BoolConverter(); diff --git a/lib/common/services/database/databaseMigration.dart b/lib/common/services/database/databaseMigration.dart new file mode 100644 index 0000000..26d397d --- /dev/null +++ b/lib/common/services/database/databaseMigration.dart @@ -0,0 +1,157 @@ +import 'package:floor/floor.dart'; + +abstract class DatabaseMigration { + /// 从版本1到版本2的迁移:添加productNamePy字段 + static Migration migration1To2 = Migration(1, 2, (database) async { + // 先检查列是否存在,不存在才添加 + final result = await database.rawQuery( + "PRAGMA table_info(supermarket_spu)", + ); + bool columnExists = false; + for (var column in result) { + if (column['name'] == 'productNamePy') { + columnExists = true; + break; + } + } + if (!columnExists) { + await database + .execute('ALTER TABLE supermarket_spu ADD COLUMN productNamePy TEXT'); + } + }); + + /// 从版本2到版本3的迁移:添加orderListJson字段 + static Migration migration2To3 = Migration(2, 3, (database) async { + // 如果表不存在则创建,存在则校验列并补齐缺失项 + final tables = await database.rawQuery( + "SELECT name FROM sqlite_master WHERE type='table' AND name='order_hold_bill'", + ); + if (tables.isEmpty) { + await database.execute(''' + CREATE TABLE IF NOT EXISTS order_hold_bill ( + id INTEGER PRIMARY KEY AUTOINCREMENT, + sysType TEXT NOT NULL, + carListJson TEXT, + userJson TEXT, + price INTEGER DEFAULT 0 NOT NULL, + extraPrice INTEGER DEFAULT 0 NOT NULL, + payPrice INTEGER DEFAULT 0 NOT NULL, + createTime TEXT NOT NULL + ) + '''); + await database.execute( + "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_sysType ON order_hold_bill(sysType)", + ); + await database.execute( + "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_createTime ON order_hold_bill(createTime)", + ); + } else { + final columns = + await database.rawQuery("PRAGMA table_info(order_hold_bill)"); + bool hasSysType = false; + bool hasCarListJson = false; + bool hasOrderListJson = false; + bool hasUserJson = false; + bool hasPrice = false; + bool hasExtraPrice = false; + bool hasPayPrice = false; + bool hasCreateTime = false; + for (final c in columns) { + final name = c['name']; + if (name == 'sysType') hasSysType = true; + if (name == 'carListJson') hasCarListJson = true; + if (name == 'orderListJson') hasOrderListJson = true; + if (name == 'userJson') hasUserJson = true; + if (name == 'price') hasPrice = true; + if (name == 'extraPrice') hasExtraPrice = true; + if (name == 'payPrice') hasPayPrice = true; + if (name == 'createTime') hasCreateTime = true; + } + if (!hasSysType) { + await database.execute( + 'ALTER TABLE order_hold_bill ADD COLUMN sysType TEXT', + ); + } + if (!hasCarListJson) { + await database.execute( + 'ALTER TABLE order_hold_bill ADD COLUMN carListJson TEXT', + ); + if (hasOrderListJson) { + // 旧列迁移到新列 + await database.execute( + "UPDATE order_hold_bill SET carListJson = orderListJson WHERE carListJson IS NULL", + ); + } + } + if (!hasUserJson) { + await database.execute( + 'ALTER TABLE order_hold_bill ADD COLUMN userJson TEXT', + ); + } + if (!hasPrice) { + await database.execute( + 'ALTER TABLE order_hold_bill ADD COLUMN price INTEGER DEFAULT 0 NOT NULL', + ); + } + if (!hasExtraPrice) { + await database.execute( + 'ALTER TABLE order_hold_bill ADD COLUMN extraPrice INTEGER DEFAULT 0 NOT NULL', + ); + } + if (!hasPayPrice) { + await database.execute( + 'ALTER TABLE order_hold_bill ADD COLUMN payPrice INTEGER DEFAULT 0 NOT NULL', + ); + } + if (!hasCreateTime) { + await database.execute( + 'ALTER TABLE order_hold_bill ADD COLUMN createTime TEXT DEFAULT "" NOT NULL', + ); + } + await database.execute( + "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_sysType ON order_hold_bill(sysType)", + ); + await database.execute( + "CREATE INDEX IF NOT EXISTS idx_order_hold_bill_createTime ON order_hold_bill(createTime)", + ); + } + }); + + /// 从版本3到版本4的迁移:添加为user_record表添加discountsList字段 + static Migration migration3To4 = Migration(3, 4, (database) async { + final columns = await database.rawQuery("PRAGMA table_info(user_record)"); + bool hasDiscountsList = false; + for (final c in columns) { + if (c['name'] == 'discountsList') { + hasDiscountsList = true; + break; + } + } + if (!hasDiscountsList) { + await database + .execute("ALTER TABLE user_record ADD COLUMN discountsList TEXT"); + await database.execute( + "UPDATE user_record SET discountsList = '[]' WHERE discountsList IS NULL", + ); + } + }); + + static Migration migration4To5 = Migration(4, 5, (database) async { + final columns = await database.rawQuery("PRAGMA table_info(user_record)"); + bool hasDiscountsUpdateTime = false; + for (final c in columns) { + if (c['name'] == 'discountsUpdateTime') { + hasDiscountsUpdateTime = true; + break; + } + } + if (!hasDiscountsUpdateTime) { + await database.execute( + "ALTER TABLE user_record ADD COLUMN discountsUpdateTime TEXT"); + } + }); + + static List getDatabaseMigrations() { + return [migration1To2, migration2To3, migration3To4]; + } +} diff --git a/lib/common/services/database/entity/user_entity.dart b/lib/common/services/database/entity/user_entity.dart index 92767bc..1e92695 100644 --- a/lib/common/services/database/entity/user_entity.dart +++ b/lib/common/services/database/entity/user_entity.dart @@ -1,9 +1,62 @@ +import 'package:common_utils/common_utils.dart'; import 'package:equatable/equatable.dart'; import 'package:floor/floor.dart'; import 'package:json_annotation/json_annotation.dart'; +import 'package:pj_supermarket_cloud/common/index.dart'; +import 'package:pj_supermarket_cloud/common/models/index.dart'; part 'user_entity.g.dart'; +// 优惠 +@JsonSerializable() +class DiscountsItem { + /// 优惠活动名称 + String name; + + /// 用餐时间段类型 + @JsonKey( + fromJson: JsonTool.stringToProductHourType, + toJson: JsonTool.productHourTypeToString, + ) + ProductHourType? hourType; + + /// 优惠类型 + @JsonKey( + fromJson: JsonTool.stringToDiscountsType, + toJson: JsonTool.discountsTypeToString, + ) + DiscountsType? type; + + /// 基础金额(分),超过了这个基数`extraPer`就生效 + int basePrice; + + /// 打折(8折->0.8) + double? extraPer; + + DiscountsItem({ + required this.name, + required this.hourType, + required this.type, + required this.basePrice, + required this.extraPer, + }); + + /// 计算优惠后的价格 + /// [totalPrice] 总金额(分) + /// [return] 优惠的价格(分) + int computedDiscountsExtraPrice(int totalPrice) { + if (totalPrice <= basePrice) return 0; + final rate = extraPer ?? 1.0; + if (rate == 1.0) return 0; + return (totalPrice * (rate - 1)).round(); + } + + factory DiscountsItem.fromJson(Map json) => + _$DiscountsItemFromJson(json); + + Map toJson() => _$DiscountsItemToJson(this); +} + @JsonSerializable() @Entity(tableName: "user_record") class UserEntity extends Equatable { @@ -38,6 +91,12 @@ class UserEntity extends Equatable { /// 用户所属的商户id(主要用于机器的离线模式) String? canteenId; + /// 优惠活动 + List? discountsList; + + /// 优惠活动更新时间 + DateTime? discountsUpdateTime; + /// 创建时间 DateTime? createTime; @@ -59,6 +118,28 @@ class UserEntity extends Equatable { this.updateTime, }); + /// 计算优惠后的价格 + /// [totalPrice] 总金额(分) + /// [return] 优惠的价格(分) + int computedDiscountsPrice(int totalPrice) { + if (ObjectUtil.isEmpty(discountsList)) { + return 0; + } + var discountsPrice = 0; + for (final item in discountsList!) { + discountsPrice += item.computedDiscountsExtraPrice(totalPrice); + } + return discountsPrice; + } + + /// 根据`discountsUpdateTime`来计算,最小更新时间30s + bool isUpdateDiscounts() { + if (ObjectUtil.isEmpty(discountsUpdateTime)) { + return true; + } + return DateTime.now().difference(discountsUpdateTime!).inSeconds > 30; + } + factory UserEntity.fromJson(Map json) => _$UserEntityFromJson(json); diff --git a/lib/common/services/database/entity/user_entity.g.dart b/lib/common/services/database/entity/user_entity.g.dart index 2cb1103..e8f1df2 100644 --- a/lib/common/services/database/entity/user_entity.g.dart +++ b/lib/common/services/database/entity/user_entity.g.dart @@ -6,6 +6,24 @@ part of 'user_entity.dart'; // JsonSerializableGenerator // ************************************************************************** +DiscountsItem _$DiscountsItemFromJson(Map json) => + DiscountsItem( + name: json['name'] as String, + hourType: JsonTool.stringToProductHourType(json['hourType'] as String?), + type: JsonTool.stringToDiscountsType(json['type'] as String?), + basePrice: (json['basePrice'] as num).toInt(), + extraPer: (json['extraPer'] as num?)?.toDouble(), + ); + +Map _$DiscountsItemToJson(DiscountsItem instance) => + { + 'name': instance.name, + 'hourType': JsonTool.productHourTypeToString(instance.hourType), + 'type': JsonTool.discountsTypeToString(instance.type), + 'basePrice': instance.basePrice, + 'extraPer': instance.extraPer, + }; + UserEntity _$UserEntityFromJson(Map json) => UserEntity( id: (json['id'] as num?)?.toInt(), userId: json['userId'] as String, @@ -23,7 +41,13 @@ UserEntity _$UserEntityFromJson(Map json) => UserEntity( updateTime: json['updateTime'] == null ? null : DateTime.parse(json['updateTime'] as String), - ); + ) + ..discountsList = (json['discountsList'] as List?) + ?.map((e) => DiscountsItem.fromJson(e as Map)) + .toList() + ..discountsUpdateTime = json['discountsUpdateTime'] == null + ? null + : DateTime.parse(json['discountsUpdateTime'] as String); Map _$UserEntityToJson(UserEntity instance) => { @@ -37,6 +61,8 @@ Map _$UserEntityToJson(UserEntity instance) => 'walletTypeId': instance.walletTypeId, 'walletBalance': instance.walletBalance, 'canteenId': instance.canteenId, + 'discountsList': instance.discountsList, + 'discountsUpdateTime': instance.discountsUpdateTime?.toIso8601String(), 'createTime': instance.createTime?.toIso8601String(), 'updateTime': instance.updateTime?.toIso8601String(), }; diff --git a/lib/common/services/database/type_converter/type_converter.dart b/lib/common/services/database/type_converter/type_converter.dart index 4d5465c..2ef3dda 100644 --- a/lib/common/services/database/type_converter/type_converter.dart +++ b/lib/common/services/database/type_converter/type_converter.dart @@ -119,6 +119,18 @@ class SupermarketNatureConverter extends TypeConverter { } } +class DiscountsTypeConverter extends TypeConverter { + @override + DiscountsType decode(String databaseValue) { + return DiscountsType.values.byName(databaseValue); + } + + @override + String encode(DiscountsType value) { + return value.name; + } +} + class ListIntConverter extends TypeConverter?, String> { @override List decode(String databaseValue) { @@ -137,6 +149,28 @@ class ListIntConverter extends TypeConverter?, String> { } } +class ListDiscountsConverter + extends TypeConverter?, String> { + @override + List decode(String databaseValue) { + if (databaseValue.isEmpty) { + return []; + } + return json + .decode(databaseValue) + .map((e) => DiscountsItem.fromJson(e)) + .toList(); + } + + @override + String encode(List? value) { + if (ObjectUtil.isEmptyList(value)) { + return ''; + } + return json.encode(value); + } +} + class BoolConverter extends TypeConverter { @override bool decode(int databaseValue) { diff --git a/lib/common/utils/discounts/discounts_tool.dart b/lib/common/utils/discounts/discounts_tool.dart new file mode 100644 index 0000000..08c6d87 --- /dev/null +++ b/lib/common/utils/discounts/discounts_tool.dart @@ -0,0 +1,54 @@ +import 'package:common_utils/common_utils.dart'; +import 'package:get/get.dart'; +import 'package:pj_supermarket_cloud/common/index.dart'; + +class DiscountsTool { + /// 更新用户优惠列表 + static Future?> updateUserDiscountsList({ + required String userId, + }) async { + final sysSetting = await AppSettingTool.getSysSetting(); + final params = { + "userId": userId, + "hardId": sysSetting.serviceId, + }; + final discountsRes = await WalletApi.getDiscountsListByUserId(params); + if (ObjectUtil.isEmpty(discountsRes)) return null; + final app = Get.find(); + final userDao = app.dataBase.getUserDao; + // 查询用户表 + final userEntity = await userDao.findByUserId(userId); + if (ObjectUtil.isEmpty(userEntity)) return discountsRes; + // 能更新优惠(防止同一个用户频繁更新) + if (userEntity!.isUpdateDiscounts()) { + userEntity.discountsList = discountsRes; + userEntity.discountsUpdateTime = DateTime.now(); + await userDao.edit(userEntity); + } + // 更新到用户表 + return discountsRes; + } + + /// 计算额外增加的金额 + /// [totalPrice] 总金额(分) + /// [discountsItem] 优惠项 + /// [return] 额外增加的金额(分) + static Future computedExtraPrice({ + required String userId, + required int totalPrice, + required String hourType, + }) async { + var discountsItems = await updateUserDiscountsList(userId: userId); + discountsItems = discountsItems + ?.where((element) => element.hourType?.code == hourType) + .toList(); + if (ObjectUtil.isEmpty(discountsItems)) return 0; + var extraPrice = 0; + for (final item in discountsItems!) { + final extraPer = item.extraPer; + if (extraPer == null || extraPer <= 1.0) continue; + extraPrice += item.computedDiscountsExtraPrice(totalPrice); + } + return extraPrice; + } +} diff --git a/lib/common/utils/index.dart b/lib/common/utils/index.dart index bf12768..99d2483 100644 --- a/lib/common/utils/index.dart +++ b/lib/common/utils/index.dart @@ -12,6 +12,8 @@ export './app/app_setting_tool.dart'; export './app/app_sys_tool.dart'; export './app/app_user_tool.dart'; +export './discounts/discounts_tool.dart'; + export './json/json_tool.dart'; export './keyboard/keyboard_tool.dart'; diff --git a/lib/common/utils/json/json_tool.dart b/lib/common/utils/json/json_tool.dart index 9327b04..274888f 100644 --- a/lib/common/utils/json/json_tool.dart +++ b/lib/common/utils/json/json_tool.dart @@ -56,4 +56,22 @@ abstract class JsonTool { if (value == null) return null; return value.toString(); } + + static DiscountsType? stringToDiscountsType(String? value) { + return DiscountsType.values.fromCode(value); + } + + static String? discountsTypeToString(DiscountsType? value) { + if (value == null) return null; + return value.toString(); + } + + static ProductHourType? stringToProductHourType(String? value) { + return ProductHourType.values.fromCode(value); + } + + static String? productHourTypeToString(ProductHourType? value) { + if (value == null) return null; + return value.toString(); + } } diff --git a/lib/common/values/constants.dart b/lib/common/values/constants.dart index dd89b57..f67f41b 100644 --- a/lib/common/values/constants.dart +++ b/lib/common/values/constants.dart @@ -10,9 +10,9 @@ class Constants { static const pwdEncKey = 'pigxpigxpigxpigx'; /// 服务 url 线上 - static const apiUrl = 'https://stgl.pj.gov.cn/api'; + // static const apiUrl = 'https://stgl.pj.gov.cn/api'; - // static const apiUrl = 'http://192.168.101.104:9999'; + static const apiUrl = 'https://rj4jv5rwqs.by.takin.cc'; /// 静态资源 url static const ossUrl = apiUrl; diff --git a/lib/common/widgets/user/user_info.dart b/lib/common/widgets/user/user_info.dart index ca96459..055108f 100644 --- a/lib/common/widgets/user/user_info.dart +++ b/lib/common/widgets/user/user_info.dart @@ -39,5 +39,21 @@ Widget appUserInfo( appPrice(context, balance), ].toRow().offstage(offstage: !visibleMoney), ].toColumn(crossAxisAlignment: CrossAxisAlignment.start), - ].toRow(mainAxisAlignment: MainAxisAlignment.center).width(double.infinity); + [ + FButton( + label: Text( + "识别", + style: theme.typography.base.copyWith( + color: theme.colorScheme.primary, + ), + ), + style: FButtonStyle.outline, + onPress: () {}, + ).width(100.w).height(50.w).offstage(offstage: true), + ].toColumn(), + ] + .toRow( + mainAxisAlignment: MainAxisAlignment.center, + ) + .width(double.infinity); } diff --git a/lib/pages/canteen_product/controller.dart b/lib/pages/canteen_product/controller.dart index f95e7e4..b275f68 100644 --- a/lib/pages/canteen_product/controller.dart +++ b/lib/pages/canteen_product/controller.dart @@ -268,17 +268,19 @@ class CanteenProductController extends GetxController with OrderMixin { // 计算额外的价格 Future _computedAmountMealPrice() async { - // final price = await getAmountMealPrice( - // price: totalPrice.value, + var extraPrice = 0; + // final extraPrice = await _getMchRulePrice( + // totalPrice.value, + // userCanteenId: payUser.value?.canteenId, // ); - // if (ObjectUtil.isNotEmpty(price)) { - // amountMealPrice.value = int.parse(price!.toString()); - // sendSubScreen(); - // } - final extraPrice = await _getMchRulePrice( - totalPrice.value, - userCanteenId: payUser.value?.canteenId, - ); + if (ObjectUtil.isNotEmpty(payUser.value?.userId) && + ObjectUtil.isNotEmpty(hourType.value)) { + extraPrice = await DiscountsTool.computedExtraPrice( + userId: payUser.value?.userId ?? "", + totalPrice: totalPrice.value, + hourType: hourType.value.code, + ); + } if (extraPrice != 0) { amountMealPrice.value = extraPrice; sendSubScreen(); diff --git a/lib/pages/setting/widgets/setting_baseInfo.dart b/lib/pages/setting/widgets/setting_baseInfo.dart index 77d0081..1f02db1 100644 --- a/lib/pages/setting/widgets/setting_baseInfo.dart +++ b/lib/pages/setting/widgets/setting_baseInfo.dart @@ -21,10 +21,10 @@ Future _bindServiceDialog(BuildContext context, SysSetting sys) async { // 正式环境-测试 // uniqueCodeC.text = "1896157295523049473"; // 正式环境-新县府02-主要测试 - uniqueCodeC.text = "1887466308336488450"; + // uniqueCodeC.text = "1887466308336488450"; /// 测试环境-测试设备-(食堂主要测试) - // uniqueCodeC.text = "1877592554489143298"; + uniqueCodeC.text = "1877592554489143298"; // 测试少年宫测试 // uniqueCodeC.text = "1927932460185784321"; // 测试环境-食堂-浦阳