( nodeId: string, textValue: string, inputData: any, config?: unknown, executionContext?: FlowExecutionContext, )
| 3389 | } |
| 3390 | |
| 3391 | async function executeLookupNode( |
| 3392 | nodeId: string, |
| 3393 | textValue: string, |
| 3394 | inputData: any, |
| 3395 | config?: unknown, |
| 3396 | executionContext?: FlowExecutionContext, |
| 3397 | ): Promise<NodeExecutionResult> { |
| 3398 | console.log(`Lookup Node ${nodeId}: Processing with input tables:`, { |
| 3399 | sourceTableCount: inputData?.source?.tables?.length, |
| 3400 | indexedTableName: inputData?.indexed?.tableName, |
| 3401 | }); |
| 3402 | |
| 3403 | // Parse configuration |
| 3404 | const parsed = getNodeConfig<{ |
| 3405 | lookupColumn?: string; |
| 3406 | joinType?: "inner" | "left" | "nested" | "cross"; |
| 3407 | indexColumns?: string[]; |
| 3408 | indexJoinColumn?: string; |
| 3409 | }>(config, textValue); |
| 3410 | if (!parsed) { |
| 3411 | return { success: false, error: "Invalid lookup configuration" }; |
| 3412 | } |
| 3413 | const lookupColumn = parsed.lookupColumn || ""; |
| 3414 | const joinType = parsed.joinType || "inner"; |
| 3415 | const indexColumns = parsed.indexColumns || []; |
| 3416 | const indexJoinColumn = parsed.indexJoinColumn || ""; |
| 3417 | |
| 3418 | // For cross join, we don't need lookup columns |
| 3419 | if (joinType !== "cross" && !lookupColumn) { |
| 3420 | return { success: false, error: "No lookup column specified" }; |
| 3421 | } |
| 3422 | |
| 3423 | // Input should be an array: [sourceData, indexedData] |
| 3424 | if (!Array.isArray(inputData) || inputData.length !== 2) { |
| 3425 | return { success: false, error: "Invalid input: Expected array with 2 inputs [source, index]" }; |
| 3426 | } |
| 3427 | |
| 3428 | const [sourceData, rightInputData] = inputData; |
| 3429 | |
| 3430 | // Validate source data |
| 3431 | if (!sourceData || sourceData.type !== "TableSelection") { |
| 3432 | return { success: false, error: "Invalid source input: Expected TableSelection data" }; |
| 3433 | } |
| 3434 | |
| 3435 | // Handle both IndexedTable and TableSelection for the second input |
| 3436 | let indexedData: any; |
| 3437 | |
| 3438 | if (rightInputData.type === "IndexedTable") { |
| 3439 | // Already indexed, use as-is |
| 3440 | indexedData = rightInputData; |
| 3441 | } else if (rightInputData.type === "TableSelection") { |
| 3442 | if (joinType === "cross") { |
| 3443 | const allRightRows: AmendedSchemaField[][] = []; |
| 3444 | let rightTable = rightInputData.tables[0]; |
| 3445 | |
| 3446 | for (const table of rightInputData.tables) { |
| 3447 | if (!table.table.schemaFields || !table.table.tableSchema) { |
| 3448 | console.warn(`Lookup Node ${nodeId}: Skipping index table without schema data`); |
no test coverage detected