import 'dart:convert'; import 'dart:io'; import 'package:archive/archive_io.dart'; import 'package:jiffy/jiffy.dart'; import 'package:myshelf/models/dtinterval.dart'; import 'package:supabase/supabase.dart'; final Map tables = { "secondprgtype.txt": "aclegs_csv", "ExportPGRGPNmois.txt": "pnlegs_csv", "exportPGRGPN.txt": "pnlegs_csv", "exportlicence.txt": "licences_csv", }; final Map> headers = { "secondprgtype.txt": [ "leg_no", "fn_carrier", "fn_number", "fn_suffix", "day_of_origin", "ac_owner", "ac_subtype", "ac_version", "ac_registration", "dep_ap_actual", "dep_ap_sched", "dep_dt_est", "dep_sched_dt", "arr_ap_actual", "arr_ap_sched", "arr_dt_est", "arr_sched_dt", "slot_time_actual", "leg_type", "status", "employer_cockpit", "employer_cabin", "cycles", "delay_code_01", "delay_code_02", "delay_code_03", "delay_code_04", "delay_time_01", "delay_time_02", "delay_time_03", "delay_time_04", "subdelay_code_01", "subdelay_code_02", "subdelay_code_03", "subdelay_code_04", "pax_booked_c", "pax_booked_y", "pax_booked_trs_c", "pax_booked_trs_y", "pad_booked_c", "pad_booked_y", "offblock_dt_a", "airborne_dt_a", "landing_dt_a", "onblock_dt_a", "offblock_dt_f", "airborne_dt_f", "landing_dt_f", "onblock_dt_f", "offblock_dt_m", "airborne_dt_m", "landing_dt_m", "onblock_dt_m", "eet", ], "exportPGRGPN.txt": [ "date", "tlc", "actype", "al", "fnum", "ddep", "hdep", "ddes", "hdes", "dep", "des", "label", "type", ], "ExportPGRGPNmois.txt": [ "date", "tlc", "actype", "al", "fnum", "ddep", "hdep", "ddes", "hdes", "dep", "des", "label", "type", ], "exportlicence.txt": [ "tlc", "fname", "mname", "lname", "expire", "ac", "college", "base", ], }; final Map scopes = { "secondprgtype.txt": "day_of_origin", "exportPGRGPN.txt": "date", "ExportPGRGPNmois.txt": "date", "exportlicence.txt": "tlc", }; final Map> idToRemove = { "secondprgtype.txt": ["day_of_origin"], "exportPGRGPN.txt": ["date", "tlc"], "ExportPGRGPNmois.txt": ["date", "tlc"], "exportlicence.txt": ["tlc"], }; final Map> ids = { "secondprgtype.txt": { "table": "aclegs_log", "headers": [ "day_of_origin", "dep_sched_dt", "fn_carrier", "fn_number", "dep_ap_sched", "arr_ap_sched", // "dep_ap_actual", // "arr_ap_actual" ] }, "exportPGRGPN.txt": { "table": "pnlegs_log", "headers": ["tlc", "date", "dep", "des", "al", "fnum,", "label"] }, "ExportPGRGPNmois.txt": { "table": "pnlegs_log", "headers": ["tlc", "date", "dep", "des", "al", "fnum,", "label"] }, "exportlicence.txt": { "table": "qualifs_log", "headers": ["tlc", "college", "ac", "base"] }, }; List> createListOfMaps( List headers, List> data) { // Initialize an empty list to hold the maps List> result = []; // Iterate over each row of data for (var row in data) { // Create a map for the current row Map map = {}; // Populate the map with header-value pairs for (int i = 0; i < headers.length; i++) { if (i < row.length) { // Convert each value to String? and handle null values map[headers[i]] = row[i] ?.toString(); // Use toString() to ensure it's a String or null } else { // If there's no corresponding data, set it as null map[headers[i]] = null; } } // Add the map to the result list result.add(map); } return result; } List> csv2list(String text, {bool nulling = true, bool quotes = true, bool trim = true}) { List> out = []; final lines = text.split("\n"); for (var line in lines) { final cols = line.split(",").map((String? e) { if (e != null && quotes) { e = e.replaceAll('"', ""); } if (e != null && trim) { e = e.trim(); } if (nulling) { e = (e == "") ? null : e; } return e; }).toList(); // print("${out.length}: $cols"); if (cols.isNotEmpty && cols.length > 1) out.add(cols); } return out; } class Qualif { String? tlc; String? lname; String? mname; String? fname; String? date; String? ac; String? college; String? base; Qualif({ this.tlc, this.lname, this.mname, this.fname, this.date, this.ac, this.college, this.base, }); Qualif copyWith({ String? tlc, String? lname, String? mname, String? fname, String? date, String? ac, String? college, String? base, }) { return Qualif( tlc: tlc ?? this.tlc, lname: lname ?? this.lname, mname: mname ?? this.mname, fname: fname ?? this.fname, date: date ?? this.date, ac: ac ?? this.ac, college: college ?? this.college, base: base ?? this.base, ); } Map toMap() { return { 'tlc': tlc, 'lname': lname, 'mname': mname, 'fname': fname, 'date': date, 'ac': ac, 'college': college, 'base': base, }; } factory Qualif.fromList(List datalist) { return Qualif( tlc: datalist[0], lname: datalist[1], mname: datalist[2], fname: datalist[3], date: datalist[4], ac: datalist[5], college: datalist[6], base: datalist[7]); } factory Qualif.fromMap(Map map) { return Qualif( tlc: map['tlc'] != null ? map['tlc'] as String : null, lname: map['lname'] != null ? map['lname'] as String : null, mname: map['mname'] != null ? map['mname'] as String : null, fname: map['fname'] != null ? map['fname'] as String : null, date: map['date'] != null ? map['date'] as String : null, ac: map['ac'] != null ? map['ac'] as String : null, college: map['college'] != null ? map['college'] as String : null, base: map['base'] != null ? map['base'] as String : null, ); } String toJson() => json.encode(toMap()); factory Qualif.fromJson(String source) => Qualif.fromMap(json.decode(source) as Map); @override String toString() { return 'Qualif(tlc: $tlc, lname: $lname, mname: $mname, fname: $fname, date: $date, ac: $ac, college: $college, base: $base)'; } @override bool operator ==(covariant Qualif other) { if (identical(this, other)) return true; return other.tlc == tlc && other.lname == lname && other.mname == mname && other.fname == fname && other.date == date && other.ac == ac && other.college == college && other.base == base; } @override int get hashCode { return tlc.hashCode ^ lname.hashCode ^ mname.hashCode ^ fname.hashCode ^ date.hashCode ^ ac.hashCode ^ college.hashCode ^ base.hashCode; } } class Pnleg { String? date; Jiffy? get jdate => date != null ? Jiffy.parse(date ?? "01/01/1970", pattern: "dd/MM/yyyy", isUtc: true) : null; String? tlc; String? actype; String? al; String? fnum; String? depdate; String? deptime; String? arrdate; String? arrtime; String? dep; String? arr; String? label; String? type; Jiffy? get jdep => deptime != null ? "$depdate $deptime".parseddmmyyyyhhmm() : null; Jiffy? get jarr => arrtime != null ? "$arrdate $arrtime".parseddmmyyyyhhmm() : null; String get dutytype { if (type == "L") { return "flight"; } else if ((type == "G")) { return "dhlimo"; } else if ((type == "F") || ((dep ?? "") != "" && (arr ?? "") != "")) { return "dhflight"; } else if ((label?.startsWith("SBY") ?? false) || (label == "R0")) { return "standby"; } else if ((!["OFF", "CM", "CA", "PP"].contains(label)) && (jarr != null && jdep != null && DTInterval(jdep!, jarr!).duration.inHours < 18)) { return "ground"; } else { return "day"; } } Pnleg({ this.date, this.tlc, this.actype, this.al, this.fnum, this.depdate, this.deptime, this.arrdate, this.arrtime, this.dep, this.arr, this.label, this.type, }); Pnleg copyWith({ String? date, String? tlc, String? actype, String? al, String? fnum, String? depdate, String? deptime, String? arrdate, String? arrtime, String? dep, String? arr, String? label, String? type, }) { return Pnleg( date: date ?? this.date, tlc: tlc ?? this.tlc, actype: actype ?? this.actype, al: al ?? this.al, fnum: fnum ?? this.fnum, depdate: depdate ?? this.depdate, deptime: deptime ?? this.deptime, arrdate: arrdate ?? this.arrdate, arrtime: arrtime ?? this.arrtime, dep: dep ?? this.dep, arr: arr ?? this.arr, label: label ?? this.label, type: type ?? this.type, ); } Map toMap() { return { 'date': date, 'tlc': tlc, 'actype': actype, 'al': al, 'fnum': fnum, 'depdate': depdate, 'deptime': deptime, 'arrdate': arrdate, 'arrtime': arrtime, 'dep': dep, 'arr': arr, 'label': label, 'type': type, }; } factory Pnleg.fromList(List datalist) { return Pnleg( date: datalist[0], tlc: datalist[1], actype: datalist[2], al: datalist[3], fnum: datalist[4], depdate: datalist[5], deptime: datalist[6], arrdate: datalist[7], arrtime: datalist[8], dep: datalist[9], arr: datalist[10], label: datalist[11], type: datalist[12]); } factory Pnleg.fromMap(Map map) { return Pnleg( date: map['date'] != null ? map['date'] as String : null, tlc: map['tlc'] != null ? map['tlc'] as String : null, actype: map['actype'] != null ? map['actype'] as String : null, al: map['al'] != null ? map['al'] as String : null, fnum: map['fnum'] != null ? map['fnum'] as String : null, depdate: map['depdate'] != null ? map['depdate'] as String : null, deptime: map['deptime'] != null ? map['deptime'] as String : null, arrdate: map['arrdate'] != null ? map['arrdate'] as String : null, arrtime: map['arrtime'] != null ? map['arrtime'] as String : null, dep: map['dep'] != null ? map['dep'] as String : null, arr: map['arr'] != null ? map['arr'] as String : null, label: map['label'] != null ? map['label'] as String : null, type: map['type'] != null ? map['type'] as String : null, ); } String toJson() => json.encode(toMap()); factory Pnleg.fromJson(String source) => Pnleg.fromMap(json.decode(source) as Map); @override String toString() { return 'Pnleg(date: $date, tlc: $tlc, actype: $actype, al: $al, fnum: $fnum, depdate: $depdate, deptime: $deptime, arrdate: $arrdate, arrtime: $arrtime, dep: $dep, arr: $arr, label: $label, type: $type)'; } @override bool operator ==(covariant Pnleg other) { if (identical(this, other)) return true; return other.date == date && other.tlc == tlc && other.actype == actype && other.al == al && other.fnum == fnum && other.depdate == depdate && other.deptime == deptime && other.arrdate == arrdate && other.arrtime == arrtime && other.dep == dep && other.arr == arr && other.label == label && other.type == type; } @override int get hashCode { return date.hashCode ^ tlc.hashCode ^ actype.hashCode ^ al.hashCode ^ fnum.hashCode ^ depdate.hashCode ^ deptime.hashCode ^ arrdate.hashCode ^ arrtime.hashCode ^ dep.hashCode ^ arr.hashCode ^ label.hashCode ^ type.hashCode; } } //enum flt_status { sched, delayed, taxiout, enroute, landed, arrived } class Acleg { String? LEG_NO; String? FN_CARRIER; String? FN_NUMBER; String? FN_SUFFIX; String? DAY_OF_ORIGIN; String? AC_OWNER; String? AC_SUBTYPE; String? AC_VERSION; String? AC_REGISTRATION; String? DEP_AP_ACTUAL; String? DEP_AP_SCHED; String? DEP_DT_EST; Jiffy? get jdepest => (DEP_DT_EST == null) ? null : DEP_DT_EST!.parseyyyymmddhhmm(); String? DEP_SCHED_DT; Jiffy? get jdepsched => (DEP_SCHED_DT == null) ? null : DEP_SCHED_DT!.parseyyyymmddhhmm(); String? ARR_AP_ACTUAL; String? ARR_AP_SCHED; String? ARR_DT_EST; Jiffy? get jarrest => (ARR_DT_EST == null) ? null : ARR_DT_EST!.parseyyyymmddhhmm(); String? ARR_SCHED_DT; Jiffy? get jarrsched => (ARR_SCHED_DT == null) ? null : ARR_SCHED_DT!.parseyyyymmddhhmm(); String? SLOT_TIME_ACTUAL; Jiffy? get slot => (SLOT_TIME_ACTUAL == null) ? null : SLOT_TIME_ACTUAL!.parseyyyymmddhhmm(); String? LEG_TYPE; String? STATUS; String? EMPLOYER_COCKPIT; String? EMPLOYER_CABIN; String? CYCLES; String? DELAY_CODE_01; String? DELAY_CODE_02; String? DELAY_CODE_03; String? DELAY_CODE_04; String? DELAY_TIME_01; String? DELAY_TIME_02; String? DELAY_TIME_03; String? DELAY_TIME_04; String? SUBDELAY_CODE_01; String? SUBDELAY_CODE_02; String? SUBDELAY_CODE_03; String? SUBDELAY_CODE_04; List get dla => [ [ SUBDELAY_CODE_01 ?? DELAY_CODE_01, DELAY_TIME_01 == null ? null : Duration(minutes: int.parse(DELAY_TIME_01!)) ], [ SUBDELAY_CODE_02 ?? DELAY_CODE_02, DELAY_TIME_02 == null ? null : Duration(minutes: int.parse(DELAY_TIME_02!)) ], [ SUBDELAY_CODE_03 ?? DELAY_CODE_03, DELAY_TIME_03 == null ? null : Duration(minutes: int.parse(DELAY_TIME_03!)) ], [ SUBDELAY_CODE_04 ?? DELAY_CODE_04, DELAY_TIME_04 == null ? null : Duration(minutes: int.parse(DELAY_TIME_04!)) ], ].where((e) => e.every((f) => f != null)).toList(); List get delaycode => [ DELAY_CODE_01, DELAY_CODE_02, DELAY_CODE_03, DELAY_CODE_04 ].nonNulls.toList(); List get delaysubcode => [ SUBDELAY_CODE_01, SUBDELAY_CODE_02, SUBDELAY_CODE_03, SUBDELAY_CODE_04 ].nonNulls.toList(); List get delaytime => [ DELAY_TIME_01 == null ? null : Duration(minutes: int.parse(DELAY_TIME_01!)), DELAY_TIME_02 == null ? null : Duration(minutes: int.parse(DELAY_TIME_02!)), DELAY_TIME_03 == null ? null : Duration(minutes: int.parse(DELAY_TIME_03!)), DELAY_TIME_04 == null ? null : Duration(minutes: int.parse(DELAY_TIME_04!)) ].nonNulls.toList(); String? PAX_BOOKED_C; String? PAX_BOOKED_Y; String? get pax_booked => (PAX_BOOKED_C != null || PAX_BOOKED_Y != null) ? "${(AC_VERSION != null && AC_VERSION!.contains("C")) ? "C${PAX_BOOKED_C ?? 0}." : ""}Y${PAX_BOOKED_Y ?? 0}" : null; String? PAX_BOOKED_TRS_C; String? PAX_BOOKED_TRS_Y; String? get pax_trs => (PAX_BOOKED_TRS_C != null || PAX_BOOKED_TRS_Y != null) ? "C${PAX_BOOKED_TRS_C ?? 0}/Y${PAX_BOOKED_TRS_Y ?? 0}" : null; String? PAD_BOOKED_C; String? PAD_BOOKED_Y; String? get pad_booked => (PAD_BOOKED_C != null || PAD_BOOKED_Y != null) ? "C${PAD_BOOKED_C ?? 0}/Y${PAD_BOOKED_Y ?? 0}" : null; String? OFFBLOCK_DT_A; String? AIRBORNE_DT_A; String? LANDING_DT_A; String? ONBLOCK_DT_A; List get blocks_a => [ (OFFBLOCK_DT_A ?? "").parseyyyymmddhhmm(), (AIRBORNE_DT_A ?? "").parseyyyymmddhhmm(), (LANDING_DT_A ?? "").parseyyyymmddhhmm(), (ONBLOCK_DT_A ?? "").parseyyyymmddhhmm() ]; String get flt_status { if (blocks[3] != null) { return "Arrived"; } else if (blocks[2] != null) { return "Landed"; } else if (blocks[1] != null) { return "Inflight"; } else if (blocks[0] != null) { return "Taxiout"; } else if (jdepest != null && jarrsched != null && jdepest!.isAfter(jdepsched!)) { return "Delayed"; } else { return "Sched"; } } String? OFFBLOCK_DT_F; String? AIRBORNE_DT_F; String? LANDING_DT_F; String? ONBLOCK_DT_F; List get blocks_f => [ (OFFBLOCK_DT_F ?? "").parseyyyymmddhhmm(), (AIRBORNE_DT_F ?? "").parseyyyymmddhhmm(), (LANDING_DT_F ?? "").parseyyyymmddhhmm(), (ONBLOCK_DT_F ?? "").parseyyyymmddhhmm() ]; String? OFFBLOCK_DT_M; String? AIRBORNE_DT_M; String? LANDING_DT_M; String? ONBLOCK_DT_M; List get blocks_m => [ (OFFBLOCK_DT_M ?? "").parseyyyymmddhhmm(), (AIRBORNE_DT_M ?? "").parseyyyymmddhhmm(), (LANDING_DT_M ?? "").parseyyyymmddhhmm(), (ONBLOCK_DT_M ?? "").parseyyyymmddhhmm() ]; List get blocks => [ blocks_m[0] ?? blocks_a[0] ?? blocks_f[0], blocks_m[1] ?? blocks_a[1] ?? blocks_f[1], blocks_m[2] ?? blocks_a[2] ?? blocks_f[2], blocks_m[3] ?? blocks_a[3] ?? blocks_f[3] ]; Jiffy? get jdep => blocks[0] ?? jdepest ?? jdepsched; Jiffy? get jarr => blocks[3] ?? blocks[2]?.add(minutes: 5) ?? (eet == null ? null : blocks[1]?.addDuration(eet!).add(minutes: 8)) ?? (eet == null ? null : blocks[0]?.add(minutes: 5).addDuration(eet!).add(minutes: 8)) ?? (eet == null ? null : jdep?.addDuration(eet!).add(minutes: 8).add(minutes: 5)) ?? jarrest ?? jarrsched; String? EET; Duration? get eet => EET == null ? null : Duration(minutes: int.parse(EET!)); Acleg({ this.LEG_NO, this.FN_CARRIER, this.FN_NUMBER, this.FN_SUFFIX, this.DAY_OF_ORIGIN, this.AC_OWNER, this.AC_SUBTYPE, this.AC_VERSION, this.AC_REGISTRATION, this.DEP_AP_ACTUAL, this.DEP_AP_SCHED, this.DEP_DT_EST, this.DEP_SCHED_DT, this.ARR_AP_ACTUAL, this.ARR_AP_SCHED, this.ARR_DT_EST, this.ARR_SCHED_DT, this.SLOT_TIME_ACTUAL, this.LEG_TYPE, this.STATUS, this.EMPLOYER_COCKPIT, this.EMPLOYER_CABIN, this.CYCLES, this.DELAY_CODE_01, this.DELAY_CODE_02, this.DELAY_CODE_03, this.DELAY_CODE_04, this.DELAY_TIME_01, this.DELAY_TIME_02, this.DELAY_TIME_03, this.DELAY_TIME_04, this.SUBDELAY_CODE_01, this.SUBDELAY_CODE_02, this.SUBDELAY_CODE_03, this.SUBDELAY_CODE_04, this.PAX_BOOKED_C, this.PAX_BOOKED_Y, this.PAX_BOOKED_TRS_C, this.PAX_BOOKED_TRS_Y, this.PAD_BOOKED_C, this.PAD_BOOKED_Y, this.OFFBLOCK_DT_A, this.AIRBORNE_DT_A, this.LANDING_DT_A, this.ONBLOCK_DT_A, this.OFFBLOCK_DT_F, this.AIRBORNE_DT_F, this.LANDING_DT_F, this.ONBLOCK_DT_F, this.OFFBLOCK_DT_M, this.AIRBORNE_DT_M, this.LANDING_DT_M, this.ONBLOCK_DT_M, this.EET, }); Acleg copyWith({ String? LEG_NO, String? FN_CARRIER, String? FN_NUMBER, String? FN_SUFFIX, String? DAY_OF_ORIGIN, String? AC_OWNER, String? AC_SUBTYPE, String? AC_VERSION, String? AC_REGISTRATION, String? DEP_AP_ACTUAL, String? DEP_AP_SCHED, String? DEP_DT_EST, String? DEP_SCHED_DT, String? ARR_AP_ACTUAL, String? ARR_AP_SCHED, String? ARR_DT_EST, String? ARR_SCHED_DT, String? SLOT_TIME_ACTUAL, String? LEG_TYPE, String? STATUS, String? EMPLOYER_COCKPIT, String? EMPLOYER_CABIN, String? CYCLES, String? DELAY_CODE_01, String? DELAY_CODE_02, String? DELAY_CODE_03, String? DELAY_CODE_04, String? DELAY_TIME_01, String? DELAY_TIME_02, String? DELAY_TIME_03, String? DELAY_TIME_04, String? SUBDELAY_CODE_01, String? SUBDELAY_CODE_02, String? SUBDELAY_CODE_03, String? SUBDELAY_CODE_04, String? PAX_BOOKED_C, String? PAX_BOOKED_Y, String? PAX_BOOKED_TRS_C, String? PAX_BOOKED_TRS_Y, String? PAD_BOOKED_C, String? PAD_BOOKED_Y, String? OFFBLOCK_DT_A, String? AIRBORNE_DT_A, String? LANDING_DT_A, String? ONBLOCK_DT_A, String? OFFBLOCK_DT_F, String? AIRBORNE_DT_F, String? LANDING_DT_F, String? ONBLOCK_DT_F, String? OFFBLOCK_DT_M, String? AIRBORNE_DT_M, String? LANDING_DT_M, String? ONBLOCK_DT_M, String? EET, }) { return Acleg( LEG_NO: LEG_NO ?? this.LEG_NO, FN_CARRIER: FN_CARRIER ?? this.FN_CARRIER, FN_NUMBER: FN_NUMBER ?? this.FN_NUMBER, FN_SUFFIX: FN_SUFFIX ?? this.FN_SUFFIX, DAY_OF_ORIGIN: DAY_OF_ORIGIN ?? this.DAY_OF_ORIGIN, AC_OWNER: AC_OWNER ?? this.AC_OWNER, AC_SUBTYPE: AC_SUBTYPE ?? this.AC_SUBTYPE, AC_VERSION: AC_VERSION ?? this.AC_VERSION, AC_REGISTRATION: AC_REGISTRATION ?? this.AC_REGISTRATION, DEP_AP_ACTUAL: DEP_AP_ACTUAL ?? this.DEP_AP_ACTUAL, DEP_AP_SCHED: DEP_AP_SCHED ?? this.DEP_AP_SCHED, DEP_DT_EST: DEP_DT_EST ?? this.DEP_DT_EST, DEP_SCHED_DT: DEP_SCHED_DT ?? this.DEP_SCHED_DT, ARR_AP_ACTUAL: ARR_AP_ACTUAL ?? this.ARR_AP_ACTUAL, ARR_AP_SCHED: ARR_AP_SCHED ?? this.ARR_AP_SCHED, ARR_DT_EST: ARR_DT_EST ?? this.ARR_DT_EST, ARR_SCHED_DT: ARR_SCHED_DT ?? this.ARR_SCHED_DT, SLOT_TIME_ACTUAL: SLOT_TIME_ACTUAL ?? this.SLOT_TIME_ACTUAL, LEG_TYPE: LEG_TYPE ?? this.LEG_TYPE, STATUS: STATUS ?? this.STATUS, EMPLOYER_COCKPIT: EMPLOYER_COCKPIT ?? this.EMPLOYER_COCKPIT, EMPLOYER_CABIN: EMPLOYER_CABIN ?? this.EMPLOYER_CABIN, CYCLES: CYCLES ?? this.CYCLES, DELAY_CODE_01: DELAY_CODE_01 ?? this.DELAY_CODE_01, DELAY_CODE_02: DELAY_CODE_02 ?? this.DELAY_CODE_02, DELAY_CODE_03: DELAY_CODE_03 ?? this.DELAY_CODE_03, DELAY_CODE_04: DELAY_CODE_04 ?? this.DELAY_CODE_04, DELAY_TIME_01: DELAY_TIME_01 ?? this.DELAY_TIME_01, DELAY_TIME_02: DELAY_TIME_02 ?? this.DELAY_TIME_02, DELAY_TIME_03: DELAY_TIME_03 ?? this.DELAY_TIME_03, DELAY_TIME_04: DELAY_TIME_04 ?? this.DELAY_TIME_04, SUBDELAY_CODE_01: SUBDELAY_CODE_01 ?? this.SUBDELAY_CODE_01, SUBDELAY_CODE_02: SUBDELAY_CODE_02 ?? this.SUBDELAY_CODE_02, SUBDELAY_CODE_03: SUBDELAY_CODE_03 ?? this.SUBDELAY_CODE_03, SUBDELAY_CODE_04: SUBDELAY_CODE_04 ?? this.SUBDELAY_CODE_04, PAX_BOOKED_C: PAX_BOOKED_C ?? this.PAX_BOOKED_C, PAX_BOOKED_Y: PAX_BOOKED_Y ?? this.PAX_BOOKED_Y, PAX_BOOKED_TRS_C: PAX_BOOKED_TRS_C ?? this.PAX_BOOKED_TRS_C, PAX_BOOKED_TRS_Y: PAX_BOOKED_TRS_Y ?? this.PAX_BOOKED_TRS_Y, PAD_BOOKED_C: PAD_BOOKED_C ?? this.PAD_BOOKED_C, PAD_BOOKED_Y: PAD_BOOKED_Y ?? this.PAD_BOOKED_Y, OFFBLOCK_DT_A: OFFBLOCK_DT_A ?? this.OFFBLOCK_DT_A, AIRBORNE_DT_A: AIRBORNE_DT_A ?? this.AIRBORNE_DT_A, LANDING_DT_A: LANDING_DT_A ?? this.LANDING_DT_A, ONBLOCK_DT_A: ONBLOCK_DT_A ?? this.ONBLOCK_DT_A, OFFBLOCK_DT_F: OFFBLOCK_DT_F ?? this.OFFBLOCK_DT_F, AIRBORNE_DT_F: AIRBORNE_DT_F ?? this.AIRBORNE_DT_F, LANDING_DT_F: LANDING_DT_F ?? this.LANDING_DT_F, ONBLOCK_DT_F: ONBLOCK_DT_F ?? this.ONBLOCK_DT_F, OFFBLOCK_DT_M: OFFBLOCK_DT_M ?? this.OFFBLOCK_DT_M, AIRBORNE_DT_M: AIRBORNE_DT_M ?? this.AIRBORNE_DT_M, LANDING_DT_M: LANDING_DT_M ?? this.LANDING_DT_M, ONBLOCK_DT_M: ONBLOCK_DT_M ?? this.ONBLOCK_DT_M, EET: EET ?? this.EET, ); } Map toMap() { return { 'LEG_NO': LEG_NO, 'FN_CARRIER': FN_CARRIER, 'FN_NUMBER': FN_NUMBER, 'FN_SUFFIX': FN_SUFFIX, 'DAY_OF_ORIGIN': DAY_OF_ORIGIN, 'AC_OWNER': AC_OWNER, 'AC_SUBTYPE': AC_SUBTYPE, 'AC_VERSION': AC_VERSION, 'AC_REGISTRATION': AC_REGISTRATION, 'DEP_AP_ACTUAL': DEP_AP_ACTUAL, 'DEP_AP_SCHED': DEP_AP_SCHED, 'DEP_DT_EST': DEP_DT_EST, 'DEP_SCHED_DT': DEP_SCHED_DT, 'ARR_AP_ACTUAL': ARR_AP_ACTUAL, 'ARR_AP_SCHED': ARR_AP_SCHED, 'ARR_DT_EST': ARR_DT_EST, 'ARR_SCHED_DT': ARR_SCHED_DT, 'SLOT_TIME_ACTUAL': SLOT_TIME_ACTUAL, 'LEG_TYPE': LEG_TYPE, 'STATUS': STATUS, 'EMPLOYER_COCKPIT': EMPLOYER_COCKPIT, 'EMPLOYER_CABIN': EMPLOYER_CABIN, 'CYCLES': CYCLES, 'DELAY_CODE_01': DELAY_CODE_01, 'DELAY_CODE_02': DELAY_CODE_02, 'DELAY_CODE_03': DELAY_CODE_03, 'DELAY_CODE_04': DELAY_CODE_04, 'DELAY_TIME_01': DELAY_TIME_01, 'DELAY_TIME_02': DELAY_TIME_02, 'DELAY_TIME_03': DELAY_TIME_03, 'DELAY_TIME_04': DELAY_TIME_04, 'SUBDELAY_CODE_01': SUBDELAY_CODE_01, 'SUBDELAY_CODE_02': SUBDELAY_CODE_02, 'SUBDELAY_CODE_03': SUBDELAY_CODE_03, 'SUBDELAY_CODE_04': SUBDELAY_CODE_04, 'PAX_BOOKED_C': PAX_BOOKED_C, 'PAX_BOOKED_Y': PAX_BOOKED_Y, 'PAX_BOOKED_TRS_C': PAX_BOOKED_TRS_C, 'PAX_BOOKED_TRS_Y': PAX_BOOKED_TRS_Y, 'PAD_BOOKED_C': PAD_BOOKED_C, 'PAD_BOOKED_Y': PAD_BOOKED_Y, 'OFFBLOCK_DT_A': OFFBLOCK_DT_A, 'AIRBORNE_DT_A': AIRBORNE_DT_A, 'LANDING_DT_A': LANDING_DT_A, 'ONBLOCK_DT_A': ONBLOCK_DT_A, 'OFFBLOCK_DT_F': OFFBLOCK_DT_F, 'AIRBORNE_DT_F': AIRBORNE_DT_F, 'LANDING_DT_F': LANDING_DT_F, 'ONBLOCK_DT_F': ONBLOCK_DT_F, 'OFFBLOCK_DT_M': OFFBLOCK_DT_M, 'AIRBORNE_DT_M': AIRBORNE_DT_M, 'LANDING_DT_M': LANDING_DT_M, 'ONBLOCK_DT_M': ONBLOCK_DT_M, 'EET': EET, }; } factory Acleg.fromList(List datalist) { //print(datalist); if (datalist.length >= 54) { return Acleg( LEG_NO: datalist[0], FN_CARRIER: datalist[1], FN_NUMBER: datalist[2], FN_SUFFIX: datalist[3], DAY_OF_ORIGIN: datalist[4], AC_OWNER: datalist[5], AC_SUBTYPE: datalist[6], AC_VERSION: datalist[7], AC_REGISTRATION: datalist[8], DEP_AP_ACTUAL: datalist[9], DEP_AP_SCHED: datalist[10], DEP_DT_EST: datalist[11], DEP_SCHED_DT: datalist[12], ARR_AP_ACTUAL: datalist[13], ARR_AP_SCHED: datalist[14], ARR_DT_EST: datalist[15], ARR_SCHED_DT: datalist[16], SLOT_TIME_ACTUAL: datalist[17], LEG_TYPE: datalist[18], STATUS: datalist[19], EMPLOYER_COCKPIT: datalist[20], EMPLOYER_CABIN: datalist[21], CYCLES: datalist[22], DELAY_CODE_01: datalist[23], DELAY_CODE_02: datalist[24], DELAY_CODE_03: datalist[25], DELAY_CODE_04: datalist[26], DELAY_TIME_01: datalist[27], DELAY_TIME_02: datalist[28], DELAY_TIME_03: datalist[29], DELAY_TIME_04: datalist[30], SUBDELAY_CODE_01: datalist[31], SUBDELAY_CODE_02: datalist[32], SUBDELAY_CODE_03: datalist[33], SUBDELAY_CODE_04: datalist[34], PAX_BOOKED_C: datalist[35], PAX_BOOKED_Y: datalist[36], PAX_BOOKED_TRS_C: datalist[37], PAX_BOOKED_TRS_Y: datalist[38], PAD_BOOKED_C: datalist[39], PAD_BOOKED_Y: datalist[40], OFFBLOCK_DT_A: datalist[41], AIRBORNE_DT_A: datalist[42], LANDING_DT_A: datalist[43], ONBLOCK_DT_A: datalist[44], OFFBLOCK_DT_F: datalist[45], AIRBORNE_DT_F: datalist[46], LANDING_DT_F: datalist[47], ONBLOCK_DT_F: datalist[48], OFFBLOCK_DT_M: datalist[49], AIRBORNE_DT_M: datalist[50], LANDING_DT_M: datalist[51], ONBLOCK_DT_M: datalist[52], EET: datalist[53]); } else { return Acleg(); } } factory Acleg.fromMap(Map map) { return Acleg( LEG_NO: map['LEG_NO'] != null ? map['LEG_NO'] as String : null, FN_CARRIER: map['FN_CARRIER'] != null ? map['FN_CARRIER'] as String : null, FN_NUMBER: map['FN_NUMBER'] != null ? map['FN_NUMBER'] as String : null, FN_SUFFIX: map['FN_SUFFIX'] != null ? map['FN_SUFFIX'] as String : null, DAY_OF_ORIGIN: map['DAY_OF_ORIGIN'] != null ? map['DAY_OF_ORIGIN'] as String : null, AC_OWNER: map['AC_OWNER'] != null ? map['AC_OWNER'] as String : null, AC_SUBTYPE: map['AC_SUBTYPE'] != null ? map['AC_SUBTYPE'] as String : null, AC_VERSION: map['AC_VERSION'] != null ? map['AC_VERSION'] as String : null, AC_REGISTRATION: map['AC_REGISTRATION'] != null ? map['AC_REGISTRATION'] as String : null, DEP_AP_ACTUAL: map['DEP_AP_ACTUAL'] != null ? map['DEP_AP_ACTUAL'] as String : null, DEP_AP_SCHED: map['DEP_AP_SCHED'] != null ? map['DEP_AP_SCHED'] as String : null, DEP_DT_EST: map['DEP_DT_EST'] != null ? map['DEP_DT_EST'] as String : null, DEP_SCHED_DT: map['DEP_SCHED_DT'] != null ? map['DEP_SCHED_DT'] as String : null, ARR_AP_ACTUAL: map['ARR_AP_ACTUAL'] != null ? map['ARR_AP_ACTUAL'] as String : null, ARR_AP_SCHED: map['ARR_AP_SCHED'] != null ? map['ARR_AP_SCHED'] as String : null, ARR_DT_EST: map['ARR_DT_EST'] != null ? map['ARR_DT_EST'] as String : null, ARR_SCHED_DT: map['ARR_SCHED_DT'] != null ? map['ARR_SCHED_DT'] as String : null, SLOT_TIME_ACTUAL: map['SLOT_TIME_ACTUAL'] != null ? map['SLOT_TIME_ACTUAL'] as String : null, LEG_TYPE: map['LEG_TYPE'] != null ? map['LEG_TYPE'] as String : null, EMPLOYER_COCKPIT: map['EMPLOYER_COCKPIT'] != null ? map['EMPLOYER_COCKPIT'] as String : null, EMPLOYER_CABIN: map['EMPLOYER_CABIN'] != null ? map['EMPLOYER_CABIN'] as String : null, // CYCLES: map['CYCLES'] != null ? map['CYCLES'] as String : null, DELAY_CODE_01: map['DELAY_CODE_01'] != null ? map['DELAY_CODE_01'] as String : null, DELAY_CODE_02: map['DELAY_CODE_02'] != null ? map['DELAY_CODE_02'] as String : null, DELAY_CODE_03: map['DELAY_CODE_03'] != null ? map['DELAY_CODE_03'] as String : null, DELAY_CODE_04: map['DELAY_CODE_04'] != null ? map['DELAY_CODE_04'] as String : null, DELAY_TIME_01: map['DELAY_TIME_01'] != null ? map['DELAY_TIME_01'] as String : null, DELAY_TIME_02: map['DELAY_TIME_02'] != null ? map['DELAY_TIME_02'] as String : null, DELAY_TIME_03: map['DELAY_TIME_03'] != null ? map['DELAY_TIME_03'] as String : null, DELAY_TIME_04: map['DELAY_TIME_04'] != null ? map['DELAY_TIME_04'] as String : null, SUBDELAY_CODE_01: map['SUBDELAY_CODE_01'] != null ? map['SUBDELAY_CODE_01'] as String : null, SUBDELAY_CODE_02: map['SUBDELAY_CODE_02'] != null ? map['SUBDELAY_CODE_02'] as String : null, SUBDELAY_CODE_03: map['SUBDELAY_CODE_03'] != null ? map['SUBDELAY_CODE_03'] as String : null, SUBDELAY_CODE_04: map['SUBDELAY_CODE_04'] != null ? map['SUBDELAY_CODE_04'] as String : null, PAX_BOOKED_C: map['PAX_BOOKED_C'] != null ? map['PAX_BOOKED_C'] as String : null, PAX_BOOKED_Y: map['PAX_BOOKED_Y'] != null ? map['PAX_BOOKED_Y'] as String : null, PAX_BOOKED_TRS_C: map['PAX_BOOKED_TRS_C'] != null ? map['PAX_BOOKED_TRS_C'] as String : null, PAX_BOOKED_TRS_Y: map['PAX_BOOKED_TRS_Y'] != null ? map['PAX_BOOKED_TRS_Y'] as String : null, PAD_BOOKED_C: map['PAD_BOOKED_C'] != null ? map['PAD_BOOKED_C'] as String : null, PAD_BOOKED_Y: map['PAD_BOOKED_Y'] != null ? map['PAD_BOOKED_Y'] as String : null, OFFBLOCK_DT_A: map['OFFBLOCK_DT_A'] != null ? map['OFFBLOCK_DT_A'] as String : null, AIRBORNE_DT_A: map['AIRBORNE_DT_A'] != null ? map['AIRBORNE_DT_A'] as String : null, LANDING_DT_A: map['LANDING_DT_A'] != null ? map['LANDING_DT_A'] as String : null, ONBLOCK_DT_A: map['ONBLOCK_DT_A'] != null ? map['ONBLOCK_DT_A'] as String : null, OFFBLOCK_DT_F: map['OFFBLOCK_DT_F'] != null ? map['OFFBLOCK_DT_F'] as String : null, AIRBORNE_DT_F: map['AIRBORNE_DT_F'] != null ? map['AIRBORNE_DT_F'] as String : null, LANDING_DT_F: map['LANDING_DT_F'] != null ? map['LANDING_DT_F'] as String : null, ONBLOCK_DT_F: map['ONBLOCK_DT_F'] != null ? map['ONBLOCK_DT_F'] as String : null, OFFBLOCK_DT_M: map['OFFBLOCK_DT_M'] != null ? map['OFFBLOCK_DT_M'] as String : null, AIRBORNE_DT_M: map['AIRBORNE_DT_M'] != null ? map['AIRBORNE_DT_M'] as String : null, LANDING_DT_M: map['LANDING_DT_M'] != null ? map['LANDING_DT_M'] as String : null, ONBLOCK_DT_M: map['ONBLOCK_DT_M'] != null ? map['ONBLOCK_DT_M'] as String : null, EET: map['EET'] != null ? map['EET'] as String : null, ); } String toJson() => json.encode(toMap()); factory Acleg.fromJson(String source) => Acleg.fromMap(json.decode(source) as Map); @override String toString() { return 'Acleg(LEG_NO: $LEG_NO, FN_CARRIER: $FN_CARRIER, FN_NUMBER: $FN_NUMBER, FN_SUFFIX: $FN_SUFFIX, DAY_OF_ORIGIN: $DAY_OF_ORIGIN, AC_OWNER: $AC_OWNER, AC_SUBTYPE: $AC_SUBTYPE, AC_VERSION: $AC_VERSION, AC_REGISTRATION: $AC_REGISTRATION, DEP_AP_ACTUAL: $DEP_AP_ACTUAL, DEP_AP_SCHED: $DEP_AP_SCHED, DEP_DT_EST: $DEP_DT_EST, DEP_SCHED_DT: $DEP_SCHED_DT, ARR_AP_ACTUAL: $ARR_AP_ACTUAL, ARR_AP_SCHED: $ARR_AP_SCHED, ARR_DT_EST: $ARR_DT_EST, ARR_SCHED_DT: $ARR_SCHED_DT, SLOT_TIME_ACTUAL: $SLOT_TIME_ACTUAL, LEG_TYPE: $LEG_TYPE, EMPLOYER_COCKPIT: $EMPLOYER_COCKPIT, EMPLOYER_CABIN: $EMPLOYER_CABIN, CYCLES: $CYCLES, DELAY_CODE_01: $DELAY_CODE_01, DELAY_CODE_02: $DELAY_CODE_02, DELAY_CODE_03: $DELAY_CODE_03, DELAY_CODE_04: $DELAY_CODE_04, DELAY_TIME_01: $DELAY_TIME_01, DELAY_TIME_02: $DELAY_TIME_02, DELAY_TIME_03: $DELAY_TIME_03, DELAY_TIME_04: $DELAY_TIME_04, SUBDELAY_CODE_01: $SUBDELAY_CODE_01, SUBDELAY_CODE_02: $SUBDELAY_CODE_02, SUBDELAY_CODE_03: $SUBDELAY_CODE_03, SUBDELAY_CODE_04: $SUBDELAY_CODE_04, PAX_BOOKED_C: $PAX_BOOKED_C, PAX_BOOKED_Y: $PAX_BOOKED_Y, PAX_BOOKED_TRS_C: $PAX_BOOKED_TRS_C, PAX_BOOKED_TRS_Y: $PAX_BOOKED_TRS_Y, PAD_BOOKED_C: $PAD_BOOKED_C, PAD_BOOKED_Y: $PAD_BOOKED_Y, OFFBLOCK_DT_A: $OFFBLOCK_DT_A, AIRBORNE_DT_A: $AIRBORNE_DT_A, LANDING_DT_A: $LANDING_DT_A, ONBLOCK_DT_A: $ONBLOCK_DT_A, OFFBLOCK_DT_F: $OFFBLOCK_DT_F, AIRBORNE_DT_F: $AIRBORNE_DT_F, LANDING_DT_F: $LANDING_DT_F, ONBLOCK_DT_F: $ONBLOCK_DT_F, OFFBLOCK_DT_M: $OFFBLOCK_DT_M, AIRBORNE_DT_M: $AIRBORNE_DT_M, LANDING_DT_M: $LANDING_DT_M, ONBLOCK_DT_M: $ONBLOCK_DT_M, EET: $EET)'; } @override bool operator ==(covariant Acleg other) { if (identical(this, other)) return true; return other.LEG_NO == LEG_NO && other.FN_CARRIER == FN_CARRIER && other.FN_NUMBER == FN_NUMBER && other.FN_SUFFIX == FN_SUFFIX && other.DAY_OF_ORIGIN == DAY_OF_ORIGIN && other.AC_OWNER == AC_OWNER && other.AC_SUBTYPE == AC_SUBTYPE && other.AC_VERSION == AC_VERSION && other.AC_REGISTRATION == AC_REGISTRATION && other.DEP_AP_ACTUAL == DEP_AP_ACTUAL && other.DEP_AP_SCHED == DEP_AP_SCHED && other.DEP_DT_EST == DEP_DT_EST && other.DEP_SCHED_DT == DEP_SCHED_DT && other.ARR_AP_ACTUAL == ARR_AP_ACTUAL && other.ARR_AP_SCHED == ARR_AP_SCHED && other.ARR_DT_EST == ARR_DT_EST && other.ARR_SCHED_DT == ARR_SCHED_DT && other.SLOT_TIME_ACTUAL == SLOT_TIME_ACTUAL && other.LEG_TYPE == LEG_TYPE && other.EMPLOYER_COCKPIT == EMPLOYER_COCKPIT && other.EMPLOYER_CABIN == EMPLOYER_CABIN && other.CYCLES == CYCLES && other.DELAY_CODE_01 == DELAY_CODE_01 && other.DELAY_CODE_02 == DELAY_CODE_02 && other.DELAY_CODE_03 == DELAY_CODE_03 && other.DELAY_CODE_04 == DELAY_CODE_04 && other.DELAY_TIME_01 == DELAY_TIME_01 && other.DELAY_TIME_02 == DELAY_TIME_02 && other.DELAY_TIME_03 == DELAY_TIME_03 && other.DELAY_TIME_04 == DELAY_TIME_04 && other.SUBDELAY_CODE_01 == SUBDELAY_CODE_01 && other.SUBDELAY_CODE_02 == SUBDELAY_CODE_02 && other.SUBDELAY_CODE_03 == SUBDELAY_CODE_03 && other.SUBDELAY_CODE_04 == SUBDELAY_CODE_04 && other.PAX_BOOKED_C == PAX_BOOKED_C && other.PAX_BOOKED_Y == PAX_BOOKED_Y && other.PAX_BOOKED_TRS_C == PAX_BOOKED_TRS_C && other.PAX_BOOKED_TRS_Y == PAX_BOOKED_TRS_Y && other.PAD_BOOKED_C == PAD_BOOKED_C && other.PAD_BOOKED_Y == PAD_BOOKED_Y && other.OFFBLOCK_DT_A == OFFBLOCK_DT_A && other.AIRBORNE_DT_A == AIRBORNE_DT_A && other.LANDING_DT_A == LANDING_DT_A && other.ONBLOCK_DT_A == ONBLOCK_DT_A && other.OFFBLOCK_DT_F == OFFBLOCK_DT_F && other.AIRBORNE_DT_F == AIRBORNE_DT_F && other.LANDING_DT_F == LANDING_DT_F && other.ONBLOCK_DT_F == ONBLOCK_DT_F && other.OFFBLOCK_DT_M == OFFBLOCK_DT_M && other.AIRBORNE_DT_M == AIRBORNE_DT_M && other.LANDING_DT_M == LANDING_DT_M && other.ONBLOCK_DT_M == ONBLOCK_DT_M && other.EET == EET; } @override int get hashCode { return LEG_NO.hashCode ^ FN_CARRIER.hashCode ^ FN_NUMBER.hashCode ^ FN_SUFFIX.hashCode ^ DAY_OF_ORIGIN.hashCode ^ AC_OWNER.hashCode ^ AC_SUBTYPE.hashCode ^ AC_VERSION.hashCode ^ AC_REGISTRATION.hashCode ^ DEP_AP_ACTUAL.hashCode ^ DEP_AP_SCHED.hashCode ^ DEP_DT_EST.hashCode ^ DEP_SCHED_DT.hashCode ^ ARR_AP_ACTUAL.hashCode ^ ARR_AP_SCHED.hashCode ^ ARR_DT_EST.hashCode ^ ARR_SCHED_DT.hashCode ^ SLOT_TIME_ACTUAL.hashCode ^ LEG_TYPE.hashCode ^ EMPLOYER_COCKPIT.hashCode ^ EMPLOYER_CABIN.hashCode ^ CYCLES.hashCode ^ DELAY_CODE_01.hashCode ^ DELAY_CODE_02.hashCode ^ DELAY_CODE_03.hashCode ^ DELAY_CODE_04.hashCode ^ DELAY_TIME_01.hashCode ^ DELAY_TIME_02.hashCode ^ DELAY_TIME_03.hashCode ^ DELAY_TIME_04.hashCode ^ SUBDELAY_CODE_01.hashCode ^ SUBDELAY_CODE_02.hashCode ^ SUBDELAY_CODE_03.hashCode ^ SUBDELAY_CODE_04.hashCode ^ PAX_BOOKED_C.hashCode ^ PAX_BOOKED_Y.hashCode ^ PAX_BOOKED_TRS_C.hashCode ^ PAX_BOOKED_TRS_Y.hashCode ^ PAD_BOOKED_C.hashCode ^ PAD_BOOKED_Y.hashCode ^ OFFBLOCK_DT_A.hashCode ^ AIRBORNE_DT_A.hashCode ^ LANDING_DT_A.hashCode ^ ONBLOCK_DT_A.hashCode ^ OFFBLOCK_DT_F.hashCode ^ AIRBORNE_DT_F.hashCode ^ LANDING_DT_F.hashCode ^ ONBLOCK_DT_F.hashCode ^ OFFBLOCK_DT_M.hashCode ^ AIRBORNE_DT_M.hashCode ^ LANDING_DT_M.hashCode ^ ONBLOCK_DT_M.hashCode ^ EET.hashCode; } } extension StringExtensions on String { String capitalize() { if (isEmpty) { return this; } else { return "${this[0].toUpperCase()}${substring(1).toLowerCase()}"; } } String capitalizeword() { return split(' ').map((word) => word.capitalize()).join(' '); } Jiffy? parseddmmyyyyhhmm() => length >= 15 ? Jiffy.parse( "${substring(6, 10)}-${substring(3, 5)}-${substring(0, 2)} ${substring(11, 13)}:${substring(13, 15)}", pattern: 'yyyy-MM-dd HH:mm', isUtc: true) : null; Jiffy? parseyyyymmddhhmm() => length >= 16 ? Jiffy.parse(this, pattern: 'yyyy-MM-dd HH:mm:ss', // "${substring(6, 10)}-${substring(3, 5)}-${substring(0, 2)} ${substring(11, 13)}${substring(13, 16)}", // pattern: 'yyyy-MM-dd HH:mm', isUtc: true) : null; } class FilesAsData { String? filename; String? updatedAt; String data; FilesAsData({ this.filename, this.updatedAt, required this.data, }); } const maxItemsToSelect = 200; const maxItemsToInsert = 500; const maxItemsToRemove = 500; processCsvData(File tempfile, SupabaseClient supabase) async { List csvData = []; final filename = tempfile.path.split('/').last; // Check if file is a zip archive if (filename.toLowerCase().endsWith('.zip')) { Archive archive = ZipDecoder().decodeBytes(await tempfile.readAsBytes()); for (final file in archive) { if (!file.isFile) continue; csvData.add(FilesAsData( filename: file.name, data: utf8.decode(file.content as List))); } archive.clearSync(); } else { // For non-zip files, store in extracted folder csvData.add(FilesAsData( filename: filename, data: utf8.decode(await tempfile.readAsBytes()))); } for (final FilesAsData data in csvData) { print(" processing ${data.filename}"); //inserting data if (tables.keys.contains(data.filename)) { List> mapsToInsert = createListOfMaps(headers[data.filename] ?? [], csv2list(data.data)); final completeMapsToInsert = mapsToInsert; final scopeName = scopes[data.filename!]!; final scopeInNew = mapsToInsert .fold({}, (t, e) => t..add(e[scopeName] ?? "")).toList(); // print("Loading old data scope: ${scopeInNew.length}"); List> oldIds = []; List> oldComparable = []; for (var e in splitList(scopeInNew, headerToNb(scopeInNew))) { final res = await supabase .from(tables[data.filename]!) .select() .inFilter(scopeName, e) .limit(100000); oldIds.addAll(res.map((e) => filterMapByKeys(e, ["id"])).toList()); oldComparable.addAll(res .map((e) => filterMapByKeys(e, headers[data.filename] ?? [])) .toList()); // print("Loaded old data scope: ${e.length}"); } // Replace with your actual table name List indexToRemove = []; List indexToMaintain = []; // print("Deleting old data scope: ${mapsToInsert.length}"); final keys2check = idToRemove[data.filename]!; final mawjoudin = oldComparable.fold(>[], (t, e) { t.add(extractMapWithKeys(e, keys2check)); return t; }); for (int i = 0; i < oldComparable.length; i++) { final item = oldComparable[i]; final index = findIndex(mapsToInsert, item); // final mawjood = // mawjoudin.contains(extractMapWithKeys(item, keys2check)); final mawjood = mawjoudin .firstWhere( (e) => mapEquals(extractMapWithKeys(item, keys2check), e), orElse: () => {}) .keys .isNotEmpty; if (index > -1) { indexToMaintain.add(i); mapsToInsert.removeAt(index); } else if (mawjood) { indexToRemove.add(i); } else { print("saved item: $item"); } } //removing index to remove with id for (var e in splitList( indexToRemove.map((e) => oldIds[e]['id']).toList(), headerToNb(indexToRemove.map((e) => oldIds[e]['id']).toList()))) { await supabase .from(tables[data.filename]!) // Replace with your actual table name .delete() .inFilter('id', e); } // print("Deleted old data scope: ${e.length}"); //insering new data await supabase .from(tables[data.filename]!) // Replace with your actual table name .insert(mapsToInsert); print( " insert:${mapsToInsert.length} remove:${indexToRemove.length} maintain:${indexToMaintain.length}"); } else { print(" filename: ${data.filename} unknown, not inserted."); } } } bool mapEquals(Map map1, Map map2) { //if (map1.length != map2.length) return false; for (var key in map1.keys) { if (map1[key] != map2[key]) return false; } return true; } int findIndex(List list, dynamic element) { for (int i = 0; i < list.length; i++) { if (mapEquals(list[i], element)) { return i; } } return -1; // Return -1 if the element is not found } Map filterMapByKeys( Map originalMap, List keysToInclude) { // Create a new map to hold the filtered results Map filteredMap = {}; // Iterate through the list of keys to include for (String key in keysToInclude) { // Check if the key exists in the original map if (originalMap.containsKey(key)) { filteredMap[key] = originalMap[key]; // Add to the new map } } return filteredMap; } List> splitList(List originalList, int maxSize) { List> sublists = []; for (int i = 0; i < originalList.length; i += maxSize) { // Create a sublist for the current chunk List sublist = originalList.sublist( i, (i + maxSize > originalList.length) ? originalList.length : i + maxSize, ); sublists.add(sublist); } return sublists; } int headerToNb(List list) { //header max of 16k final maxheader = 4 * 1024 * 8; if (list.isEmpty) { return list.length; } final length1 = (list.toString().length / list.length).ceil() * 8; final lengthurl = 200 * 8; final res = ((maxheader - lengthurl) / length1).floor(); //print("header2nb: $res"); return res; } Map findDifferences( Map map1, Map map2) { Map differences = {}; // Iterate through keys in map2 for (var key in map2.keys) { // Check if key exists in map1 if (!map1.containsKey(key) || map1[key] != map2[key]) { // Add to differences if it's different or doesn't exist in map1 differences[key] = map2[key]; } } return differences; } Map findSimilarities( Map map1, Map map2) { Map similarities = {}; // Iterate through keys in map1 for (var key in map1.keys) { // Check if key exists in map2 and has the same value as map1 if (map2.containsKey(key) && map1[key] == map2[key]) { // Add to similarities if it's the same in both maps similarities[key] = map1[key]; } } return similarities; } bool containsAll(List sourceList, List targetList) { for (var item in sourceList) { if (!targetList.contains(item)) { return false; } } return true; } Map extractMapWithKeys(Map originalMap, List keys) { Map extractedMap = {}; for (K key in keys) { if (originalMap.containsKey(key)) { extractedMap[key] = originalMap[key]!; } } return extractedMap; }