@actual-app/api 6.2.0 → 6.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -23551,7 +23551,8 @@
23551
23551
  \***********************************************/
23552
23552
  /***/ ((module) => {
23553
23553
  (function () {
23554
- var _global = this;
23554
+ const _global = this;
23555
+ const createBuffer = val => new TextEncoder().encode(val);
23555
23556
  /**
23556
23557
  * JS Implementation of MurmurHash2
23557
23558
  *
@@ -23560,14 +23561,16 @@
23560
23561
  * @author <a href="mailto:aappleby@gmail.com">Austin Appleby</a>
23561
23562
  * @see http://sites.google.com/site/murmurhash/
23562
23563
  *
23563
- * @param {string} str ASCII only
23564
+ * @param {Uint8Array | string} str ASCII only
23564
23565
  * @param {number} seed Positive integer only
23565
23566
  * @return {number} 32-bit positive integer hash
23566
23567
  */
23567
23568
  function MurmurHashV2(str, seed) {
23568
- var l = str.length, h = seed ^ l, i = 0, k;
23569
+ if (typeof str === 'string')
23570
+ str = createBuffer(str);
23571
+ let l = str.length, h = seed ^ l, i = 0, k;
23569
23572
  while (l >= 4) {
23570
- k = str.charCodeAt(i) & 0xff | (str.charCodeAt(++i) & 0xff) << 8 | (str.charCodeAt(++i) & 0xff) << 16 | (str.charCodeAt(++i) & 0xff) << 24;
23573
+ k = str[i] & 0xff | (str[++i] & 0xff) << 8 | (str[++i] & 0xff) << 16 | (str[++i] & 0xff) << 24;
23571
23574
  k = (k & 0xffff) * 0x5bd1e995 + (((k >>> 16) * 0x5bd1e995 & 0xffff) << 16);
23572
23575
  k ^= k >>> 24;
23573
23576
  k = (k & 0xffff) * 0x5bd1e995 + (((k >>> 16) * 0x5bd1e995 & 0xffff) << 16);
@@ -23577,11 +23580,11 @@
23577
23580
  }
23578
23581
  switch (l) {
23579
23582
  case 3:
23580
- h ^= (str.charCodeAt(i + 2) & 0xff) << 16;
23583
+ h ^= (str[i + 2] & 0xff) << 16;
23581
23584
  case 2:
23582
- h ^= (str.charCodeAt(i + 1) & 0xff) << 8;
23585
+ h ^= (str[i + 1] & 0xff) << 8;
23583
23586
  case 1:
23584
- h ^= str.charCodeAt(i) & 0xff;
23587
+ h ^= str[i] & 0xff;
23585
23588
  h = (h & 0xffff) * 0x5bd1e995 + (((h >>> 16) * 0x5bd1e995 & 0xffff) << 16);
23586
23589
  }
23587
23590
  h ^= h >>> 13;
@@ -23590,7 +23593,7 @@
23590
23593
  return h >>> 0;
23591
23594
  }
23592
23595
  ;
23593
- /**
23596
+ /*
23594
23597
  * JS Implementation of MurmurHash3 (r136) (as of May 20, 2011)
23595
23598
  *
23596
23599
  * @author <a href="mailto:gary.court@gmail.com">Gary Court</a>
@@ -23598,12 +23601,14 @@
23598
23601
  * @author <a href="mailto:aappleby@gmail.com">Austin Appleby</a>
23599
23602
  * @see http://sites.google.com/site/murmurhash/
23600
23603
  *
23601
- * @param {string} key ASCII only
23604
+ * @param {Uint8Array | string} key ASCII only
23602
23605
  * @param {number} seed Positive integer only
23603
23606
  * @return {number} 32-bit positive integer hash
23604
23607
  */
23605
23608
  function MurmurHashV3(key, seed) {
23606
- var remainder, bytes, h1, h1b, c1, c1b, c2, c2b, k1, i;
23609
+ if (typeof key === 'string')
23610
+ key = createBuffer(key);
23611
+ let remainder, bytes, h1, h1b, c1, c1b, c2, c2b, k1, i;
23607
23612
  remainder = key.length & 3; // key.length % 4
23608
23613
  bytes = key.length - remainder;
23609
23614
  h1 = seed;
@@ -23611,7 +23616,7 @@
23611
23616
  c2 = 0x1b873593;
23612
23617
  i = 0;
23613
23618
  while (i < bytes) {
23614
- k1 = key.charCodeAt(i) & 0xff | (key.charCodeAt(++i) & 0xff) << 8 | (key.charCodeAt(++i) & 0xff) << 16 | (key.charCodeAt(++i) & 0xff) << 24;
23619
+ k1 = key[i] & 0xff | (key[++i] & 0xff) << 8 | (key[++i] & 0xff) << 16 | (key[++i] & 0xff) << 24;
23615
23620
  ++i;
23616
23621
  k1 = (k1 & 0xffff) * c1 + (((k1 >>> 16) * c1 & 0xffff) << 16) & 0xffffffff;
23617
23622
  k1 = k1 << 15 | k1 >>> 17;
@@ -23624,11 +23629,11 @@
23624
23629
  k1 = 0;
23625
23630
  switch (remainder) {
23626
23631
  case 3:
23627
- k1 ^= (key.charCodeAt(i + 2) & 0xff) << 16;
23632
+ k1 ^= (key[i + 2] & 0xff) << 16;
23628
23633
  case 2:
23629
- k1 ^= (key.charCodeAt(i + 1) & 0xff) << 8;
23634
+ k1 ^= (key[i + 1] & 0xff) << 8;
23630
23635
  case 1:
23631
- k1 ^= key.charCodeAt(i) & 0xff;
23636
+ k1 ^= key[i] & 0xff;
23632
23637
  k1 = (k1 & 0xffff) * c1 + (((k1 >>> 16) * c1 & 0xffff) << 16) & 0xffffffff;
23633
23638
  k1 = k1 << 15 | k1 >>> 17;
23634
23639
  k1 = (k1 & 0xffff) * c2 + (((k1 >>> 16) * c2 & 0xffff) << 16) & 0xffffffff;
@@ -23642,15 +23647,13 @@
23642
23647
  h1 ^= h1 >>> 16;
23643
23648
  return h1 >>> 0;
23644
23649
  }
23645
- var murmur = MurmurHashV3;
23650
+ const murmur = MurmurHashV3;
23646
23651
  murmur.v2 = MurmurHashV2;
23647
23652
  murmur.v3 = MurmurHashV3;
23648
23653
  if (true) {
23649
23654
  module.exports = murmur;
23650
23655
  }
23651
- else {
23652
- var _previousRoot;
23653
- }
23656
+ else { }
23654
23657
  })();
23655
23658
  /***/
23656
23659
  }),
@@ -26022,8 +26025,11 @@
26022
26025
  };
26023
26026
  }
