Files
umbrix/lib/data/local/dao/profiles_dao.dart

127 lines
4.0 KiB
Dart
Raw Normal View History

2023-07-06 17:18:41 +03:30
import 'package:drift/drift.dart';
import 'package:hiddify/data/local/data_mappers.dart';
import 'package:hiddify/data/local/database.dart';
import 'package:hiddify/data/local/tables.dart';
2023-07-26 16:42:31 +03:30
import 'package:hiddify/domain/enums.dart';
2023-07-06 17:18:41 +03:30
import 'package:hiddify/domain/profiles/profiles.dart';
import 'package:hiddify/utils/utils.dart';
part 'profiles_dao.g.dart';
2023-07-26 16:42:31 +03:30
Map<SortMode, OrderingMode> orderMap = {
SortMode.ascending: OrderingMode.asc,
2023-09-06 21:03:43 +03:30
SortMode.descending: OrderingMode.desc,
2023-07-26 16:42:31 +03:30
};
2023-07-06 17:18:41 +03:30
@DriftAccessor(tables: [ProfileEntries])
class ProfilesDao extends DatabaseAccessor<AppDatabase>
with _$ProfilesDaoMixin, InfraLogger {
ProfilesDao(super.db);
Future<Profile?> getById(String id) async {
return (profileEntries.select()..where((tbl) => tbl.id.equals(id)))
.map(ProfileMapper.fromEntry)
.getSingleOrNull();
}
Future<Profile?> getProfileByUrl(String url) async {
return (select(profileEntries)..where((tbl) => tbl.url.like('%$url%')))
.map(ProfileMapper.fromEntry)
.get()
.then((value) => value.firstOrNull);
}
2023-07-06 17:18:41 +03:30
Stream<Profile?> watchActiveProfile() {
return (profileEntries.select()..where((tbl) => tbl.active.equals(true)))
.map(ProfileMapper.fromEntry)
.watchSingleOrNull();
}
Stream<int> watchProfileCount() {
final count = profileEntries.id.count();
return (profileEntries.selectOnly()..addColumns([count]))
.map((exp) => exp.read(count)!)
.watchSingle();
}
2023-07-26 16:42:31 +03:30
Stream<List<Profile>> watchAll({
ProfilesSort sort = ProfilesSort.lastUpdate,
SortMode mode = SortMode.ascending,
}) {
2023-07-06 17:18:41 +03:30
return (profileEntries.select()
..orderBy(
2023-07-26 16:42:31 +03:30
[
2023-07-26 20:00:17 +03:30
(tbl) {
final trafficRatio = (tbl.download + tbl.upload) / tbl.total;
final isExpired =
tbl.expire.isSmallerOrEqualValue(DateTime.now());
return OrderingTerm(
expression: (trafficRatio.isNull() |
trafficRatio.isSmallerThanValue(1)) &
(isExpired.isNull() | isExpired.equals(false)),
mode: OrderingMode.desc,
);
},
2023-07-26 16:42:31 +03:30
switch (sort) {
ProfilesSort.name => (tbl) => OrderingTerm(
expression: tbl.name,
mode: orderMap[mode]!,
),
2023-07-26 20:00:17 +03:30
ProfilesSort.lastUpdate => (tbl) => OrderingTerm(
2023-07-26 16:42:31 +03:30
expression: tbl.lastUpdate,
mode: orderMap[mode]!,
),
2023-07-26 20:00:17 +03:30
},
2023-07-26 16:42:31 +03:30
],
2023-07-06 17:18:41 +03:30
))
.map(ProfileMapper.fromEntry)
.watch();
}
Future<void> create(Profile profile) async {
await transaction(
() async {
if (profile.active) {
await (update(profileEntries)
..where((tbl) => tbl.id.isNotValue(profile.id)))
.write(const ProfileEntriesCompanion(active: Value(false)));
}
await into(profileEntries).insert(profile.toCompanion());
},
);
}
Future<void> edit(Profile patch) async {
await transaction(
() async {
if (patch.active) {
await (update(profileEntries)
..where((tbl) => tbl.id.isNotValue(patch.id)))
.write(const ProfileEntriesCompanion(active: Value(false)));
}
2023-07-06 17:18:41 +03:30
await (update(profileEntries)..where((tbl) => tbl.id.equals(patch.id)))
.write(patch.toCompanion());
},
);
}
Future<void> setAsActive(String id) async {
await transaction(
() async {
await (update(profileEntries)..where((tbl) => tbl.id.isNotValue(id)))
.write(const ProfileEntriesCompanion(active: Value(false)));
await (update(profileEntries)..where((tbl) => tbl.id.equals(id)))
.write(const ProfileEntriesCompanion(active: Value(true)));
},
);
}
Future<void> removeById(String id) async {
await transaction(
() async {
await (delete(profileEntries)..where((tbl) => tbl.id.equals(id))).go();
},
);
}
}