@doeixd/machine 0.0.23 → 1.0.2

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 (53) hide show
  1. package/README.md +101 -65
  2. package/dist/cjs/development/core.js +56 -57
  3. package/dist/cjs/development/core.js.map +4 -4
  4. package/dist/cjs/development/index.js +99 -58
  5. package/dist/cjs/development/index.js.map +4 -4
  6. package/dist/cjs/development/react.js +56 -58
  7. package/dist/cjs/development/react.js.map +4 -4
  8. package/dist/cjs/production/core.js +1 -1
  9. package/dist/cjs/production/index.js +3 -3
  10. package/dist/cjs/production/react.js +1 -1
  11. package/dist/esm/development/core.js +56 -57
  12. package/dist/esm/development/core.js.map +4 -4
  13. package/dist/esm/development/index.js +99 -58
  14. package/dist/esm/development/index.js.map +4 -4
  15. package/dist/esm/development/react.js +56 -58
  16. package/dist/esm/development/react.js.map +4 -4
  17. package/dist/esm/production/core.js +1 -1
  18. package/dist/esm/production/index.js +3 -3
  19. package/dist/esm/production/react.js +1 -1
  20. package/dist/types/actor.d.ts +4 -4
  21. package/dist/types/actor.d.ts.map +1 -1
  22. package/dist/types/context-bound.d.ts +94 -0
  23. package/dist/types/context-bound.d.ts.map +1 -0
  24. package/dist/types/entry-react.d.ts +1 -1
  25. package/dist/types/entry-react.d.ts.map +1 -1
  26. package/dist/types/functional-combinators.d.ts +5 -5
  27. package/dist/types/generators.d.ts +2 -2
  28. package/dist/types/index.d.ts +14 -34
  29. package/dist/types/index.d.ts.map +1 -1
  30. package/dist/types/internal-transitions.d.ts +5 -0
  31. package/dist/types/internal-transitions.d.ts.map +1 -0
  32. package/dist/types/primitives.d.ts +25 -5
  33. package/dist/types/primitives.d.ts.map +1 -1
  34. package/dist/types/react.d.ts.map +1 -1
  35. package/dist/types/utils.d.ts +22 -22
  36. package/dist/types/utils.d.ts.map +1 -1
  37. package/package.json +1 -1
  38. package/src/actor.ts +1 -1
  39. package/src/context-bound.ts +160 -0
  40. package/src/entry-react.ts +9 -2
  41. package/src/functional-combinators.ts +5 -5
  42. package/src/generators.ts +2 -2
  43. package/src/higher-order.ts +2 -2
  44. package/src/index.ts +47 -80
  45. package/src/internal-transitions.ts +32 -0
  46. package/src/middleware/time-travel.ts +2 -2
  47. package/src/middleware.ts +2 -2
  48. package/src/multi.ts +4 -4
  49. package/src/primitives.ts +34 -14
  50. package/src/prototype_functional.ts +2 -2
  51. package/src/react.ts +1 -2
  52. package/src/test.ts +7 -7
  53. package/src/utils.ts +31 -31
package/README.md CHANGED
@@ -76,12 +76,12 @@ import { createMachine } from "@doeixd/machine";
76
76
  const counter = createMachine(
77
77
  { count: 0 }, // Initial state (s₀)
78
78
  (next) => ({
79
- // Transitions (δ) - `this` is automatically typed
79
+ // Transitions (δ) - access state via this.context
80
80
  increment() {
81
- return next({ count: this.count + 1 });
81
+ return next({ count: this.context.count + 1 });
82
82
  },
83
83
  add(n: number) {
84
- return next({ count: this.count + n });
84
+ return next({ count: this.context.count + n });
85
85
  }
86
86
  })
87
87
  );
