"use strict";
var __importDefault = (this && this.__importDefault) || function (mod) {
    return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.JSONATA_DIALECT = exports.JsonataDialect = exports.JSON_PATH_DIALECT = exports.JsonPathDialect = exports.buildChoiceRule = exports.buildParameters = exports.buildStateMachine = void 0;
exports.generateStateMachine = generateStateMachine;
exports.deriveStateMachineName = deriveStateMachineName;
const typescript_1 = __importDefault(require("typescript"));
const variableResolver_js_1 = require("../analysis/variableResolver.js");
const types_js_1 = require("../analysis/types.js");
const stateBuilder_js_1 = require("./stateBuilder.js");
const pathDialect_js_1 = require("./pathDialect.js");
// ---------------------------------------------------------------------------
// Public API
// ---------------------------------------------------------------------------
/**
 * Generate an ASL StateMachineDefinition from a compiled call site.
 */
function generateStateMachine(context, callSite, cfg, serviceRegistry, substitutions, analyzer, inlineBindings, dialect = pathDialect_js_1.JSON_PATH_DIALECT, timeoutSeconds, version, sourceMap) {
    const variables = (0, variableResolver_js_1.resolveVariables)(context, callSite, serviceRegistry, substitutions, analyzer, dialect);
    // Apply inline bindings: map helper parameter symbols to the same
    // variable info as the call-site argument expressions.
    // Bindings are registered as deferred so they resolve lazily — this handles
    // arguments that reference runtime variables (e.g. service call results)
    // which aren't in the resolution until the state builder processes them.
    if (inlineBindings && inlineBindings.length > 0) {
        for (const binding of inlineBindings) {
            // Try eager resolution first (works for input refs, literals, intrinsics)
            const resolved = (0, variableResolver_js_1.resolveExpression)(context, binding.argExpression, variables.toResolution(), dialect);
            if (resolved.kind === 'jsonpath' && resolved.path) {
                variables.addVariable(binding.paramSymbol, {
                    symbol: binding.paramSymbol,
                    type: types_js_1.StepVariableType.StateOutput,
                    jsonPath: resolved.path,
                    definitelyAssigned: true,
                    constant: false,
                });
            }
            else if (resolved.kind === 'literal') {
                variables.addVariable(binding.paramSymbol, {
                    symbol: binding.paramSymbol,
                    type: types_js_1.StepVariableType.Constant,
                    definitelyAssigned: true,
                    constant: true,
                    literalValue: resolved.value,
                });
            }
            else if (resolved.kind === 'intrinsic' && resolved.path) {
                variables.addVariable(binding.paramSymbol, {
                    symbol: binding.paramSymbol,
                    type: types_js_1.StepVariableType.Derived,
                    definitelyAssigned: true,
                    constant: true,
                    intrinsicPath: resolved.path,
                });
            }
            else {
                // Defer: the argument references a runtime variable not yet registered.
                // It will be resolved lazily when the parameter is accessed during state building.
                variables.addDeferredBinding(binding.paramSymbol, binding.argExpression);
            }
        }
    }
    return (0, stateBuilder_js_1.buildStateMachine)(context, cfg, callSite, serviceRegistry, variables, dialect, timeoutSeconds, version, sourceMap);
}
/**
 * Derive the state machine name from the call site.
 *
 * For `export const processOrder = Steps.createFunction(...)`, returns "processOrder".
 * For `@stepFunction method() { ... }`, returns the method name.
 */
function deriveStateMachineName(callSite) {
    const origin = callSite.origin;
    if (origin.kind === 'createFunction') {
        // Walk up: CallExpression → VariableDeclaration → name
        const parent = origin.call.parent;
        if (typescript_1.default.isVariableDeclaration(parent) && typescript_1.default.isIdentifier(parent.name)) {
            return parent.name.text;
        }
        return 'StateMachine';
    }
    if (origin.kind === 'decorator') {
        return origin.method.name.getText();
    }
    return 'StateMachine';
}
// Re-exports
var stateBuilder_js_2 = require("./stateBuilder.js");
Object.defineProperty(exports, "buildStateMachine", { enumerable: true, get: function () { return stateBuilder_js_2.buildStateMachine; } });
var expressionMapper_js_1 = require("./expressionMapper.js");
Object.defineProperty(exports, "buildParameters", { enumerable: true, get: function () { return expressionMapper_js_1.buildParameters; } });
Object.defineProperty(exports, "buildChoiceRule", { enumerable: true, get: function () { return expressionMapper_js_1.buildChoiceRule; } });
var pathDialect_js_2 = require("./pathDialect.js");
Object.defineProperty(exports, "JsonPathDialect", { enumerable: true, get: function () { return pathDialect_js_2.JsonPathDialect; } });
Object.defineProperty(exports, "JSON_PATH_DIALECT", { enumerable: true, get: function () { return pathDialect_js_2.JSON_PATH_DIALECT; } });
Object.defineProperty(exports, "JsonataDialect", { enumerable: true, get: function () { return pathDialect_js_2.JsonataDialect; } });
Object.defineProperty(exports, "JSONATA_DIALECT", { enumerable: true, get: function () { return pathDialect_js_2.JSONATA_DIALECT; } });
//# sourceMappingURL=index.js.map