"use strict";
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
    function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.AutoBeAgent = void 0;
const core_1 = require("@agentica/core");
const tstl_1 = require("tstl");
const uuid_1 = require("uuid");
const AutoBeAgentBase_1 = require("./AutoBeAgentBase");
const AutoBeTokenUsage_1 = require("./context/AutoBeTokenUsage");
const createAgenticaHistory_1 = require("./factory/createAgenticaHistory");
const createAutoBeApplication_1 = require("./factory/createAutoBeApplication");
const createAutoBeContext_1 = require("./factory/createAutoBeContext");
const createAutoBeState_1 = require("./factory/createAutoBeState");
const transformFacadeStateMessage_1 = require("./orchestrate/facade/transformFacadeStateMessage");
const backoffRetry_1 = require("./utils/backoffRetry");
/**
 * Main agent class that orchestrates the entire vibe coding pipeline through
 * conversation-driven development.
 *
 * The AutoBeAgent serves as the central coordinator for the waterfall-based
 * development process with spiral model iterative improvements. It manages the
 * five specialized agents (Analyze, Prisma, Interface, Test, Realize) that
 * transform user conversations into complete working applications through a
 * sophisticated AST-based compilation infrastructure.
 *
 * The agent operates through natural language conversation, supporting
 * multimodal input including text, images, files, and audio. It maintains
 * conversation history, tracks development progress through real-time events,
 * and provides access to all generated artifacts including requirements
 * documentation, database schemas, API specifications, test suites, and
 * implementation code.
 *
 * The vibe coding approach eliminates traditional development barriers by
 * enabling users to express requirements naturally while the agent handles all
 * technical implementation details through validated AST transformations and
 * continuous quality assurance feedback loops.
 *
 * @author Samchon
 */