@@ -104,10 +104,10 @@ console.log(counter.context.count); // 0
104
104
  ```typescript
105
105
  const transitions = {
106
106
  increment: function() {
107
- return createMachine({ count: this.count + 1 }, transitions);
107
+ return createMachine({ count: this.context.count + 1 }, transitions);
108
108
  },
109
109
  add: function(n: number) {
110
- return createMachine({ count: this.count + n }, transitions);
110
+ return createMachine({ count: this.context.count + n }, transitions);
111
111
  }
112
112
  };
113
113
  const counter = createMachine({ count: 0 }, transitions);
@@ -161,49 +161,84 @@ This shows the **flexibility** of the library: immutability is the default patte
161
161
  The most powerful pattern: different machine types represent different states.
162
162
 
163
163
  ```typescript
164
- import { createMachine, Machine } from "@doeixd/machine";
164
+ import { MachineBase } from "@doeixd/machine";
165
165
 
166
- // Define distinct machine types for each state
167
- type LoggedOut = Machine<{ status: "loggedOut" }, {
168
- login: (username: string) => LoggedIn;
169
- };
166
+ /**
167
+ * Type-State Programming with classes:
168
+ * - Each distinct class *is* a distinct state.
169
+ * - The methods on that class are the only valid transitions from that state.
170
+ * - Returning a different class type moves you to a different state (at compile time).
171
+ */
170
172
 
171
- type LoggedIn = Machine<{ status: "loggedIn"; username: string }, {
172
- logout: () => LoggedOut;
173
- viewProfile: () => LoggedIn;
174
- };
173
+ /** "LoggedOut" state: only transitions available are methods on this class. */
174
+ class LoggedOut extends MachineBase<{ status: "loggedOut" }> {
175
+ constructor() {
176
+ // MachineBase stores state data in `this.context`
177
+ super({ status: "loggedOut" });
178
+ }
175
179
 
176
- // Create factory functions
177
- const createLoggedOut = (): LoggedOut => {
178
- return createMachine({ status: "loggedOut" }, {
179
- login: function(username: string): LoggedIn {
180
- return createLoggedIn(username);
181
- }
182
- });
183
- };
180
+ /**
181
+ * Transition: LoggedOut -> LoggedIn
182
+ * Notice: there's no `logout()` method here, so you literally cannot call it.
183
+ */
184
+ login(username: string): LoggedIn {
185
+ return new LoggedIn(username);
186
+ }
187
+ }
184
188
 
185
- const createLoggedIn = (username: string): LoggedIn => {
186
- return createMachine({ status: "loggedIn", username }, {
187
- logout: function(): LoggedOut {
188
- return createLoggedOut();
189
- },
190
- viewProfile: function(): LoggedIn {
191
- console.log(`Viewing ${this.username}'s profile`);
192
- return this;
193
- }
194
- });
195
- };
189
+ /** "LoggedIn" state: different data + different allowed transitions. */
190
+ class LoggedIn extends MachineBase<{ status: "loggedIn"; username: string }> {
191
+ constructor(username: string) {
192
+ // Context shape changes in this state (now includes `username`)
193
+ super({ status: "loggedIn", username });
194
+ }
195
+
196
+ /**
197
+ * Transition: LoggedIn -> LoggedOut
198
+ * This exists only on LoggedIn, so you cannot log out unless you're logged in.
199
+ */
200
+ logout(): LoggedOut {
201
+ return new LoggedOut();
202
+ }
196
203
 
197
- // Usage
198
- const machine = createLoggedOut();
204
+ /**
205
+ * Transition: LoggedIn -> LoggedIn (self-transition)
206
+ * Returning `this` means "stay in the same state".
207
+ */
208
+ viewProfile(): LoggedIn {
209
+ // With MachineBase, context lives under `this.context`
210
+ console.log(`Viewing ${this.context.username}'s profile`);
211
+ return this;
212
+ }
213
+ }
214
+
215
+ // -------------------- Usage --------------------
199
216
 