26024
26027
  exports.emptyTrie = emptyTrie;
26028
+ function isNumberTrieNodeKey(input) {
26029
+ return ['0', '1', '2'].includes(input);
26030
+ }
26025
26031
  function getKeys(trie) {
26026
- return Object.keys(trie).filter(x => x !== 'hash');
26032
+ return Object.keys(trie).filter(isNumberTrieNodeKey);
26027
26033
  }
26028
26034
  exports.getKeys = getKeys;
26029
26035
  function keyToTimestamp(key) {
@@ -26041,7 +26047,7 @@
26041
26047
  let hash = timestamp.hash();
26042
26048
  let key = Number(Math.floor(timestamp.millis() / 1000 / 60)).toString(3);
26043
26049
  trie = Object.assign({}, trie, {
26044
- hash: trie.hash ^ hash
26050
+ hash: (trie.hash || 0) ^ hash
26045
26051
  });
26046
26052
  return insertKey(trie, key, hash);
26047
26053
  }
@@ -26051,10 +26057,11 @@
26051
26057
  return trie;
26052
26058
  }
26053
26059
  const c = key[0];
26054
- const n = trie[c] || {};
26060
+ const t = isNumberTrieNodeKey(c) ? trie[c] : undefined;
26061
+ const n = t || {};
26055
26062
  return Object.assign({}, trie, {
26056
26063
  [c]: Object.assign({}, n, insertKey(n, key.slice(1), hash), {
26057
- hash: n.hash ^ hash
26064
+ hash: (n.hash || 0) ^ hash
26058
26065
  })
26059
26066
  });
