"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.AcrossPlusMessageCoder = exports.MulticallHandlerCoder = exports.LargeAccountsCoder = void 0;
var tslib_1 = require("tslib");
var anchor_1 = require("@coral-xyz/anchor");
var idl_1 = require("@coral-xyz/anchor/dist/cjs/coder/borsh/idl");
var borsh = tslib_1.__importStar(require("@coral-xyz/borsh"));
var web3_js_1 = require("@solana/web3.js");
var bs58_1 = tslib_1.__importDefault(require("bs58"));
var LargeAccountsCoder = (function (_super) {
    tslib_1.__extends(LargeAccountsCoder, _super);
    function LargeAccountsCoder() {
        return _super !== null && _super.apply(this, arguments) || this;
    }
    LargeAccountsCoder.prototype.getAccountLayouts = function () {
        return this.accountLayouts;
    };
    LargeAccountsCoder.prototype.encode = function (accountName, account) {
        return tslib_1.__awaiter(this, void 0, void 0, function () {
            var buffer, layout, len, accountData, discriminator;
            return tslib_1.__generator(this, function (_a) {
                buffer = Buffer.alloc(10240);
                layout = this.getAccountLayouts().get(accountName);
                if (!layout) {
                    throw new Error("Unknown account: ".concat(accountName));
                }
                len = layout.layout.encode(account, buffer);
                accountData = buffer.slice(0, len);
                discriminator = this.accountDiscriminator(accountName);
                return [2, Buffer.concat([discriminator, accountData])];
            });
        });
    };
    return LargeAccountsCoder;
}(anchor_1.BorshAccountsCoder));
exports.LargeAccountsCoder = LargeAccountsCoder;
var UnsignedCompiledKeys = (function () {
    function UnsignedCompiledKeys(keyModeMap, payer) {
        this.keyModeMap = keyModeMap;
        this.payer = payer;
    }
    UnsignedCompiledKeys.compileUnsigned = function (instructions, payer) {
        var keyModeMap = new Map();
        var getOrInsertDefault = function (pubkey) {
            var address = pubkey.toBase58();
            var keyMode = keyModeMap.get(address);
            if (keyMode === undefined) {
                keyMode = {
                    isWritable: false,
                };
                keyModeMap.set(address, keyMode);
            }
            return keyMode;
        };
        if (payer !== undefined) {
            var payerKeyMode = getOrInsertDefault(payer);
            payerKeyMode.isWritable = true;
        }
        for (var _i = 0, instructions_1 = instructions; _i < instructions_1.length; _i++) {
            var ix = instructions_1[_i];
            getOrInsertDefault(ix.programId);
            for (var _a = 0, _b = ix.keys; _a < _b.length; _a++) {
                var accountMeta = _b[_a];
                var keyMode = getOrInsertDefault(accountMeta.pubkey);
                keyMode.isWritable || (keyMode.isWritable = accountMeta.isWritable);
            }
        }
        return new UnsignedCompiledKeys(keyModeMap, payer);
    };
    UnsignedCompiledKeys.prototype.getMessageComponents = function () {
        var mapEntries = Array.from(this.keyModeMap.entries());
        if (mapEntries.length > 256)
            throw new Error("Max static account keys length exceeded");
        var writableNonSigners = mapEntries.filter(function (_a) {
            var mode = _a[1];
            return mode.isWritable;
        });
        var readonlyNonSigners = mapEntries.filter(function (_a) {
            var mode = _a[1];
            return !mode.isWritable;
        });
        var header = {
            numRequiredSignatures: 0,
            numReadonlySignedAccounts: 0,
            numReadonlyUnsignedAccounts: readonlyNonSigners.length,
        };
        var staticAccountKeys = tslib_1.__spreadArray(tslib_1.__spreadArray([], writableNonSigners.map(function (_a) {
            var address = _a[0];
            return new web3_js_1.PublicKey(address);
        }), true), readonlyNonSigners.map(function (_a) {
            var address = _a[0];
            return new web3_js_1.PublicKey(address);
        }), true);
        return [header, staticAccountKeys];
    };
    return UnsignedCompiledKeys;
}());
var UnsignedMessage = (function (_super) {
    tslib_1.__extends(UnsignedMessage, _super);
    function UnsignedMessage() {
        return _super !== null && _super.apply(this, arguments) || this;
    }
    UnsignedMessage.compileUnsigned = function (instructions, payer) {
        var compiledKeys = UnsignedCompiledKeys.compileUnsigned(instructions, payer);
        var _a = compiledKeys.getMessageComponents(), header = _a[0], staticAccountKeys = _a[1];
        var accountKeys = new web3_js_1.MessageAccountKeys(staticAccountKeys);
        var compiledInstructions = accountKeys.compileInstructions(instructions).map(function (ix) { return ({
            programIdIndex: ix.programIdIndex,
            accounts: ix.accountKeyIndexes,
            data: bs58_1.default.encode(ix.data),
        }); });
        return new web3_js_1.Message({
            header: header,
            accountKeys: staticAccountKeys,
            recentBlockhash: "",
            instructions: compiledInstructions,
        });
    };
    return UnsignedMessage;
}(web3_js_1.Message));
var MulticallHandlerCoder = (function () {
    function MulticallHandlerCoder(instructions, payerKey) {
        this.compiledMessage = UnsignedMessage.compileUnsigned(instructions, payerKey);
        var fieldLayouts = [idl_1.IdlCoder.fieldLayout(MulticallHandlerCoder.coderArg, MulticallHandlerCoder.coderTypes)];
        this.layout = borsh.struct(fieldLayouts);
    }
    Object.defineProperty(MulticallHandlerCoder.prototype, "readOnlyLen", {
        get: function () {
            return (this.compiledMessage.header.numReadonlySignedAccounts + this.compiledMessage.header.numReadonlyUnsignedAccounts);
        },
        enumerable: false,
        configurable: true
    });
    Object.defineProperty(MulticallHandlerCoder.prototype, "compiledKeyMetas", {
        get: function () {
            var _this = this;
            return this.compiledMessage.accountKeys.map(function (key, index) {
                return {
                    pubkey: key,
                    isSigner: _this.compiledMessage.isAccountSigner(index),
                    isWritable: _this.compiledMessage.isAccountWritable(index),
                };
            });
        },
        enumerable: false,
        configurable: true
    });
    MulticallHandlerCoder.prototype.encode = function () {
        var buffer = Buffer.alloc(1280);
        var len = this.layout.encode({ compiledIxs: this.compiledMessage.compiledInstructions }, buffer);
        return buffer.slice(0, len);
    };
    MulticallHandlerCoder.coderArg = {
        name: "compiledIxs",
        type: {
            vec: {
                defined: {
                    name: "compiledIx",
                },
            },
        },
    };
    MulticallHandlerCoder.coderTypes = [
        {
            name: "compiledIx",
            type: {
                kind: "struct",
                fields: [
                    {
                        name: "programIdIndex",
                        type: "u8",
                    },
                    {
                        name: "accountKeyIndexes",
                        type: {
                            vec: "u8",
                        },
                    },
                    {
                        name: "data",
                        type: "bytes",
                    },
                ],
            },
        },
    ];
    return MulticallHandlerCoder;
}());
exports.MulticallHandlerCoder = MulticallHandlerCoder;
var AcrossPlusMessageCoder = (function () {
    function AcrossPlusMessageCoder(acrossPlusMessage) {
        this.acrossPlusMessage = acrossPlusMessage;
    }
    AcrossPlusMessageCoder.prototype.encode = function () {
        var fieldLayouts = [idl_1.IdlCoder.fieldLayout(AcrossPlusMessageCoder.coderArg, AcrossPlusMessageCoder.coderTypes)];
        var layout = borsh.struct(fieldLayouts);
        var buffer = Buffer.alloc(12800);
        var len = layout.encode({ message: this.acrossPlusMessage }, buffer);
        return buffer.slice(0, len);
    };
    AcrossPlusMessageCoder.coderArg = {
        name: "message",
        type: {
            defined: {
                name: "acrossPlusMessage",
            },
        },
    };
    AcrossPlusMessageCoder.coderTypes = [
        {
            name: "acrossPlusMessage",
            type: {
                kind: "struct",
                fields: [
                    {
                        name: "handler",
                        type: "pubkey",
                    },
                    {
                        name: "readOnlyLen",
                        type: "u8",
                    },
                    {
                        name: "valueAmount",
                        type: "u64",
                    },
                    {
                        name: "accounts",
                        type: {
                            vec: "pubkey",
                        },
                    },
                    {
                        name: "handlerMessage",
                        type: "bytes",
                    },
                ],
            },
        },
    ];
    return AcrossPlusMessageCoder;
}());
exports.AcrossPlusMessageCoder = AcrossPlusMessageCoder;
//# sourceMappingURL=coders.js.map