UNPKG

effector

Version:

Business logic with ease

1 lines 8.38 kB
{"version":3,"file":"inspect.mjs","sources":["effector/inspect.ts"],"sourcesContent":["import {\n Scope,\n Subscription,\n Stack,\n Node,\n // private\n // @ts-expect-error\n setInspector,\n // private\n // @ts-expect-error\n setGraphInspector,\n} from 'effector'\nimport { ID } from './index.h'\n\ntype Loc = {\n file: string\n line: number\n column: number\n}\n\ntype NodeCommonMeta = {\n kind: string\n sid?: string\n id: string\n name?: string\n loc?: Loc\n meta: Record<string, unknown>\n derived?: boolean\n}\n\n// Watch calculations\ntype Message = {\n type: 'update' | 'error'\n error?: unknown\n value: unknown\n stack: Record<string, unknown>\n trace?: Message[]\n} & NodeCommonMeta\n\nconst inspectSubs = new Set<{\n scope?: Scope\n trace?: boolean\n fn: (message: Message) => void\n}>()\n\nsetInspector((stack: Stack, local: {fail: boolean; failReason?: unknown}) => {\n const {scope} = stack\n const nodeMeta = getNodeMeta(stack)\n let trace: Message[]\n inspectSubs.forEach(config => {\n if (\n !(\n // must be the same scope\n (\n config.scope === scope ||\n // or no scope at all\n (!config.scope && !scope)\n )\n )\n ) {\n /**\n * Inspection is restriced by scope\n */\n return\n }\n\n if (config.trace && !trace) {\n trace = collectMessageTrace(stack)\n }\n\n config.fn({\n type: local.fail ? 'error' : 'update',\n value: stack.value,\n error: local.fail ? local.failReason : undefined,\n stack: stack.meta || {},\n trace: config.trace ? trace : [],\n meta: nodeMeta.meta,\n id: nodeMeta.id,\n sid: nodeMeta.sid,\n name: nodeMeta.name,\n kind: nodeMeta.kind,\n loc: nodeMeta.loc,\n derived: nodeMeta.derived,\n })\n })\n})\n\nexport function inspect(config: {\n scope?: Scope\n trace?: boolean\n fn: (message: Message) => void\n}): Subscription {\n inspectSubs.add(config)\n\n return createSubscription(() => {\n inspectSubs.delete(config)\n })\n}\n\n// Track declarations and graph structure\ntype Region =\n | {\n type: 'region'\n id: ID,\n meta: Record<string, unknown>\n region?: Region\n }\n | {\n type: 'factory'\n id: ID,\n meta: Record<string, unknown>\n region?: Region\n sid?: string\n name?: string\n method?: string\n loc?: {\n file: string\n line: number\n column: number\n }\n }\n\ntype UnitDeclaration = {\n type: 'unit'\n meta: Record<string, unknown>\n region?: Region\n} & NodeCommonMeta\n\ntype Declaration = UnitDeclaration | Region\n\nconst inspectGraphSubs = new Set<{\n fn: (declaration: Declaration) => void\n}>()\n\nsetGraphInspector((node: Node | 'region', regionStack: RegionStack) => {\n let decl: Declaration | undefined\n\n if (node === 'region') {\n decl = readRegionStack(regionStack)\n } else {\n decl = readUnitDeclaration(node, regionStack)\n }\n\n if (decl) {\n inspectGraphSubs.forEach(sub => {\n sub.fn(decl!)\n })\n }\n})\n\nexport function inspectGraph(config: {\n fn: (declaration: Declaration) => void\n}): Subscription {\n inspectGraphSubs.add(config)\n return createSubscription(() => {\n inspectGraphSubs.delete(config)\n })\n}\n\n// Utils\nfunction createSubscription(cleanup: () => void): Subscription {\n const result = () => cleanup()\n result.unsubscribe = result\n return result\n}\n\nfunction getNodeMeta(stack: Stack) {\n return readNodeMeta(stack.node)\n}\n\nfunction readNodeMeta(node: Node): NodeCommonMeta {\n const {meta, id} = node\n const loc = getLoc(meta)\n const {sid, name, op: kind} = meta\n\n return {meta, id, sid, name, kind, loc, derived: meta.derived}\n}\n\nfunction getLoc(meta: Record<string, unknown>) {\n return meta.config ? (meta.config as any).loc : meta.loc\n}\n\nfunction collectMessageTrace(stack: Stack) {\n const trace: Message[] = []\n let currentStack = stack.parent\n\n while (currentStack) {\n const nodeMeta = getNodeMeta(currentStack)\n trace.push({\n type: 'update',\n value: currentStack.value,\n stack: currentStack.meta || {},\n meta: nodeMeta.meta,\n id: nodeMeta.id,\n sid: nodeMeta.sid,\n name: nodeMeta.name,\n kind: nodeMeta.kind,\n loc: nodeMeta.loc,\n derived: nodeMeta.derived,\n })\n\n currentStack = currentStack.parent\n }\n\n return trace\n}\n\nfunction readUnitDeclaration(\n node: Node,\n regionStack: RegionStack,\n): UnitDeclaration {\n const nodeMeta = readNodeMeta(node)\n\n return {\n type: 'unit',\n region: readRegionStack(regionStack),\n meta: nodeMeta.meta,\n id: nodeMeta.id,\n sid: nodeMeta.sid,\n name: nodeMeta.name,\n kind: nodeMeta.kind,\n loc: nodeMeta.loc,\n derived: nodeMeta.derived,\n }\n}\n\nfunction readRegionStack(regionStack?: RegionStack | null): Region | undefined {\n if (!regionStack) return\n const {parent, meta, id} = regionStack\n const parentRegion = readRegionStack(parent) || undefined\n\n if (meta.type === 'factory') {\n const {sid, name, loc, method} = meta as any\n\n return {\n type: 'factory',\n id,\n region: parentRegion,\n meta,\n sid,\n name,\n loc,\n method,\n }\n }\n\n return {\n type: 'region',\n id,\n region: parentRegion,\n meta,\n }\n}\n\ntype RegionStack = {\n id: ID,\n parent: RegionStack | null\n meta:\n | Record<string, unknown>\n | {\n type: 'factory'\n sid?: string\n name?: string\n method?: string\n loc?: Loc\n }\n}\n"],"names":["inspect","config","inspectSubs","add","createSubscription","delete","inspectGraph","inspectGraphSubs","cleanup","result","unsubscribe","getNodeMeta","stack","readNodeMeta","node","meta","id","loc","getLoc","sid","name","op","kind","derived","readRegionStack","regionStack","parent","parentRegion","undefined","type","method","region","Set","setInspector","local","scope","nodeMeta","trace","forEach","currentStack","push","value","collectMessageTrace","fn","fail","error","failReason","setGraphInspector","decl","readUnitDeclaration","sub"],"mappings":"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"}