26060
26067
  }
@@ -26098,11 +26105,11 @@
26098
26105
  // multiple passes to sync up a trie.
26099
26106
  for (let i = 0; i < keys.length; i++) {
26100
26107
  let key = keys[i];
26101
- if (!node1[key] || !node2[key]) {
26102
- break;
26103
- }
26104
26108
  let next1 = node1[key];
26105
26109
  let next2 = node2[key];
26110
+ if (!next1 || !next2) {
26111
+ break;
26112
+ }
26106
26113
  if (next1.hash !== next2.hash) {
26107
26114
  diffkey = key;
26108
26115
  break;
@@ -26115,6 +26122,7 @@
26115
26122
  node1 = node1[diffkey] || emptyTrie();
26116
26123
  node2 = node2[diffkey] || emptyTrie();
26117
26124
  }
26125
+ return null;
26118
26126
  }
26119
26127
  exports.diff = diff;
26120
26128
  function prune(trie, n = 2) {
@@ -26129,7 +26137,11 @@
26129
26137
  };
26130
26138
  // Prune child nodes.
26131
26139
  for (let k of keys.slice(-n)) {
26132
- next[k] = prune(trie[k], n);
26140
+ const node = trie[k];
26141
+ if (!node) {
26142
+ throw new Error(`TrieNode for key ${k} could not be found`);
26143
+ }
26144
+ next[k] = prune(node, n);
26133
26145
  }
26134
26146
  return next;
26135
26147
  }
@@ -26137,7 +26149,10 @@
26137
26149
  function debug(trie, k = '', indent = 0) {
26138
26150
  const str = ' '.repeat(indent) + (k !== '' ? `k: ${k} ` : '') + `hash: ${trie.hash || '(empty)'}\n`;
26139
26151
  return str + getKeys(trie).map(key => {
26140
- return debug(trie[key], key, indent + 2);
26152
+ const node = trie[key];
26153
+ if (!node)
26154
+ return '';
26155
+ return debug(node, key, indent + 2);
26141
26156
  }).join('');
26142
26157
  }
26143
26158
  exports.debug = debug;
@@ -26161,7 +26176,7 @@
26161
26176
  const murmurhash_1 = __importDefault(__webpack_require__(/*! murmurhash */ "./node_modules/murmurhash/murmurhash.js"));
26162
26177
  const uuid_1 = __webpack_require__(/*! uuid */ "./node_modules/uuid/dist/esm-node/index.js");
26163
26178
  // A mutable global clock
26164
- let clock = null;
26179
+ let clock;
26165
26180
  function setClock(clock_) {
26166
26181
  clock = clock_;
26167
26182
  }
@@ -26195,8 +26210,12 @@
26195
26210
  merkle: {}
26196
26211
  };
26197
26212
  }
26213
+ const ts = Timestamp.parse(data.timestamp);
26214
+ if (!ts) {
26215
+ throw new Timestamp.InvalidError(data.timestamp);
26216
+ }
26198
26217
  return {
26199
- timestamp: MutableTimestamp.from(Timestamp.parse(data.timestamp)),
26218
+ timestamp: MutableTimestamp.from(ts),
26200
26219
  merkle: data.merkle
26201
26220
  };
26202
26221
  }
@@ -26346,10 +26365,12 @@
26346
26365
  /**
26347
26366
  * maximum timestamp
26348
26367
  */
26368
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
26349
26369
  Timestamp.max = Timestamp.parse('9999-12-31T23:59:59.999Z-FFFF-FFFFFFFFFFFFFFFF');
26350
26370
  /**
26351
26371
  * zero/minimum timestamp
26352
26372
  */
26373
+ // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
26353
26374
  Timestamp.zero = Timestamp.parse('1970-01-01T00:00:00.000Z-0000-0000000000000000');
26354
26375
  Timestamp.since = isoString => isoString + '-0000-0000000000000000';
