"use strict";
Object.defineProperty(exports, "__esModule", {
    value: true
});
Object.defineProperty(exports, "BambuApi", {
    enumerable: true,
    get: function() {
        return BambuApi;
    }
});
const _printerapiinterface = require("./printer-api.interface");
const _bambumqttadapter = require("./bambu/bambu-mqtt.adapter");
const _nodefs = require("node:fs");
const defaultLog = {
    adapter: "bambu-lab"
};
class BambuApi {
    logger;
    client;
    printerLogin;
    printerSocketStore;
    printerId;
    constructor(bambuClient, printerLogin, printerSocketStore, loggerFactory){
        this.logger = loggerFactory(BambuApi.name);
        this.client = bambuClient;
        this.printerLogin = printerLogin;
        this.printerSocketStore = printerSocketStore;
        this.logger.debug("Constructed Bambu API client", this.logMeta());
    }
    setPrinterId(printerId) {
        this.printerId = printerId;
    }
    getMqttAdapter() {
        if (!this.printerId) {
            throw new Error("Printer ID not set. Cannot access MQTT adapter.");
        }
        const adapter = this.printerSocketStore.getPrinterSocket(this.printerId);
        if (!adapter) {
            throw new Error(`MQTT adapter not found for printer ${this.printerId}`);
        }
        if (!(adapter instanceof _bambumqttadapter.BambuMqttAdapter)) {
            throw new Error(`Adapter for printer ${this.printerId} is not a BambuMqttAdapter`);
        }
        return adapter;
    }
    async ensureFtpConnected() {
        if (!this.client.isConnected) {
            this.logger.debug("FTP not connected, connecting automatically");
            await this.client.connect(this.printerLogin);
        }
    }
    get type() {
        return _printerapiinterface.BambuType;
    }
    set login(login) {
        this.printerLogin = login;
    }
    async getVersion() {
        const response = await this.client.getApiVersion(this.printerLogin);
        return response.version;
    }
    async validateConnection() {
        this.logger.debug("Validating Bambu connection", this.logMeta());
        try {
            await this.ensureFtpConnected();
            const files = await this.client.ftp.listFiles("/");
            this.logger.debug(`FTP connection successful - found ${files.length} directories`, this.logMeta());
        } catch (ftpError) {
            this.logger.debug(`FTP validation failed: ${ftpError}`, this.logMeta());
            throw new Error(`Bambu FTP connection failed: ${ftpError}`);
        }
    }
    async connect() {
        await this.client.connect(this.printerLogin);
    }
    async disconnect() {
        await this.client.disconnect();
    }
    restartServer() {
        this.logger.warn("restartServer not supported by Bambu Lab printers");
        throw new Error("Method not supported");
    }
    restartHost() {
        this.logger.warn("restartHost not supported by Bambu Lab printers");
        throw new Error("Method not supported");
    }
    restartPrinterFirmware() {
        this.logger.warn("restartPrinterFirmware not supported by Bambu Lab printers");
        throw new Error("Method not supported");
    }
    async startPrint(path) {
        this.logger.log(`Starting print: ${path}`, this.logMeta());
        const mqttAdapter = this.getMqttAdapter();
        await mqttAdapter.startPrint(path);
    }
    async pausePrint() {
        this.logger.log("Pausing print", this.logMeta());
        const mqttAdapter = this.getMqttAdapter();
        await mqttAdapter.pausePrint();
    }
    async resumePrint() {
        this.logger.log("Resuming print", this.logMeta());
        const mqttAdapter = this.getMqttAdapter();
        await mqttAdapter.resumePrint();
    }
    async cancelPrint() {
        this.logger.log("Canceling print", this.logMeta());
        const mqttAdapter = this.getMqttAdapter();
        await mqttAdapter.stopPrint();
    }
    async quickStop() {
        this.logger.log("Quick stop (same as cancel for Bambu)", this.logMeta());
        const mqttAdapter = this.getMqttAdapter();
        await mqttAdapter.stopPrint();
    }
    async sendGcode(script) {
        this.logger.log(`Sending GCode: ${script}`, this.logMeta());
        const mqttAdapter = this.getMqttAdapter();
        await mqttAdapter.sendGcode(script);
    }
    movePrintHead(amounts) {
        this.logger.warn("movePrintHead not implemented for Bambu Lab printers");
        throw new Error("Method not implemented");
    }
    homeAxes(axes) {
        this.logger.warn("homeAxes not implemented for Bambu Lab printers");
        throw new Error("Method not implemented");
    }
    async getFile(path) {
        this.logger.debug(`Getting file info: ${path}`, this.logMeta());
        await this.ensureFtpConnected();
        const files = await this.client.ftp.listFiles("/");
        const file = files.find((f)=>f.name === path || f.name.endsWith(path));
        if (!file) {
            throw new Error(`File not found: ${path}`);
        }
        return {
            path: file.name,
            size: file.size,
            date: file.modifiedAt ? new Date(file.modifiedAt).getTime() : null,
            dir: file.isDirectory
        };
    }
    async getFiles(recursive = false, startDir = "/") {
        if (recursive) {
            throw new Error("Recursive listing not supported for Bambu Lab printers");
        }
        this.logger.debug(`Listing files from ${startDir}`, this.logMeta());
        await this.ensureFtpConnected();
        const items = await this.client.ftp.listFiles(startDir);
        const mapped = items.map((item)=>{
            const fullPath = startDir === "/" ? `/${item.name}` : `${startDir}/${item.name}`;
            return {
                path: fullPath,
                size: item.size,
                date: item.modifiedAt ? new Date(item.modifiedAt).getTime() : null,
                dir: item.isDirectory
            };
        });
        return {
            dirs: mapped.filter((i)=>i.dir),
            files: mapped.filter((i)=>!i.dir)
        };
    }
    async downloadFile(path) {
        this.logger.log(`Downloading file via FTP: ${path}`, this.logMeta());
        await this.ensureFtpConnected();
        const { stream, tempPath } = await this.client.ftp.downloadFileAsStream(path);
        const stats = (0, _nodefs.statSync)(tempPath);
        const filename = path.split("/").pop() || "download";
        return {
            data: stream,
            status: 200,
            statusText: "OK",
            headers: {
                "content-type": "application/octet-stream",
                "content-length": String(stats.size),
                "content-disposition": `attachment; filename="${filename}"`
            },
            config: {
                headers: {}
            }
        };
    }
    getFileChunk(path, startBytes, endBytes) {
        this.logger.warn("getFileChunk not implemented for Bambu Lab printers");
        throw new Error("Method not implemented");
    }
    async uploadFile(input) {
        const validated = _printerapiinterface.uploadFileInputSchema.parse(input);
        this.logger.log(`Uploading file: ${validated.fileName} (${validated.contentLength} bytes)`, this.logMeta());
        try {
            await this.ensureFtpConnected();
            await this.client.ftp.uploadFile(validated.stream, validated.fileName, validated.uploadToken);
            if (validated.startPrint) {
                this.logger.log(`Starting print after upload: ${validated.fileName}`, this.logMeta());
                const mqttAdapter = this.getMqttAdapter();
                await mqttAdapter.startPrint(validated.fileName);
            }
        } catch (error) {
            this.logger.error(`Upload failed: ${error.message}`, this.logMeta());
            throw error;
        }
    }
    async deleteFile(path) {
        this.logger.log(`Deleting file: ${path}`, this.logMeta());
        await this.ensureFtpConnected();
        await this.client.ftp.deleteFile(path);
    }
    deleteFolder(path) {
        this.logger.warn("deleteFolder not implemented for Bambu Lab printers");
        throw new Error("Method not implemented");
    }
    getSettings() {
        this.logger.warn("getSettings not implemented for Bambu Lab printers");
        throw new Error("Method not implemented");
    }
    async getReprintState() {
        const mqttAdapter = this.getMqttAdapter();
        const state = mqttAdapter.getLastState();
        if (!state) {
            return {
                reprintState: _printerapiinterface.ReprintState.PrinterNotAvailable,
                connectionState: null
            };
        }
        const lastFile = state.gcode_file;
        if (!lastFile) {
            return {
                reprintState: _printerapiinterface.ReprintState.NoLastPrint,
                connectionState: null
            };
        }
        return {
            file: {
                path: lastFile,
                size: -1,
                date: null,
                dir: false
            },
            reprintState: _printerapiinterface.ReprintState.LastPrintReady,
            connectionState: null
        };
    }
    logMeta() {
        return defaultLog;
    }
}

//# sourceMappingURL=bambu.api.js.map