Merge branch 'feat/analysis-build-type-edges'
# Conflicts: # src/analysis/index.ts # src/graph/construction.ts # src/index.ts
This commit is contained in:
@@ -4,7 +4,7 @@ export {
|
||||
defaultEdgeType,
|
||||
resolveDefaultNodeAttrs,
|
||||
} from "./defaults.js";
|
||||
export { typeCompat, type TypeCompatResult, type TypeMismatch } from "./type-compat.js";
|
||||
export { typeCompat, buildTypeEdges, type TypeCompatResult, type TypeMismatch } from "./type-compat.js";
|
||||
export {
|
||||
topologicalOrder,
|
||||
parallelGroups,
|
||||
@@ -13,7 +13,6 @@ export {
|
||||
ancestors,
|
||||
descendants,
|
||||
} from "./ordering.js";
|
||||
export { buildTypeEdges } from "../graph/construction.js";
|
||||
export {
|
||||
validateSchema,
|
||||
validateGraph,
|
||||
|
||||
@@ -1,4 +1,11 @@
|
||||
import { KindGuard, Kind, type TSchema } from "@alkdev/typebox";
|
||||
import { willCreateCycle } from "graphology-dag";
|
||||
import type { FlowGraph } from "../graph/construction.js";
|
||||
import {
|
||||
OperationNodeAttrs as OperationNodeAttrsSchema,
|
||||
OperationEdgeAttrs as OperationEdgeAttrsSchema,
|
||||
} from "../schema/index.js";
|
||||
import type { OperationNodeAttrs } from "../schema/index.js";
|
||||
|
||||
export interface TypeMismatch {
|
||||
path: string;
|
||||
@@ -275,4 +282,25 @@ export function typeCompat(outputSchema: TSchema, inputSchema: TSchema): TypeCom
|
||||
}
|
||||
|
||||
return { compatible: false, mismatches };
|
||||
}
|
||||
|
||||
export function buildTypeEdges(graph: FlowGraph<typeof OperationNodeAttrsSchema, typeof OperationEdgeAttrsSchema>): void {
|
||||
const nodeKeys = graph.nodes();
|
||||
for (const source of nodeKeys) {
|
||||
for (const target of nodeKeys) {
|
||||
if (source === target) continue;
|
||||
const sourceAttrs = graph.getNodeAttributes(source as never) as unknown as OperationNodeAttrs;
|
||||
const targetAttrs = graph.getNodeAttributes(target as never) as unknown as OperationNodeAttrs;
|
||||
const result = typeCompat(sourceAttrs.outputSchema as TSchema, targetAttrs.inputSchema as TSchema);
|
||||
if (result === undefined) continue;
|
||||
if (graph.hasEdge(source, target)) continue;
|
||||
if (willCreateCycle(graph.graph, source, target)) continue;
|
||||
const detail = result.detail ?? `${sourceAttrs.namespace}.${sourceAttrs.name}.output → ${targetAttrs.namespace}.${targetAttrs.name}.input`;
|
||||
graph.addTypedEdge(source, target, {
|
||||
compatible: result.compatible,
|
||||
detail,
|
||||
...(result.mismatches !== undefined ? { mismatches: result.mismatches } : {}),
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -24,8 +24,10 @@ import {
|
||||
CallNodeAttrs as CallNodeAttrsSchema,
|
||||
CallEdgeAttrs as CallEdgeAttrsSchema,
|
||||
} from "../schema/index.js";
|
||||
import type { OperationNodeAttrs, FlowGraphSerialized, CallNodeAttrs } from "../schema/index.js";
|
||||
import { typeCompat, type TypeCompatResult } from "../analysis/type-compat.js";
|
||||
import type { FlowGraphSerialized, CallNodeAttrs } from "../schema/index.js";
|
||||
import { buildTypeEdges, type TypeCompatResult } from "../analysis/type-compat.js";
|
||||
|
||||
export { buildTypeEdges } from "../analysis/type-compat.js";
|
||||
|
||||
export interface FlowGraphOptions {
|
||||
type?: "directed";
|
||||
@@ -654,25 +656,4 @@ export class FlowGraph<
|
||||
}
|
||||
return [];
|
||||
}
|
||||
}
|
||||
|
||||
export function buildTypeEdges(graph: OperationGraph): void {
|
||||
const nodeKeys = graph.nodes();
|
||||
for (const source of nodeKeys) {
|
||||
for (const target of nodeKeys) {
|
||||
if (source === target) continue;
|
||||
const sourceAttrs = graph.getNodeAttributes(source as never) as unknown as OperationNodeAttrs;
|
||||
const targetAttrs = graph.getNodeAttributes(target as never) as unknown as OperationNodeAttrs;
|
||||
const result = typeCompat(sourceAttrs.outputSchema as TSchema, targetAttrs.inputSchema as TSchema);
|
||||
if (result === undefined) continue;
|
||||
if (graph.hasEdge(source, target)) continue;
|
||||
if (willCreateCycle(graph.graph, source, target)) continue;
|
||||
const detail = result.detail ?? `${sourceAttrs.namespace}.${sourceAttrs.name}.output → ${targetAttrs.namespace}.${targetAttrs.name}.input`;
|
||||
graph.addTypedEdge(source, target, {
|
||||
compatible: result.compatible,
|
||||
detail,
|
||||
...(result.mismatches !== undefined ? { mismatches: result.mismatches } : {}),
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,6 +1,7 @@
|
||||
export * from "./error/index.js";
|
||||
|
||||
export { FlowGraph, buildTypeEdges, type FlowGraphOptions, type OperationSpec, type CallEventMapValue, type CallRequestedEvent, type CallRespondedEvent, type CallErrorEvent, type CallAbortedEvent, type CallCompletedEvent } from "./graph/index.js";
|
||||
export { typeCompat, type TypeCompatResult, type TypeMismatch } from "./analysis/type-compat.js";
|
||||
export {
|
||||
validateSchema,
|
||||
validateGraph,
|
||||
|
||||
Reference in New Issue
Block a user