@ghostlytools/cli 1.3.1 → 1.3.3

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.
Files changed (72) hide show
  1. package/README.md +6 -6
  2. package/dist/assets/{api-Dq2QXQDk.js → api-B1fADtqd.js} +65 -20
  3. package/dist/assets/api-B1fADtqd.js.map +1 -0
  4. package/dist/assets/{api-TiB5QSG9.js → api-Bg7bh_6E.js} +2 -2
  5. package/dist/assets/{apiKit-CA2x5GJF.js → apiKit-BsUZPHLn.js} +44 -33
  6. package/dist/assets/apiKit-BsUZPHLn.js.map +1 -0
  7. package/dist/assets/{apps-BxV9i_Y4.js → apps-BaUNt-5c.js} +91 -24
  8. package/dist/assets/apps-BaUNt-5c.js.map +1 -0
  9. package/dist/assets/{apps-C-T8jeji.js → apps-DepomCiX.js} +1 -1
  10. package/dist/assets/{arkade-C_qDmHnm.js → arkade-CNnMaoEQ.js} +4 -4
  11. package/dist/assets/arkade-CNnMaoEQ.js.map +1 -0
  12. package/dist/assets/{backup-Bugnn3Ue.js → backup-B5Q1W-Ey.js} +1 -1
  13. package/dist/assets/{backup-CnMN2oUK.js → backup-Bbz3lyC5.js} +6 -6
  14. package/dist/assets/{backup-CnMN2oUK.js.map → backup-Bbz3lyC5.js.map} +1 -1
  15. package/dist/assets/buttons-CUd7j0ZA.js +2 -0
  16. package/dist/assets/{buttons-CvNBzh2S.js → buttons-DS1iURp8.js} +4 -4
  17. package/dist/assets/{buttons-CvNBzh2S.js.map → buttons-DS1iURp8.js.map} +1 -1
  18. package/dist/assets/{envelope-WjingYSc.js → envelope-fNC941z4.js} +2 -2
  19. package/dist/assets/{envelope-WjingYSc.js.map → envelope-fNC941z4.js.map} +1 -1
  20. package/dist/assets/{errors-DO5z6h_l.js → errors-B-zMxbcd.js} +6 -5
  21. package/dist/assets/{errors-DO5z6h_l.js.map → errors-B-zMxbcd.js.map} +1 -1
  22. package/dist/assets/{ghostly_iroh_web-Dvzh3Y6E.js → ghostly_iroh_web-BsAEFIjl.js} +30 -36
  23. package/dist/assets/ghostly_iroh_web-BsAEFIjl.js.map +1 -0
  24. package/dist/assets/ghostly_iroh_web_bg.wasm +0 -0
  25. package/dist/assets/{groupFiles-IEUW3DQz.js → groupFiles-6qnLCnOm.js} +82 -29
  26. package/dist/assets/groupFiles-6qnLCnOm.js.map +1 -0
  27. package/dist/assets/{host-CWt-jtqz.js → host-Dj3C1fn3.js} +305 -68
  28. package/dist/assets/host-Dj3C1fn3.js.map +1 -0
  29. package/dist/assets/{hyperdhtRelay-CPYwSLLS.js → hyperdhtRelay-CrgYQN-g.js} +2 -2
  30. package/dist/assets/{hyperdhtRelay-CPYwSLLS.js.map → hyperdhtRelay-CrgYQN-g.js.map} +1 -1
  31. package/dist/assets/{irohWeb-4oChIOIp.js → irohWeb-DSyLp5Re.js} +3 -3
  32. package/dist/assets/{irohWeb-4oChIOIp.js.map → irohWeb-DSyLp5Re.js.map} +1 -1
  33. package/dist/assets/{main-DbqcdShN.js → main-BDd11Yd1.js} +159 -54
  34. package/dist/assets/main-BDd11Yd1.js.map +1 -0
  35. package/dist/assets/{mainline-ZkiOnevs.js → mainline-CLTo0nGa.js} +2 -2
  36. package/dist/assets/{mainline-ZkiOnevs.js.map → mainline-CLTo0nGa.js.map} +1 -1
  37. package/dist/assets/{networkReason-CetKkTPo.js → networkReason-DwcadZz5.js} +2 -2
  38. package/dist/assets/{networkReason-CetKkTPo.js.map → networkReason-DwcadZz5.js.map} +1 -1
  39. package/dist/assets/{nwc-CgkqyvsE.js → nwc-BNFyyECH.js} +3 -3
  40. package/dist/assets/{nwc-CgkqyvsE.js.map → nwc-BNFyyECH.js.map} +1 -1
  41. package/dist/assets/{nwcProvider-4eVz_8HP.js → nwcProvider-BbjJOfLD.js} +2 -2
  42. package/dist/assets/{nwcProvider-4eVz_8HP.js.map → nwcProvider-BbjJOfLD.js.map} +1 -1
  43. package/dist/assets/{profiles-BHc9pEYg.js → profiles-gPCjLOQq.js} +2 -2
  44. package/dist/assets/{profiles-BHc9pEYg.js.map → profiles-gPCjLOQq.js.map} +1 -1
  45. package/dist/assets/{registry-DlAKO0Fy.js → registry-CoLHpxkb.js} +17 -32
  46. package/dist/assets/registry-CoLHpxkb.js.map +1 -0
  47. package/dist/assets/{registry-OBJBnHVQ.js → registry-DoTb6uEr.js} +1 -1
  48. package/dist/assets/{resolve-CouHhCpJ.js → resolve-BIDJ-UUl.js} +18 -3
  49. package/dist/assets/resolve-BIDJ-UUl.js.map +1 -0
  50. package/dist/assets/{server-Ss0gJ-nw.js → server-Bx3RGkBC.js} +380 -116
  51. package/dist/assets/server-Bx3RGkBC.js.map +1 -0
  52. package/dist/assets/{src-DDzSERyc.js → src-D7gcJElT.js} +470 -242
  53. package/dist/assets/src-D7gcJElT.js.map +1 -0
  54. package/dist/assets/{turnRefs-B87dtrHM.js → turnRefs-PN644M9o.js} +2 -2
  55. package/dist/assets/{turnRefs-B87dtrHM.js.map → turnRefs-PN644M9o.js.map} +1 -1
  56. package/dist/assets/{usdt-Fj8CQO2z.js → usdt-B2TLRlYa.js} +3 -3
  57. package/dist/assets/{usdt-Fj8CQO2z.js.map → usdt-B2TLRlYa.js.map} +1 -1
  58. package/dist/ghostly.mjs +1 -1
  59. package/package.json +1 -1
  60. package/dist/assets/api-Dq2QXQDk.js.map +0 -1
  61. package/dist/assets/apiKit-CA2x5GJF.js.map +0 -1
  62. package/dist/assets/apps-BxV9i_Y4.js.map +0 -1
  63. package/dist/assets/arkade-C_qDmHnm.js.map +0 -1
  64. package/dist/assets/buttons-Bj7Vf7Pn.js +0 -2
  65. package/dist/assets/ghostly_iroh_web-Dvzh3Y6E.js.map +0 -1
  66. package/dist/assets/groupFiles-IEUW3DQz.js.map +0 -1
  67. package/dist/assets/host-CWt-jtqz.js.map +0 -1
  68. package/dist/assets/main-DbqcdShN.js.map +0 -1
  69. package/dist/assets/registry-DlAKO0Fy.js.map +0 -1
  70. package/dist/assets/resolve-CouHhCpJ.js.map +0 -1
  71. package/dist/assets/server-Ss0gJ-nw.js.map +0 -1
  72. package/dist/assets/src-DDzSERyc.js.map +0 -1