200
- // TypeScript prevents invalid transitions at compile time!
201
- // machine.logout(); // ❌ Error: Property 'logout' does not exist on type 'LoggedOut'
217
+ const machine = new LoggedOut();
218
+
219
+ /**
220
+ * ✅ Compiler-enforced validity:
221
+ * LoggedOut has only `.login()`, so calling `.logout()` is a type error.
222
+ */
223
+ // machine.logout(); // ❌ Property 'logout' does not exist on type 'LoggedOut'
202
224
 
203
225
  const loggedIn = machine.login("alice");
204
- // loggedIn.login("bob"); // ❌ Error: Property 'login' does not exist on type 'LoggedIn'
205
226
 
206
- const loggedOut = loggedIn.logout(); // ✅ Valid
227
+ /**
228
+ * LoggedIn has `.logout()` and `.viewProfile()`.
229
+ * It does NOT have `.login()`, so calling it is a compile-time error.
230
+ */
231
+ // loggedIn.login("bob"); // ❌ Property 'login' does not exist on type 'LoggedIn'
232
+
233
+ const stillLoggedIn = loggedIn.viewProfile(); // ✅ OK (self-transition)
234
+ const loggedOut = loggedIn.logout(); // ✅ OK (LoggedIn -> LoggedOut)
235
+
236
+ /**
237
+ * The key idea:
238
+ * - You never check `status` at runtime to know what you can do.
239
+ * - The *type* tells you what transitions are available.
240
+ * - Autocomplete only offers valid transitions for the current state.
241
+ */
207
242
  ```
208
243
 
209
244
  This pattern makes **illegal states unrepresentable** in your type system.
@@ -439,11 +474,11 @@ Creates a synchronous state machine using the **Functional Builder** pattern. Th
439
474
  ```typescript
440
475
  const machine = createMachine({ count: 0 }, (next) => ({
441
476
  increment() {
442
- // `this` is correctly inferred as Context
443
- return next({ count: this.count + 1 });
477
+ // `this` points at the machine; read state via this.context
478
+ return next({ count: this.context.count + 1 });
444
479
  },
445
480
  add(n: number) {
446
- return next({ count: this.count + n });
481
+ return next({ count: this.context.count + n });
447
482
  }
448
483
  }));
449
484
  ```
@@ -457,7 +492,7 @@ const machine = createMachine(
457
492
  { count: 0 }, // Context (state data)
458
493
  { // Transitions (state transformations)
459
494
  increment: function() {
460
- return createMachine({ count: this.count + 1 }, this);
495
+ return createMachine({ count: this.context.count + 1 }, this);
461
496
  }
462
497
  }
463
498
  );
@@ -470,11 +505,11 @@ Creates a synchronous state machine using the **Functional Builder** pattern. Th
470
505
  ```typescript
471
506
  const machine = createMachine({ count: 0 }, (transition) => ({
472
507
  increment() {
473
- // `this` is correctly inferred as Context
474
- return transition({ count: this.count + 1 });
508
+ // `this` points at the machine; read state via this.context
509
+ return transition({ count: this.context.count + 1 });
475
510
  },
476
511
  add(n: number) {
477
- return transition({ count: this.count + n });
512
+ return transition({ count: this.context.count + n });
478
513
  }
479
514
  }));
480
515
  ```
@@ -581,45 +616,46 @@ const updated = next(counter, (ctx) => ({ count: ctx.count + 1 }));
581
616
 
582
617
  ### Transition Binding Helpers
583
618
 
584
- These utilities eliminate the need for `.call(m.context, ...)` boilerplate when invoking transitions.
619
+ These utilities eliminate the need for `.call(m, ...)` boilerplate when invoking transitions.
585
620
 
586
- #### `call<C, F>(fn, context, ...args)`
621
+ #### `call<M, F>(fn, machine, ...args)`
587
622
 
588
- Explicitly binds a transition function to a context and invokes it. Useful when you need to call a transition with proper `this` binding.
623
+ Explicitly binds a transition function to a machine and invokes it. Useful when you need to call a transition with proper `this` binding.
589
624
 
590
625
  ```typescript
