"use strict";
/*!
 * Copyright (c) Microsoft Corporation and contributors. All rights reserved.
 * Licensed under the MIT License.
 */
Object.defineProperty(exports, "__esModule", { value: true });
exports.ReconnectTestHelper = void 0;
const assert_1 = require("assert");
const testClientLogger_1 = require("./testClientLogger.cjs");
const ClientIds = ["A", "B", "C", "D"];
class ReconnectTestHelper {
    constructor() {
        this.clients = (0, testClientLogger_1.createClientsAtInitialState)({
            initialState: "",
            options: { mergeTreeEnableObliterate: true },
        }, ...ClientIds);
        this.logger = new testClientLogger_1.TestClientLogger(this.clients.all);
        this.ops = [];
        this.perClientOps = this.clients.all.map(() => []);
        this.seq = 0;
    }
    idxFromName(name) {
        return name.charCodeAt(0) - "A".charCodeAt(0);
    }
    insertText(clientName, pos, text) {
        const client = this.clients[clientName];
        this.ops.push(client.makeOpMessage(client.insertTextLocal(pos, text), ++this.seq));
    }
    removeRange(clientName, start, end) {
        const client = this.clients[clientName];
        this.ops.push(client.makeOpMessage(client.removeRangeLocal(start, end), ++this.seq));
    }
    obliterateRange(clientName, start, end) {
        const client = this.clients[clientName];
        this.ops.push(client.makeOpMessage(client.obliterateRangeLocal(start, end), ++this.seq));
    }
    insertTextLocal(clientName, pos, text) {
        const client = this.clients[clientName];
        const op = client.insertTextLocal(pos, text);
        (0, assert_1.strict)(op);
        const seg = client.peekPendingSegmentGroups();
        (0, assert_1.strict)(seg);
        return { op, seg, refSeq: client.getCollabWindow().currentSeq };
    }
    removeRangeLocal(clientName, start, end) {
        const client = this.clients[clientName];
        const op = client.removeRangeLocal(start, end);
        (0, assert_1.strict)(op);
        const seg = client.peekPendingSegmentGroups();
        (0, assert_1.strict)(seg);
        return { op, seg, refSeq: client.getCollabWindow().currentSeq };
    }
    obliterateRangeLocal(clientName, start, end) {
        const client = this.clients[clientName];
        const op = client.obliterateRangeLocal(start, end);
        (0, assert_1.strict)(op);
        const seg = client.peekPendingSegmentGroups();
        (0, assert_1.strict)(seg);
        return { op, seg, refSeq: client.getCollabWindow().currentSeq };
    }
    disconnect(clientNames) {
        const clientIdxs = clientNames.map(this.idxFromName);
        this.ops
            .splice(0)
            .forEach((op) => this.clients.all.forEach((c, i) => clientIdxs.includes(i) ? this.perClientOps[i].push(op) : c.applyMsg(op)));
    }
    processAllOps() {
        this.ops.splice(0).forEach((op) => this.clients.all.forEach((c) => {
            c.applyMsg(op);
        }));
    }
    reconnect(clientNames) {
        const clientIdxs = clientNames.map(this.idxFromName);
        this.perClientOps.forEach((clientOps, i) => {
            if (clientIdxs.includes(i)) {
                clientOps.splice(0).forEach((op) => this.clients.all[i].applyMsg(op));
            }
        });
    }
    submitDisconnectedOp(clientName, op) {
        const client = this.clients[clientName];
        this.ops.push(client.makeOpMessage(client.regeneratePendingOp(op.op, op.seg), ++this.seq, op.refSeq));
    }
}
exports.ReconnectTestHelper = ReconnectTestHelper;
//# sourceMappingURL=reconnectHelper.cjs.map