@deslop/workbench 0.0.344 → 0.0.352

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 (39) hide show
  1. package/dist/client/assets/-workbench-terminal-CCVJPrdb.js +145 -0
  2. package/dist/client/assets/agent-BZ18RxQW.js +1 -0
  3. package/dist/client/assets/agent-BnTXp8Z6.js +2 -0
  4. package/dist/client/assets/button-Dz6Az3h_.js +16 -0
  5. package/dist/client/assets/{diff-BwOj6t_o.js → diff-BEB3UWZx.js} +44 -44
  6. package/dist/client/assets/{diff-COOvYjfB.js → diff-CY2kgf7E.js} +2 -2
  7. package/dist/client/assets/{external-link-DR7_wu3r.js → external-link-DPI4TAq4.js} +1 -1
  8. package/dist/client/assets/{fallbacks-D-9MltuA.js → fallbacks-uU4M5NOw.js} +1 -1
  9. package/dist/client/assets/{index-DCRiD9Nz.js → index-D7PR2398.js} +3 -3
  10. package/dist/client/assets/input-group-1-P7Y_75.js +153 -0
  11. package/dist/client/assets/loader-circle-BxillczB.js +1 -0
  12. package/dist/client/assets/portless-awDcAz4M.js +2 -0
  13. package/dist/client/assets/{portless-nerboxiJ.js → portless-pP9lIJV5.js} +1 -1
  14. package/dist/client/assets/{resizable-ChkQg6Mj.js → resizable-BaJ5ba6-.js} +1 -1
  15. package/dist/client/assets/route-C1dfpe_m.js +2 -0
  16. package/dist/client/assets/route-CqbL4Afj.js +45 -0
  17. package/dist/client/assets/run-BUDRFy83.js +2 -0
  18. package/dist/client/assets/run-uQZTd28E.js +1 -0
  19. package/dist/client/assets/state-miC_P4x2.js +2 -0
  20. package/dist/client/assets/terminal-Bh-R28qb.js +1 -0
  21. package/dist/client/assets/terminal-CXg5GJ7J.js +2 -0
  22. package/dist/client/assets/{triangle-alert-CQsOhrGn.js → triangle-alert-CTEZG9zF.js} +1 -1
  23. package/dist/client/index.html +11 -11
  24. package/dist/server.js +420 -1423
  25. package/package.json +2 -4
  26. package/dist/client/assets/agent-BATV5D0O.js +0 -1
  27. package/dist/client/assets/agent-K-v27T1K.js +0 -2
  28. package/dist/client/assets/button-f42ZKq6E.js +0 -16
  29. package/dist/client/assets/input-group-mMwtG03E.js +0 -153
  30. package/dist/client/assets/loader-circle-DEYAvEPU.js +0 -1
  31. package/dist/client/assets/portless-C8dLcQQw.js +0 -2
  32. package/dist/client/assets/route-DAz8IJkt.js +0 -2
  33. package/dist/client/assets/route-GFqYSDK4.js +0 -45
  34. package/dist/client/assets/run-B16WQaws.js +0 -2
  35. package/dist/client/assets/run-BHEbhvk3.js +0 -1
  36. package/dist/client/assets/state-BOj5tZ-Q.js +0 -2
  37. package/dist/client/assets/terminal-B410vkZ0.js +0 -1
  38. package/dist/client/assets/terminal-BQ9AR6VK.js +0 -145
  39. package/dist/client/assets/terminal-Br297Oa8.js +0 -2
package/dist/server.js CHANGED
@@ -21,8 +21,6 @@ import * as NodeStreamP from "node:stream/promises";
21
21
  import { pipeline } from "node:stream/promises";
22
22
  import * as readline from "node:readline";
23
23
  import * as nodePty from "@lydell/node-pty";
24
- import SerializeModule from "@xterm/addon-serialize";
25
- import HeadlessModule from "@xterm/headless";
26
24
  //#region \0rolldown/runtime.js
27
25
  var __create = Object.create;
28
26
  var __defProp = Object.defineProperty;
@@ -6386,7 +6384,7 @@ const clamp = (i, as) => Math.floor(Math.min(Math.max(0, i), as.length));
6386
6384
  * @category getters
6387
6385
  * @since 2.0.0
6388
6386
  */