@@ -1,7 +1,7 @@
1
- import { Fn as decodeBolt11, Fr as ChatFiles, Lr as transferEnded, Nn as requestLnurlInvoice, Pn as resolveLightningDestination, Qn as GROUP_HAVE_FRAME, Ta as RateWindow, Ua as replySnippet, Xn as engineText, Yn as engineError, Zn as GROUP_FILE_LIMITS, _l as randomBytes, _n as walletNetworkOf, ar as readGroupHave, er as GROUP_WANT_NO_FRAME, fn as WALLET_NETWORKS, nr as groupFileFallback, or as readGroupWant, rr as isGroupMessageId, sr as readGroupWantNo, tr as fetchesByItself, vl as toBase64Url, ya as fileMessageText } from "./src-DDzSERyc.js";
1
+ import { $n as GROUP_FILE_LIMITS, Cl as randomBytes, Da as RateWindow, Fn as resolveLightningDestination, Ga as replySnippet, In as decodeBolt11, Lr as ChatFiles, Pn as requestLnurlInvoice, Xn as engineError, Zn as engineText, ar as isGroupMessageId, cr as readGroupWant, er as GROUP_HAVE_FRAME, fn as WALLET_NETWORKS, ir as groupFileFallback, lr as readGroupWantNo, nr as GROUP_WANT_NO_FRAME, rr as fetchesByItself, sr as readGroupHave, vn as walletNetworkOf, wl as toBase64Url, ya as fileMessageText, zr as transferEnded } from "./src-D7gcJElT.js";
2
2
  import { a as describeProvider, c as offeredIn, d as sourceProblem, n as PROVIDER_PLATFORMS, o as isNothingSpentError, s as networkMode, t as NothingSpentError, u as redact } from "./types-C4_KafL_.js";