class AutoBeAgent extends AutoBeAgentBase_1.AutoBeAgentBase {
    /* -----------------------------------------------------------
      CONSTRUCTOR
    ----------------------------------------------------------- */
    /**
     * Initializes a new AutoBeAgent instance with the specified configuration.
     *
     * Creates and configures the agent with AI vendor settings, behavioral
     * context (locale/timezone), and compilation infrastructure. The agent can
     * optionally resume from previous conversation histories to continue
     * development sessions or build upon existing work.
     *
     * The constructor sets up the internal MicroAgentica engine, initializes the
     * development state from provided histories, and establishes the event
     * dispatch system for real-time progress notifications. The agent becomes
     * ready for conversation-driven development immediately after construction.
     *
     * @param props Configuration properties including AI vendor settings,
     *   behavioral context, compilation tools, and optional conversation
     *   histories for session continuation
     */
    constructor(props) {
        var _a, _b, _c, _d, _e, _f;
        // INITIALIZE MEMBERS
        super({
            compiler: () => this.context_.compiler(),
            state: () => this.state_,
        });
        this.props_ = props;
        this.histories_ = (_b = (_a = props.histories) === null || _a === void 0 ? void 0 : _a.slice()) !== null && _b !== void 0 ? _b : [];
        this.state_ = (0, createAutoBeState_1.createAutoBeState)(this.histories_);
        this.usage_ =
            props.tokenUsage instanceof AutoBeTokenUsage_1.AutoBeTokenUsage
                ? props.tokenUsage
                : new AutoBeTokenUsage_1.AutoBeTokenUsage(props.tokenUsage);
        // CONSTRUCT AGENTICA
        const vendor = Object.assign(Object.assign({}, props.vendor), { semaphore: new tstl_1.Semaphore((_c = props.vendor.semaphore) !== null && _c !== void 0 ? _c : 16) });
        const compilerListener = {
            realize: {
                test: {
                    onOperation: () => __awaiter(this, void 0, void 0, function* () { }),
                    onReset: () => __awaiter(this, void 0, void 0, function* () { }),
                },
            },
        };
        const compiler = new tstl_1.Singleton(() => __awaiter(this, void 0, void 0, function* () { return props.compiler(compilerListener); }));
        this.context_ = (0, createAutoBeContext_1.createAutoBeContext)({
            model: props.model,
            vendor: props.vendor,
            config: Object.assign({ backoffStrategy: backoffRetry_1.randomBackoffStrategy }, props.config),
            compiler: () => compiler.get(),
            compilerListener,
            state: () => this.state_,
            files: (options) => this.getFiles(options),
            histories: () => this.histories_,
            usage: () => this.usage_,
            dispatch: (event) => this.dispatch(event),
        });
        this.agentica_ = new core_1.MicroAgentica({
            vendor,
            model: props.model,
            config: Object.assign(Object.assign({}, ((_d = props.config) !== null && _d !== void 0 ? _d : {})), { retry: (_f = (_e = props.config) === null || _e === void 0 ? void 0 : _e.retry) !== null && _f !== void 0 ? _f : 4 /* AutoBeConfigConstant.RETRY */, executor: {
                    describe: null,
                }, systemPrompt: {
                    execute: () => (0, transformFacadeStateMessage_1.transformFacadeStateMessage)(this.state_),
                } }),
            controllers: [
                (0, createAutoBeApplication_1.createAutoBeController)({
                    model: props.model,
                    context: this.context_,
                }),
            ],
        });
        // HISTORIES MANIPULATION
        this.agentica_.getHistories().push(...this.histories_
            .map((history) => (0, createAgenticaHistory_1.createAgenticaHistory)({
            operations: this.agentica_.getOperations(),
            history,
        }))
            .filter((h) => h !== null));
        // TRACE FACADE TOKEN USAGE
        let previous = this.agentica_
            .getTokenUsage()
            .toJSON().aggregate;
        const increment = () => {
            const current = this.agentica_
                .getTokenUsage()
                .toJSON().aggregate;
            this.usage_.facade.increment({
                total: current.total - previous.total,
                input: {
                    total: current.input.total - previous.input.total,
                    cached: current.input.cached - previous.input.cached,
                },
                output: {
                    total: current.output.total - previous.output.total,
                    reasoning: current.output.reasoning - previous.output.reasoning,
                    accepted_prediction: current.output.accepted_prediction -
                        previous.output.accepted_prediction,
                    rejected_prediction: current.output.rejected_prediction -
                        previous.output.rejected_prediction,
                },
            });
            previous = current;
        };
        // SHIFT EVENTS
        this.agentica_.on("assistantMessage", (message) => __awaiter(this, void 0, void 0, function* () {
            const start = new Date();
            const history = {
                id: (0, uuid_1.v7)(),
                type: "assistantMessage",
                text: yield message.join(),
                created_at: start.toISOString(),
                completed_at: new Date().toISOString(),
            };
            increment();
            this.histories_.push(history);
            this.dispatch({
                type: "assistantMessage",
                id: history.id,
                text: history.text,
                created_at: history.created_at,
            }).catch(() => { });
        }));
        this.agentica_.on("call", () => __awaiter(this, void 0, void 0, function* () {
            increment();
        }));
        this.agentica_.on("request", (e) => {
            if (e.body.parallel_tool_calls !== undefined)
                delete e.body.parallel_tool_calls;
            void this.dispatch(Object.assign(Object.assign({}, e), { type: "vendorRequest", source: "facade", retry: 0 })).catch(() => { });
        });
        this.agentica_.on("response", (e) => {
            void this.dispatch(Object.assign(Object.assign({}, e), { type: "vendorResponse", source: "facade", retry: 0 })).catch(() => { });
        });
    }
    /** @internal */
    clone() {
        return new AutoBeAgent(Object.assign(Object.assign({}, this.props_), { histories: this.histories_.slice() }));
    }
    /* -----------------------------------------------------------
      ACCESSORS
    ----------------------------------------------------------- */
    conversate(content) {
        return __awaiter(this, void 0, void 0, function* () {
            const index = this.histories_.length;
            const userMessageHistory = {
                id: (0, uuid_1.v7)(),
                type: "userMessage",
                contents: typeof content === "string"
                    ? [
                        {
                            type: "text",
                            text: content,
                        },
                    ]
                    : Array.isArray(content)
                        ? content
                        : [content],
                created_at: new Date().toISOString(),
            };
            this.histories_.push(userMessageHistory);
            this.dispatch(userMessageHistory).catch(() => { });
            yield this.agentica_.conversate(content);
            return this.histories_.slice(index);
        });
    }
    getHistories() {
        return this.histories_;
    }
    getTokenUsage() {
        return this.usage_;
    }
    getPhase() {
        var _a, _b, _c, _d;
        if (this.state_.analyze === null)
            return null;
        else if (((_a = this.state_.realize) === null || _a === void 0 ? void 0 : _a.step) === this.state_.analyze.step)
            return "realize";
        else if (((_b = this.state_.test) === null || _b === void 0 ? void 0 : _b.step) === this.state_.analyze.step)
            return "test";
        else if (((_c = this.state_.interface) === null || _c === void 0 ? void 0 : _c.step) === this.state_.analyze.step)
            return "interface";
        else if (((_d = this.state_.prisma) === null || _d === void 0 ? void 0 : _d.step) === this.state_.analyze.step)
            return "prisma";
        return "analyze";
    }
    /** @internal */
    getContext() {
        return this.context_;
    }
}
exports.AutoBeAgent = AutoBeAgent;
//# sourceMappingURL=AutoBeAgent.js.map