6389
- const get$10 = /*#__PURE__*/ dual(2, (self, index) => {
6387
+ const get$9 = /*#__PURE__*/ dual(2, (self, index) => {
6390
6388
  const i = Math.floor(index);
6391
6389
  return isOutOfBounds(i, self) ? none() : some(self[i]);
6392
6390
  });
@@ -6445,7 +6443,7 @@ const getUnsafe$1 = /*#__PURE__*/ dual(2, (self, index) => {
6445
6443
  * @category getters
6446
6444
  * @since 2.0.0
6447
6445
  */
6448
- const head = /*#__PURE__*/ get$10(0);
6446
+ const head = /*#__PURE__*/ get$9(0);
6449
6447
  /**
6450
6448
  * Returns the first element of a `NonEmptyReadonlyArray` directly (no `Option`
6451
6449
  * wrapper).
@@ -7200,7 +7198,7 @@ const ServiceProto = {
7200
7198
  .../*#__PURE__*/ Prototype({
7201
7199
  label: "Service",
7202
7200
  evaluate(fiber) {
7203
- return exitSucceed(get$9(fiber.context, this));
7201
+ return exitSucceed(get$8(fiber.context, this));
7204
7202
  }
7205
7203
  }),
7206
7204
  toJSON() {
@@ -7217,10 +7215,10 @@ const ServiceProto = {
7217
7215
  return make$62(this, self);
7218
7216
  },
7219
7217
  use(f) {
7220
- return withFiber$1((fiber) => f(get$9(fiber.context, this)));
7218
+ return withFiber$1((fiber) => f(get$8(fiber.context, this)));
7221
7219
  },
7222
7220
  useSync(f) {
7223
- return withFiber$1((fiber) => exitSucceed(f(get$9(fiber.context, this))));
7221
+ return withFiber$1((fiber) => exitSucceed(f(get$8(fiber.context, this))));
7224
7222
  }
7225
7223
  };
7226
7224
  const ReferenceTypeId = "~effect/Context/Reference";
@@ -7559,7 +7557,7 @@ const getUnsafe = /*#__PURE__*/ dual(2, (self, service) => {
7559
7557
  * @category getters
7560
7558
  * @since 2.0.0
7561
7559
  */
7562
- const get$9 = getUnsafe;
7560
+ const get$8 = getUnsafe;
7563
7561
  /**
7564
7562
  * Gets the value for a `Context.Reference`, returning its cached default when
7565
7563
  * the context does not contain an override.
@@ -10107,7 +10105,7 @@ const scope$1 = scopeTag;
10107
10105
  /** @internal */
10108
10106
  const provideScope = /*#__PURE__*/ provideService$1(scopeTag);
10109
10107
  /** @internal */
10110
- const scoped$4 = (self) => withFiber$1((fiber) => {
10108
+ const scoped$2 = (self) => withFiber$1((fiber) => {
10111
10109
  const prev = fiber.context;
10112
10110
  const scope = scopeMakeUnsafe();
10113
10111
  fiber.setContext(add(fiber.context, scopeTag, scope));
@@ -10597,11 +10595,11 @@ const NoopSpanProto = {
10597
10595
  const noopSpan = (options) => Object.assign(Object.create(NoopSpanProto), options);
10598
10596
  const filterDisablePropagation = (span) => {
10599
10597
  if (!span) return none();
10600
- return get$9(span.annotations, DisablePropagation) ? span._tag === "Span" ? filterDisablePropagation(getOrUndefined$1(span.parent)) : none() : some(span);
10598
+ return get$8(span.annotations, DisablePropagation) ? span._tag === "Span" ? filterDisablePropagation(getOrUndefined$1(span.parent)) : none() : some(span);
10601
10599
  };
10602
10600
  /** @internal */
10603
10601
  const makeSpanUnsafe = (fiber, name, options) => {
10604
- const disablePropagation = !fiber.getRef(TracerEnabled$1) || options?.annotations && get$9(options.annotations, DisablePropagation);
10602
+ const disablePropagation = !fiber.getRef(TracerEnabled$1) || options?.annotations && get$8(options.annotations, DisablePropagation);
10605
10603
  const parent = options?.parent !== void 0 ? some(options.parent) : options?.root ? none() : filterDisablePropagation(fiber.currentSpan);
10606
10604
  let span;
10607
10605
  if (disablePropagation) span = noopSpan({
@@ -12521,7 +12519,7 @@ const effectDiscard = (effect) => effectContext(as$1(effect, empty$12()));
12521
12519
  */
12522
12520
  const unwrap$4 = (self) => {
12523
12521
  const service = Service("effect/Layer/unwrap");
12524
- return flatMap$3(effect(service)(self), get$9(service));
12522
+ return flatMap$3(effect(service)(self), get$8(service));
12525
12523
  };
12526
12524
  const mergeAllEffect = (layers, memoMap, scope) => {
12527
12525
  const parentScope = forkUnsafe(scope, "parallel");
@@ -12870,7 +12868,7 @@ const flatMap$3 = /*#__PURE__*/ dual(2, (self, f) => fromBuild((memoMap, scope)
12870
12868
  * @category converting
12871
12869
  * @since 2.0.0
12872
12870
  */
12873
- const launch = (self) => scoped$4(andThen$1(build(self), never$2));
12871
+ const launch = (self) => scoped$2(andThen$1(build(self), never$2));
12874
12872
  //#endregion
12875
12873
  //#region ../../node_modules/.pnpm/effect@4.0.0-beta.74/node_modules/effect/dist/Cause.js
12876
12874
  /**
@@ -13827,30 +13825,6 @@ const toDateUtc$1 = (self) => new Date(self.epochMilliseconds);
13827
13825
  */
13828
13826
  const Number$4 = globalThis.Number;
13829
13827
  /**
13830
- * Returns the next power of 2 from the given number.
13831
- *
13832
- * **When to use**
13833
- *
13834
- * Use to round a number up to the next power of two.
13835
- *
13836
- * **Example** (Finding the next power of two)
13837
- *
13838
- * ```ts
13839
- * import { Number } from "effect"
13840
- * import * as assert from "node:assert"
13841
- *
13842
- * assert.deepStrictEqual(Number.nextPow2(5), 8)
13843
- * assert.deepStrictEqual(Number.nextPow2(17), 32)
13844
- * ```
13845
- *
13846
- * @category math
13847
- * @since 2.0.0
13848
- */
13849
- const nextPow2 = (n) => {
13850
- const nextPow = Math.ceil(Math.log(n) / Math.log(2));
13851
- return Math.max(Math.pow(2, nextPow), 2);
13852
- };
13853
- /**
13854
13828
  * Parses a `number` from a `string` safely using the `Number()` function.
13855
13829
  * The following special string values are supported: "NaN", "Infinity", "-Infinity".
13856
13830
  *
@@ -14571,7 +14545,7 @@ const MetricRegistry = /*#__PURE__*/ Reference("~effect/observability/Metric/Met
14571
14545
  * @since 4.0.0
14572
14546
  */
14573
14547
  const snapshotUnsafe = (context) => {
14574
- const registry = get$9(context, MetricRegistry);
14548
+ const registry = get$8(context, MetricRegistry);
14575
14549
  return Array.from(registry.values()).map(({ hooks, ...meta }) => ({
14576
14550
  ...meta,
14577
14551
  state: hooks.get(context)
@@ -17046,7 +17020,7 @@ const scope = scope$1;
17046
17020
  * @category resource management
17047
17021
  * @since 2.0.0
17048
17022
  */
17049
- const scoped$3 = scoped$4;
17023
+ const scoped$1 = scoped$2;
17050
17024
  /**
17051
17025
  * Creates a scoped effect by providing access to the scope.
17052
17026
  *
@@ -23356,7 +23330,7 @@ const takeAll$2 = (self) => takeN(self, self.length);
23356
23330
  * @category elements
23357
23331
  * @since 4.0.0
23358
23332
  */
23359
- const take$3 = (self) => {
23333
+ const take$2 = (self) => {
23360
23334
  if (!self.head) return Empty$2;
23361
23335
  const message = self.head.array[self.head.offset];
23362
23336
  if (self.head.mutable) self.head.array[self.head.offset] = void 0;
@@ -23525,39 +23499,6 @@ const make$50 = (value) => {
23525
23499
  return ref;
23526
23500
  };
23527
23501
  /**
23528
- * Gets the current value of the MutableRef.
23529
- *
23530
- * **When to use**
23531
- *
23532
- * Use to read the current value without mutating the reference.
23533
- *
23534
- * **Example** (Reading current values)
23535
- *
23536
- * ```ts
23537
- * import { MutableRef } from "effect"
23538
- *
23539
- * const ref = MutableRef.make("hello")
23540
- * console.log(MutableRef.get(ref)) // "hello"
23541
- *
23542
- * MutableRef.set(ref, "world")
23543
- * console.log(MutableRef.get(ref)) // "world"
23544
- *
23545
- * // Reading complex objects
23546
- * const config = MutableRef.make({ port: 3000, host: "localhost" })
23547
- * const currentConfig = MutableRef.get(config)
23548
- * console.log(currentConfig.port) // 3000
23549
- *
23550
- * // Multiple reads return the same value
23551
- * const value1 = MutableRef.get(ref)
23552
- * const value2 = MutableRef.get(ref)
23553
- * console.log(value1 === value2) // true
23554
- * ```
23555
- *
23556
- * @category general
23557
- * @since 2.0.0
23558
- */
23559
- const get$8 = (self) => self.current;
23560
- /**
23561
23502
  * Sets the MutableRef to a new value and returns the reference.
23562
23503
  *
23563
23504
  * **When to use**
@@ -23694,41 +23635,6 @@ const SubscriptionTypeId = "~effect/PubSub/Subscription";
23694
23635
  */
23695
23636
  const make$49 = (options) => sync(() => makePubSubUnsafe(options.atomicPubSub(), /* @__PURE__ */ new Map(), makeUnsafe$6(), makeUnsafe$4(false), make$50(false), options.strategy()));
23696
23637
  /**
23697
- * Creates a bounded `PubSub` that applies backpressure when it reaches
23698
- * capacity.
23699
- *
23700
- * **Details**
23701
- *
23702
- * Published messages are retained until all current subscribers have taken
23703
- * them. When the capacity is full, publishers suspend until space is available.
23704
- * Pass an options object to configure both `capacity` and an optional replay
23705
- * buffer for late subscribers.
23706
- *
23707
- * **Example** (Creating a bounded PubSub)
23708
- *
23709
- * ```ts
23710
- * import { Effect, PubSub } from "effect"
23711
- *
23712
- * const program = Effect.gen(function*() {
23713
- * // Create bounded PubSub with capacity 100
23714
- * const pubsub = yield* PubSub.bounded<string>(100)
23715
- *
23716
- * // Create with replay buffer for late subscribers
23717
- * const pubsubWithReplay = yield* PubSub.bounded<string>({
23718
- * capacity: 100,
23719
- * replay: 10 // Last 10 messages replayed to new subscribers
23720
- * })
23721
- * })
23722
- * ```
23723
- *
23724
- * @category constructors
23725
- * @since 2.0.0
23726
- */
23727
- const bounded$1 = (capacity) => make$49({
23728
- atomicPubSub: () => makeAtomicBounded(capacity),
23729
- strategy: () => new BackPressureStrategy()
23730
- });
23731
- /**
23732
23638
  * Creates an unbounded `PubSub`.
23733
23639
  *
23734
23640
  * **Example** (Creating an unbounded PubSub)
@@ -23762,47 +23668,11 @@ const bounded$1 = (capacity) => make$49({
23762
23668
  * @category constructors
23763
23669
  * @since 2.0.0
23764
23670
  */
23765
- const unbounded$1 = (options) => make$49({
23671
+ const unbounded = (options) => make$49({
23766
23672
  atomicPubSub: () => makeAtomicUnbounded(options),
23767
23673
  strategy: () => new DroppingStrategy()
23768
23674
  });
23769
23675
  /**
23770
- * Creates a bounded atomic PubSub implementation with optional replay buffer.
23771
- *
23772
- * **When to use**
23773
- *
23774
- * Use to provide bounded message storage when building a custom `PubSub` with
23775
- * `make` and an explicit delivery strategy.
23776
- *
23777
- * **Details**
23778
- *
23779
- * Pass either a capacity number or an options object with `capacity` and
23780
- * optional `replay`. A positive `replay` value enables a replay buffer for late
23781
- * subscribers, and fractional replay sizes are rounded up.
23782
- *
23783
- * **Gotchas**
23784
- *
23785
- * The capacity must be greater than zero; invalid capacities throw
23786
- * synchronously before an atomic implementation is created.
23787
- *
23788
- * @see {@link make} for constructing a `PubSub` from an atomic implementation and delivery strategy
23789
- * @see {@link makeAtomicUnbounded} for an atomic implementation without a bounded capacity
23790
- * @see {@link bounded} for the higher-level backpressure constructor
23791
- * @see {@link dropping} for the higher-level dropping constructor
23792
- * @see {@link sliding} for the higher-level sliding constructor
23793
- *
23794
- * @category constructors
23795
- * @since 4.0.0
23796
- */
23797
- const makeAtomicBounded = (capacity) => {
23798
- const options = typeof capacity === "number" ? { capacity } : capacity;
23799
- ensureCapacity(options.capacity);
23800
- const replayBuffer = options.replay && options.replay > 0 ? new ReplayBuffer(Math.ceil(options.replay)) : void 0;
23801
- if (options.capacity === 1) return new BoundedPubSubSingle(replayBuffer);
23802
- else if (nextPow2(options.capacity) === options.capacity) return new BoundedPubSubPow2(options.capacity, replayBuffer);
23803
- else return new BoundedPubSubArb(options.capacity, replayBuffer);
23804
- };
23805
- /**
23806
23676
  * Creates an unbounded atomic PubSub implementation with optional replay buffer.
23807
23677
  *
23808
23678
  * **When to use**
@@ -23824,93 +23694,6 @@ const makeAtomicBounded = (capacity) => {
23824
23694
  */
23825
23695
  const makeAtomicUnbounded = (options) => new UnboundedPubSub(options?.replay ? new ReplayBuffer(options.replay) : void 0);
23826
23696
  /**
23827
- * Shuts down the `PubSub`, interrupting suspended publishers and subscribers
23828
- * and finalizing active subscriptions.
23829
- *
23830
- * **Details**
23831
- *
23832
- * After shutdown, `publish` and `publishAll` succeed with `false`,
23833
- * `publishUnsafe` returns `false`, and subscription operations such as `take`
23834
- * interrupt.
23835
- *
23836
- * **Example** (Shutting down a PubSub)
23837
- *
23838
- * ```ts
23839
- * import { Effect, PubSub } from "effect"
23840
- *
23841
- * const program = Effect.gen(function*() {
23842
- * const pubsub = yield* PubSub.bounded<string>(1)
23843
- *
23844
- * // Shutdown the PubSub
23845
- * yield* PubSub.shutdown(pubsub)
23846
- *
23847
- * const isShutdown = yield* PubSub.isShutdown(pubsub)
23848
- * console.log("Is shutdown:", isShutdown) // true
23849
- *
23850
- * // Publishing after shutdown returns false
23851
- * const published = yield* PubSub.publish(pubsub, "msg1")
23852
- * console.log("Published after shutdown:", published) // false
23853
- * })
23854
- * ```
23855
- *
23856
- * @category lifecycle
23857
- * @since 2.0.0
23858
- */
23859
- const shutdown$1 = (self) => uninterruptible(withFiber((fiber) => {
23860
- set$6(self.shutdownFlag, true);
23861
- return close(self.scope, interrupt$2(fiber.id)).pipe(andThen(self.strategy.shutdown), when$2(self.shutdownHook.open), asVoid);
23862
- }));
23863
- /**
23864
- * Publishes a message to the `PubSub` as an `Effect`, returning whether the
23865
- * message was accepted.
23866
- *
23867
- * **When to use**
23868
- *
23869
- * Use when publishing from effectful code and the configured PubSub strategy
23870
- * should handle surplus messages.
23871
- *
23872
- * **Details**
23873
- *
23874
- * The effect succeeds with `false` if the `PubSub` is shut down. If the message
23875
- * cannot be accepted immediately, the configured strategy decides how surplus
23876
- * messages are handled.
23877
- *
23878
- * **Example** (Publishing a message)
23879
- *
23880
- * ```ts
23881
- * import { Effect, PubSub } from "effect"
23882
- *
23883
- * const program = Effect.gen(function*() {
23884
- * const pubsub = yield* PubSub.bounded<string>(10)
23885
- *
23886
- * // Publish a message
23887
- * const published = yield* PubSub.publish(pubsub, "Hello World")
23888
- * console.log("Message published:", published) // true
23889
- *
23890
- * yield* Effect.scoped(Effect.gen(function*() {
23891
- * const subscription = yield* PubSub.subscribe(pubsub)
23892
- *
23893
- * yield* PubSub.publish(pubsub, "Hello")
23894
- * const message = yield* PubSub.take(subscription)
23895
- * console.log("Received:", message) // "Hello"
23896
- * }))
23897
- * })
23898
- * ```
23899
- *
23900
- * @see {@link publishUnsafe} for a synchronous non-blocking attempt that does not run effectful surplus handling
23901
- *
23902
- * @category publishing
23903
- * @since 2.0.0
23904
- */
23905
- const publish = /*#__PURE__*/ dual(2, (self, value) => suspend$2(() => {
23906
- if (self.shutdownFlag.current) return succeed$3(false);
23907
- if (self.pubsub.publish(value)) {
23908
- self.strategy.completeSubscribersUnsafe(self.pubsub, self.subscribers);
23909
- return succeed$3(true);
23910
- }
23911
- return self.strategy.handleSurplus(self.pubsub, self.subscribers, [value], self.shutdownFlag);
23912
- }));
23913
- /**
23914
23697
  * Attempts to publish a message synchronously without applying the PubSub
23915
23698
  * strategy's effectful surplus handling.
23916
23699
  *
@@ -24009,7 +23792,7 @@ const publishUnsafe = /*#__PURE__*/ dual(2, (self, value) => {
24009
23792
  * @since 2.0.0
24010
23793
  */
24011
23794
  const subscribe = (self) => uninterruptible(contextWith((services) => {
24012
- const localScope = get$9(services, Scope);
23795
+ const localScope = get$8(services, Scope);
24013
23796
  const scope = forkUnsafe(self.scope);
24014
23797
  const subscription = makeSubscriptionUnsafe(self.pubsub, self.subscribers, self.strategy);
24015
23798
  return addFinalizer$1(scope, unsubscribe(subscription)).pipe(andThen(addFinalizerExit(localScope, (exit) => close(scope, exit))), as(subscription));
@@ -24026,49 +23809,6 @@ const unsubscribe = (self) => uninterruptible(withFiber((state) => {
24026
23809
  })), when$2(self.shutdownHook.open), asVoid);
24027
23810
  }));
24028
23811
  /**
24029
- * Takes a single message from the subscription. If no messages are available,
24030
- * this will suspend until a message becomes available.
24031
- *
24032
- * **Example** (Taking a message)
24033
- *
24034
- * ```ts
24035
- * import { Effect, Fiber, PubSub } from "effect"
24036
- *
24037
- * const program = Effect.gen(function*() {
24038
- * const pubsub = yield* PubSub.bounded<string>(10)
24039
- *
24040
- * yield* Effect.scoped(Effect.gen(function*() {
24041
- * const subscription = yield* PubSub.subscribe(pubsub)
24042
- *
24043
- * // Start a fiber to take a message (will suspend)
24044
- * const takeFiber = yield* Effect.forkChild(
24045
- * PubSub.take(subscription)
24046
- * )
24047
- *
24048
- * // Publish a message
24049
- * yield* PubSub.publish(pubsub, "Hello")
24050
- *
24051
- * // The take will now complete
24052
- * const message = yield* Fiber.join(takeFiber)
24053
- * console.log("Received:", message) // "Hello"
24054
- * }))
24055
- * })
24056
- * ```
24057
- *
24058
- * @category subscriptions
24059
- * @since 4.0.0
24060
- */
24061
- const take$2 = (self) => suspend$2(() => {
24062
- if (self.shutdownFlag.current) return interrupt$1;
24063
- if (self.replayWindow.remaining > 0) return succeed$3(self.replayWindow.take());
24064
- const message = self.pollers.length === 0 ? self.subscription.poll() : Empty$2;
24065
- if (message === Empty$2) return pollForItem(self);
24066
- else {
24067
- self.strategy.onPubSubEmptySpaceUnsafe(self.pubsub, self.subscribers);
24068
- return succeed$3(message);
24069
- }
24070
- });
24071
- /**
24072
23812
  * Takes all available messages from the subscription, suspending if no items
24073
23813
  * are available.
24074
23814
  *
@@ -24120,53 +23860,6 @@ const pollForItem = (self) => {
24120
23860
  return void_$1;
24121
23861
  });
24122
23862
  };
24123
- /**
24124
- * Takes up to the specified number of messages from the subscription without suspending.
24125
- *
24126
- * **Example** (Taking up to a maximum number of messages)
24127
- *
24128
- * ```ts
24129
- * import { Effect, PubSub } from "effect"
24130
- *
24131
- * const program = Effect.gen(function*() {
24132
- * const pubsub = yield* PubSub.bounded<string>(10)
24133
- *
24134
- * yield* Effect.scoped(Effect.gen(function*() {
24135
- * const subscription = yield* PubSub.subscribe(pubsub)
24136
- *
24137
- * // Publish multiple messages
24138
- * yield* PubSub.publishAll(pubsub, ["msg1", "msg2", "msg3", "msg4", "msg5"])
24139
- *
24140
- * // Take up to 3 messages
24141
- * const upTo3 = yield* PubSub.takeUpTo(subscription, 3)
24142
- * console.log("Up to 3:", upTo3) // ["msg1", "msg2", "msg3"]
24143
- *
24144
- * // Take up to 5 more (only 2 remaining)
24145
- * const upTo5 = yield* PubSub.takeUpTo(subscription, 5)
24146
- * console.log("Up to 5:", upTo5) // ["msg4", "msg5"]
24147
- *
24148
- * // No more messages available
24149
- * const noMore = yield* PubSub.takeUpTo(subscription, 10)
24150
- * console.log("No more:", noMore) // []
24151
- * }))
24152
- * })
24153
- * ```
24154
- *
24155
- * @category subscriptions
24156
- * @since 4.0.0
24157
- */
24158
- const takeUpTo = /*#__PURE__*/ dual(2, (self, max) => suspend$2(() => {
24159
- if (self.shutdownFlag.current) return interrupt$1;
24160
- let replay = void 0;
24161
- if (self.replayWindow.remaining >= max) return succeed$3(self.replayWindow.takeN(max));
24162
- else if (self.replayWindow.remaining > 0) {
24163
- replay = self.replayWindow.takeAll();
24164
- max = max - replay.length;
24165
- }
24166
- const as = self.pollers.length === 0 ? self.subscription.pollUpTo(max) : [];
24167
- self.strategy.onPubSubEmptySpaceUnsafe(self.pubsub, self.subscribers);
24168
- return replay ? succeed$3(replay.concat(as)) : succeed$3(as);
24169
- }));
24170
23863
  const AbsentValue = /*#__PURE__*/ Symbol.for("effect/PubSub/AbsentValue");
24171
23864
  const addSubscribers = (subscribers, subscription, pollers) => {
24172
23865
  if (!subscribers.has(subscription)) subscribers.set(subscription, /* @__PURE__ */ new Set());
@@ -24179,395 +23872,6 @@ const removeSubscribers = (subscribers, subscription, pollers) => {
24179
23872
  if (set.size === 0) subscribers.delete(subscription);
24180
23873
  };
24181
23874
  const makeSubscriptionUnsafe = (pubsub, subscribers, strategy) => new SubscriptionImpl(pubsub, subscribers, pubsub.subscribe(), make$51(), makeUnsafe$4(false), make$50(false), strategy, pubsub.replayWindow());
24182
- var BoundedPubSubArb = class {
24183
- array;
24184
- publisherIndex = 0;
24185
- subscribers;
24186
- subscriberCount = 0;
24187
- subscribersIndex = 0;
24188
- capacity;
24189
- replayBuffer;
24190
- constructor(capacity, replayBuffer) {
24191
- this.capacity = capacity;
24192
- this.replayBuffer = replayBuffer;
24193
- this.array = Array.from({ length: capacity });
24194
- this.subscribers = Array.from({ length: capacity });
24195
- }
24196
- replayWindow() {
24197
- return this.replayBuffer ? new ReplayWindowImpl(this.replayBuffer) : emptyReplayWindow;
24198
- }
24199
- isEmpty() {
24200
- return this.publisherIndex === this.subscribersIndex;
24201
- }
24202
- isFull() {
24203
- return this.publisherIndex === this.subscribersIndex + this.capacity;
24204
- }
24205
- size() {
24206
- return this.publisherIndex - this.subscribersIndex;
24207
- }
24208
- publish(value) {
24209
- if (this.isFull()) return false;
24210
- if (this.subscriberCount !== 0) {
24211
- const index = this.publisherIndex % this.capacity;
24212
- this.array[index] = value;
24213
- this.subscribers[index] = this.subscriberCount;
24214
- this.publisherIndex += 1;
24215
- }
24216
- if (this.replayBuffer) this.replayBuffer.offer(value);
24217
- return true;
24218
- }
24219
- publishAll(elements) {
24220
- if (this.subscriberCount === 0) {
24221
- if (this.replayBuffer) this.replayBuffer.offerAll(elements);
24222
- return [];
24223
- }
24224
- const chunk = fromIterable$2(elements);
24225
- const n = chunk.length;
24226
- const size = this.publisherIndex - this.subscribersIndex;
24227
- const available = this.capacity - size;
24228
- const forPubSub = Math.min(n, available);
24229
- if (forPubSub === 0) return chunk;
24230
- let iteratorIndex = 0;
24231
- const publishAllIndex = this.publisherIndex + forPubSub;
24232
- while (this.publisherIndex !== publishAllIndex) {
24233
- const a = chunk[iteratorIndex++];
24234
- const index = this.publisherIndex % this.capacity;
24235
- this.array[index] = a;
24236
- this.subscribers[index] = this.subscriberCount;
24237
- this.publisherIndex += 1;
24238
- if (this.replayBuffer) this.replayBuffer.offer(a);
24239
- }
24240
- return chunk.slice(iteratorIndex);
24241
- }
24242
- slide() {
24243
- if (this.subscribersIndex !== this.publisherIndex) {
24244
- const index = this.subscribersIndex % this.capacity;
24245
- this.array[index] = AbsentValue;
24246
- this.subscribers[index] = 0;
24247
- this.subscribersIndex += 1;
24248
- }
24249
- if (this.replayBuffer) this.replayBuffer.slide();
24250
- }
24251
- subscribe() {
24252
- this.subscriberCount += 1;
24253
- return new BoundedPubSubArbSubscription(this, this.publisherIndex, false);
24254
- }
24255
- };
24256
- var BoundedPubSubArbSubscription = class {
24257
- self;
24258
- subscriberIndex;
24259
- unsubscribed;
24260
- constructor(self, subscriberIndex, unsubscribed) {
24261
- this.self = self;
24262
- this.subscriberIndex = subscriberIndex;
24263
- this.unsubscribed = unsubscribed;
24264
- }
24265
- isEmpty() {
24266
- return this.unsubscribed || this.self.publisherIndex === this.subscriberIndex || this.self.publisherIndex === this.self.subscribersIndex;
24267
- }
24268
- size() {
24269
- if (this.unsubscribed) return 0;
24270
- return this.self.publisherIndex - Math.max(this.subscriberIndex, this.self.subscribersIndex);
24271
- }
24272
- poll() {
24273
- if (this.unsubscribed) return Empty$2;
24274
- this.subscriberIndex = Math.max(this.subscriberIndex, this.self.subscribersIndex);
24275
- if (this.subscriberIndex !== this.self.publisherIndex) {
24276
- const index = this.subscriberIndex % this.self.capacity;
24277
- const elem = this.self.array[index];
24278
- this.self.subscribers[index] -= 1;
24279
- if (this.self.subscribers[index] === 0) {
24280
- this.self.array[index] = AbsentValue;
24281
- this.self.subscribersIndex += 1;
24282
- }
24283
- this.subscriberIndex += 1;
24284
- return elem;
24285
- }
24286
- return Empty$2;
24287
- }
24288
- pollUpTo(n) {
24289
- if (this.unsubscribed) return [];
24290
- this.subscriberIndex = Math.max(this.subscriberIndex, this.self.subscribersIndex);
24291
- const size = this.self.publisherIndex - this.subscriberIndex;
24292
- const toPoll = Math.min(n, size);
24293
- if (toPoll <= 0) return [];
24294
- const builder = [];
24295
- const pollUpToIndex = this.subscriberIndex + toPoll;
24296
- while (this.subscriberIndex !== pollUpToIndex) {
24297
- const index = this.subscriberIndex % this.self.capacity;
24298
- const a = this.self.array[index];
24299
- this.self.subscribers[index] -= 1;
24300
- if (this.self.subscribers[index] === 0) {
24301
- this.self.array[index] = AbsentValue;
24302
- this.self.subscribersIndex += 1;
24303
- }
24304
- builder.push(a);
24305
- this.subscriberIndex += 1;
24306
- }
24307
- return builder;
24308
- }
24309
- unsubscribe() {
24310
- if (!this.unsubscribed) {
24311
- this.unsubscribed = true;
24312
- this.self.subscriberCount -= 1;
24313
- this.subscriberIndex = Math.max(this.subscriberIndex, this.self.subscribersIndex);
24314
- while (this.subscriberIndex !== this.self.publisherIndex) {
24315
- const index = this.subscriberIndex % this.self.capacity;
24316
- this.self.subscribers[index] -= 1;
24317
- if (this.self.subscribers[index] === 0) {
24318
- this.self.array[index] = AbsentValue;
24319
- this.self.subscribersIndex += 1;
24320
- }
24321
- this.subscriberIndex += 1;
24322
- }
24323
- }
24324
- }
24325
- };
24326
- var BoundedPubSubPow2 = class {
24327
- array;
24328
- mask;
24329
- publisherIndex = 0;
24330
- subscribers;
24331
- subscriberCount = 0;
24332
- subscribersIndex = 0;
24333
- capacity;
24334
- replayBuffer;
24335
- constructor(capacity, replayBuffer) {
24336
- this.capacity = capacity;
24337
- this.replayBuffer = replayBuffer;
24338
- this.array = Array.from({ length: capacity });
24339
- this.mask = capacity - 1;
24340
- this.subscribers = Array.from({ length: capacity });
24341
- }
24342
- replayWindow() {
24343
- return this.replayBuffer ? new ReplayWindowImpl(this.replayBuffer) : emptyReplayWindow;
24344
- }
24345
- isEmpty() {
24346
- return this.publisherIndex === this.subscribersIndex;
24347
- }
24348
- isFull() {
24349
- return this.publisherIndex === this.subscribersIndex + this.capacity;
24350
- }
24351
- size() {
24352
- return this.publisherIndex - this.subscribersIndex;
24353
- }
24354
- publish(value) {
24355
- if (this.isFull()) return false;
24356
- if (this.subscriberCount !== 0) {
24357
- const index = this.publisherIndex & this.mask;
24358
- this.array[index] = value;
24359
- this.subscribers[index] = this.subscriberCount;
24360
- this.publisherIndex += 1;
24361
- }
24362
- if (this.replayBuffer) this.replayBuffer.offer(value);
24363
- return true;
24364
- }
24365
- publishAll(elements) {
24366
- if (this.subscriberCount === 0) {
24367
- if (this.replayBuffer) this.replayBuffer.offerAll(elements);
24368
- return [];
24369
- }
24370
- const chunk = fromIterable$2(elements);
24371
- const n = chunk.length;
24372
- const size = this.publisherIndex - this.subscribersIndex;
24373
- const available = this.capacity - size;
24374
- const forPubSub = Math.min(n, available);
24375
- if (forPubSub === 0) return chunk;
24376
- let iteratorIndex = 0;
24377
- const publishAllIndex = this.publisherIndex + forPubSub;
24378
- while (this.publisherIndex !== publishAllIndex) {
24379
- const elem = chunk[iteratorIndex++];
24380
- const index = this.publisherIndex & this.mask;
24381
- this.array[index] = elem;
24382
- this.subscribers[index] = this.subscriberCount;
24383
- this.publisherIndex += 1;
24384
- if (this.replayBuffer) this.replayBuffer.offer(elem);
24385
- }
24386
- return chunk.slice(iteratorIndex);
24387
- }
24388
- slide() {
24389
- if (this.subscribersIndex !== this.publisherIndex) {
24390
- const index = this.subscribersIndex & this.mask;
24391
- this.array[index] = AbsentValue;
24392
- this.subscribers[index] = 0;
24393
- this.subscribersIndex += 1;
24394
- }
24395
- if (this.replayBuffer) this.replayBuffer.slide();
24396
- }
24397
- subscribe() {
24398
- this.subscriberCount += 1;
24399
- return new BoundedPubSubPow2Subscription(this, this.publisherIndex, false);
24400
- }
24401
- };
24402
- var BoundedPubSubPow2Subscription = class {
24403
- self;
24404
- subscriberIndex;
24405
- unsubscribed;
24406
- constructor(self, subscriberIndex, unsubscribed) {
24407
- this.self = self;
24408
- this.subscriberIndex = subscriberIndex;
24409
- this.unsubscribed = unsubscribed;
24410
- }
24411
- isEmpty() {
24412
- return this.unsubscribed || this.self.publisherIndex === this.subscriberIndex || this.self.publisherIndex === this.self.subscribersIndex;
24413
- }
24414
- size() {
24415
- if (this.unsubscribed) return 0;
24416
- return this.self.publisherIndex - Math.max(this.subscriberIndex, this.self.subscribersIndex);
24417
- }
24418
- poll() {
24419
- if (this.unsubscribed) return Empty$2;
24420
- this.subscriberIndex = Math.max(this.subscriberIndex, this.self.subscribersIndex);
24421
- if (this.subscriberIndex !== this.self.publisherIndex) {
24422
- const index = this.subscriberIndex & this.self.mask;
24423
- const elem = this.self.array[index];
24424
- this.self.subscribers[index] -= 1;
24425
- if (this.self.subscribers[index] === 0) {
24426
- this.self.array[index] = AbsentValue;
24427
- this.self.subscribersIndex += 1;
24428
- }
24429
- this.subscriberIndex += 1;
24430
- return elem;
24431
- }
24432
- return Empty$2;
24433
- }
24434
- pollUpTo(n) {
24435
- if (this.unsubscribed) return [];
24436
- this.subscriberIndex = Math.max(this.subscriberIndex, this.self.subscribersIndex);
24437
- const size = this.self.publisherIndex - this.subscriberIndex;
24438
- const toPoll = Math.min(n, size);
24439
- if (toPoll <= 0) return [];
24440
- const builder = [];
24441
- const pollUpToIndex = this.subscriberIndex + toPoll;
24442
- while (this.subscriberIndex !== pollUpToIndex) {
24443
- const index = this.subscriberIndex & this.self.mask;
24444
- const elem = this.self.array[index];
24445
- this.self.subscribers[index] -= 1;
24446
- if (this.self.subscribers[index] === 0) {
24447
- this.self.array[index] = AbsentValue;
24448
- this.self.subscribersIndex += 1;
24449
- }
24450
- builder.push(elem);
24451
- this.subscriberIndex += 1;
24452
- }
24453
- return builder;
24454
- }
24455
- unsubscribe() {
24456
- if (!this.unsubscribed) {
24457
- this.unsubscribed = true;
24458
- this.self.subscriberCount -= 1;
24459
- this.subscriberIndex = Math.max(this.subscriberIndex, this.self.subscribersIndex);
24460
- while (this.subscriberIndex !== this.self.publisherIndex) {
24461
- const index = this.subscriberIndex & this.self.mask;
24462
- this.self.subscribers[index] -= 1;
24463
- if (this.self.subscribers[index] === 0) {
24464
- this.self.array[index] = AbsentValue;
24465
- this.self.subscribersIndex += 1;
24466
- }
24467
- this.subscriberIndex += 1;
24468
- }
24469
- }
24470
- }
24471
- };
24472
- var BoundedPubSubSingle = class {
24473
- publisherIndex = 0;
24474
- subscriberCount = 0;
24475
- subscribers = 0;
24476
- value = AbsentValue;
24477
- capacity = 1;
24478
- replayBuffer;
24479
- constructor(replayBuffer) {
24480
- this.replayBuffer = replayBuffer;
24481
- }
24482
- replayWindow() {
24483
- return this.replayBuffer ? new ReplayWindowImpl(this.replayBuffer) : emptyReplayWindow;
24484
- }
24485
- pipe() {
24486
- return pipeArguments(this, arguments);
24487
- }
24488
- isEmpty() {
24489
- return this.subscribers === 0;
24490
- }
24491
- isFull() {
24492
- return !this.isEmpty();
24493
- }
24494
- size() {
24495
- return this.isEmpty() ? 0 : 1;
24496
- }
24497
- publish(value) {
24498
- if (this.isFull()) return false;
24499
- if (this.subscriberCount !== 0) {
24500
- this.value = value;
24501
- this.subscribers = this.subscriberCount;
24502
- this.publisherIndex += 1;
24503
- }
24504
- if (this.replayBuffer) this.replayBuffer.offer(value);
24505
- return true;
24506
- }
24507
- publishAll(elements) {
24508
- if (this.subscriberCount === 0) {
24509
- if (this.replayBuffer) this.replayBuffer.offerAll(elements);
24510
- return [];
24511
- }
24512
- const chunk = fromIterable$2(elements);
24513
- if (chunk.length === 0) return chunk;
24514
- if (this.publish(chunk[0])) return chunk.slice(1);
24515
- else return chunk;
24516
- }
24517
- slide() {
24518
- if (this.isFull()) {
24519
- this.subscribers = 0;
24520
- this.value = AbsentValue;
24521
- }
24522
- if (this.replayBuffer) this.replayBuffer.slide();
24523
- }
24524
- subscribe() {
24525
- this.subscriberCount += 1;
24526
- return new BoundedPubSubSingleSubscription(this, this.publisherIndex, false);
24527
- }
24528
- };
24529
- var BoundedPubSubSingleSubscription = class {
24530
- self;
24531
- subscriberIndex;
24532
- unsubscribed;
24533
- constructor(self, subscriberIndex, unsubscribed) {
24534
- this.self = self;
24535
- this.subscriberIndex = subscriberIndex;
24536
- this.unsubscribed = unsubscribed;
24537
- }
24538
- isEmpty() {
24539
- return this.unsubscribed || this.self.subscribers === 0 || this.subscriberIndex === this.self.publisherIndex;
24540
- }
24541
- size() {
24542
- return this.isEmpty() ? 0 : 1;
24543
- }
24544
- poll() {
24545
- if (this.isEmpty()) return Empty$2;
24546
- const elem = this.self.value;
24547
- this.self.subscribers -= 1;
24548
- if (this.self.subscribers === 0) this.self.value = AbsentValue;
24549
- this.subscriberIndex += 1;
24550
- return elem;
24551
- }
24552
- pollUpTo(n) {
24553
- if (this.isEmpty() || n < 1) return [];
24554
- const a = this.self.value;
24555
- this.self.subscribers -= 1;
24556
- if (this.self.subscribers === 0) this.self.value = AbsentValue;
24557
- this.subscriberIndex += 1;
24558
- return [a];
24559
- }
24560
- unsubscribe() {
24561
- if (!this.unsubscribed) {
24562
- this.unsubscribed = true;
24563
- this.self.subscriberCount -= 1;
24564
- if (this.subscriberIndex !== this.self.publisherIndex) {
24565
- this.self.subscribers -= 1;
24566
- if (this.self.subscribers === 0) this.self.value = AbsentValue;
24567
- }
24568
- }
24569
- }
24570
- };
24571
23875
  var UnboundedPubSub = class {
24572
23876
  publisherHead = {
24573
23877
  value: AbsentValue,
@@ -24753,99 +24057,6 @@ var PubSubImpl = class {
24753
24057
  }
24754
24058
  };
24755
24059
  const makePubSubUnsafe = (pubsub, subscribers, scope, shutdownHook, shutdownFlag, strategy) => new PubSubImpl(pubsub, subscribers, scope, shutdownHook, shutdownFlag, strategy);
24756
- const ensureCapacity = (capacity) => {
24757
- if (capacity <= 0) throw new Error(`Cannot construct PubSub with capacity of ${capacity}`);
24758
- };
24759
- /**
24760
- * Represents the back-pressure strategy for bounded `PubSub` values.
24761
- *
24762
- * **When to use**
24763
- *
24764
- * Use to preserve every message for current subscribers when a bounded custom
24765
- * `PubSub` should make publishers wait for capacity instead of dropping or
24766
- * evicting messages.
24767
- *
24768
- * **Details**
24769
- *
24770
- * Publishers wait when the `PubSub` is at capacity, so all current subscribers
24771
- * can receive every published message.
24772
- *
24773
- * **Gotchas**
24774
- *
24775
- * A slow subscriber can slow down publishers and other subscribers.
24776
- *
24777
- * @see {@link bounded} for creating bounded PubSubs with back pressure by default
24778
- * @see {@link DroppingStrategy} for dropping new messages when capacity is full
24779
- * @see {@link SlidingStrategy} for evicting old messages when capacity is full
24780
- *
24781
- * @category models
24782
- * @since 4.0.0
24783
- */
24784
- var BackPressureStrategy = class {
24785
- publishers = /*#__PURE__*/ make$51();
24786
- get shutdown() {
24787
- return withFiber((fiber) => forEach$1(takeAll$2(this.publishers), ([_, deferred, last]) => last ? interruptWith(deferred, fiber.id) : void_$1, {
24788
- concurrency: "unbounded",
24789
- discard: true
24790
- }));
24791
- }
24792
- handleSurplus(pubsub, subscribers, elements, isShutdown) {
24793
- return suspend$2(() => {
24794
- const deferred = makeUnsafe$7();
24795
- this.offerUnsafe(elements, deferred);
24796
- this.onPubSubEmptySpaceUnsafe(pubsub, subscribers);
24797
- this.completeSubscribersUnsafe(pubsub, subscribers);
24798
- return (get$8(isShutdown) ? interrupt$1 : _await(deferred)).pipe(onInterrupt(() => {
24799
- this.removeUnsafe(deferred);
24800
- return void_$1;
24801
- }));
24802
- });
24803
- }
24804
- onPubSubEmptySpaceUnsafe(pubsub, subscribers) {
24805
- let keepPolling = true;
24806
- while (keepPolling && !pubsub.isFull()) {
24807
- const publisher = take$3(this.publishers);
24808
- if (publisher === Empty$2) keepPolling = false;
24809
- else {
24810
- const [value, deferred] = publisher;
24811
- const published = pubsub.publish(value);
24812
- if (published && publisher[2]) doneUnsafe(deferred, succeed$5(true));
24813
- else if (!published) prepend(this.publishers, publisher);
24814
- this.completeSubscribersUnsafe(pubsub, subscribers);
24815
- }
24816
- }
24817
- }
24818
- completePollersUnsafe(pubsub, subscribers, subscription, pollers) {
24819
- return strategyCompletePollersUnsafe(this, pubsub, subscribers, subscription, pollers);
24820
- }
24821
- completeSubscribersUnsafe(pubsub, subscribers) {
24822
- return strategyCompleteSubscribersUnsafe(this, pubsub, subscribers);
24823
- }
24824
- offerUnsafe(elements, deferred) {
24825
- const iterator = elements[Symbol.iterator]();
24826
- let next = iterator.next();
24827
- if (!next.done) while (1) {
24828
- const value = next.value;
24829
- next = iterator.next();
24830
- if (next.done) {
24831
- append(this.publishers, [
24832
- value,
24833
- deferred,
24834
- true
24835
- ]);
24836
- break;
24837
- }
24838
- append(this.publishers, [
24839
- value,
24840
- deferred,
24841
- false
24842
- ]);
24843
- }
24844
- }
24845
- removeUnsafe(deferred) {
24846
- filter(this.publishers, ([_, d]) => d !== deferred);
24847
- }
24848
- };
24849
24060
  /**
24850
24061
  * Represents the dropping strategy for bounded `PubSub` values.
24851
24062
  *
@@ -24916,7 +24127,7 @@ var DroppingStrategy = class {
24916
24127
  const strategyCompletePollersUnsafe = (strategy, pubsub, subscribers, subscription, pollers) => {
24917
24128
  let keepPolling = true;
24918
24129
  while (keepPolling && !subscription.isEmpty()) {
24919
- const poller = take$3(pollers);
24130
+ const poller = take$2(pollers);
24920
24131
  if (poller === Empty$2) {
24921
24132
  removeSubscribers(subscribers, subscription, pollers);
24922
24133
  if (pollers.length === 0) keepPolling = false;
@@ -25224,41 +24435,43 @@ const sliding = (capacity) => make$48({
25224
24435
  strategy: "sliding"
25225
24436
  });
25226
24437
  /**
25227
- * Creates an unbounded queue that can grow to any size without blocking producers.
24438
+ * Creates a bounded queue with dropping strategy. When the queue reaches capacity,
24439
+ * new elements are dropped and the offer operation returns false.
25228
24440
  *
25229
24441
  * **When to use**
25230
24442
  *
25231
- * Use when producers should never be blocked; unbounded queues never apply backpressure, so producers
25232
- * can always add messages successfully. This is useful when you want to prioritize
25233
- * producer throughput over memory usage control.
24443
+ * Use when producers should not block and existing messages should be preserved,
24444
+ * but new messages may be lost when the queue is full.
25234
24445
  *
25235
- * **Example** (Creating unbounded queues)
24446
+ * **Example** (Creating dropping queues)
25236
24447
  *
25237
24448
  * ```ts
25238
24449
  * import { Effect, Queue } from "effect"
25239
24450
  *
25240
24451
  * const program = Effect.gen(function*() {
25241
- * const queue = yield* Queue.unbounded<string>()
24452
+ * const queue = yield* Queue.dropping<number>(2)
25242
24453
  *
25243
- * // Producers can always add messages without blocking
25244
- * yield* Queue.offer(queue, "message1")
25245
- * yield* Queue.offer(queue, "message2")
25246
- * yield* Queue.offerAll(queue, ["message3", "message4", "message5"])
24454
+ * // Fill the queue to capacity
24455
+ * const success1 = yield* Queue.offer(queue, 1)
24456
+ * const success2 = yield* Queue.offer(queue, 2)
24457
+ * console.log(success1, success2) // true, true
25247
24458
  *
25248
- * // Check current size
25249
- * const size = yield* Queue.size(queue)
25250
- * console.log(size) // 5
24459
+ * // This will be dropped
24460
+ * const success3 = yield* Queue.offer(queue, 3)
24461
+ * console.log(success3) // false
25251
24462
  *
25252
- * // Take all messages
25253
- * const messages = yield* Queue.takeAll(queue)
25254
- * console.log(messages) // ["message1", "message2", "message3", "message4", "message5"]
24463
+ * const all = yield* Queue.takeAll(queue)
24464
+ * console.log(all) // [1, 2] - element 3 was dropped
25255
24465
  * })
25256
24466
  * ```
25257
24467
  *
25258
24468
  * @category constructors
25259
24469
  * @since 2.0.0
25260
24470
  */
25261
- const unbounded = () => make$48();
24471
+ const dropping = (capacity) => make$48({
24472
+ capacity,
24473
+ strategy: "dropping"
24474
+ });
25262
24475
  /**
25263
24476
  * Adds a message to the queue. Returns `false` if the queue is done.
25264
24477
  *
@@ -25302,7 +24515,7 @@ const offer = (self, message) => suspend$3(() => {
25302
24515
  }
25303
24516
  return offerRemainingSingle(self, message);
25304
24517
  case "sliding":
25305
- take$3(self.messages);
24518
+ take$2(self.messages);
25306
24519
  append(self.messages, message);
25307
24520
  return exitTrue;
25308
24521
  }
@@ -25345,7 +24558,7 @@ const offerUnsafe = (self, message) => {
25345
24558
  if (self.state._tag !== "Open") return false;
25346
24559
  else if (self.messages.length >= self.capacity) {
25347
24560
  if (self.strategy === "sliding") {
25348
- take$3(self.messages);
24561
+ take$2(self.messages);
25349
24562
  append(self.messages, message);
25350
24563
  return true;
25351
24564
  } else if (self.capacity <= 0 && self.state.takers.size > 0) {
@@ -25750,14 +24963,14 @@ const take$1 = (self) => suspend$3(() => takeUnsafe(self) ?? andThen$1(awaitTake
25750
24963
  const takeUnsafe = (self) => {
25751
24964
  if (self.state._tag === "Done") return self.state.exit;
25752
24965
  if (self.messages.length > 0) {
25753
- const message = take$3(self.messages);
24966
+ const message = take$2(self.messages);
25754
24967
  releaseCapacity(self);
25755
24968
  return exitSucceed(message);
25756
24969
  } else if (self.capacity <= 0 && self.state.offers.size > 0) {
25757
24970
  self.capacity = 1;
25758
24971
  releaseCapacity(self);
25759
24972
  self.capacity = 0;
25760
- const message = take$3(self.messages);
24973
+ const message = take$2(self.messages);
25761
24974
  releaseCapacity(self);
25762
24975
  return exitSucceed(message);
25763
24976
  }
@@ -25829,7 +25042,7 @@ const takeBetweenUnsafe = (self, min, max) => {
25829
25042
  self.capacity = 1;
25830
25043
  releaseCapacity(self);
25831
25044
  self.capacity = 0;
25832
- const messages = [take$3(self.messages)];
25045
+ const messages = [take$2(self.messages)];
25833
25046
  releaseCapacity(self);
25834
25047
  return exitSucceed(messages);
25835
25048
  }
@@ -26281,21 +25494,6 @@ const fromTransformBracket = (f) => fromTransform$1(fnUntraced(function* (upstre
26281
25494
  * @since 4.0.0
26282
25495
  */
26283
25496
  const toTransform = (channel) => channel.transform;
26284
- /**
26285
- * The default chunk size used by channels for batching operations.
26286
- *
26287
- * **Example** (Reading the default chunk size)
26288
- *
26289
- * ```ts
26290
- * import { Channel } from "effect"
26291
- *
26292
- * console.log(Channel.DefaultChunkSize) // 4096
26293
- * ```
26294
- *
26295
- * @category constants
26296
- * @since 4.0.0
26297
- */
26298
- const DefaultChunkSize = 4096;
26299
25497
  const asyncQueue = (scope, f, options) => make$48({
26300
25498
  capacity: options?.bufferSize,
26301
25499
  strategy: options?.strategy
@@ -26336,87 +25534,6 @@ const callbackArray = (f, options) => fromTransform$1((_, scope) => map$4(asyncQ
26336
25534
  */
26337
25535
  const suspend$1 = (evaluate) => fromTransform$1((upstream, scope) => suspend$2(() => toTransform(evaluate())(upstream, scope)));
26338
25536
  /**
26339
- * Creates a `Channel` from an iterator that emits arrays of elements.
26340
- *
26341
- * **Example** (Batching iterator output)
26342
- *
26343
- * ```ts
26344
- * import { Channel } from "effect"
26345
- *
26346
- * // Create a channel from a simple iterator
26347
- * const numberIterator = (): Iterator<number, string> => {
26348
- * let count = 0
26349
- * return {
26350
- * next: () => {
26351
- * if (count < 3) {
26352
- * return { value: count++, done: false }
26353
- * }
26354
- * return { value: "finished", done: true }
26355
- * }
26356
- * }
26357
- * }
26358
- *
26359
- * const channel = Channel.fromIteratorArray(() => numberIterator(), 2)
26360
- * // This will emit arrays: [0, 1], [2], then complete with "finished"
26361
- * ```
26362
- *
26363
- * **Example** (Batching generator output)
26364
- *
26365
- * ```ts
26366
- * import { Channel } from "effect"
26367
- *
26368
- * // Create channel from a generator function
26369
- * function* fibonacci(): Generator<number, void, unknown> {
26370
- * let a = 0, b = 1
26371
- * for (let i = 0; i < 5; i++) {
26372
- * yield a
26373
- * ;[a, b] = [b, a + b]
26374
- * }
26375
- * }
26376
- *
26377
- * const fibChannel = Channel.fromIteratorArray(() => fibonacci(), 3)
26378
- * // Emits: [0, 1, 1], [2, 3], then completes
26379
- * ```
26380
- *
26381
- * @category constructors
26382
- * @since 4.0.0
26383
- */
26384
- const fromIteratorArray = (iterator, chunkSize = DefaultChunkSize) => fromPull$1(sync(() => {
26385
- const iter = iterator();
26386
- let done$15 = none();
26387
- return suspend$2(() => {
26388
- if (done$15._tag === "Some") return done(done$15.value);
26389
- const buffer = [];
26390
- while (buffer.length < chunkSize) {
26391
- const state = iter.next();
26392
- if (state.done) {
26393
- if (buffer.length === 0) return done(state.value);
26394
- done$15 = some(state.value);
26395
- break;
26396
- }
26397
- buffer.push(state.value);
26398
- }
26399
- return succeed$3(buffer);
26400
- });
26401
- }));
26402
- /**
26403
- * Creates a `Channel` that emits arrays of elements from an iterable.
26404
- *
26405
- * **Example** (Batching iterable output)
26406
- *
26407
- * ```ts
26408
- * import { Channel } from "effect"
26409
- *
26410
- * const numbers = [1, 2, 3, 4, 5]
26411
- * const channel = Channel.fromIterableArray(numbers)
26412
- * // Emits arrays like: [1, 2, 3, 4], [5] (based on chunk size)
26413
- * ```
26414
- *
26415
- * @category constructors
26416
- * @since 4.0.0
26417
- */
26418
- const fromIterableArray = (iterable, chunkSize = DefaultChunkSize) => fromIteratorArray(() => iterable[Symbol.iterator](), chunkSize);
26419
- /**
26420
25537
  * Creates a `Channel` that emits a single value and then ends.
26421
25538
  *
26422
25539
  * **Example** (Creating channels that succeed)
@@ -27493,14 +26610,6 @@ const unwrap$3 = (channel) => fromTransform$1((upstream, scope) => {
27493
26610
  }));
27494
26611
  });
27495
26612
  /**
27496
- * Runs a channel with a scope provided for the duration of the channel
27497
- * execution, removing the channel's `Scope` requirement.
27498
- *
27499
- * @category resource management
27500
- * @since 2.0.0
27501
- */
27502
- const scoped$2 = (self) => fromTransformBracket((upstream, scope, forkedScope) => map$4(provide$3(toTransform(self)(upstream, scope), forkedScope), provide$3(forkedScope)));
27503
- /**
27504
26613
  * Returns a channel with an exit-aware finalizer that is guaranteed to run once
27505
26614
  * the channel begins execution, whether it succeeds or fails.
27506
26615
  *
@@ -28328,7 +27437,7 @@ const makeUnsafe$2 = (options) => ({
28328
27437
  */
28329
27438
  const make$46 = (options) => withFiber((fiber) => {
28330
27439
  const context = fiber.context;
28331
- const scope = get$9(context, Scope);
27440
+ const scope = get$8(context, Scope);
28332
27441
  const self = makeUnsafe$2({
28333
27442
  lookup: options.lookup,
28334
27443
  context,
@@ -28521,7 +27630,7 @@ var RcRefImpl = class {
28521
27630
  /** @internal */
28522
27631
  const make$45 = (options) => withFiber((fiber) => {
28523
27632
  const context = fiber.context;
28524
- const scope = get$9(context, Scope);
27633
+ const scope = get$8(context, Scope);
28525
27634
  const ref = new RcRefImpl(options.acquire, context, scope, options.idleTimeToLive ? fromInputUnsafe(options.idleTimeToLive) : void 0);
28526
27635
  return as(addFinalizerExit(scope, () => {
28527
27636
  const close$1 = ref.state._tag === "Acquired" ? close(ref.state.scope, void_$2) : void_$1;
@@ -28837,30 +27946,6 @@ const fromChannel = fromChannel$2;
28837
27946
  */
28838
27947
  const fromEffect = (effect) => fromChannel(fromEffect$1(map$4(effect, of)));
28839
27948
  /**
28840
- * Creates a stream from an effect producing a value of type `A` which repeats forever.
28841
- *
28842
- * **Example** (Repeating an effect forever)
28843
- *
28844
- * ```ts
28845
- * import { Console, Effect, Random, Stream } from "effect"
28846
- *
28847
- * const program = Effect.gen(function*() {
28848
- * const stream = Stream.fromEffectRepeat(Random.nextInt).pipe(
28849
- * Stream.take(5)
28850
- * )
28851
- * const values = yield* Stream.runCollect(stream)
28852
- * yield* Console.log(values)
28853
- * })
28854
- *
28855
- * Effect.runPromise(program)
28856
- * // Output: [ 3891571149, 4239494205, 2352981603, 2339111046, 1488052210 ]
28857
- * ```
28858
- *
28859
- * @category constructors
28860
- * @since 4.0.0
28861
- */
28862
- const fromEffectRepeat = (effect) => fromPull(succeed$3(map$4(effect, of)));
28863
- /**
28864
27949
  * Creates a stream from a pull effect, such as one produced by `Stream.toPull`.
28865
27950
  *
28866
27951
  * **Details**
@@ -29071,34 +28156,6 @@ const suspend = (stream) => fromChannel(suspend$1(() => stream().channel));
29071
28156
  */
29072
28157
  const fail$1 = (error) => fromChannel(fail$2(error));
29073
28158
  /**
29074
- * Creates a new `Stream` from an iterable collection of values.
29075
- *
29076
- * **Details**
29077
- *
29078
- * - `chunkSize`: Maximum number of values emitted per chunk.
29079
- *
29080
- * **Example** (Creating a stream from an iterable)
29081
- *
29082
- * ```ts
29083
- * import { Console, Effect, Stream } from "effect"
29084
- *
29085
- * const numbers = [1, 2, 3]
29086
- *
29087
- * const program = Effect.gen(function*() {
29088
- * const stream = Stream.fromIterable(numbers)
29089
- * const values = yield* Stream.runCollect(stream)
29090
- * yield* Console.log(values)
29091
- * })
29092
- *
29093
- * Effect.runPromise(program)
29094
- * // Output: [ 1, 2, 3 ]
29095
- * ```
29096
- *
29097
- * @category constructors
29098
- * @since 2.0.0
29099
- */
29100
- const fromIterable$1 = (iterable, options) => Array.isArray(iterable) && options?.chunkSize === void 0 ? fromArray(iterable) : fromChannel(fromIterableArray(iterable, options?.chunkSize));
29101
- /**
29102
28159
  * Creates a stream from an array of values.
29103
28160
  *
29104
28161
  * **Example** (Creating a stream from an array of values)
@@ -29259,34 +28316,6 @@ const fromReadableStream = (options) => fromChannel(fromTransform$1(fnUntraced(f
29259
28316
  */
29260
28317
  const unwrap$1 = (effect) => fromChannel(unwrap$3(map$4(effect, toChannel)));
29261
28318
  /**
29262
- * Runs a stream that requires `Scope` in a managed scope, ensuring its
29263
- * finalizers are run when the stream completes.
29264
- *
29265
- * **Example** (Scoping a stream)
29266
- *
29267
- * ```ts
29268
- * import { Console, Effect, Stream } from "effect"
29269
- *
29270
- * const stream = Stream.scoped(
29271
- * Stream.fromEffect(
29272
- * Effect.acquireRelease(
29273
- * Console.log("acquire").pipe(Effect.as("resource")),
29274
- * () => Console.log("release")
29275
- * )
29276
- * )
29277
- * )
29278
- *
29279
- * Effect.runPromise(Stream.runCollect(stream)).then(console.log)
29280
- * // acquire
29281
- * // release
29282
- * // [ "resource" ]
29283
- * ```
29284
- *
29285
- * @category constructors
29286
- * @since 2.0.0
29287
- */
29288
- const scoped$1 = (self) => fromChannel(scoped$2(self.channel));
29289
- /**
29290
28319
  * Transforms the elements of this stream using the supplied function.
29291
28320
  *
29292
28321
  * **Example** (Mapping stream values)
@@ -29489,53 +28518,6 @@ const catch_ = /*#__PURE__*/ dual(2, (self, f) => fromChannel(catch_$1(self.chan
29489
28518
  */
29490
28519
  const orDie = (self) => fromChannel(orDie$1(self.channel));
29491
28520
  /**
29492
- * Takes elements until the predicate matches.
29493
- *
29494
- * **Details**
29495
- *
29496
- * When `excludeLast` is `true`, the matching element is dropped.
29497
- *
29498
- * **Example** (Taking until a predicate matches)
29499
- *
29500
- * ```ts
29501
- * import { Console, Effect, Stream } from "effect"
29502
- *
29503
- * const stream = Stream.range(1, 5)
29504
- *
29505
- * const program = Effect.gen(function*() {
29506
- * const inclusive = yield* stream.pipe(
29507
- * Stream.takeUntil((n) => n % 3 === 0),
29508
- * Stream.runCollect
29509
- * )
29510
- * yield* Console.log(inclusive)
29511
- * // Output: [ 1, 2, 3 ]
29512
- *
29513
- * const exclusive = yield* stream.pipe(
29514
- * Stream.takeUntil((n) => n % 3 === 0, { excludeLast: true }),
29515
- * Stream.runCollect
29516
- * )
29517
- * yield* Console.log(exclusive)
29518
- * // Output: [ 1, 2 ]
29519
- * })
29520
- * ```
29521
- *
29522
- * @category filtering
29523
- * @since 2.0.0
29524
- */
29525
- const takeUntil = /*#__PURE__*/ dual((args) => isStream(args[0]), (self, predicate, options) => transformPull(self, (pull, _scope) => sync(() => {
29526
- let i = 0;
29527
- let done$9 = false;
29528
- return flatMap$2(suspend$2(() => done$9 ? done() : pull), (chunk) => {
29529
- const index = chunk.findIndex((a) => predicate(a, i++));
29530
- if (index >= 0) {
29531
- done$9 = true;
29532
- const arr = chunk.slice(0, options?.excludeLast ? index : index + 1);
29533
- return isReadonlyArrayNonEmpty(arr) ? succeed$3(arr) : done();
29534
- }
29535
- return succeed$3(chunk);
29536
- });
29537
- })));
29538
- /**
29539
28521
  * Drops the first `n` elements from this stream.
29540
28522
  *
29541
28523
  * **Example** (Dropping values from the left)
@@ -30610,7 +29592,7 @@ const make$41 = (spawn) => {
30610
29592
  const streamLines = (command, options) => splitLines(streamString(command, options));
30611
29593
  return ChildProcessSpawner.of({
30612
29594
  spawn,
30613
- exitCode: (command) => scoped$3(flatMap$2(spawn(command), (handle) => handle.exitCode)),
29595
+ exitCode: (command) => scoped$1(flatMap$2(spawn(command), (handle) => handle.exitCode)),
30614
29596
  streamString,
30615
29597
  streamLines,
30616
29598
  lines: (command, options) => runCollect(streamLines(command, options)),
@@ -31710,53 +30692,71 @@ const get$3 = (self) => sync(() => self.ref.current);
31710
30692
  */
31711
30693
  const set$4 = /*#__PURE__*/ dual(2, (self, value) => sync(() => set$6(self.ref, value)));
31712
30694
  /**
31713
- * Updates the value of the Ref atomically using the given function.
30695
+ * Modifies the value of the Ref atomically using the given function.
31714
30696
  *
31715
30697
  * **When to use**
31716
30698
  *
31717
- * Use to apply a state transition without returning a value.
30699
+ * Use to compute both a separate return value and the next stored value in one
30700
+ * atomic update.
31718
30701
  *
31719
- * **Example** (Updating a value)
30702
+ * **Details**
30703
+ *
30704
+ * The function receives the current value and returns a tuple of
30705
+ * `[result, newValue]`. The Ref is updated with `newValue`, and `result` is
30706
+ * returned by the effect.
30707
+ *
30708
+ * **Example** (Modifying a value atomically)
31720
30709
  *
31721
30710
  * ```ts
31722
30711
  * import { Effect, Ref } from "effect"
31723
30712
  *
31724
30713
  * const program = Effect.gen(function*() {
31725
- * const counter = yield* Ref.make(5)
30714
+ * const counter = yield* Ref.make(10)
31726
30715
  *
31727
- * // Update the value
31728
- * yield* Ref.update(counter, (n) => n * 2)
30716
+ * // Modify the ref and return some computation result
30717
+ * const result = yield* Ref.modify(counter, (n) => [
30718
+ * `Previous value was ${n}`, // Return value
30719
+ * n * 2 // New ref value
30720
+ * ])
31729
30721
  *
31730
- * const value = yield* Ref.get(counter)
31731
- * console.log(value) // 10
30722
+ * console.log(result) // "Previous value was 10"
30723
+ *
30724
+ * const current = yield* Ref.get(counter)
30725
+ * console.log(current) // 20
31732
30726
  * })
31733
30727
  *
31734
- * // Using multiple operations
30728
+ * // Example with more complex computation
31735
30729
  * const program2 = Effect.gen(function*() {
31736
- * const counter = yield* Ref.make(5)
31737
- * yield* Ref.update(counter, (n: number) => n + 10)
31738
- * const value = yield* Ref.get(counter)
31739
- * console.log(value) // 15
30730
+ * const state = yield* Ref.make({ count: 0, total: 0 })
30731
+ *
30732
+ * const incremented = yield* Ref.modify(state, (s) => [
30733
+ * s.count, // Return previous count
30734
+ * { count: s.count + 1, total: s.total + s.count + 1 } // New state
30735
+ * ])
30736
+ *
30737
+ * console.log(incremented) // 0
31740
30738
  * })
31741
30739
  * ```
31742
30740
  *
31743
- * @see {@link updateAndGet} for returning the new value
31744
- * @see {@link getAndUpdate} for returning the previous value
30741
+ * @see {@link updateAndGet} for returning the new stored value
30742
+ * @see {@link modifySome} for optionally updating while returning a separate result
31745
30743
  *
31746
30744
  * @category setters
31747
30745
  * @since 2.0.0
31748
30746
  */
31749
- const update$1 = /*#__PURE__*/ dual(2, (self, f) => sync(() => {
31750
- self.ref.current = f(self.ref.current);
30747
+ const modify$2 = /*#__PURE__*/ dual(2, (self, f) => sync(() => {
30748
+ const [b, a] = f(self.ref.current);
30749
+ self.ref.current = a;
30750
+ return b;
31751
30751
  }));
31752
30752
  /**
31753
- * Updates the value of the Ref atomically using the given function and returns the new value.
30753
+ * Updates the value of the Ref atomically using the given function.
31754
30754
  *
31755
30755
  * **When to use**
31756
30756
  *
31757
- * Use to apply a state transition and return the new stored value.
30757
+ * Use to apply a state transition without returning a value.
31758
30758
  *
31759
- * **Example** (Updating and returning the new value)
30759
+ * **Example** (Updating a value)
31760
30760
  *
31761
30761
  * ```ts
31762
30762
  * import { Effect, Ref } from "effect"
@@ -31764,23 +30764,31 @@ const update$1 = /*#__PURE__*/ dual(2, (self, f) => sync(() => {
31764
30764
  * const program = Effect.gen(function*() {
31765
30765
  * const counter = yield* Ref.make(5)
31766
30766
  *
31767
- * // Update and get the new value in one operation
31768
- * const newValue = yield* Ref.updateAndGet(counter, (n) => n * 3)
31769
- * console.log(newValue) // 15
30767
+ * // Update the value
30768
+ * yield* Ref.update(counter, (n) => n * 2)
31770
30769
  *
31771
- * // Verify the ref contains the new value
31772
- * const current = yield* Ref.get(counter)
31773
- * console.log(current) // 15
30770
+ * const value = yield* Ref.get(counter)
30771
+ * console.log(value) // 10
30772
+ * })
30773
+ *
30774
+ * // Using multiple operations
30775
+ * const program2 = Effect.gen(function*() {
30776
+ * const counter = yield* Ref.make(5)
30777
+ * yield* Ref.update(counter, (n: number) => n + 10)
30778
+ * const value = yield* Ref.get(counter)
30779
+ * console.log(value) // 15
31774
30780
  * })
31775
30781
  * ```
31776
30782
  *
31777
- * @see {@link update} for updating without returning the new value
31778
- * @see {@link getAndUpdate} for returning the previous value instead
30783
+ * @see {@link updateAndGet} for returning the new value
30784
+ * @see {@link getAndUpdate} for returning the previous value
31779
30785
  *
31780
- * @category mutations
30786
+ * @category setters
31781
30787
  * @since 2.0.0
31782
30788
  */
31783
- const updateAndGet = /*#__PURE__*/ dual(2, (self, f) => sync(() => self.ref.current = f(self.ref.current)));
30789
+ const update$1 = /*#__PURE__*/ dual(2, (self, f) => sync(() => {
30790
+ self.ref.current = f(self.ref.current);
30791
+ }));
31784
30792
  //#endregion
31785
30793
  //#region ../../node_modules/.pnpm/effect@4.0.0-beta.74/node_modules/effect/dist/internal/hashMap.js
31786
30794
  /**
@@ -35040,7 +34048,7 @@ const Proto$10 = /*#__PURE__*/ Object.create(null);
35040
34048
  Object.defineProperties(Proto$10, {
35041
34049
  [TypeId$22]: { value: TypeId$22 },
35042
34050
  [symbolRedactable]: { value(context) {
35043
- return redact(this, get$9(context, CurrentRedactedNames));
34051
+ return redact(this, get$8(context, CurrentRedactedNames));
35044
34052
  } },
35045
34053
  toJSON: { value() {
35046
34054
  return redact$1(this);
@@ -39414,7 +38422,7 @@ var MultipartError = class MultipartError extends TaggedError("MultipartError")
39414
38422
  * @since 4.0.0
39415
38423
  */
39416
38424
  const makeConfig = (headers) => withFiber((fiber) => {
39417
- const mimeTypes = get$9(fiber.context, FieldMimeTypes);
38425
+ const mimeTypes = get$8(fiber.context, FieldMimeTypes);
39418
38426
  return succeed$3({
39419
38427
  headers,
39420
38428
  maxParts: fiber.getRef(MaxParts),
@@ -40482,7 +39490,7 @@ var MiddlewareImpl = class MiddlewareImpl {
40482
39490
  const stack = [context.mapUnsafe.get(fnContextKey)];
40483
39491
  if (this.dependencies) {
40484
39492
  const memoMap = yield* CurrentMemoMap;
40485
- const scope = get$9(context, Scope);
39493
+ const scope = get$8(context, Scope);
40486
39494
  const depsContext = yield* buildWithMemoMap(this.dependencies, memoMap, scope);
40487
39495
  stack.push(...getMiddleware(depsContext));
40488
39496
  }
@@ -43534,7 +42542,7 @@ const makeNoSerialization = /*#__PURE__*/ fnUntraced(function* (group, options)
43534
42542
  const concurrency = options.concurrency ?? "unbounded";
43535
42543
  const disableFatalDefects = options.disableFatalDefects ?? false;
43536
42544
  const services = yield* context$1();
43537
- const scope = get$9(services, Scope);
42545
+ const scope = get$8(services, Scope);
43538
42546
  const trackFiber = runIn(forkUnsafe(scope, "parallel"));
43539
42547
  const concurrencySemaphore = concurrency === "unbounded" ? void 0 : yield* make$47(concurrency);
43540
42548
  const clients = /* @__PURE__ */ new Map();
@@ -43731,7 +42739,7 @@ const makeNoSerialization = /*#__PURE__*/ fnUntraced(function* (group, options)
43731
42739
  return flatMap$2(write, () => latch.await);
43732
42740
  })),
43733
42741
  step: constVoid
43734
- })), catchDone(() => void_$1), scoped$3);
42742
+ })), catchDone(() => void_$1), scoped$1);
43735
42743
  return runForEachArray(stream, (values) => {
43736
42744
  const write = options.onFromServer({
43737
42745
  _tag: "Chunk",
@@ -50250,7 +49258,7 @@ const layer$8 = /*#__PURE__*/ effect(Terminal$1, /*#__PURE__*/ (/* @__PURE__ */
50250
49258
  stdin.on("keypress", handleKeypress);
50251
49259
  return queue;
50252
49260
  });
50253
- const readLine = scoped$3(flatMap$2(get$4(rlRef), (readlineInterface) => callback$1((resume) => {
49261
+ const readLine = scoped$1(flatMap$2(get$4(rlRef), (readlineInterface) => callback$1((resume) => {
50254
49262
  const onLine = (line) => resume(succeed$3(line));
50255
49263
  readlineInterface.once("line", onLine);
50256
49264
  return sync(() => readlineInterface.off("line", onLine));
@@ -51752,7 +50760,7 @@ const Proto = {
51752
50760
  * @category constructors
51753
50761
  * @since 2.0.0
51754
50762
  */
51755
- const make$3 = (value) => map$4(unbounded$1({ replay: 1 }), (pubsub) => {
50763
+ const make$3 = (value) => map$4(unbounded({ replay: 1 }), (pubsub) => {
51756
50764
  const self = Object.create(Proto);
51757
50765
  self.semaphore = makeUnsafe$3(1);
51758
50766
  self.value = value;
@@ -51825,6 +50833,49 @@ const setUnsafe = (self, value) => {
51825
50833
  publishUnsafe(self.pubsub, value);
51826
50834
  };
51827
50835
  /**
50836
+ * Retrieves the current value and optionally updates the reference.
50837
+ *
50838
+ * **When to use**
50839
+ *
50840
+ * Use to read the old value while applying a synchronous update only when a
50841
+ * new value is available.
50842
+ *
50843
+ * **Details**
50844
+ *
50845
+ * If the function returns `Option.some`, the new value is set and published. If
50846
+ * it returns `Option.none`, the reference is left unchanged and no update is
50847
+ * published.
50848
+ *
50849
+ * **Example** (Getting and conditionally updating a value)
50850
+ *
50851
+ * ```ts
50852
+ * import { Effect, Option, SubscriptionRef } from "effect"
50853
+ *
50854
+ * const program = Effect.gen(function*() {
50855
+ * const ref = yield* SubscriptionRef.make(10)
50856
+ *
50857
+ * const oldValue = yield* SubscriptionRef.getAndUpdateSome(
50858
+ * ref,
50859
+ * (n) => n > 5 ? Option.some(n * 2) : Option.none()
50860
+ * )
50861
+ * console.log("Old value:", oldValue)
50862
+ *
50863
+ * const newValue = yield* SubscriptionRef.get(ref)
50864
+ * console.log("New value:", newValue)
50865
+ * })
50866
+ * ```
50867
+ *
50868
+ * @category getters
50869
+ * @since 2.0.0
50870
+ */
50871
+ const getAndUpdateSome = /*#__PURE__*/ dual(2, (self, update) => self.semaphore.withPermit(sync(() => {
50872
+ const current = self.value;
50873
+ const option = update(current);
50874
+ if (isNone(option)) return succeed$3(current);
50875
+ setUnsafe(self, option.value);
50876
+ return current;
50877
+ })));
50878
+ /**
51828
50879
  * Modifies the `SubscriptionRef` atomically with a function that computes a
51829
50880
  * return value and a new value, notifying subscribers of the change.
51830
50881
  *
@@ -52362,13 +51413,7 @@ var TerminalError = class extends TaggedErrorClass()("TerminalError", {
52362
51413
  cause: optional(Defect),
52363
51414
  message: optional(String$1)
52364
51415
  }) {};
52365
- const TerminalEvent = Struct({
52366
- data: String$1,
52367
- sequence: Number$1,
52368
- type: Literal("data")
52369
- });
52370
- const TerminalState = Struct({
52371
- runId: Number$1,
51416
+ const TerminalStatus = Struct({
52372
51417
  state: Literals([
52373
51418
  "idle",
52374
51419
  "starting",
@@ -52380,13 +51425,23 @@ const TerminalState = Struct({
52380
51425
  ]),
52381
51426
  title: String$1
52382
51427
  });
52383
- function terminalStateActive(state) {
51428
+ function terminalStatusActive(state) {
52384
51429
  return state === "idle" || state === "starting" || state === "running" || state === "waiting";
52385
51430
  }
52386
- const TerminalUpdate = Union([Struct({
52387
- state: TerminalState,
52388
- type: Literal("state")
52389
- }), TerminalEvent]);
51431
+ const TerminalAttachUpdate = Union([
51432
+ Struct({
51433
+ data: String$1,
51434
+ type: Literal("snapshot")
51435
+ }),
51436
+ Struct({
51437
+ data: String$1,
51438
+ type: Literal("data")
51439
+ }),
51440
+ Struct({
51441
+ status: TerminalStatus,
51442
+ type: Literal("status")
51443
+ })
51444
+ ]);
52390
51445
  //#endregion
52391
51446
  //#region src/rpcs/contracts.ts
52392
51447
  const CreateWorktreeSource = Union([
@@ -52427,7 +51482,7 @@ const AgentSession = Struct({
52427
51482
  "pi"
52428
51483
  ]),
52429
51484
  label: String$1,
52430
- state: TerminalState,
51485
+ state: TerminalStatus,
52431
51486
  uuid: String$1
52432
51487
  });
52433
51488
  var RpcContracts = class extends make$15(make$18("agents.create", {
@@ -52563,21 +51618,21 @@ var RpcContracts = class extends make$15(make$18("agents.create", {
52563
51618
  }), make$18("terminal.restart", {
52564
51619
  error: TerminalError,
52565
51620
  payload: TerminalPayload,
52566
- success: TerminalState
52567
- }), make$18("terminal.state.watch", {
51621
+ success: TerminalStatus
51622
+ }), make$18("terminal.status.watch", {
52568
51623
  error: TerminalError,
52569
51624
  payload: TerminalPayload,
52570
51625
  stream: true,
52571
- success: TerminalState
51626
+ success: TerminalStatus
52572
51627
  }), make$18("terminal.stop", {
52573
51628
  error: TerminalError,
52574
51629
  payload: TerminalPayload,
52575
- success: TerminalState
52576
- }), make$18("terminal.watch", {
51630
+ success: TerminalStatus
51631
+ }), make$18("terminal.attach", {
52577
51632
  error: TerminalError,
52578
51633
  payload: TerminalPayload,
52579
51634
  stream: true,
52580
- success: TerminalUpdate
51635
+ success: TerminalAttachUpdate
52581
51636
  })) {};
52582
51637
  //#endregion
52583
51638
  //#region ../../packages/git/src/service.ts
@@ -52588,7 +51643,7 @@ var GitCommand = class extends Service()("@deslop/git/service/GitCommand", { mak
52588
51643
  command: args[0] ?? "git",
52589
51644
  cwd
52590
51645
  });
52591
- return yield* scoped$3(gen(function* () {
51646
+ return yield* scoped$1(gen(function* () {
52592
51647
  const handle = yield* pipe(spawner.spawn(make$40("git", args, {
52593
51648
  cwd,
52594
51649
  stderr: "pipe",
@@ -53178,7 +52233,7 @@ var GitReview = class extends Service()("@deslop/git/service/GitReview", { make:
53178
52233
  command: args[0] ?? "gh",
53179
52234
  cwd: config.cwd
53180
52235
  });
53181
- return yield* scoped$3(gen(function* () {
52236
+ return yield* scoped$1(gen(function* () {
53182
52237
  const handle = yield* pipe(spawner.spawn(make$40("gh", args, {
53183
52238
  cwd: config.cwd,
53184
52239
  stderr: "pipe",
@@ -53439,7 +52494,7 @@ var GitCommitAction = class extends Service()("@deslop/git/service/GitCommitActi
53439
52494
  command: args[0] ?? "gh",
53440
52495
  cwd: config.cwd
53441
52496
  });
53442
- return yield* scoped$3(gen(function* () {
52497
+ return yield* scoped$1(gen(function* () {
53443
52498
  const handle = yield* pipe(spawner.spawn(make$40("gh", args, {
53444
52499
  cwd: config.cwd,
53445
52500
  stderr: "pipe",
@@ -53812,244 +52867,172 @@ var Portless = class Portless extends Service()("@deslop/portless/Portless", { m
53812
52867
  });
53813
52868
  };
53814
52869
  //#endregion
53815
- //#region ../../packages/terminal/src/service.ts
53816
- var import_addon_progress = /* @__PURE__ */ __toESM((/* @__PURE__ */ __commonJSMin(((exports, module) => {
53817
- (function(e, t) {
53818
- "object" == typeof exports && "object" == typeof module ? module.exports = t() : "function" == typeof define && define.amd ? define([], t) : "object" == typeof exports ? exports.ProgressAddon = t() : e.ProgressAddon = t();
53819
- })(globalThis, (() => (() => {
53820
- "use strict";
53821
- var e = {};
53822
- return (() => {
53823
- var t = e;
53824
- function s(e) {
53825
- let t = 0;
53826
- for (let s = 0; s < e.length; ++s) {
53827
- const r = e.charCodeAt(s);
53828
- if (r < 48 || 57 < r) return -1;
53829
- t = 10 * t + r - 48;
53830
- }
53831
- return t;
53832
- }
53833
- Object.defineProperty(t, "__esModule", { value: !0 }), t.ProgressAddon = void 0, t.ProgressAddon = class {
53834
- constructor() {
53835
- this._st = 0, this._pr = 0;
53836
- }
53837
- dispose() {
53838
- this._seqHandler?.dispose(), this._onChange?.dispose();
53839
- }
53840
- activate(e) {
53841
- this._seqHandler = e.parser.registerOscHandler(9, ((e) => {
53842
- if (!e.startsWith("4;")) return !1;
53843
- const t = e.split(";");
53844
- if (t.length > 3) return !0;
53845
- 2 === t.length && t.push("");
53846
- const r = s(t[1]), o = s(t[2]);
53847
- switch (r) {
53848
- case 0:
53849
- this.progress = {
53850
- state: r,
53851
- value: 0
53852
- };
53853
- break;
53854
- case 1:
53855
- if (o < 0) return !0;
53856
- this.progress = {
53857
- state: r,
53858
- value: o
53859
- };
53860
- break;
53861
- case 2:
53862
- case 4:
53863
- if (o < 0) return !0;
53864
- this.progress = {
53865
- state: r,
53866
- value: o || this._pr
53867
- };
53868
- break;
53869
- case 3: this.progress = {
53870
- state: r,
53871
- value: this._pr
53872
- };
53873
- }
53874
- return !0;
53875
- })), this._onChange = new e._core._onData.constructor(), this.onChange = this._onChange.event;
53876
- }
53877
- get progress() {
53878
- return {
53879
- state: this._st,
53880
- value: this._pr
53881
- };
53882
- }
53883
- set progress(e) {
53884
- e.state < 0 || e.state > 4 ? console.warn("progress state out of bounds, not applied") : (this._st = e.state, this._pr = Math.min(Math.max(e.value, 0), 100), this._onChange?.fire({
53885
- state: this._st,
53886
- value: this._pr
53887
- }));
53888
- }
53889
- };
53890
- })(), e;
53891
- })()));
53892
- })))(), 1);
53893
- const terminalReset = "\x1Bc";
53894
- function parseTitleSignal(title) {
52870
+ //#region ../../packages/terminal/src/model.ts
52871
+ const terminalReplayBytes = 8 * 1024 * 1024;
52872
+ const terminalChunkBytes = 64 * 1024;
52873
+ const terminalOscCarryBytes = 4096;
52874
+ function terminalByteLength(data) {
52875
+ return Buffer.byteLength(data);
52876
+ }
52877
+ function terminalChunks(data, chunkSize = terminalChunkBytes) {
52878
+ if (data === "") return empty$13();
52879
+ return pipe(range(0, Math.floor((data.length - 1) / chunkSize)), map$7((index) => data.slice(index * chunkSize, (index + 1) * chunkSize)));
52880
+ }
52881
+ function terminalReplayPush(ring, data, maxBytes = terminalReplayBytes) {
52882
+ let chunks = [...ring, data];
52883
+ let bytes = chunks.reduce((total, chunk) => total + terminalByteLength(chunk), 0);
52884
+ while (bytes > maxBytes) {
52885
+ const head = chunks[0];
52886
+ if (head === void 0) break;
52887
+ const excess = bytes - maxBytes;
52888
+ const headBytes = terminalByteLength(head);
52889
+ if (headBytes <= excess) {
52890
+ chunks = chunks.slice(1);
52891
+ bytes -= headBytes;
52892
+ continue;
52893
+ }
52894
+ let offset = Math.min(head.length, excess);
52895
+ while (offset < head.length && terminalByteLength(head.slice(offset)) > maxBytes - (bytes - headBytes)) offset += 1;
52896
+ chunks[0] = head.slice(offset);
52897
+ bytes = chunks.reduce((total, chunk) => total + terminalByteLength(chunk), 0);
52898
+ }
52899
+ return chunks;
52900
+ }
52901
+ function terminalTitleStatus(title) {
53895
52902
  const trimmed = title.trim();
53896
- if (/^\[\s*[!.]\s*\]\s*Action Required\b/iu.test(trimmed)) return {
53897
- state: "waiting",
53898
- title: trimmed.replace(/^\[\s*[!.]\s*\]\s*/iu, "") || trimmed
53899
- };
53900
- const spinner = /^(?:[⠋⠙⠹⠸⠼⠴⠦⠧⠇⠏|/\\-])(?:\s|\s*\|)/u.test(trimmed);
53901
- const nextTitle = trimmed.replace(/^OC\s*\|\s*/iu, "").replace(/^π\s*-\s*/iu, "").replace(/^\[\s*[^\]]+\s*\]\s*/u, "").replace(/^(?:[⠋⠙⠹⠸⠼⠴⠦⠧⠇⠏|/\\-]\s*)+/u, "").replace(/^\|\s*/u, "").trim() || trimmed;
53902
- const segment = /^(Idle|Ready|Starting|Working|Thinking|Waiting)\b/iu.exec(nextTitle)?.[1]?.toLowerCase();
53903
- if (segment === "idle" || segment === "ready") return {
52903
+ if (trimmed === "") return {
53904
52904
  state: "idle",
53905
- title: nextTitle
53906
- };
53907
- if (segment === "starting") return {
53908
- state: "starting",
53909
- title: nextTitle
52905
+ title: ""
53910
52906
  };
53911
- if (segment === "waiting") return {
52907
+ if (/^\[\s*[!.]\s*\]\s*Action Required\b/iu.test(trimmed)) return {
53912
52908
  state: "waiting",
53913
- title: nextTitle
52909
+ title: trimmed.replace(/^\[\s*[!.]\s*\]\s*/iu, "") || trimmed
53914
52910
  };
53915
- if (segment === "working" || segment === "thinking" || spinner) return {
52911
+ return {
53916
52912
  state: "running",
53917
- title: nextTitle
53918
- };
53919
- if (trimmed !== "") return {
53920
- state: "idle",
53921
- title: nextTitle
52913
+ title: trimmed
53922
52914
  };
52915
+ }
52916
+ function terminalProgressStatus(value) {
52917
+ const progressState = Number.parseInt(value, 10);
52918
+ if (progressState === 0) return "idle";
52919
+ if (progressState === 2) return "failed";
52920
+ if (progressState === 4) return "waiting";
52921
+ return "running";
52922
+ }
52923
+ function terminalOscUpdates(data, carry = "") {
52924
+ const input = `${carry}${data}`;
52925
+ const updates = [];
52926
+ let nextCarry = "";
52927
+ for (let index = 0; index < input.length; index += 1) {
52928
+ if (input.charCodeAt(index) !== 27) continue;
52929
+ if (index === input.length - 1) {
52930
+ nextCarry = input.slice(index);
52931
+ break;
52932
+ }
52933
+ if (input[index + 1] !== "]") continue;
52934
+ const start = index + 2;
52935
+ let end = input.indexOf("\x07", start);
52936
+ let skip = 1;
52937
+ const st = input.indexOf("\x1B\\", start);
52938
+ if (end === -1 || st !== -1 && st < end) {
52939
+ end = st;
52940
+ skip = 2;
52941
+ }
52942
+ if (end === -1) {
52943
+ nextCarry = input.slice(index);
52944
+ break;
52945
+ }
52946
+ const payload = input.slice(start, end);
52947
+ const separator = payload.indexOf(";");
52948
+ const command = separator === -1 ? payload : payload.slice(0, separator);
52949
+ const value = separator === -1 ? "" : payload.slice(separator + 1);
52950
+ if (command === "0" || command === "2") updates.push({
52951
+ title: value,
52952
+ type: "title"
52953
+ });
52954
+ if (command === "9" && value.startsWith("4;")) updates.push({
52955
+ state: terminalProgressStatus(value.slice(2)),
52956
+ type: "progress"
52957
+ });
52958
+ index = end + skip - 1;
52959
+ }
53923
52960
  return {
53924
- state: "idle",
53925
- title: ""
52961
+ carry: terminalByteLength(nextCarry) > terminalOscCarryBytes ? "" : nextCarry,
52962
+ updates
53926
52963
  };
53927
52964
  }
53928
- function snapshotEvents(data, sequence) {
53929
- if (data === "") return empty$13();
53930
- return pipe(range(0, Math.floor((data.length - 1) / (256 * 1024))), map$7((index) => ({
53931
- data: data.slice(index * 256 * 1024, (index + 1) * 256 * 1024),
53932
- sequence,
53933
- type: "data"
53934
- })));
53935
- }
53936
- function adjacentGroups(items, sameGroup, merge) {
52965
+ //#endregion
52966
+ //#region ../../packages/terminal/src/service.ts
52967
+ function mergeWrites(items) {
53937
52968
  return pipe(items, reduce(empty$13(), (groups, item) => {
53938
52969
  const previous = groups.at(-1);
53939
- if (previous === void 0 || !sameGroup(previous, item)) return append$1(groups, item);
53940
- return append$1(dropRight(groups, 1), merge(previous, item));
52970
+ if (previous === void 0 || previous.process !== item.process) return append$1(groups, item);
52971
+ return append$1(dropRight(groups, 1), {
52972
+ data: `${previous.data}${item.data}`,
52973
+ process: item.process
52974
+ });
53941
52975
  }));
53942
52976
  }
53943
- function queuedDataGroups(items, merge) {
53944
- return adjacentGroups(items, (previous, item) => previous.generation === item.generation, merge);
53945
- }
53946
- function mergeQueuedData(previous, item) {
53947
- return {
53948
- data: `${previous.data}${item.data}`,
53949
- generation: item.generation
53950
- };
52977
+ function pauseProcess(subprocess) {
52978
+ if ("pause" in subprocess && typeof subprocess.pause === "function") subprocess.pause();
53951
52979
  }
53952
- function queuedWriteGroups(items) {
53953
- return adjacentGroups(items, (previous, item) => previous.process === item.process, (previous, item) => ({
53954
- data: `${previous.data}${item.data}`,
53955
- process: item.process
53956
- }));
52980
+ function resumeProcess(subprocess) {
52981
+ if ("resume" in subprocess && typeof subprocess.resume === "function") subprocess.resume();
53957
52982
  }
53958
52983
  var Terminal = class extends Service()("@deslop/terminal/service/Terminal", { make: fnUntraced(function* (config) {
53959
- const dataQueue = yield* unbounded();
53960
- const writeQueue = yield* unbounded();
52984
+ const dataQueue = yield* bounded(128);
52985
+ const writeQueue = yield* bounded(128);
53961
52986
  const resizeQueue = yield* sliding(1);
53962
- const events = yield* bounded$1(1024);
53963
52987
  const lifecycleLock = yield* make$47(1);
53964
- const screenLock = yield* make$47(1);
53965
- const eventSequenceRef = yield* make$38(0);
53966
- const parsedSequenceRef = yield* make$38(0);
53967
- const screenGenerationRef = yield* make$38(0);
53968
52988
  const processRef = yield* make$38(void 0);
52989
+ const replayProcessRef = yield* make$38(void 0);
53969
52990
  const sizeRef = yield* make$38({
53970
52991
  cols: 120,
53971
52992
  rows: 32
53972
52993
  });
52994
+ const replayRef = yield* make$38(empty$13());
52995
+ const oscRef = yield* make$38("");
52996
+ const attachRef = yield* make$38(void 0);
53973
52997
  const shell = yield* string("SHELL").pipe(orElseSucceed(() => "bash"));
53974
52998
  const processCommand = config.command?.command ?? shell;
53975
52999
  const processArgs = config.command?.args ?? [];
53976
53000
  const processEnv = config.command?.options.env ?? {};
53977
53001
  const autostart = config.command === void 0;
53978
- const stateRef = yield* make$3({
53979
- runId: 0,
53002
+ const statusRef = yield* make$3({
53980
53003
  state: autostart ? "starting" : "idle",
53981
53004
  title: ""
53982
53005
  });
53983
- const screen = new HeadlessModule.Terminal({
53984
- allowProposedApi: true,
53985
- cols: 120,
53986
- rows: 32,
53987
- scrollback: 1e4
53988
- });
53989
- const serialize = new SerializeModule.SerializeAddon();
53990
- const progressAddon = new import_addon_progress.ProgressAddon();
53991
- screen.loadAddon(serialize);
53992
- screen.loadAddon(progressAddon);
53993
- const publish$1 = fnUntraced(function* (data) {
53994
- const sequence = yield* updateAndGet(eventSequenceRef, (current) => current + 1);
53995
- yield* publish(events, {
53996
- data,
53997
- sequence,
53998
- type: "data"
53006
+ const publishStatus = fnUntraced(function* (status) {
53007
+ const previous = yield* getAndUpdateSome(statusRef, (current) => current.state === status.state && current.title === status.title ? none() : some(status));
53008
+ if (previous.state === status.state && previous.title === status.title) return;
53009
+ const attach = yield* get$3(attachRef);
53010
+ if (attach) yield* offer(attach, {
53011
+ status,
53012
+ type: "status"
53999
53013
  });
54000
- return sequence;
54001
53014
  });
54002
- const requestSnapshot = withPermit(screenLock, gen(function* () {
54003
- return {
54004
- data: serialize.serialize({ scrollback: 1e4 }),
54005
- sequence: yield* get$3(parsedSequenceRef)
54006
- };
54007
- }));
54008
- function setState(state) {
54009
- return update(stateRef, (current) => current.state === state ? current : {
53015
+ function setStatus(state) {
53016
+ return get(statusRef).pipe(flatMap$2((current) => publishStatus({
54010
53017
  ...current,
54011
53018
  state
54012
- });
54013
- }
54014
- function setProgressState(progressState) {
54015
- return update(stateRef, (current) => {
54016
- if (current.state === "stopped" || current.state === "exited" || current.state === "failed") return current;
54017
- const state = pipe(progressState.state, value, when(0, () => "idle"), when(2, () => "failed"), when(4, () => "waiting"), orElse(() => "running"));
54018
- if (current.state === state) return current;
54019
- return {
54020
- ...current,
54021
- state
54022
- };
54023
- });
53019
+ })));
54024
53020
  }
54025
53021
  function setTitle(title) {
54026
- return update(stateRef, (current) => {
54027
- if (!terminalStateActive(current.state)) return current;
54028
- const next = parseTitleSignal(title);
54029
- if (current.state === next.state && current.title === next.title) return current;
54030
- return {
53022
+ return get(statusRef).pipe(flatMap$2((current) => {
53023
+ if (!terminalStatusActive(current.state)) return void_$1;
53024
+ return publishStatus({
54031
53025
  ...current,
54032
- ...next
54033
- };
54034
- });
53026
+ ...terminalTitleStatus(title)
53027
+ });
53028
+ }));
53029
+ }
53030
+ function setProgress(state) {
53031
+ return get(statusRef).pipe(flatMap$2((current) => terminalStatusActive(current.state) ? publishStatus({
53032
+ ...current,
53033
+ state
53034
+ }) : void_$1));
54035
53035
  }
54036
- const startRun = pipe(update(stateRef, (state) => ({
54037
- ...state,
54038
- runId: state.runId + 1,
54039
- state: "starting",
54040
- title: ""
54041
- })), andThen(get(stateRef)));
54042
- screen.parser.registerOscHandler(0, (title) => {
54043
- runFork(setTitle(title));
54044
- return false;
54045
- });
54046
- screen.parser.registerOscHandler(2, (title) => {
54047
- runFork(setTitle(title));
54048
- return false;
54049
- });
54050
- progressAddon.onChange((nextProgress) => {
54051
- runFork(setProgressState(nextProgress));
54052
- });
54053
53036
  const interruptProcess = fnUntraced(function* (subprocess, signal) {
54054
53037
  yield* sync(() => {
54055
53038
  try {
@@ -54062,23 +53045,13 @@ var Terminal = class extends Service()("@deslop/terminal/service/Terminal", { ma
54062
53045
  yield* sleep("250 millis");
54063
53046
  yield* interruptProcess(subprocess, "SIGKILL");
54064
53047
  });
54065
- const writeScreen = fnUntraced(function* (input) {
54066
- if ((yield* get$3(screenGenerationRef)) !== input.generation) return;
54067
- yield* withPermit(screenLock, pipe(callback$1((resume) => {
54068
- screen.write(input.data, () => {
54069
- resume(succeed$3(void 0));
54070
- });
54071
- }), andThen(gen(function* () {
54072
- if ((yield* get$3(screenGenerationRef)) === input.generation) yield* set$4(parsedSequenceRef, yield* publish$1(input.data));
54073
- }))));
54074
- });
54075
53048
  const clearProcess = fnUntraced(function* (handle) {
54076
53049
  yield* update$1(processRef, (current) => current === handle ? void 0 : current);
54077
53050
  });
54078
53051
  const stopProcess = fnUntraced(function* (state) {
54079
53052
  const handle = yield* get$3(processRef);
54080
53053
  if (!handle) {
54081
- if (state) yield* setState(state);
53054
+ if (state) yield* setStatus(state);
54082
53055
  return;
54083
53056
  }
54084
53057
  yield* sync(() => {
@@ -54087,14 +53060,22 @@ var Terminal = class extends Service()("@deslop/terminal/service/Terminal", { ma
54087
53060
  });
54088
53061
  yield* clearProcess(handle);
54089
53062
  yield* pipe(terminateProcess(handle.process), ignore$1);
54090
- if (state) yield* setState(state);
53063
+ if (state) yield* setStatus(state);
54091
53064
  });
54092
53065
  const spawnProcess = fnUntraced(function* () {
54093
- const generation = yield* updateAndGet(screenGenerationRef, (current) => current + 1);
54094
- yield* withPermit(screenLock, pipe(sync(() => {
54095
- screen.reset();
54096
- }), andThen(publish$1(terminalReset)), tap((sequence) => set$4(parsedSequenceRef, sequence))));
54097
- yield* startRun;
53066
+ yield* stopProcess();
53067
+ yield* set$4(replayProcessRef, void 0);
53068
+ yield* set$4(replayRef, ["\x1Bc"]);
53069
+ yield* set$4(oscRef, "");
53070
+ yield* publishStatus({
53071
+ state: "starting",
53072
+ title: ""
53073
+ });
53074
+ const attach = yield* get$3(attachRef);
53075
+ if (attach) yield* offer(attach, {
53076
+ data: "\x1Bc",
53077
+ type: "data"
53078
+ });
54098
53079
  const size = yield* get$3(sizeRef);
54099
53080
  const subprocess = yield* try_({
54100
53081
  catch: (cause) => new TerminalError({
@@ -54115,54 +53096,36 @@ var Terminal = class extends Service()("@deslop/terminal/service/Terminal", { ma
54115
53096
  });
54116
53097
  const handle = {
54117
53098
  data: subprocess.onData((chunk) => {
54118
- offerUnsafe(dataQueue, {
53099
+ const output = {
54119
53100
  data: chunk,
54120
- generation
54121
- });
53101
+ process: subprocess
53102
+ };
53103
+ if (offerUnsafe(dataQueue, output)) return;
53104
+ pauseProcess(subprocess);
53105
+ runFork(offer(dataQueue, output).pipe(andThen(sync(() => resumeProcess(subprocess)))));
54122
53106
  }),
54123
53107
  exit: subprocess.onExit((event) => {
54124
53108
  runFork(withPermit(lifecycleLock, gen(function* () {
54125
53109
  if ((yield* get$3(processRef)) !== handle) return;
54126
53110
  yield* clearProcess(handle);
54127
53111
  if (autostart) {
54128
- yield* pipe(sleep("1 second"), andThen(spawnProcess()), catch_$2(() => setState("failed")));
53112
+ yield* pipe(sleep("1 second"), andThen(spawnProcess()), catch_$2(() => setStatus("failed")));
54129
53113
  return;
54130
53114
  }
54131
- yield* setState(event.exitCode === 0 ? "exited" : "failed");
53115
+ yield* setStatus(event.exitCode === 0 ? "exited" : "failed");
54132
53116
  })));
54133
53117
  }),
54134
53118
  process: subprocess
54135
53119
  };
54136
53120
  yield* set$4(processRef, handle);
54137
- yield* setState("running");
54138
- return yield* get(stateRef);
54139
- });
54140
- const startProcess = fnUntraced(function* () {
54141
- yield* stopProcess();
54142
- return yield* spawnProcess();
53121
+ yield* set$4(replayProcessRef, subprocess);
53122
+ yield* setStatus("running");
53123
+ return yield* get(statusRef);
54143
53124
  });
54144
- yield* pipe(fromQueue(dataQueue), groupedWithin(256, millis(16)), runForEach((items) => forEach$1(queuedDataGroups(fromIterable$2(items), mergeQueuedData), writeScreen, { discard: true })), forkScoped);
54145
- yield* addFinalizer(() => all([
54146
- stopProcess(),
54147
- shutdown$1(events),
54148
- shutdown(dataQueue),
54149
- shutdown(writeQueue),
54150
- shutdown(resizeQueue),
54151
- sync(() => {
54152
- screen.dispose();
54153
- })
54154
- ], {
54155
- concurrency: "unbounded",
54156
- discard: true
54157
- }));
54158
- if (autostart) yield* pipe(startProcess(), withPermit(lifecycleLock), catch_$2(() => setState("failed")));
54159
53125
  const resizeProcess = fnUntraced(function* (nextSize) {
54160
53126
  const size = yield* get$3(sizeRef);
54161
53127
  if (size.cols === nextSize.cols && size.rows === nextSize.rows) return;
54162
53128
  yield* set$4(sizeRef, nextSize);
54163
- yield* withPermit(screenLock, sync(() => {
54164
- screen.resize(nextSize.cols, nextSize.rows);
54165
- }));
54166
53129
  const process = yield* get$3(processRef);
54167
53130
  if (!process) return;
54168
53131
  yield* try_({
@@ -54175,10 +53138,6 @@ var Terminal = class extends Service()("@deslop/terminal/service/Terminal", { ma
54175
53138
  }
54176
53139
  });
54177
53140
  });
54178
- yield* pipe(fromQueue(resizeQueue), groupedWithin(32, millis(16)), runForEach((items) => pipe(last(fromIterable$2(items)), match$4({
54179
- onNone: () => void_$1,
54180
- onSome: resizeProcess
54181
- }))), forkScoped);
54182
53141
  const writeProcess = fnUntraced(function* (input) {
54183
53142
  if ((yield* get$3(processRef)) !== input.process) return;
54184
53143
  yield* try_({
@@ -54191,42 +53150,77 @@ var Terminal = class extends Service()("@deslop/terminal/service/Terminal", { ma
54191
53150
  }
54192
53151
  });
54193
53152
  });
54194
- yield* pipe(fromQueue(writeQueue), groupedWithin(128, millis(4)), runForEach((items) => forEach$1(queuedWriteGroups(fromIterable$2(items)), writeProcess, { discard: true })), forkScoped);
54195
- const eventsStream = scoped$1(unwrap$1(gen(function* () {
54196
- const subscription = yield* subscribe(events);
54197
- const snapshot = yield* requestSnapshot;
54198
- const pending = yield* takeUpTo(subscription, Number.POSITIVE_INFINITY);
54199
- const replay = filter$1(pending, (event) => event.sequence > snapshot.sequence);
54200
- const replaySequence = replay.at(-1)?.sequence ?? snapshot.sequence;
54201
- return pipe(fromIterable$1([
54202
- {
54203
- data: terminalReset,
54204
- sequence: snapshot.sequence,
53153
+ yield* pipe(fromQueue(dataQueue), groupedWithin(128, millis(16)), runForEach((items) => forEach$1(fromIterable$2(items), (output) => gen(function* () {
53154
+ if ((yield* get$3(replayProcessRef)) !== output.process) return;
53155
+ for (const chunk of terminalChunks(output.data)) {
53156
+ yield* update$1(replayRef, (ring) => terminalReplayPush(ring, chunk));
53157
+ const updates = yield* modify$2(oscRef, (carry) => {
53158
+ const parsed = terminalOscUpdates(chunk, carry);
53159
+ return [parsed.updates, parsed.carry];
53160
+ });
53161
+ for (const update of updates) yield* update.type === "title" ? setTitle(update.title) : setProgress(update.state);
53162
+ const attach = yield* get$3(attachRef);
53163
+ if (attach) yield* offer(attach, {
53164
+ data: chunk,
54205
53165
  type: "data"
54206
- },
54207
- ...snapshotEvents(snapshot.data, snapshot.sequence),
54208
- ...replay,
54209
- ...filter$1(pending, (event) => event.sequence > replaySequence)
54210
- ]), concat(fromEffectRepeat(take$2(subscription))));
54211
- })));
54212
- const stateUpdates = unwrap$1(pipe(get(stateRef), map$4((state) => concat(drop(1)(changes(stateRef)))(make$43(state)))));
54213
- const updates = merge$1(stateUpdates.pipe(map$2((state) => ({
54214
- state,
54215
- type: "state"
54216
- }))), eventsStream);
53166
+ });
53167
+ }
53168
+ }), { discard: true })), forkScoped);
53169
+ yield* pipe(fromQueue(resizeQueue), groupedWithin(32, millis(16)), runForEach((items) => pipe(last(fromIterable$2(items)), match$4({
53170
+ onNone: () => void_$1,
53171
+ onSome: resizeProcess
53172
+ }))), forkScoped);
53173
+ yield* pipe(fromQueue(writeQueue), groupedWithin(128, millis(4)), runForEach((items) => forEach$1(mergeWrites(fromIterable$2(items)), writeProcess, { discard: true })), forkScoped);
53174
+ yield* addFinalizer(() => all([
53175
+ stopProcess(),
53176
+ shutdown(dataQueue),
53177
+ shutdown(writeQueue),
53178
+ shutdown(resizeQueue),
53179
+ get$3(attachRef).pipe(flatMap$2((queue) => queue ? end(queue) : void_$1))
53180
+ ], {
53181
+ concurrency: "unbounded",
53182
+ discard: true
53183
+ }));
53184
+ if (autostart) yield* pipe(spawnProcess(), withPermit(lifecycleLock), catch_$2(() => setStatus("failed")));
53185
+ const attachQueue = gen(function* () {
53186
+ const previous = yield* get$3(attachRef);
53187
+ const queue = yield* dropping(16);
53188
+ yield* offer(queue, {
53189
+ status: yield* get(statusRef),
53190
+ type: "status"
53191
+ });
53192
+ yield* offer(queue, {
53193
+ data: pipe(yield* get$3(replayRef), join$2("")),
53194
+ type: "snapshot"
53195
+ });
53196
+ yield* set$4(attachRef, queue);
53197
+ if (previous) yield* end(previous);
53198
+ yield* addFinalizer(() => update$1(attachRef, (current) => current === queue ? void 0 : current).pipe(andThen(end(queue))));
53199
+ return queue;
53200
+ });
53201
+ const statusQueue = gen(function* () {
53202
+ const queue = yield* sliding(1);
53203
+ yield* addFinalizer(() => end(queue));
53204
+ yield* offer(queue, yield* get(statusRef));
53205
+ yield* pipe(changes(statusRef), drop(1), groupedWithin(32, millis(250)), runForEach((items) => pipe(last(fromIterable$2(items)), match$4({
53206
+ onNone: () => void_$1,
53207
+ onSome: (status) => offer(queue, status)
53208
+ }))), forkScoped);
53209
+ return queue;
53210
+ });
54217
53211
  return {
53212
+ attachQueue,
54218
53213
  resize: fnUntraced(function* (size) {
54219
53214
  yield* offer(resizeQueue, size);
54220
53215
  }),
54221
53216
  restart: fnUntraced(function* () {
54222
- return yield* pipe(startProcess(), withPermit(lifecycleLock), catch_$2(() => pipe(setState("failed"), andThen(get(stateRef)))));
53217
+ return yield* pipe(spawnProcess(), withPermit(lifecycleLock), catch_$2(() => pipe(setStatus("failed"), andThen(get(statusRef)))));
54223
53218
  }),
54224
- stateUpdates,
53219
+ statusQueue,
54225
53220
  stop: fnUntraced(function* () {
54226
53221
  yield* pipe(stopProcess("stopped"), withPermit(lifecycleLock));
54227
- return yield* get(stateRef);
53222
+ return yield* get(statusRef);
54228
53223
  }),
54229
- updates,
54230
53224
  write: fnUntraced(function* (data) {
54231
53225
  if (data === "") return;
54232
53226
  const process = yield* get$3(processRef);
@@ -54256,6 +53250,9 @@ const AgentSessionKey = Struct({
54256
53250
  cwd: String$1,
54257
53251
  uuid: String$1
54258
53252
  });
53253
+ function terminalStatusDone(state) {
53254
+ return !terminalStatusActive(state.state);
53255
+ }
54259
53256
  function terminalSessionInput(session) {
54260
53257
  if ("args" in session || "env" in session) return {
54261
53258
  command: session.command === void 0 ? void 0 : make$40(session.command, session.args ?? [], { env: session.env }),
@@ -54276,19 +53273,19 @@ function terminalSessionInput(session) {
54276
53273
  const TerminalSessions = make$46({
54277
53274
  idleTimeToLive: infinity,
54278
53275
  lookup: fnUntraced(function* (config) {
54279
- return get$9(yield* buildWithScope(Terminal.layer(config), yield* scope), Terminal);
53276
+ return get$8(yield* buildWithScope(Terminal.layer(config), yield* scope), Terminal);
54280
53277
  })
54281
53278
  });
54282
53279
  const GitReviewSessions = make$46({
54283
53280
  idleTimeToLive: zero$1,
54284
53281
  lookup: fnUntraced(function* (cwd) {
54285
- return get$9(yield* buildWithScope(pipe(GitReview.layer({ cwd }), provide$2(GitCommand.layer)), yield* scope), GitReview);
53282
+ return get$8(yield* buildWithScope(pipe(GitReview.layer({ cwd }), provide$2(GitCommand.layer)), yield* scope), GitReview);
54286
53283
  })
54287
53284
  });
54288
53285
  const GitCommitSessions = make$46({
54289
53286
  idleTimeToLive: minutes(5),
54290
53287
  lookup: fnUntraced(function* (cwd) {
54291
- return get$9(yield* buildWithScope(pipe(GitCommitAction.layer({ cwd }), provide$2(GitCommand.layer)), yield* scope), GitCommitAction);
53288
+ return get$8(yield* buildWithScope(pipe(GitCommitAction.layer({ cwd }), provide$2(GitCommand.layer)), yield* scope), GitCommitAction);
54292
53289
  })
54293
53290
  });
54294
53291
  const RpcHandlers = RpcContracts.toLayer(gen(function* () {
@@ -54341,7 +53338,7 @@ const RpcHandlers = RpcContracts.toLayer(gen(function* () {
54341
53338
  }) });
54342
53339
  const updateReviewState = fn("RpcHandlers.updateReviewState")(function* (cwd, f) {
54343
53340
  yield* annotateCurrentSpan({ cwd });
54344
- return yield* pipe(scoped$3(gen(function* () {
53341
+ return yield* pipe(scoped$1(gen(function* () {
54345
53342
  yield* modify(yield* get$6(reviewStates, cwd), (current) => {
54346
53343
  const next = f(current);
54347
53344
  return [next, next];
@@ -54372,7 +53369,6 @@ const RpcHandlers = RpcContracts.toLayer(gen(function* () {
54372
53369
  icon: payload.icon,
54373
53370
  label: `${payload.label} ${labelCount + 1}`,
54374
53371
  state: {
54375
- runId: 0,
54376
53372
  state: "starting",
54377
53373
  title: ""
54378
53374
  },
@@ -54382,33 +53378,34 @@ const RpcHandlers = RpcContracts.toLayer(gen(function* () {
54382
53378
  cwd: agentSession.cwd,
54383
53379
  uuid: agentSession.uuid
54384
53380
  }), agentSession));
54385
- const sessionTerminal = yield* terminalSession(TerminalSessionKey.make({
53381
+ const input = yield* terminalSession(TerminalSessionKey.make({
54386
53382
  args: agentSession.args,
54387
53383
  command: agentSession.command,
54388
53384
  cwd: agentSession.cwd,
54389
53385
  sessionId: agentSession.uuid
54390
- })).pipe(map$4(terminalSessionInput), flatMap$2((input) => get$6(terminals, input)));
53386
+ })).pipe(map$4(terminalSessionInput));
53387
+ const sessionTerminal = yield* get$6(terminals, input);
54391
53388
  yield* sessionTerminal.restart();
54392
- yield* pipe(sessionTerminal.stateUpdates, takeUntil((state) => state.state === "exited" || state.state === "failed" || state.state === "stopped"), runForEach((state) => gen(function* () {
54393
- const key = AgentSessionKey.make({
54394
- cwd: agentSession.cwd,
54395
- uuid: agentSession.uuid
53389
+ const key = AgentSessionKey.make({
53390
+ cwd: agentSession.cwd,
53391
+ uuid: agentSession.uuid
53392
+ });
53393
+ yield* pipe(scoped$1(gen(function* () {
53394
+ const states = yield* sessionTerminal.statusQueue;
53395
+ let done = false;
53396
+ yield* whileLoop({
53397
+ body: () => flatMap$2(take$1(states), (state) => pipe(update(agents, (sessions) => modifyAt(sessions, key, match$4({
53398
+ onNone: () => none(),
53399
+ onSome: (session) => some({
53400
+ ...session,
53401
+ state
53402
+ })
53403
+ }))), andThen(terminalStatusDone(state) ? pipe(update(agents, (sessions) => remove$2(sessions, key)), andThen(pipe(invalidate(terminals, input), ignore$1))) : void_$1), as(state))),
53404
+ step(state) {
53405
+ done = terminalStatusDone(state);
53406
+ },
53407
+ while: () => !done
54396
53408
  });
54397
- yield* update(agents, (sessions) => modifyAt(sessions, key, match$4({
54398
- onNone: () => none(),
54399
- onSome: (session) => some({
54400
- ...session,
54401
- state
54402
- })
54403
- })));
54404
- if (state.state !== "exited" && state.state !== "failed" && state.state !== "stopped") return;
54405
- yield* update(agents, (sessions) => remove$2(sessions, key));
54406
- yield* pipe(invalidate(terminals, terminalSessionInput({
54407
- args: agentSession.args,
54408
- command: agentSession.command,
54409
- cwd: agentSession.cwd,
54410
- sessionId: agentSession.uuid
54411
- })), ignore$1);
54412
53409
  })), forkDetach);
54413
53410
  return agentSession;
54414
53411
  }),
@@ -54442,14 +53439,14 @@ const RpcHandlers = RpcContracts.toLayer(gen(function* () {
54442
53439
  } })),
54443
53440
  "review.state.watch": (payload) => unwrap$1(pipe(get$6(reviewStates, payload.cwd), flatMap$2((ref) => pipe(get(ref), map$4((state) => concat(drop(1)(changes(ref)))(make$43(state))))))),
54444
53441
  "runs.portless": (payload) => get$6(portlessWorktrees, payload.cwd),
53442
+ "terminal.attach": (payload) => flatMap$2(getTerminal(TerminalSessionKey.make(payload)), (sessionTerminal) => sessionTerminal.attachQueue),
54445
53443
  "terminal.resize": (payload) => pipe(getTerminal(TerminalSessionKey.make(payload)), flatMap$2((sessionTerminal) => sessionTerminal.resize({
54446
53444
  cols: payload.cols,
54447
53445
  rows: payload.rows
54448
53446
  }))),
54449
53447
  "terminal.restart": (payload) => flatMap$2(getTerminal(TerminalSessionKey.make(payload)), (sessionTerminal) => sessionTerminal.restart()),
54450
- "terminal.state.watch": (payload) => unwrap$1(map$4(getTerminal(TerminalSessionKey.make(payload)), (sessionTerminal) => sessionTerminal.stateUpdates)),
53448
+ "terminal.status.watch": (payload) => flatMap$2(getTerminal(TerminalSessionKey.make(payload)), (sessionTerminal) => sessionTerminal.statusQueue),
54451
53449
  "terminal.stop": (payload) => flatMap$2(getTerminal(TerminalSessionKey.make(payload)), (sessionTerminal) => sessionTerminal.stop()),
54452
- "terminal.watch": (payload) => unwrap$1(map$4(getTerminal(TerminalSessionKey.make(payload)), (sessionTerminal) => sessionTerminal.updates)),
54453
53450
  "terminal.write": (payload) => pipe(getTerminal(TerminalSessionKey.make(payload)), flatMap$2((sessionTerminal) => sessionTerminal.write(payload.data)))
54454
53451
  });
54455
53452
  }));