From 4abca7c3343dea79fd8c7db51ac97328691766ec Mon Sep 17 00:00:00 2001 From: Bruno Crosier Date: Wed, 8 Jun 2022 21:59:02 +0100 Subject: [PATCH 1/6] style: :art: formatting --- packages/shared/src/__tests__/getTypegenOutput.test.ts | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/packages/shared/src/__tests__/getTypegenOutput.test.ts b/packages/shared/src/__tests__/getTypegenOutput.test.ts index f8a67555..187a00af 100644 --- a/packages/shared/src/__tests__/getTypegenOutput.test.ts +++ b/packages/shared/src/__tests__/getTypegenOutput.test.ts @@ -21,22 +21,22 @@ describe("getTypegenOutput", () => { tsExtensionFiles.forEach((file) => { const fileText = fs.readFileSync( path.resolve(__dirname, "__examples__", file), - "utf8", + "utf8" ); const event = makeXStateUpdateEvent( // URI doesn't matter here "", - getDocumentValidationsResults(fileText), + getDocumentValidationsResults(fileText) ); fs.writeFileSync( path.resolve( __dirname, "__examples__", - file.slice(0, -3) + ".typegen.ts", + file.slice(0, -3) + ".typegen.ts" ), - getTypegenOutput(event), + getTypegenOutput(event) ); }); From a192890e257376bf4481c5099e7d22d1f33b8006 Mon Sep 17 00:00:00 2001 From: Bruno Crosier Date: Wed, 8 Jun 2022 21:59:55 +0100 Subject: [PATCH 2/6] fix: :bug: delete generated `.typegen.ts` example files --- .../shared/src/__tests__/getTypegenOutput.test.ts | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/packages/shared/src/__tests__/getTypegenOutput.test.ts b/packages/shared/src/__tests__/getTypegenOutput.test.ts index 187a00af..41a48452 100644 --- a/packages/shared/src/__tests__/getTypegenOutput.test.ts +++ b/packages/shared/src/__tests__/getTypegenOutput.test.ts @@ -6,17 +6,19 @@ import { getTypegenOutput, makeXStateUpdateEvent, } from ".."; -import * as minimatch from "minimatch"; describe("getTypegenOutput", () => { const examplesPath = path.resolve(__dirname, "__examples__"); - const examplesFiles = fs.readdirSync(examplesPath); - minimatch - .match(examplesFiles, "*.typegen.ts") - .map((file) => fs.unlinkSync(path.join(examplesPath, file))); + fs.readdirSync(examplesPath).forEach((file) => { + if (file.endsWith(".typegen.ts")) { + fs.unlinkSync(path.resolve(__dirname, "__examples__", file)); + } + }); - const tsExtensionFiles = examplesFiles.filter((file) => file.endsWith(".ts")); + const tsExtensionFiles = fs + .readdirSync(examplesPath) + .filter((file) => file.endsWith(".ts")); tsExtensionFiles.forEach((file) => { const fileText = fs.readFileSync( From 5c971d8c76891ac319c8f4bf25d4f75593578915 Mon Sep 17 00:00:00 2001 From: Bruno Crosier Date: Wed, 8 Jun 2022 22:01:02 +0100 Subject: [PATCH 3/6] style: :fire: unused import --- packages/shared/src/getTypegenOutput.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/packages/shared/src/getTypegenOutput.ts b/packages/shared/src/getTypegenOutput.ts index d61bcada..8ba4fd83 100644 --- a/packages/shared/src/getTypegenOutput.ts +++ b/packages/shared/src/getTypegenOutput.ts @@ -2,7 +2,6 @@ import { createMachine } from "xstate"; import { introspectMachine } from "./introspectMachine"; import { getStateMatchesObjectSyntax } from "./getStateMatchesObjectSyntax"; import { XStateUpdateMachine } from "./types"; -import { choose } from "xstate/lib/actions"; export const getTypegenOutput = (event: { machines: Pick< From 5cf69d0b2e6fd814a8019a560c5f235b40392f1a Mon Sep 17 00:00:00 2001 From: Bruno Crosier Date: Wed, 8 Jun 2022 22:04:04 +0100 Subject: [PATCH 4/6] style: :art: formatting --- packages/shared/src/getTransitionsFromNode.ts | 24 +++++++++++-------- 1 file changed, 14 insertions(+), 10 deletions(-) diff --git a/packages/shared/src/getTransitionsFromNode.ts b/packages/shared/src/getTransitionsFromNode.ts index 66d47e9c..285e99b0 100644 --- a/packages/shared/src/getTransitionsFromNode.ts +++ b/packages/shared/src/getTransitionsFromNode.ts @@ -1,5 +1,5 @@ import { StateNode } from 'xstate'; -import { toStatePaths, pathToStateValue } from 'xstate/lib/utils'; +import { toStatePaths, pathToStateValue } from "xstate/lib/utils"; export const getTransitionsFromNode = (node: StateNode): string[] => { const transitions = new Set(); @@ -8,15 +8,15 @@ export const getTransitionsFromNode = (node: StateNode): string[] => { Object.keys(node.parent.states).forEach((key) => transitions.add(key)); Object.values(node.parent.states).forEach((siblingNode) => { getMatchesStates(siblingNode).forEach((key) => { - if (key === siblingNode.path.join('.')) { + if (key === siblingNode.path.join(".")) { return; } let relativeKey = key; if ((node.parent?.path.length || 0) > 0) { relativeKey = relativeKey.replace( - new RegExp(`^${(node.parent as StateNode).path.join('.')}\.`), - '' + new RegExp(`^${(node.parent as StateNode).path.join(".")}\.`), + "" ); } @@ -30,8 +30,8 @@ export const getTransitionsFromNode = (node: StateNode): string[] => { if ((childNode.parent?.path.length || 0) > 0) { relativeKey = relativeKey.replace( - new RegExp(`^${(childNode.parent as StateNode).path.join('.')}\.`), - '' + new RegExp(`^${(childNode.parent as StateNode).path.join(".")}\.`), + "" ); } @@ -54,14 +54,14 @@ export const getTransitionsFromNode = (node: StateNode): string[] => { } transitions.add( - match.replace(new RegExp(`^${idNode.path.join('.')}`), `#${idNode.id}`) + match.replace(new RegExp(`^${idNode.path.join(".")}`), `#${idNode.id}`) ); }); }); toStatePaths(pathToStateValue(node.path)).forEach((path) => { if (path.length > 1) { - transitions.delete(path.join('.')); + transitions.delete(path.join(".")); } }); @@ -69,12 +69,16 @@ export const getTransitionsFromNode = (node: StateNode): string[] => { }; export const getMatchesStates = (machine: StateNode) => { - const allStateNodes = machine.stateIds.map((id) => machine.getStateNodeById(id)); + const allStateNodes = machine.stateIds.map((id) => + machine.getStateNodeById(id) + ); const states = allStateNodes.reduce((arr: string[], node) => { return [ ...arr, - ...toStatePaths(pathToStateValue(node.path)).map((path) => path.join('.')), + ...toStatePaths(pathToStateValue(node.path)).map((path) => + path.join(".") + ), ]; }, [] as string[]); From 892efb235563c864d9a3968417d0dbfd05dd5cba Mon Sep 17 00:00:00 2001 From: Bruno Crosier Date: Wed, 8 Jun 2022 22:05:58 +0100 Subject: [PATCH 5/6] feat: :label: add `stateValues` to typegen output --- packages/shared/src/getTransitionsFromNode.ts | 132 ++++++++++-------- packages/shared/src/getTypegenOutput.ts | 5 + packages/shared/src/introspectMachine.ts | 2 + 3 files changed, 80 insertions(+), 59 deletions(-) diff --git a/packages/shared/src/getTransitionsFromNode.ts b/packages/shared/src/getTransitionsFromNode.ts index 285e99b0..b5688ebb 100644 --- a/packages/shared/src/getTransitionsFromNode.ts +++ b/packages/shared/src/getTransitionsFromNode.ts @@ -1,71 +1,71 @@ -import { StateNode } from 'xstate'; +import { StateNode, StateValue } from "xstate"; import { toStatePaths, pathToStateValue } from "xstate/lib/utils"; export const getTransitionsFromNode = (node: StateNode): string[] => { - const transitions = new Set(); + const transitions = new Set(); - if (node.parent) { - Object.keys(node.parent.states).forEach((key) => transitions.add(key)); - Object.values(node.parent.states).forEach((siblingNode) => { - getMatchesStates(siblingNode).forEach((key) => { + if (node.parent) { + Object.keys(node.parent.states).forEach((key) => transitions.add(key)); + Object.values(node.parent.states).forEach((siblingNode) => { + getMatchesStates(siblingNode).forEach((key) => { if (key === siblingNode.path.join(".")) { - return; - } - let relativeKey = key; + return; + } + let relativeKey = key; - if ((node.parent?.path.length || 0) > 0) { - relativeKey = relativeKey.replace( + if ((node.parent?.path.length || 0) > 0) { + relativeKey = relativeKey.replace( new RegExp(`^${(node.parent as StateNode).path.join(".")}\.`), "" - ); - } - - transitions.add(relativeKey); - }); - }); - } - Object.values(node.states).map((childNode) => { - getMatchesStates(childNode).map((key) => { - let relativeKey = key; - - if ((childNode.parent?.path.length || 0) > 0) { - relativeKey = relativeKey.replace( + ); + } + + transitions.add(relativeKey); + }); + }); + } + Object.values(node.states).map((childNode) => { + getMatchesStates(childNode).map((key) => { + let relativeKey = key; + + if ((childNode.parent?.path.length || 0) > 0) { + relativeKey = relativeKey.replace( new RegExp(`^${(childNode.parent as StateNode).path.join(".")}\.`), "" - ); - } + ); + } - transitions.add(`.${relativeKey}`); - transitions.add(`${relativeKey}`); - }); - }); + transitions.add(`.${relativeKey}`); + transitions.add(`${relativeKey}`); + }); + }); - const rootNode = getRootNode(node); + const rootNode = getRootNode(node); - const nodesWithId = rootNode.stateIds - .filter((id) => !/(\.|\(machine\))/.test(id)) - .map((id) => rootNode.getStateNodeById(id)); + const nodesWithId = rootNode.stateIds + .filter((id) => !/(\.|\(machine\))/.test(id)) + .map((id) => rootNode.getStateNodeById(id)); - nodesWithId.forEach((idNode) => { - getMatchesStates(idNode).forEach((match) => { - if (idNode.id === rootNode.id) { - transitions.add(`#${idNode.id}.${match}`); - return; - } + nodesWithId.forEach((idNode) => { + getMatchesStates(idNode).forEach((match) => { + if (idNode.id === rootNode.id) { + transitions.add(`#${idNode.id}.${match}`); + return; + } - transitions.add( + transitions.add( match.replace(new RegExp(`^${idNode.path.join(".")}`), `#${idNode.id}`) - ); - }); - }); + ); + }); + }); - toStatePaths(pathToStateValue(node.path)).forEach((path) => { - if (path.length > 1) { + toStatePaths(pathToStateValue(node.path)).forEach((path) => { + if (path.length > 1) { transitions.delete(path.join(".")); - } - }); + } + }); - return Array.from(transitions); + return Array.from(transitions); }; export const getMatchesStates = (machine: StateNode) => { @@ -73,21 +73,35 @@ export const getMatchesStates = (machine: StateNode) => { machine.getStateNodeById(id) ); - const states = allStateNodes.reduce((arr: string[], node) => { - return [ - ...arr, + const states = allStateNodes.reduce((arr: string[], node) => { + return [ + ...arr, ...toStatePaths(pathToStateValue(node.path)).map((path) => path.join(".") ), - ]; - }, [] as string[]); + ]; + }, [] as string[]); - return states; + return states; +}; + +export const getStateValues = (machine: StateNode) => { + const allStateNodes = machine.stateIds.map((id) => + machine.getStateNodeById(id) + ); + + const states = allStateNodes.reduce((arr: StateValue[], node) => { + return Object.keys(pathToStateValue(node.path)).length === 0 + ? arr + : [...arr, pathToStateValue(node.path)]; + }, []); + + return states; }; export const getRootNode = (node: StateNode): StateNode => { - if (!node.parent) { - return node; - } - return getRootNode(node.parent); + if (!node.parent) { + return node; + } + return getRootNode(node.parent); }; diff --git a/packages/shared/src/getTypegenOutput.ts b/packages/shared/src/getTypegenOutput.ts index 8ba4fd83..214f514b 100644 --- a/packages/shared/src/getTypegenOutput.ts +++ b/packages/shared/src/getTypegenOutput.ts @@ -91,6 +91,10 @@ export const getTypegenOutput = (event: { const objectSyntax = getStateMatchesObjectSyntax(introspectResult); + const stateValues = introspectResult.stateValues.map((candidate) => + JSON.stringify(candidate) + ); + if (objectSyntax) { matchesStates.push(objectSyntax); } @@ -161,6 +165,7 @@ export const getTypegenOutput = (event: { ${displayEventsCausing(delays)} }; matchesStates: ${matchesStates.join(" | ") || "undefined"}; + stateValues: ${stateValues.join(" | ") || "undefined"}; tags: ${tags || "never"}; }`; } catch (e) { diff --git a/packages/shared/src/introspectMachine.ts b/packages/shared/src/introspectMachine.ts index b69e14e3..b1ef8bd3 100644 --- a/packages/shared/src/introspectMachine.ts +++ b/packages/shared/src/introspectMachine.ts @@ -4,6 +4,7 @@ import { pathToStateValue } from "xstate/lib/utils"; import { INLINE_IMPLEMENTATION_TYPE } from "@xstate/machine-extractor"; import { getMatchesStates, + getStateValues, getTransitionsFromNode, } from "./getTransitionsFromNode"; @@ -294,6 +295,7 @@ export const introspectMachine = (machine: XState.StateNode) => { }; }), stateMatches: getMatchesStates(machine), + stateValues: getStateValues(machine), subState, guards: guards.toDataShape(), actions: actions.toDataShape(), From f8420228cf9f3226704b162d6d8bb39391d6e30f Mon Sep 17 00:00:00 2001 From: Bruno Crosier Date: Sat, 20 Aug 2022 00:59:55 +0100 Subject: [PATCH 6/6] update snapshots --- .../getTypegenOutput.test.ts.snap | 1165 +++++++++++++++++ 1 file changed, 1165 insertions(+) create mode 100644 packages/shared/src/__tests__/__snapshots__/getTypegenOutput.test.ts.snap diff --git a/packages/shared/src/__tests__/__snapshots__/getTypegenOutput.test.ts.snap b/packages/shared/src/__tests__/__snapshots__/getTypegenOutput.test.ts.snap new file mode 100644 index 00000000..df8e186d --- /dev/null +++ b/packages/shared/src/__tests__/__snapshots__/getTypegenOutput.test.ts.snap @@ -0,0 +1,1165 @@ +// Jest Snapshot v1, https://goo.gl/fbAQLP + +exports[`getTypegenOutput action-missing 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "notImplementedYet" | "anotherNotImplementedYet"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + anotherNotImplementedYet: "xstate.init"; + notImplementedYet: "xstate.init"; + otherAction: "xstate.init"; + someAction: "xstate.init"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: undefined; + stateValues: undefined; + tags: never; +} +" +`; + +exports[`getTypegenOutput action-provided-function 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: never; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + someAction: "xstate.init"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: undefined; + stateValues: undefined; + tags: never; +} +" +`; + +exports[`getTypegenOutput after-numeric-like-delay 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.after(500)#(machine)": { type: "xstate.after(500)#(machine)" }; + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "sayHello"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + sayHello: "xstate.after(500)#(machine)"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: undefined; + stateValues: undefined; + tags: never; +} +" +`; + +exports[`getTypegenOutput after-string-delay 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.after(myDelay)#(machine).b": { + type: "xstate.after(myDelay)#(machine).b"; + }; + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "someAction"; + services: never; + guards: never; + delays: "myDelay"; + }; + eventsCausingActions: { + someAction: "xstate.after(myDelay)#(machine).b"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: { + myDelay: "NEXT"; + }; + matchesStates: "a" | "b" | "c"; + stateValues: "a" | "b" | "c"; + tags: never; +} +" +`; + +exports[`getTypegenOutput choose-defined-in-implementations 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: never; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + a: "FOO"; + b: "FOO"; + c: "FOO"; + wow: "FOO"; + }; + eventsCausingServices: {}; + eventsCausingGuards: { + cond1: "FOO"; + }; + eventsCausingDelays: {}; + matchesStates: "a" | "b"; + stateValues: "a" | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput entry-action-on-ancestor-of-targeted-descendant 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "sayHello"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + sayHello: "GO_STRING"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "b.c" | { b?: "c" }; + stateValues: "a" | "b" | { b: "c" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput entry-action-on-initial-state-of-targeted-ancestor 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "sayHello"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + sayHello: "GO_STRING"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "b.c" | { b?: "c" }; + stateValues: "a" | "b" | { b: "c" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput entry-action-on-state-between-lca-and-target 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootEntry" | "sayHello"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + rootEntry: "xstate.init"; + sayHello: "FOO"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "b.b1" | { b?: "b1" }; + stateValues: "a" | "b" | { b: "b1" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput entry-action-root-external-transition 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootEntry"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + rootEntry: "FOO" | "xstate.init"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b"; + stateValues: "a" | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput entry-actions-basic 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "someAction" | "otherAction"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + otherAction: "BAR"; + someAction: "FOO"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "c"; + stateValues: "a" | "b" | "c"; + tags: never; +} +" +`; + +exports[`getTypegenOutput entry-actions-receive-init-event 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootEntry" | "entryA1" | "entryA"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + entryA: "FOO" | "xstate.init"; + entryA1: "FOO" | "xstate.init"; + rootEntry: "FOO" | "xstate.init"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "a.a1" | { a?: "a1" }; + stateValues: "a" | { a: "a1" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput entry-actions-within-targeted-parallel 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "sayBazinga" | "sayHello"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + sayBazinga: "GO_STRING"; + sayHello: "GO_STRING"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "b.c" | "b.d" | { b?: "c" | "d" }; + stateValues: "a" | "b" | { b: "c" } | { b: "d" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-external-transition-out-of-source 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "doSomethingWithFoo"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + doSomethingWithFoo: "FOO" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b"; + stateValues: "a" | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-external-transition-within-source 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "exitA"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + exitA: "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "a.c" | "a.d" | { a?: "c" | "d" }; + stateValues: "a" | { a: "c" } | { a: "d" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-internal-transition 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "exitA"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + exitA: "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "a.c" | "a.d" | { a?: "c" | "d" }; + stateValues: "a" | { a: "c" } | { a: "d" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-on-ancestor-with-external-transition-on-descendant 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "doSomethingWithFoo"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + doSomethingWithFoo: "FOO" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "a.a1" | "b" | { a?: "a1" }; + stateValues: "a" | { a: "a1" } | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-on-state-between-lca-and-source-state 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootExit" | "sayHello"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + rootExit: "xstate.stop"; + sayHello: "FOO" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "a.a1" | "b" | { a?: "a1" }; + stateValues: "a" | { a: "a1" } | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-parallel-root-event-only-within-final-configuration 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: + | "rootExit" + | "aExit" + | "a1Exit" + | "a2Exit" + | "a3Exit" + | "bExit" + | "b1Exit" + | "b2Exit" + | "b3Exit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + a1Exit: "TICK_A1" | "xstate.stop"; + a2Exit: "TICK_A2" | "xstate.stop"; + a3Exit: "TICK_A2" | "TICK_B2" | "xstate.stop"; + aExit: "TICK_A2" | "TICK_B2" | "xstate.stop"; + b1Exit: "TICK_B1" | "xstate.stop"; + b2Exit: "TICK_B2" | "xstate.stop"; + b3Exit: "TICK_A2" | "TICK_B2" | "xstate.stop"; + bExit: "TICK_A2" | "TICK_B2" | "xstate.stop"; + rootExit: "TICK_A2" | "TICK_B2" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: + | "a" + | "a.a1" + | "a.a2" + | "a.a3" + | "b" + | "b.b1" + | "b.b2" + | "b.b3" + | { a?: "a1" | "a2" | "a3"; b?: "b1" | "b2" | "b3" }; + stateValues: + | "a" + | { a: "a1" } + | { a: "a2" } + | { a: "a3" } + | "b" + | { b: "b1" } + | { b: "b2" } + | { b: "b3" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-parallel-root-with-final-states 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootExit" | "aExit" | "bExit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + aExit: "TICK_A" | "TICK_B" | "xstate.stop"; + bExit: "TICK_A" | "TICK_B" | "xstate.stop"; + rootExit: "TICK_A" | "TICK_B" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: + | "a" + | "a.a1" + | "a.a2" + | "b" + | "b.b1" + | "b.b2" + | { a?: "a1" | "a2"; b?: "b1" | "b2" }; + stateValues: + | "a" + | { a: "a1" } + | { a: "a2" } + | "b" + | { b: "b1" } + | { b: "b2" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-parallel-root-with-missing-final-state 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootExit" | "aExit" | "bExit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + aExit: "xstate.stop"; + bExit: "xstate.stop"; + rootExit: "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: + | "a" + | "a.a1" + | "a.a2" + | "b" + | "b.b1" + | "b.b2" + | { a?: "a1" | "a2"; b?: "b1" | "b2" }; + stateValues: + | "a" + | { a: "a1" } + | { a: "a2" } + | "b" + | { b: "b1" } + | { b: "b2" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-parallel-root-with-mixed-states 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: + | "rootExit" + | "aExit" + | "a12Exit" + | "a22Exit" + | "bExit" + | "b12Exit" + | "b22Exit" + | "cExit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + a12Exit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + a22Exit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + aExit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + b12Exit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + b22Exit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + bExit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + cExit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + rootExit: + | "TICK_A11" + | "TICK_A21" + | "TICK_B11" + | "TICK_B21" + | "TICK_C1" + | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: + | "a" + | "a.a1" + | "a.a1.a11" + | "a.a1.a12" + | "a.a2" + | "a.a2.a21" + | "a.a2.a22" + | "b" + | "b.b1" + | "b.b1.b11" + | "b.b1.b12" + | "b.b2" + | "b.b2.b21" + | "b.b2.b22" + | "c" + | "c.c1" + | "c.c2" + | { + a?: "a1" | "a2" | { a1?: "a11" | "a12"; a2?: "a21" | "a22" }; + b?: "b1" | "b2" | { b1?: "b11" | "b12"; b2?: "b21" | "b22" }; + c?: "c1" | "c2"; + }; + stateValues: + | "a" + | { a: "a1" } + | { a: { a1: "a11" } } + | { a: { a1: "a12" } } + | { a: "a2" } + | { a: { a2: "a21" } } + | { a: { a2: "a22" } } + | "b" + | { b: "b1" } + | { b: { b1: "b11" } } + | { b: { b1: "b12" } } + | { b: "b2" } + | { b: { b2: "b21" } } + | { b: { b2: "b22" } } + | "c" + | { c: "c1" } + | { c: "c2" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-parallel-root-with-parallel-states 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: + | "rootExit" + | "aExit" + | "a1Exit" + | "a12Exit" + | "a2Exit" + | "a22Exit" + | "bExit" + | "b1Exit" + | "b12Exit" + | "b2Exit" + | "b22Exit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + a12Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + a1Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + a22Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + a2Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + aExit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + b12Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + b1Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + b22Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + b2Exit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + bExit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + rootExit: "TICK_A11" | "TICK_A21" | "TICK_B11" | "TICK_B21" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: + | "a" + | "a.a1" + | "a.a1.a11" + | "a.a1.a12" + | "a.a2" + | "a.a2.a21" + | "a.a2.a22" + | "b" + | "b.b1" + | "b.b1.b11" + | "b.b1.b12" + | "b.b2" + | "b.b2.b21" + | "b.b2.b22" + | { + a?: "a1" | "a2" | { a1?: "a11" | "a12"; a2?: "a21" | "a22" }; + b?: "b1" | "b2" | { b1?: "b11" | "b12"; b2?: "b21" | "b22" }; + }; + stateValues: + | "a" + | { a: "a1" } + | { a: { a1: "a11" } } + | { a: { a1: "a12" } } + | { a: "a2" } + | { a: { a2: "a21" } } + | { a: { a2: "a22" } } + | "b" + | { b: "b1" } + | { b: { b1: "b11" } } + | { b: { b1: "b12" } } + | { b: "b2" } + | { b: { b2: "b21" } } + | { b: { b2: "b22" } }; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-root-external-transition 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootExit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + rootExit: "FOO" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b"; + stateValues: "a" | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-root-final-state 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootExit" | "finalExit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + finalExit: "TICK" | "xstate.stop"; + rootExit: "TICK" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b"; + stateValues: "a" | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-root-multiple-final-states 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "rootExit" | "bExit" | "cExit" | "dExit"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + bExit: "TICK_B" | "xstate.stop"; + cExit: "TICK_C" | "xstate.stop"; + dExit: "xstate.stop"; + rootExit: "TICK_B" | "TICK_C" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "c" | "d"; + stateValues: "a" | "b" | "c" | "d"; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-within-ancestor-with-external-transition-outside-of-source 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "myAction"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + myAction: "FOO" | "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "a.b" | "c" | { a?: "b" }; + stateValues: "a" | { a: "b" } | "c"; + tags: never; +} +" +`; + +exports[`getTypegenOutput exit-action-within-ancestor-with-internal-transition 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + "xstate.stop": { type: "xstate.stop" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "exitA1" | "exitA2"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + exitA1: "FOO" | "xstate.stop"; + exitA2: "xstate.stop"; + }; + eventsCausingServices: {}; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "a.a1" | "a.a2" | { a?: "a1" | "a2" }; + stateValues: "a" | { a: "a1" } | { a: "a2" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput guard-provided-function 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: "sayHello"; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: { + sayHello: "FOO"; + }; + eventsCausingServices: {}; + eventsCausingGuards: { + guard: "FOO"; + }; + eventsCausingDelays: {}; + matchesStates: undefined; + stateValues: undefined; + tags: never; +} +" +`; + +exports[`getTypegenOutput invoke-within-targeted-parallel 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: { + jump: "done.invoke.(machine).b.c:invocation[0]"; + }; + missingImplementations: { + actions: never; + services: "jump"; + guards: never; + delays: never; + }; + eventsCausingActions: {}; + eventsCausingServices: { + jump: "GO_STRING"; + }; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "b.c" | { b?: "c" }; + stateValues: "a" | "b" | { b: "c" }; + tags: never; +} +" +`; + +exports[`getTypegenOutput parametrized-guard-in-always-transition 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "": { type: "" }; + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: never; + services: never; + guards: "myAwesomeGuard"; + delays: never; + }; + eventsCausingActions: {}; + eventsCausingServices: {}; + eventsCausingGuards: { + myAwesomeGuard: ""; + }; + eventsCausingDelays: {}; + matchesStates: "a" | "b" | "c"; + stateValues: "a" | "b" | "c"; + tags: never; +} +" +`; + +exports[`getTypegenOutput parametrized-guard-in-transition 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: {}; + missingImplementations: { + actions: never; + services: never; + guards: "myAwesomeGuard"; + delays: never; + }; + eventsCausingActions: {}; + eventsCausingServices: {}; + eventsCausingGuards: { + myAwesomeGuard: "MY_AWESOME_EVENT"; + }; + eventsCausingDelays: {}; + matchesStates: "a" | "b"; + stateValues: "a" | "b"; + tags: never; +} +" +`; + +exports[`getTypegenOutput service-provided-function 1`] = ` +"// This file was automatically generated. Edits will be overwritten + +export interface Typegen0 { + "@@xstate/typegen": true; + internalEvents: { + "xstate.init": { type: "xstate.init" }; + }; + invokeSrcNameMap: { + service1: "done.invoke.(machine):invocation[0]"; + service2: "done.invoke.(machine):invocation[1]"; + }; + missingImplementations: { + actions: never; + services: never; + guards: never; + delays: never; + }; + eventsCausingActions: {}; + eventsCausingServices: { + service1: "xstate.init"; + service2: "xstate.init"; + }; + eventsCausingGuards: {}; + eventsCausingDelays: {}; + matchesStates: undefined; + stateValues: undefined; + tags: never; +} +" +`;