26355
26376
  /**
@@ -26373,6 +26394,12 @@
26373
26394
  this.name = 'OverflowError';
26374
26395
  }
26375
26396
  };
26397
+ Timestamp.InvalidError = class InvalidError extends Error {
26398
+ constructor(...args) {
26399
+ super(['timestamp is not valid'].concat(args.map(String)).join(' '));
26400
+ this.name = 'InvalidError';
26401
+ }
26402
+ };
26376
26403
  exports.Timestamp = Timestamp;
26377
26404
  class MutableTimestamp extends Timestamp {
26378
26405
  static from(timestamp) {
@@ -26495,6 +26522,7 @@
26495
26522
  !*** ./packages/crdt/dist/src/proto/sync_pb.js ***!
26496
26523
  \*************************************************/
26497
26524
  /***/ ((__unused_webpack_module, exports, __webpack_require__) => {
26525
+ "use strict";
26498
26526
  // source: sync.proto
26499
26527
  /**
26500
26528
  * @fileoverview
@@ -35507,40 +35535,37 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
35507
35535
  let errors = [];
35508
35536
  let lowestPriority = 0;
35509
35537
  let originalCategoryBalance = [];
35538
+ let setToZero = [];
35510
35539
  let categories = await _db__WEBPACK_IMPORTED_MODULE_3__.all('SELECT * FROM v_categories WHERE tombstone = 0');
35511
35540
  //clears templated categories
35512
35541
  for (let c = 0; c < categories.length; c++) {
35513
35542
  let category = categories[c];
35514
35543
  let budgeted = await (0, _actions__WEBPACK_IMPORTED_MODULE_6__.getSheetValue)(_shared_months__WEBPACK_IMPORTED_MODULE_0__.sheetForMonth(month), `budget-${category.id}`);
35515
- if (budgeted) {
35516
- originalCategoryBalance.push({
35517
- cat: category,
35518
- amount: budgeted,
35519
- isIncome: category.is_income
35520
- });
35521
- }
35522
35544
  let template = category_templates[category.id];
35523
35545
  if (template) {
35524
35546
  for (let l = 0; l < template.length; l++) {
35525
35547
  lowestPriority = template[l].priority > lowestPriority ? template[l].priority : lowestPriority;
35526
35548
  }
35527
35549
  }
35528
- }
35529
- await (0, _actions__WEBPACK_IMPORTED_MODULE_6__.setZero)({
35530
- month
35531
- });
35532
- //setZero() sets budgeted Income to 0. Reset income categories before continuing.
35533
- if ((0, _actions__WEBPACK_IMPORTED_MODULE_6__.isReflectBudget)()) {
35534
- for (let l = 0; l < originalCategoryBalance.length; l++) {
35535
- if (originalCategoryBalance[l].isIncome) {
35536
- await (0, _actions__WEBPACK_IMPORTED_MODULE_6__.setBudget)({
35537
- category: originalCategoryBalance[l].cat.id,
35538
- month,
35539
- amount: originalCategoryBalance[l].amount
35540
- });
35541
- }
35550
+ if (budgeted) {
35551
+ originalCategoryBalance.push({
35552
+ category: category.id,
35553
+ amount: budgeted,
35554
+ isIncome: category.is_income,
35555
+ isTemplate: template ? true : false
35556
+ });
35557
+ setToZero.push({
35558
+ category: category.id,
35559
+ amount: 0,
35560
+ isIncome: category.is_income,
35561
+ isTemplate: template ? true : false
35562
+ });
35542
35563
  }
35543
35564
  }
35565
+ await setGoalBudget({
35566
+ month,
35567
+ templateBudget: setToZero.filter(f => f.isTemplate === true && f.isIncome === 0)
35568
+ });
35544
35569
  // find all remainder templates, place them after all other templates
35545
35570
  let remainder_found;
35546
35571
  let remainder_priority = lowestPriority + 1;
@@ -35579,7 +35604,8 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
35579
35604
  let skipSchedule = false;
35580
35605
  let isScheduleOrBy = false;
35581
35606
  let priorityCheck = 0;
35582
- if (template.filter(t => t.type === 'schedule' || t.type === 'by').length > 0) {
35607
+ if (template.filter(t => (t.type === 'schedule' || t.type === 'by') && t.priority === priority).length > 0) {
35608
+ template = template.filter(t => t.priority === priority && (t.type !== 'schedule' || t.type !== 'by') || t.type === 'schedule' || t.type === 'by');
35583
35609
  let { lowPriority, errorNotice } = await checkScheduleTemplates(template);
35584
35610
  priorityCheck = lowPriority;
35585
35611
  skipSchedule = priorityCheck !== priority ? true : false;
@@ -35617,17 +35643,18 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
35617
35643
  });
35618
35644
  }
35619
35645
  if (!force) {
35620
- //if overwrite is not preferred, set cell to original value
35646
+ //if overwrite is not preferred, set cell to original value;
35647
+ originalCategoryBalance = originalCategoryBalance.filter(c => c.isIncome === 0 && c.isTemplate);
35621
35648
  for (let l = 0; l < originalCategoryBalance.length; l++) {
35622
35649
  await (0, _actions__WEBPACK_IMPORTED_MODULE_6__.setBudget)({
35623
- category: originalCategoryBalance[l].cat.id,
35650
+ category: originalCategoryBalance[l].category,
35624
35651
  month,
35625
35652
  amount: originalCategoryBalance[l].amount
35626
35653
  });
35627
35654
  //if overwrite is not preferred, remove template errors for category
35628
35655
  let j = errors.length;
35629
35656
  for (let k = 0; k < j; k++) {
35630
- if (errors[k].includes(originalCategoryBalance[l].cat.name)) {
35657
+ if (errors[k].includes(categories.filter(c => c.id === originalCategoryBalance[l].category)[0].name)) {
35631
35658
  errors.splice(k, 1);
35632
35659
  j--;
35633
35660
  }
@@ -35704,6 +35731,7 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
35704
35731
  let errors = [];
35705
35732
  let all_schedule_names = await _db__WEBPACK_IMPORTED_MODULE_3__.all('SELECT name from schedules WHERE name NOT NULL AND tombstone = 0');
35706
35733
  all_schedule_names = all_schedule_names.map(v => v.name);
35734
+ let scheduleFlag = false; //only run schedules portion once
35707
35735
  // remove lines for past dates, calculate repeating dates
35708
35736
  template_lines = template_lines.filter(template => {
35709
35737
  switch (template.type) {
@@ -35747,6 +35775,9 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
35747
35775
  if (a.type === 'by' && !a.annual) {
35748
35776
  return _shared_months__WEBPACK_IMPORTED_MODULE_0__.differenceInCalendarMonths(`${a.month}-01`, `${b.month}-01`);
35749
35777
  }
35778
+ else if (a.type === 'schedule' || b.type === 'schedule') {
35779
+ return a.priority - b.priority;
35780
+ }
35750
35781
  else {
35751
35782
  return a.type.localeCompare(b.type);
35752
35783
  }
@@ -35786,7 +35817,7 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
35786
35817
  else {
35787
35818
  increment = limit;
35788
35819
  }
35789
- if (increment < budgetAvailable || !priority) {
35820
+ if (to_budget + increment < budgetAvailable || !priority) {
35790
35821
  to_budget += increment;
35791
35822
  }
35792
35823
  else {
@@ -35960,61 +35991,123 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
35960
35991
  }
35961
35992
  case 'schedule':
35962
35993
  {
35963
- let { id: schedule_id } = await _db__WEBPACK_IMPORTED_MODULE_3__.first('SELECT id FROM schedules WHERE name = ?', [template.name]);
35964
- let rule = await (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getRuleForSchedule)(schedule_id);
35965
- let conditions = rule.serialize().conditions;
35966
- let { date: dateCond, amount: amountCond } = (0, _shared_schedules__WEBPACK_IMPORTED_MODULE_1__.extractScheduleConds)(conditions);
35967
- let next_date_string = (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getNextDate)(dateCond, _shared_months__WEBPACK_IMPORTED_MODULE_0__._parse(current_month));
35968
- let isRepeating = Object(dateCond.value) === dateCond.value && 'frequency' in dateCond.value;
35969
- let num_months = _shared_months__WEBPACK_IMPORTED_MODULE_0__.differenceInCalendarMonths(next_date_string, current_month);
35970
- if (isRepeating) {
35971
- let monthlyTarget = 0;
35972
- let next_month = _shared_months__WEBPACK_IMPORTED_MODULE_0__.addMonths(current_month, num_months + 1);
35973
- let next_date = (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getNextDate)(dateCond, _shared_months__WEBPACK_IMPORTED_MODULE_0__._parse(current_month));
35974
- while (next_date < next_month) {
35975
- monthlyTarget += amountCond.value;
35976
- next_date = _shared_months__WEBPACK_IMPORTED_MODULE_0__.addDays(next_date, 1);
35977
- next_date = (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getNextDate)(dateCond, _shared_months__WEBPACK_IMPORTED_MODULE_0__._parse(next_date));
35994
+ if (!scheduleFlag) {
35995
+ scheduleFlag = true;
35996
+ let template = template_lines.filter(t => t.type === 'schedule');
35997
+ //in the case of multiple templates per category, schedules may have wrong priority level
35998
+ let t = [];
35999
+ let totalScheduledGoal = 0;
36000
+ for (let ll = 0; ll < template.length; ll++) {
36001
+ let { id: sid, completed: complete } = await _db__WEBPACK_IMPORTED_MODULE_3__.first('SELECT * FROM schedules WHERE name = ?', [template[ll].name]);
36002
+ console.log(complete);
36003
+ let rule = await (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getRuleForSchedule)(sid);
36004
+ let conditions = rule.serialize().conditions;
36005
+ let { date: dateConditions, amount: amountCondition } = (0, _shared_schedules__WEBPACK_IMPORTED_MODULE_1__.extractScheduleConds)(conditions);
36006
+ let target = -amountCondition.value;
36007
+ let next_date_string = (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getNextDate)(dateConditions, _shared_months__WEBPACK_IMPORTED_MODULE_0__._parse(current_month));
36008
+ let target_interval = dateConditions.value.interval ? dateConditions.value.interval : 1;
36009
+ let target_frequency = dateConditions.value.frequency;
36010
+ let isRepeating = Object(dateConditions.value) === dateConditions.value && 'frequency' in dateConditions.value;
36011
+ let num_months = _shared_months__WEBPACK_IMPORTED_MODULE_0__.differenceInCalendarMonths(next_date_string, current_month);
36012
+ t.push({
36013
+ template: template[ll],
36014
+ target: target,
36015
+ next_date_string: next_date_string,
36016
+ target_interval: target_interval,
36017
+ target_frequency: target_frequency,
36018
+ num_months: num_months,
36019
+ completed: complete
36020
+ });
36021
+ if (!complete) {
36022
+ if (isRepeating) {
36023
+ let monthlyTarget = 0;
36024
+ let next_month = _shared_months__WEBPACK_IMPORTED_MODULE_0__.addMonths(current_month, t[ll].num_months + 1);
36025
+ let next_date = (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getNextDate)(dateConditions, _shared_months__WEBPACK_IMPORTED_MODULE_0__._parse(current_month));
36026
+ while (next_date < next_month) {
36027
+ monthlyTarget += amountCondition.value;
36028
+ next_date = _shared_months__WEBPACK_IMPORTED_MODULE_0__.addDays(next_date, 1);
36029
+ next_date = (0, _schedules_app__WEBPACK_IMPORTED_MODULE_4__.getNextDate)(dateConditions, _shared_months__WEBPACK_IMPORTED_MODULE_0__._parse(next_date));
36030
+ }
36031
+ t[ll].target = -monthlyTarget;
36032
+ totalScheduledGoal += target;
36033
+ }
36034
+ }
36035
+ else {
36036
+ errors.push(`Schedule ${t[ll].template.name} is a completed schedule.`);
36037
+ }
35978
36038
  }
35979
- amountCond.value = monthlyTarget;
35980
- }
35981
- if (template.full === true || (0, _actions__WEBPACK_IMPORTED_MODULE_6__.isReflectBudget)()) {
35982
- if (num_months === 0) {
35983
- to_budget = -(0, _shared_schedules__WEBPACK_IMPORTED_MODULE_1__.getScheduledAmount)(amountCond.value);
36039
+ t = t.filter(t => t.completed === 0);
36040
+ t = t.sort((a, b) => b.target - a.target);
36041
+ let diff = 0;
36042
+ if (balance >= totalScheduledGoal) {
36043
+ for (let ll = 0; ll < t.length; ll++) {
36044
+ if (t[ll].num_months < 0) {
36045
+ errors.push(`Non-repeating schedule ${t[ll].template.name} was due on ${t[ll].next_date_string}, which is in the past.`);
36046
+ break;
36047
+ }
36048
+ if (t[ll].template.full && t[ll].num_months === 0 || t[ll].target_frequency === 'weekly' || t[ll].target_frequency === 'daily') {
36049
+ diff += t[ll].target;
36050
+ }
36051
+ else if (t[ll].template.full && t[ll].num_months > 0) {
36052
+ diff += 0;
36053
+ }
36054
+ else {
36055
+ diff += t[ll].target / t[ll].target_interval;
36056
+ }
36057
+ }
35984
36058
  }
35985
- if ((0, _actions__WEBPACK_IMPORTED_MODULE_6__.isReflectBudget)() && !template.full) {
35986
- errors.push(`Report budgets require the full option for Schedules.`);
36059
+ else if (balance < totalScheduledGoal) {
36060
+ for (let ll = 0; ll < t.length; ll++) {
36061
+ if ((0, _actions__WEBPACK_IMPORTED_MODULE_6__.isReflectBudget)()) {
36062
+ if (!t[ll].template.full) {
36063
+ errors.push(`Report budgets require the full option for Schedules.`);
36064
+ break;
36065
+ }
36066
+ if (t[ll].template.full && t[ll].num_months === 0) {
36067
+ to_budget += t[ll].target;
36068
+ }
36069
+ }
36070
+ if (!(0, _actions__WEBPACK_IMPORTED_MODULE_6__.isReflectBudget)()) {
36071
+ if (t[ll].num_months < 0) {
36072
+ errors.push(`Non-repeating schedule ${t[ll].template.name} was due on ${t[ll].next_date_string}, which is in the past.`);
36073
+ break;
36074
+ }
36075
+ if (t[ll].template.full && t[ll].num_months > 0) {
36076
+ remainder = 0;
36077
+ }
36078
+ else if (ll === 0 && !t[ll].template.full) {
36079
+ remainder = t[ll].target - last_month_balance;
36080
+ }
36081
+ else {
36082
+ remainder = t[ll].target - remainder;
36083
+ }
36084
+ let tg = 0;
36085
+ if (remainder >= 0) {
36086
+ tg = remainder;
36087
+ remainder = 0;
36088
+ }
36089
+ else {
36090
+ tg = 0;
36091
+ remainder = Math.abs(remainder);
36092
+ }
36093
+ if (t[ll].template.full || t[ll].num_months === 0 || t[ll].target_frequency === 'weekly' || t[ll].target_frequency === 'daily') {
36094
+ diff += tg;
36095
+ }
36096
+ else if (t[ll].template.full && t[ll].num_months > 0) {
36097
+ diff += 0;
36098
+ }
36099
+ else {
36100
+ diff += tg / (t[ll].num_months + 1);
36101
+ }
36102
+ }
36103
+ }
35987
36104
  }
35988
- break;
35989
- }
35990
- if (l === 0)
35991
- remainder = last_month_balance;
35992
- remainder = -(0, _shared_schedules__WEBPACK_IMPORTED_MODULE_1__.getScheduledAmount)(amountCond.value) - remainder;
35993
- let target = 0;
35994
- if (remainder >= 0) {
35995
- target = remainder;
35996
- remainder = 0;
35997
- }
35998
- else {
35999
- target = 0;
36000
- remainder = Math.abs(remainder);
36001
- }
36002
- let diff = num_months >= 0 ? Math.round(target / (num_months + 1)) : 0;
36003
- if (num_months < 0) {
36004
- errors.push(`Non-repeating schedule ${template.name} was due on ${next_date_string}, which is in the past.`);
36005
- return {
36006
- errors
36007
- };
36008
- }
36009
- else if (num_months >= 0) {
36010
- if (diff >= 0 && num_months >= 0 && to_budget + diff < budgetAvailable || !priority) {
36105
+ diff = Math.round(diff);
36106
+ if (diff > 0 && to_budget + diff <= budgetAvailable || !priority) {
36011
36107
  to_budget += diff;
36012
- if (l === template_lines.length - 1)
36013
- to_budget -= spent;
36014
36108
  }
36015
- else {
36016
- if (budgetAvailable > 0)
36017
- to_budget = budgetAvailable;
36109
+ else if (to_budget + diff > budgetAvailable && budgetAvailable >= 0) {
36110
+ to_budget = budgetAvailable;
36018
36111
  errors.push(`Insufficient funds.`);
36019
36112
  }
36020
36113
  }
@@ -36046,8 +36139,8 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
36046
36139
  if (hold && balance > limit) {
36047
36140
  to_budget = 0;
36048
36141
  }
36049
- else if (to_budget + last_month_balance > limit) {
36050
- to_budget = limit - last_month_balance;
36142
+ else if (to_budget + balance > limit) {
36143
+ to_budget = limit - balance;
36051
36144
  }
36052
36145
  }
36053
36146
  if ((category.budgeted != null && category.budgeted !== 0 || to_budget === 0) && !force) {
@@ -38533,10 +38626,13 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
38533
38626
  if (data.data) {
38534
38627
  data = data.data;
38535
38628
  }
38629
+ if (data.budget) {
38630
+ data = data.budget;
38631
+ }
38536
38632
  return data;
38537
38633
  }
38538
38634
  function getBudgetName(_filepath, data) {
38539
- return data.budget_name;
38635
+ return data.budget_name || data.name;
38540
38636
  }
38541
38637
  /***/
38542
38638
  }),
