first commit
This commit is contained in:
@@ -0,0 +1,112 @@
|
||||
import { extractTriggersFromPoint } from "./extractTriggersFromPoint";
|
||||
|
||||
export function determineExecutionOrder(products: productsSchema): PointsScheme[] {
|
||||
// Create maps for all events and points
|
||||
const eventMap = new Map<string, EventsSchema>();
|
||||
const pointMap = new Map<string, PointsScheme>();
|
||||
const allPoints: PointsScheme[] = [];
|
||||
|
||||
// First pass: collect all points
|
||||
products.forEach(product => {
|
||||
product.eventDatas.forEach(event => {
|
||||
eventMap.set(event.modelUuid, event);
|
||||
|
||||
if (event.type === 'transfer') {
|
||||
event.points.forEach(point => {
|
||||
pointMap.set(point.uuid, point);
|
||||
allPoints.push(point);
|
||||
});
|
||||
} else if (event.type === 'vehicle' ||
|
||||
event.type === 'machine' ||
|
||||
event.type === 'storageUnit' ||
|
||||
event.type === 'roboticArm') {
|
||||
pointMap.set(event.point.uuid, event.point);
|
||||
allPoints.push(event.point);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Build dependency graphs
|
||||
const graph = new Map<string, string[]>();
|
||||
const reverseGraph = new Map<string, string[]>();
|
||||
const allTriggeredPoints = new Set<string>();
|
||||
|
||||
allPoints.forEach(point => {
|
||||
const triggers = extractTriggersFromPoint(point);
|
||||
const dependencies: string[] = [];
|
||||
|
||||
triggers.forEach(trigger => {
|
||||
const targetUuid = trigger.triggeredAsset?.triggeredPoint?.pointUuid;
|
||||
if (targetUuid && pointMap.has(targetUuid)) {
|
||||
dependencies.push(targetUuid);
|
||||
allTriggeredPoints.add(targetUuid);
|
||||
|
||||
if (!reverseGraph.has(targetUuid)) {
|
||||
reverseGraph.set(targetUuid, []);
|
||||
}
|
||||
reverseGraph.get(targetUuid)!.push(point.uuid);
|
||||
}
|
||||
});
|
||||
|
||||
graph.set(point.uuid, dependencies);
|
||||
});
|
||||
|
||||
// Identify root points (points that trigger others but aren't triggered themselves)
|
||||
const rootPoints = allPoints
|
||||
.filter(point => !allTriggeredPoints.has(point.uuid))
|
||||
.filter(point => {
|
||||
// Only include roots that actually have triggers pointing FROM them
|
||||
const triggers = extractTriggersFromPoint(point);
|
||||
return triggers.some(t => t.triggeredAsset?.triggeredPoint?.pointUuid);
|
||||
});
|
||||
|
||||
// If no root points found but we have triggered points, find the earliest triggers
|
||||
if (rootPoints.length === 0 && allTriggeredPoints.size > 0) {
|
||||
// This handles cases where we have circular dependencies
|
||||
// but still want to include the triggered points
|
||||
const minTriggerCount = Math.min(
|
||||
...Array.from(allTriggeredPoints)
|
||||
.map(uuid => (graph.get(uuid) || []).length)
|
||||
);
|
||||
const potentialRoots = Array.from(allTriggeredPoints)
|
||||
.filter(uuid => (graph.get(uuid) || []).length === minTriggerCount);
|
||||
|
||||
rootPoints.push(...potentialRoots.map(uuid => pointMap.get(uuid)!));
|
||||
}
|
||||
|
||||
// Topological sort only for triggered points
|
||||
const visited = new Set<string>();
|
||||
const temp = new Set<string>();
|
||||
const order: string[] = [];
|
||||
let hasCycle = false;
|
||||
|
||||
function visit(node: string) {
|
||||
if (temp.has(node)) {
|
||||
hasCycle = true;
|
||||
return;
|
||||
}
|
||||
if (visited.has(node)) return;
|
||||
|
||||
temp.add(node);
|
||||
|
||||
const dependencies = reverseGraph.get(node) || [];
|
||||
for (const dep of dependencies) {
|
||||
visit(dep);
|
||||
}
|
||||
|
||||
temp.delete(node);
|
||||
visited.add(node);
|
||||
order.push(node);
|
||||
}
|
||||
|
||||
// Start processing from root points
|
||||
rootPoints.forEach(root => visit(root.uuid));
|
||||
|
||||
// Convert UUIDs back to points and filter out untriggered points
|
||||
const triggeredPoints = order
|
||||
.map(uuid => pointMap.get(uuid)!)
|
||||
.filter(point => allTriggeredPoints.has(point.uuid) ||
|
||||
rootPoints.some(root => root.uuid === point.uuid));
|
||||
|
||||
return triggeredPoints;
|
||||
}
|
||||
Reference in New Issue
Block a user