591
- import { call } from "@doeixd/machine";
626
+ import { call, Machine } from "@doeixd/machine";
592
627
 
593
- type MyContext = { count: number };
594
- const increment = function(this: MyContext) {
595
- return { count: this.count + 1 };
628
+ type MyMachine = Machine<{ count: number }>;
629
+ const increment = function(this: MyMachine) {
630
+ return { count: this.context.count + 1 };
596
631
  };
597
632
 
598
- const result = call(increment, { count: 5 }); // Returns { count: 6 }
633
+ const machine = { context: { count: 5 } } as MyMachine;
634
+ const result = call(increment, machine); // Returns { count: 6 }
599
635
 
600
636
  // Particularly useful with generator-based flows:
601
637
  const result = run(function* (m) {
602
- m = yield* step(call(m.increment, m.context));
603
- m = yield* step(call(m.add, m.context, 5));
638
+ m = yield* step(call(m.increment, m));
639
+ m = yield* step(call(m.add, m, 5));
604
640
  return m;
605
641
  }, counter);
606
642
  ```
607
643
 
608
644
  #### `bindTransitions<M>(machine)`
609
645
 
610
- Returns a Proxy that automatically binds all transition methods to the machine's context. Eliminates `.call(m.context, ...)` boilerplate entirely.
646
+ Returns a Proxy that automatically binds all transition methods to the machine. Eliminates `.call(m, ...)` boilerplate entirely.
611
647
 
612
648
  ```typescript
613
- import { bindTransitions } from "@doeixd/machine";
649
+ import { bindTransitions, Machine } from "@doeixd/machine";
614
650
 
615
651
  const counter = bindTransitions(createMachine(
616
652
  { count: 0 },
617
653
  {
618
- increment(this: { count: number }) {
619
- return createMachine({ count: this.count + 1 }, this);
654
+ increment(this: Machine<{ count: number }>) {
655
+ return createMachine({ count: this.context.count + 1 }, this);
620
656
  },
621
- add(this: { count: number }, n: number) {
622
- return createMachine({ count: this.count + n }, this);
657
+ add(this: Machine<{ count: number }>, n: number) {
658
+ return createMachine({ count: this.context.count + n }, this);
623
659
  }
624
660
  }
625
661
  ));
@@ -637,7 +673,7 @@ const result = run(function* (m) {
637
673
  ```
638
674
 
639
675
  **How it works:**
640
- The Proxy intercepts all property access on the machine. When a property is a function (transition method), it wraps it to automatically call `.apply(machine.context, args)` before invoking. Non-callable properties are returned as-is.
676
+ The Proxy intercepts all property access on the machine. When a property is a function (transition method), it wraps it to automatically call `.apply(machine, args)` before invoking. Non-callable properties are returned as-is.
641
677
 
642
678
  **Note:** The Proxy preserves type safety while providing ergonomic syntax. Use this when writing generator-based flows or any code that frequently calls transitions.
643
679
 
@@ -761,7 +797,7 @@ const mocked = overrideTransitions(counter, {
761
797
  // Decorate with logging
762
798
  const logged = overrideTransitions(counter, {
763
799
  increment: function() {
764
- console.log("Before:", this.count);
800
+ console.log("Before:", this.context.count);
765
801
  const next = counter.increment.call(this);
766
802
  console.log("After:", next.context.count);
767
803
  return next;
@@ -2104,7 +2140,7 @@ We avoid magic strings wherever possible. Instead, we use **typed object referen
2104
2140
  // ✅ Good: Typed method reference
2105
2141
  const counter = createMachine({ count: 0 }, {
2106
2142
  increment: function() {
2107
- return createMachine({ count: this.count + 1 }, this);
2143
+ return createMachine({ count: this.context.count + 1 }, this);
2108
2144
  }
2109
2145
  });
2110
2146
 
@@ -116,6 +116,32 @@ __export(core_exports, {
116
116
  });
117
117
  module.exports = __toCommonJS(core_exports);
118
118
 
119
+ // src/internal-transitions.ts
120
+ var TRANSITIONS_SYMBOL = Symbol.for("__machine_transitions__");
121
+ function attachTransitions(machine, transitions) {
122
+ Object.defineProperty(machine, TRANSITIONS_SYMBOL, {
123
+ value: transitions,
124
+ enumerable: false,
125
+ configurable: false
126
+ });
127
+ return machine;
128
+ }
129
+ function getStoredTransitions(machine) {
130
+ if (!machine || typeof machine !== "object") {
131
+ return void 0;
132
+ }
133
+ return machine[TRANSITIONS_SYMBOL];
134
+ }
135
+ function snapshotOwnTransitions(source) {
136
+ if (!source || typeof source !== "object") {
137
+ return {};
138
+ }
139
+ const entries = Object.entries(source).filter(
140
+ ([key, value]) => key !== "context" && typeof value === "function"
141
+ );
142
+ return Object.fromEntries(entries);
143
+ }
144
+
119
145
  // src/generators.ts
120
146
  function run(flow, initial) {
121
147
  const generator = flow(initial);
@@ -246,8 +272,8 @@ function guard(condition, transition, options = {}) {
246
272
  const ctx = isMachine ? this.context : this;
247
273
  const conditionResult = condition(ctx, ...args);
248
274
  if (conditionResult) {
249
- const contextForTransition = isMachine ? this.context : this;
250
- return transition.apply(contextForTransition, args);
275
+ const machineForTransition = isMachine ? this : { context: this };
276
+ return transition.apply(machineForTransition, args);
251
277
  } else {
252
278
  if (onFail === "throw") {
253
279
  const message = errorMessage || "Guard condition failed";
@@ -287,8 +313,8 @@ function guardAsync(condition, transition, options = {}) {
287
313
  const ctx = isMachine ? this.context : this;
288
314
  const conditionResult = await Promise.resolve(condition(ctx, ...args));
289
315
  if (conditionResult) {
290
- const contextForTransition = isMachine ? this.context : this;
291
- return transition.apply(contextForTransition, args);
316
+ const machineForTransition = isMachine ? this : { context: this };
317
+ return transition.apply(machineForTransition, args);
292
318
  } else {
293
319
  if (onFail === "throw") {
294
320
  const message = errorMessage || "Guard condition failed";
@@ -369,7 +395,7 @@ function createRunner(initialMachine, onChange) {
369
395
  return void 0;
370
396
  }
371
397
  return (...args) => {
372
- const nextState = transition.apply(currentMachine.context, args);
398
+ const nextState = transition.apply(currentMachine, args);
373
399
  const nextStateWithTransitions = Object.assign(
374
400
  { context: nextState.context },
375
401
  originalTransitions
@@ -412,7 +438,7 @@ function createEnsemble(store, factories, getDiscriminant) {
412
438
  );
413
439
  }
414
440
  return (...args) => {
415
- return action2.apply(currentMachine.context, args);
441
+ return action2.apply(currentMachine, args);
416
442
  };
417
443
  }
418
444
  });
@@ -563,7 +589,7 @@ function createMutableMachine(sharedContext, factories, getDiscriminant) {
563
589
  const transition = currentMachine[prop];
564
590
  if (typeof transition === "function") {
565
591
  return (...args) => {
566
- const nextContext = transition.apply(currentMachine.context, args);
592
+ const nextContext = transition.apply(currentMachine, args);
567
593
  if (typeof nextContext !== "object" || nextContext === null) {
568
594
  console.warn(`[MutableMachine] Transition "${String(prop)}" did not return a valid context object. State may be inconsistent.`);
569
595
  return;
@@ -685,14 +711,14 @@ function createParallelMachine(m1, m2) {
685
711
  for (const key in transitions1) {
686
712
  const transitionFn = transitions1[key];
687
713
  combinedTransitions[key] = (...args) => {
688
- const nextM1 = transitionFn.apply(m1.context, args);
714
+ const nextM1 = transitionFn.apply(m1, args);
689
715
  return createParallelMachine(nextM1, m2);
690
716
  };
691
717
  }
692
718
  for (const key in transitions2) {
693
719
  const transitionFn = transitions2[key];
694
720
  combinedTransitions[key] = (...args) => {
695
- const nextM2 = transitionFn.apply(m2.context, args);
721
+ const nextM2 = transitionFn.apply(m2, args);
696
722
  return createParallelMachine(m1, nextM2);
697
723
  };
698
724
  }
@@ -1163,7 +1189,7 @@ function withTimeTravel(machine, options = {}) {
1163
1189
  for (const entry of transitionsToReplay) {
1164
1190
  const transitionFn = replayedMachine[entry.transitionName];
1165
1191
  if (transitionFn) {
1166
- replayedMachine = transitionFn.apply(replayedMachine.context, entry.args);
1192
+ replayedMachine = transitionFn.apply(replayedMachine, entry.args);
1167
1193
  }
1168
1194
  }
1169
1195
  return replayedMachine;
@@ -1583,8 +1609,8 @@ function createTransition(getTransitions, transformer) {
1583
1609
  return createMachine(nextContext, getTransitions());
1584
1610
  };
1585
1611
  }
1586
- function call(fn, context, ...args) {
1587
- return fn.apply(context, args);
1612
+ function call(fn, machine, ...args) {
1613
+ return fn.apply(machine, args);
1588
1614
  }
1589
1615
  function bindTransitions(machine) {
1590
1616
  return new Proxy(machine, {
@@ -1592,7 +1618,7 @@ function bindTransitions(machine) {
1592
1618
  const value = target[prop];
1593
1619
  if (typeof value === "function") {
1594
1620
  return function(...args) {
1595
- const result = value.apply(target.context, args);
1621
+ const result = value.apply(target, args);
1596
1622
  if (result && typeof result === "object" && "context" in result) {
1597
1623
  return bindTransitions(result);
1598
1624
  }
@@ -1617,7 +1643,7 @@ var BoundMachine = class _BoundMachine {
1617
1643
  const value = this.wrappedMachine[prop];
1618
1644
  if (typeof value === "function") {
1619
1645
  return (...args) => {
1620
- const result = value.apply(this.wrappedMachine.context, args);
1646
+ const result = value.apply(this.wrappedMachine, args);
1621
1647
  if (result && typeof result === "object" && "context" in result) {
1622
1648
  return new _BoundMachine(result);
1623
1649
  }
@@ -1680,57 +1706,29 @@ function createMachine(context, fnsOrFactory) {
1680
1706
  if (typeof fnsOrFactory === "function") {
1681
1707
  let transitions2;
1682
1708
  const transition = (newContext) => {
1683
- const machine2 = createMachine(newContext, transitions2);
1684
- const boundTransitions2 = Object.fromEntries(
1685
- Object.entries(transitions2).map(([key, fn]) => [
1686
- key,
1687
- fn.bind(newContext)
1688
- ])
1689
- );
1690
- return Object.assign(machine2, boundTransitions2);
1709
+ return createMachine(newContext, transitions2);
1691
1710
  };
1692
1711
  transitions2 = fnsOrFactory(transition);
1693
- const boundTransitions = Object.fromEntries(
1694
- Object.entries(transitions2).map(([key, fn]) => [
1695
- key,
1696
- fn.bind(context)
1697
- ])
1698
- );
1699
- return Object.assign({ context }, boundTransitions);
1712
+ return attachTransitions(Object.assign({ context }, transitions2), transitions2);
1700
1713
  }
1701
- const transitions = "context" in fnsOrFactory ? Object.fromEntries(
1702
- Object.entries(fnsOrFactory).filter(([key]) => key !== "context")
1703
- ) : fnsOrFactory;
1714
+ const stored = getStoredTransitions(fnsOrFactory);
1715
+ const transitions = stored != null ? stored : "context" in fnsOrFactory ? snapshotOwnTransitions(fnsOrFactory) : fnsOrFactory;
1704
1716
  const machine = Object.assign({ context }, transitions);
1705
- return machine;
1717
+ return attachTransitions(machine, transitions);
1706
1718
  }
1707
1719
  function createAsyncMachine(context, fnsOrFactory) {
1708
1720
  if (typeof fnsOrFactory === "function") {
1709
1721
  let transitions2;
1710
1722
  const transition = (newContext) => {
1711
- const machine2 = createAsyncMachine(newContext, transitions2);
1712
- const boundTransitions2 = Object.fromEntries(
1713
- Object.entries(transitions2).map(([key, fn]) => [
1714
- key,
1715
- fn.bind(newContext)
1716
- ])
1717
- );
1718
- return Object.assign(machine2, boundTransitions2);
1723
+ return createAsyncMachine(newContext, transitions2);
1719
1724
  };
1720
1725
  transitions2 = fnsOrFactory(transition);
1721
- const boundTransitions = Object.fromEntries(
1722
- Object.entries(transitions2).map(([key, fn]) => [
1723
- key,
1724
- fn.bind(context)
1725
- ])
1726
- );
1727
- return Object.assign({ context }, boundTransitions);
1726
+ return attachTransitions(Object.assign({ context }, transitions2), transitions2);
1728
1727
  }
1729
- const transitions = "context" in fnsOrFactory ? Object.fromEntries(
1730
- Object.entries(fnsOrFactory).filter(([key]) => key !== "context")
1731
- ) : fnsOrFactory;
1728
+ const stored = getStoredTransitions(fnsOrFactory);
1729
+ const transitions = stored != null ? stored : "context" in fnsOrFactory ? snapshotOwnTransitions(fnsOrFactory) : fnsOrFactory;
1732
1730
  const machine = Object.assign({ context }, transitions);
1733
- return machine;
1731
+ return attachTransitions(machine, transitions);
1734
1732
  }
1735
1733
  function createMachineFactory() {
1736
1734
  return (transformers) => {
@@ -1749,8 +1747,10 @@ function createMachineFactory() {
1749
1747
  };
1750
1748
  }
1751
1749
  function setContext(machine, newContextOrFn) {
1752
- const { context, ...transitions } = machine;
1753
- const newContext = typeof newContextOrFn === "function" ? newContextOrFn(context) : newContextOrFn;
1750
+ var _a;
1751
+ const currentContext = machine.context;
1752
+ const transitions = (_a = getStoredTransitions(machine)) != null ? _a : snapshotOwnTransitions(machine);
1753
+ const newContext = typeof newContextOrFn === "function" ? newContextOrFn(currentContext) : newContextOrFn;
1754
1754
  return createMachine(newContext, transitions);
1755
1755
  }
1756
1756
  function overrideTransitions(machine, overrides) {
@@ -1806,7 +1806,7 @@ function runMachine(initial, onChange) {
1806
1806
  const controller = new AbortController();
1807
1807
  activeController = controller;
1808
1808
  try {
1809
- const nextStatePromise = fn.apply(current.context, [...event.args, { signal: controller.signal }]);
1809
+ const nextStatePromise = fn.apply(current, [...event.args, { signal: controller.signal }]);
1810
1810
  const nextState = await nextStatePromise;
1811
1811
  if (controller.signal.aborted) {
1812
1812
  return current;
@@ -1846,7 +1846,6 @@ var MachineBase = class {
1846
1846
  }
1847
1847
  };
1848
1848
  function next(m, update) {
1849
- const { context, ...transitions } = m;
1850
- return createMachine(update(context), transitions);
1849
+ return setContext(m, (ctx) => update(ctx));
1851
1850
  }
1852
1851
  //# sourceMappingURL=core.js.map