3
3
  import { c as fileStore, f as store, i as STORES, m as wrap, o as databaseName, p as transact } from "./idb-B5L8wuOm.js";
4
- import { a as sealSeed, i as newDeviceKey, o as unsealSeed, t as networkReason } from "./networkReason-CetKkTPo.js";
4
+ import { a as sealSeed, i as newDeviceKey, o as unsealSeed, t as networkReason } from "./networkReason-DwcadZz5.js";
5
5
  import { t as BITCOIN_INVOICE_ON_TESTNET, u as mintNetwork } from "./mints-BrlY773j.js";
6
6
  import { f as FILE_BYTES_STEP, o as fileBytes, s as fileBytesOf } from "./fileBytes-Di7VZtmU.js";
7
7
  import { sha256 } from "@noble/hashes/sha2.js";
@@ -2296,6 +2296,7 @@ var GroupFileDesk = class {
2296
2296
  if (kept.held || kept.mine) return;
2297
2297
  const want = this.wants.get(kept.id);
2298
2298
  this.wants.delete(kept.id);
2299
+ if (want?.wire && want.holder) kept.left = want.holder;
2299
2300
  const edge = want?.wire && want.linkId ? this.edgesById.get(want.linkId) : void 0;
2300
2301
  const record = edge?.files.get("in", want.wire);
2301
2302
  const { size } = kept.meta;
@@ -2477,6 +2478,7 @@ var GroupFileDesk = class {
2477
2478
  this.byMessage.delete(`${groupId}\n${kept.message}`);
2478
2479
  this.wants.delete(kept.id);
2479
2480
  this.deps.transfers.delete(kept.id);
2481
+ await kept.writing?.catch(() => {});
2480
2482
  await this.deps.store.remove(kept.id).catch(() => {});
2481
2483
  }
2482
2484
  for (const [linkId, edge] of this.edgesById) if (edge.groupId === groupId) {
@@ -2515,7 +2517,7 @@ var GroupFileDesk = class {
2515
2517
  if (no) this.refused(groupId, peer, linkId, no.id, no.why);
2516
2518
  } else if (frame.t === "group-have") {
2517
2519
  const ids = readGroupHave(frame, groupId);
2518
- if (ids) this.heard(groupId, peer, ids);
2520
+ if (ids && this.edge(groupId, peer, linkId).haveTaken.take()) this.heard(groupId, peer, ids);
2519
2521
  }
2520
2522
  }
2521
2523
  /** A community's `group-have`, an application frame its signer sent the group. */
@@ -2545,6 +2547,7 @@ var GroupFileDesk = class {
2545
2547
  kept.holders = newestHolder(peer, kept.holders);
2546
2548
  want.wire = frame.id;
2547
2549
  want.why = void 0;
2550
+ want.moved = -1;
2548
2551
  want.movedAt = this.deps.now();
2549
2552
  }
2550
2553
  return edge.files.handle(frame);
@@ -2560,6 +2563,7 @@ var GroupFileDesk = class {
2560
2563
  }
2561
2564
  if (now - (want.wire ? want.movedAt : want.at) < GROUP_FILE_LIMITS.wantWaitMs) continue;
2562
2565
  if (want.wire) {
2566
+ kept.left = want.holder;
2563
2567
  const edge = want.linkId ? this.edgesById.get(want.linkId) : void 0;
2564
2568
  if (edge?.files.get("in", want.wire) && !transferEnded(edge.files.get("in", want.wire))) {
2565
2569
  edge.files.cancel("in", want.wire);
@@ -2630,16 +2634,16 @@ var GroupFileDesk = class {
2630
2634
  return [kept.author, ...kept.holders.filter((key) => key !== kept.author)].filter((key) => membership && key !== membership.me && membership.inRoster(key));
2631
2635
  }
2632
2636
  /**
2633
- * A known holder that answered busy, or the author whose edge another file of this device's is asked of, its edge up,
2634
- * serves when its place frees: the others are asked only when no known holder is worth waiting for (none in reach, or
2635
- * every one gone), as after a restart here. Only the author's edge holds them back while it is asked of: any member
2636
- * can say it holds files, and one that serves the file asked of it slowly would keep every other file it named here.
2637
+ * The author, its edge up, that answered busy or whose edge another file of this device's is asked of, serves when its
2638
+ * place frees: the others are asked only when it is not worth waiting for (out of reach), as after a restart here.
2639
+ * Only the author holds them back: any member can say it holds files, and one that answers busy, or serves the file
2640
+ * asked of it slowly, would keep every file it named here from coming while the author is away. Its busy only skips
2641
+ * it for the round.
2637
2642
  */
2638
2643
  waitForKnown(kept, want, known, edges) {
2639
- return known.some((key) => {
2640
- const linkId = edges.get(key) ?? "";
2641
- return this.deps.ready(linkId) && (want.busy?.has(key) || key === kept.author && this.askedOf(linkId, want));
2642
- });
2644
+ if (!known.includes(kept.author)) return false;
2645
+ const linkId = edges.get(kept.author) ?? "";
2646
+ return this.deps.ready(linkId) && (!!want.busy?.has(kept.author) || this.askedOf(linkId, want));
2643
2647
  }
2644
2648
  /** The want may ask this member in this round: not asked yet, it did not serve it damaged, and did not say it is gone. */
2645
2649
  mayAsk(kept, want, key, linkId) {
@@ -2666,6 +2670,7 @@ var GroupFileDesk = class {
2666
2670
  }
2667
2671
  const others = this.waitForKnown(kept, want, known, edges) ? [] : [...edges.keys()].filter((key) => !known.includes(key) && membership && key !== membership.me && membership.couldRead(key, kept.message));
2668
2672
  const order = [...known, ...others].filter((key) => this.mayAsk(kept, want, key, edges.get(key)));
2673
+ if (kept.left && order.includes(kept.left)) order.push(...order.splice(order.indexOf(kept.left), 1));
2669
2674
  let behind = false;
2670
2675
  for (const key of order) {
2671
2676
  const linkId = edges.get(key);
@@ -2821,7 +2826,8 @@ var GroupFileDesk = class {
2821
2826
  edge.serving.set(wire, kept.id);
2822
2827
  edge.servedMoved.set(wire, {
2823
2828
  confirmed: 0,
2824
- at: this.deps.now()
2829
+ at: this.deps.now(),
2830
+ from: this.deps.now()
2825
2831
  });
2826
2832
  const { name, mime, size, voice, video, image } = kept.meta;
2827
2833
  const file = {
@@ -2848,22 +2854,40 @@ var GroupFileDesk = class {
2848
2854
  if (!this.deps.settings().serveFiles || !edge.files.live) return "busy";
2849
2855
  this.letGo();
2850
2856
  const active = this.servingNow();
2851
- if (active.length >= GROUP_FILE_LIMITS.serveAtOnce) {
2857
+ const theirs = active.filter((a) => a.peer === edge.peer);
2858
+ const placed = theirs.length > 1 || theirs.some((a) => a.sending || this.deps.now() - a.since >= GROUP_FILE_LIMITS.doneWaitMs);
2859
+ if (active.length >= GROUP_FILE_LIMITS.serveAtOnce && (placed || !this.makeRoom())) {
2852
2860
  edge.busy.add(messageId);
2853
2861
  return "busy";
2854
2862
  }
2855
- if (active.some((a) => a.peer === edge.peer && a.sending)) return "busy";
2863
+ if (placed) return "busy";
2856
2864
  const today = Math.floor(this.deps.now() / 864e5);
2857
2865
  if (this.served.day !== today) this.served = {
2858
2866
  day: today,
2859
2867
  bytes: 0
2860
2868
  };
2861
- const reserved = active.reduce((sum, a) => sum + a.size, 0);
2869
+ const reserved = this.servingNow().reduce((sum, a) => sum + a.size, 0);
2862
2870
  return this.served.bytes + reserved + kept.meta.size > GROUP_FILE_LIMITS.serveBytesPerDay ? "busy" : null;
2863
2871
  }
2872
+ /** Ends the served transfer that has held its place longest, once past `servePlaceMs`: false when none has. */
2873
+ makeRoom() {
2874
+ const now = this.deps.now();
2875
+ let oldest;
2876
+ for (const edge of this.edgesById.values()) for (const wire of edge.serving.keys()) {
2877
+ const record = edge.files.get("out", wire), from = edge.servedMoved.get(wire)?.from ?? now;
2878
+ if (record && !transferEnded(record) && now - from >= GROUP_FILE_LIMITS.servePlaceMs && (!oldest || from < oldest.from)) oldest = {
2879
+ edge,
2880
+ wire,
2881
+ from
2882
+ };
2883
+ }
2884
+ if (!oldest) return false;
2885
+ oldest.edge.files.cancel("out", oldest.wire);
2886
+ return true;
2887
+ }
2864
2888
  /**
2865
2889
  * Transfers served now, all groups together: to whom, what each takes of the day (its size, or what it sent when that
2866
- * is more), and whether bytes are still to go.
2890
+ * is more), whether bytes are still to go, and since when it has not gone further.
2867
2891
  */
2868
2892
  servingNow() {
2869
2893
  const active = [];
@@ -2872,7 +2896,8 @@ var GroupFileDesk = class {
2872
2896
  if (record && !transferEnded(record)) active.push({
2873
2897
  peer: edge.peer,
2874
2898
  size: Math.max(record.file.size, edge.files.sent(wire)),
2875
- sending: record.confirmed < record.file.size
2899
+ sending: record.confirmed < record.file.size,
2900
+ since: edge.servedMoved.get(wire)?.at ?? this.deps.now()
2876
2901
  });
2877
2902
  }
2878
2903
  return active;
@@ -2891,20 +2916,29 @@ var GroupFileDesk = class {
2891
2916
  }
2892
2917
  /**
2893
2918
  * Served transfers that no longer count end, their places free for others (WISP 503 § Serving limits): the asker's
2894
- * session closed, it is not in the roster any more, or its bytes have not moved for `wantWaitMs` (the asker has moved
2895
- * on by then).
2919
+ * session closed, it is not in the roster any more, it has not had `serveMoveBytes` more confirmed (or the rest of
2920
+ * its file) for `wantWaitMs` (the asker has moved on by then), or it has all its bytes and the member's next want has
2921
+ * overtaken its word for `doneWaitMs`.
2896
2922
  */
2897
2923
  letGo() {
2898
2924
  const now = this.deps.now();
2925
+ const theirs = /* @__PURE__ */ new Map();
2926
+ for (const a of this.servingNow()) theirs.set(a.peer, (theirs.get(a.peer) ?? 0) + 1);
2899
2927
  for (const edge of this.edgesById.values()) for (const wire of [...edge.serving.keys()]) {
2900
2928
  const record = edge.files.get("out", wire);
2901
2929
  if (!record || transferEnded(record)) continue;
2902
2930
  let moved = edge.servedMoved.get(wire);
2903
- if (!moved || moved.confirmed !== record.confirmed) edge.servedMoved.set(wire, moved = {
2931
+ if (!moved) edge.servedMoved.set(wire, moved = {
2904
2932
  confirmed: record.confirmed,
2905
- at: now
2933
+ at: now,
2934
+ from: now
2906
2935
  });
2907
- if (!edge.files.live || !this.deps.membership(edge.groupId)?.inRoster(edge.peer) || now - moved.at >= GROUP_FILE_LIMITS.wantWaitMs) edge.files.cancel("out", wire);
2936
+ const gone = !edge.files.live || !this.deps.membership(edge.groupId)?.inRoster(edge.peer);
2937
+ const overtaken = record.confirmed === record.file.size && theirs.get(edge.peer) > 1 && now - moved.at >= GROUP_FILE_LIMITS.doneWaitMs;
2938
+ if (gone || overtaken || now - moved.at >= GROUP_FILE_LIMITS.wantWaitMs) {
2939
+ edge.files.cancel("out", wire);
2940
+ theirs.set(edge.peer, theirs.get(edge.peer) - 1);
2941
+ }
2908
2942
  }
2909
2943
  }
2910
2944
  /**
@@ -2955,6 +2989,7 @@ var GroupFileDesk = class {
2955
2989
  ended: [],
2956
2990
  have: /* @__PURE__ */ new Set(),
2957
2991
  haveSent: new RateWindow(GROUP_FILE_LIMITS.haveFrames, GROUP_FILE_LIMITS.haveWindowMs, () => this.deps.now()),
2992
+ haveTaken: new RateWindow(GROUP_FILE_LIMITS.haveFrames, GROUP_FILE_LIMITS.haveWindowMs, () => this.deps.now()),
2958
2993
  busy: /* @__PURE__ */ new Set(),
2959
2994
  gone: /* @__PURE__ */ new Set()
2960
2995
  };
@@ -2995,13 +3030,23 @@ var GroupFileDesk = class {
2995
3030
  const writer = await this.deps.store.write(kept.id, !kept.fresh);
2996
3031
  kept.fresh = false;
2997
3032
  const resumed = writer.offset > 0;
3033
+ if (!resumed) kept.storedBy = edge.peer;
3034
+ else if (kept.storedBy !== edge.peer) kept.storedBy = void 0;
2998
3035
  let damaged = false;
3036
+ const gone = () => this.kept.get(kept.id) !== kept;
3037
+ const write = async (op) => {
3038
+ if (gone()) {
3039
+ await writer.discard();
3040
+ throw new Error("No such file");
3041
+ }
3042
+ return await (kept.writing = op());
3043
+ };
2999
3044
  return {
3000
3045
  offset: writer.offset,
3001
- append: (bytes) => writer.append(bytes),
3002
- flush: () => writer.flush(),
3046
+ append: (bytes) => write(() => writer.append(bytes)),
3047
+ flush: () => write(() => writer.flush()),
3003
3048
  verify: async () => {
3004
- damaged = await writer.digest() !== kept.meta.d;
3049
+ damaged = await write(() => writer.digest()) !== kept.meta.d;
3005
3050
  const want = this.wants.get(kept.id);
3006
3051
  if (damaged && want) want.why = "damaged";
3007
3052
  return !damaged;
@@ -3009,10 +3054,11 @@ var GroupFileDesk = class {
3009
3054
  discard: () => {
3010
3055
  if (damaged) {
3011
3056
  kept.stored = 0;
3012
- if (resumed) kept.fresh = kept.unclear = true;
3057
+ if (resumed && kept.storedBy !== edge.peer) kept.fresh = kept.unclear = true;
3013
3058
  else kept.damaged.add(edge.peer);
3059
+ kept.storedBy = void 0;
3014
3060
  }
3015
- return kept.idle = (damaged || kept.dropped === record.id ? writer.discard() : writer.close()).catch(() => {});
3061
+ return kept.idle = (damaged || kept.dropped === record.id || gone() ? writer.discard() : writer.close()).catch(() => {});
3016
3062
  }
3017
3063
  };
3018
3064
  }
@@ -3034,6 +3080,12 @@ var GroupFileDesk = class {
3034
3080
  transferChanged(edge, record, transferred) {
3035
3081
  if (transferEnded(record)) this.transferOver(edge, record);
3036
3082
  if (record.direction === "out") {
3083
+ const moved = edge.servedMoved.get(record.id);
3084
+ if (moved && record.confirmed > moved.confirmed && (record.confirmed - moved.confirmed >= GROUP_FILE_LIMITS.serveMoveBytes || record.confirmed === record.file.size)) edge.servedMoved.set(record.id, {
3085
+ ...moved,
3086
+ confirmed: record.confirmed,
3087
+ at: this.deps.now()
3088
+ });
3037
3089
  if (transferEnded(record) && edge.serving.has(record.id)) {
3038
3090
  const today = Math.floor(this.deps.now() / 864e5);
3039
3091
  if (this.served.day !== today) this.served = {
@@ -3053,7 +3105,8 @@ var GroupFileDesk = class {
3053
3105
  }
3054
3106
  const kept = this.kept.get(edge.taking.get(record.id) ?? ""), want = kept && this.wants.get(kept.id);
3055
3107
  if (!kept || !want || want.wire !== record.id || want.linkId !== edge.linkId) return;
3056
- if (transferred !== want.moved) {
3108
+ if (want.moved < 0) want.moved = transferred;
3109
+ else if (transferred - want.moved >= Math.min(GROUP_FILE_LIMITS.wantMoveBytes, kept.meta.size - want.moved)) {
3057
3110
  want.moved = transferred;
3058
3111
  want.movedAt = this.deps.now();
3059
3112
  }
@@ -3199,4 +3252,4 @@ function messageFile(kept) {
3199
3252
  //#endregion
3200
3253
  export { setSingleWriterGate as $, LightningCards as A, breezDatabaseInUse as B, FileAppender as C, streamStored as D, storedSize as E, ProviderSources as F, ModeChanged as G, dropBreezDatabase as H, sourceKey as I, networkLabel as J, ModeGate as K, CASHU_MINT_SOURCE as L, isRecoveryPhrase as M, normalizePhrase as N, waitingGroupFile as O, lightningPaying as P, setAwayWallets as Q, cashuMint as R, WALLET_TYPES as S, removeStored as T, iceServerProblem as U, breezDatabasesFor as V, iceServerSetting as W, refuseAway as X, awayFrom as Y, requireTurn as Z, crossNetwork as _, storedGroupFiles as a, walletInstances as b, receivedPairedReply as c, paymentAlias as d, paymentWireId as f, createTiming as g, createFailure as h, groupOfFile as i, cardsKey as j, CASHU_CARD as k, replyRef as l, assertConfirmedReal as m, groupFileId as n, groupReply as o, WALLET_NAMES as p, WrongNetworkError as q, groupFileText as r, pairedWireReply as s, GroupFileDesk as t, replyTo as u, paymentNetwork as v, readStored as w, MESSAGE_DETAILS_MAX_BYTES as x, paymentNetworksOf as y, breezDatabase as z };
3201
3254
 
3202
- //# sourceMappingURL=groupFiles-IEUW3DQz.js.map
3255
+ //# sourceMappingURL=groupFiles-6qnLCnOm.js.map