@@ -40277,7 +40373,8 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
40277
40373
  throw new Error(`File not found at the provided path: ${filepath}`);
40278
40374
  }
40279
40375
  let buffer = Buffer.from(await _platform_server_fs__WEBPACK_IMPORTED_MODULE_7__.readFile(filepath, 'binary'));
40280
- await (0, _importers__WEBPACK_IMPORTED_MODULE_34__.handleBudgetImport)(type, filepath, buffer);
40376
+ let results = await (0, _importers__WEBPACK_IMPORTED_MODULE_34__.handleBudgetImport)(type, filepath, buffer);
40377
+ return results || {};
40281
40378
  }
40282
40379
  catch (err) {
40283
40380
  err.message = 'Error importing budget: ' + err.message;
@@ -40286,7 +40383,6 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
40286
40383
  error: 'internal-error'
40287
40384
  };
40288
40385
  }
40289
- return {};
40290
40386
  };
40291
40387
  handlers['export-budget'] = async function () {
40292
40388
  return await _cloud_storage__WEBPACK_IMPORTED_MODULE_28__.exportBuffer();
@@ -41377,7 +41473,7 @@ CREATE TABLE kvcache_key (id INTEGER PRIMARY KEY, key REAL);
41377
41473
  }
41378
41474
  // Methods
41379
41475
  async function checkIfScheduleExists(name, scheduleId) {
41380
- let idForName = await _db__WEBPACK_IMPORTED_MODULE_11__.first('SELECT id from schedules WHERE name = ?', [name]);
41476
+ let idForName = await _db__WEBPACK_IMPORTED_MODULE_11__.first('SELECT id from schedules WHERE tombstone = 0 AND name = ?', [name]);
41381
41477
  if (idForName == null) {
41382
41478
  return false;
41383
41479
  }
@@ -0,0 +1,5 @@
1
+ BEGIN TRANSACTION;
2
+
3
+ ALTER TABLE schedules_next_date ADD COLUMN tombstone INTEGER DEFAULT 0;
4
+
5
+ COMMIT;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@actual-app/api",
3
- "version": "6.2.0",
3
+ "version": "6.2.1",
4
4
  "license": "MIT",
5
5
  "description": "An API for Actual",
6
6
  "main": "dist/index.js",