PHP WebShell

Текущая директория: /opt/BitGoJS/modules/utxo-ord/dist/src

Просмотр файла: OutputLayout.js

"use strict";
/*

This file contains code for creating an output layouts for transactions that pass on inscriptions.

When passing on an inscription, we want to satisfy a few constraints:

* All outputs should be larger than a minimal value (dust limit)
* The sum of all output values needs to be less than the input to cover the transaction fee.
* The output containing the inscription should be as small as possible, but large enough to
  contain the inscription.

To keep the inscription output small, we can pad the satoshi range preceding and following the range
with change outputs, which have a minimal size and incur a fee cost.


Broadly speaking, there are four scenarios:

(1) Small inscription input that has just enough value to pay for fee and a single inscription
    output (u0). No padding outputs.
    ┌────────┬────────┐
    │        │ u0     │
    │      r ┼        │
    │        ├────────┘
    │        │ fee
    └────────┘


(2) Large inscription input with inscription close to start of input.
    Inscription output followed by change output (u1) padding the remaining value.

    ┌────────┬────────┐
    │        │ u0     │
    │      r ┼        │
    │        ├────────┤
    │        │ u1     │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        ├────────┘
    │        │
    │        │ fee
    │        │
    └────────┘


(3) Large inscription input with inscription close to end of input.
    Change output padding start followed by inscription output.

    ┌────────┬────────┐
    │        │ u0     │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        ├────────┤
    │      r ┼        │
    │        │ u1     │
    │        ├────────┘
    │        │
    │        │ fee
    │        │
    └────────┘


(4) Large inscription input with inscription in the middle.
    Inscription input (u1) with padding on both sides (u0 and u2)

    ┌────────┬────────┐
    │        │ u0     │
    │        │        │
    │        │        │
    │        │        │
    │        │        │
    │        ├────────┤
    │        │ u1     │
    │      r ┼        │
    │        ├────────┤
    │        │ u2     │
    │        │        │
    │        │        │
    │        │        │
    │        ├────────┘
    │        │
    │        │ fee
    │        │
    └────────┘
 */
Object.defineProperty(exports, "__esModule", { value: true });
exports.toArray = toArray;
exports.toParameters = toParameters;
exports.getOrdOutputsForLayout = getOrdOutputsForLayout;
exports.findOutputLayout = findOutputLayout;
const ZERO = BigInt(0);
const ONE = BigInt(1);
function max(a, b) {
    return a < b ? b : a;
}
function min(a, b) {
    return a < b ? a : b;
}
function sum(arr) {
    return arr.reduce((a, b) => a + b, ZERO);
}
/** @return canonical sequence of parameters */
function toArray(p) {
    return [p.firstChangeOutput, p.inscriptionOutput, p.secondChangeOutput, p.feeOutput];
}
function toParameters(firstChangeOutput, inscriptionOutput, secondChangeOutput, feeOutput) {
    return {
        firstChangeOutput,
        inscriptionOutput,
        secondChangeOutput,
        feeOutput,
    };
}
/**
 * Translates a layout into OrdOutputs. Absent outputs are set to `null`.
 *
 * @param inscriptionInput
 * @param layout
 * @return OrdOutputs for layout
 */
function getOrdOutputsForLayout(inscriptionInput, layout) {
    const outputs = inscriptionInput.splitAllWithParams(toArray(layout), { exact: true, allowZero: true });
    if (outputs.length !== 4) {
        throw new Error(`unexpected result`);
    }
    return toParameters(...outputs);
}
/**
 * @param constraints
 * @param inscriptionInput
 * @param layout
 * @return true iff layout satisfies constraints
 */
function check(constraints, inscriptionInput, layout) {
    if ((layout.firstChangeOutput === ZERO || constraints.minChangeOutput <= layout.firstChangeOutput) &&
        (layout.secondChangeOutput === ZERO || constraints.minChangeOutput <= layout.secondChangeOutput) &&
        constraints.minInscriptionOutput <= layout.inscriptionOutput &&
        layout.inscriptionOutput <= constraints.maxInscriptionOutput &&
        getFeeForOutputs(constraints, [layout.firstChangeOutput, layout.inscriptionOutput, layout.secondChangeOutput]) <=
            layout.feeOutput &&
        sum(toArray(layout)) === inscriptionInput.value) {
        /* make sure inscription actually lies on the inscriptionOutput */
        const outputs = getOrdOutputsForLayout(inscriptionInput, layout);
        return outputs.inscriptionOutput?.ordinals.length === 1;
    }
    return false;
}
function getFeeForOutputs(p, outputs) {
    return outputs.reduce((sum, oValue) => sum + (oValue === ZERO ? ZERO : p.feePerOutput), p.feeFixed);
}
function getStartChangeOutput(c) {
    // we don't need a change padding output
    if (c.satPos < c.maxInscriptionOutput) {
        return ZERO;
    }
    if (c.minChangeOutput <= c.satPos) {
        return c.satPos;
    }
    return null;
}
function getInscriptionOutput(c, startChangeOutput) {
    const result = min(c.maxInscriptionOutput, max(c.minInscriptionOutput, c.satPos - startChangeOutput + ONE));
    if (c.satPos < startChangeOutput || startChangeOutput + result < c.satPos) {
        return null;
    }
    // if is not worth creating an end change output, let's maximize the inscription output
    if (getEndChangeOutput(c, startChangeOutput, result) === ZERO) {
        const remainder = c.total - startChangeOutput - getFeeForOutputs(c, [startChangeOutput, result]);
        return min(remainder, c.maxInscriptionOutput);
    }
    return result;
}
function getEndChangeOutput(c, startChangeOutput, inscriptionOutput) {
    const remainder = c.total - sum([startChangeOutput, inscriptionOutput]);
    const minFeeWithoutSecondOutput = getFeeForOutputs(c, [startChangeOutput, inscriptionOutput]);
    const minFeeWithSecondOutput = getFeeForOutputs(c, [startChangeOutput, inscriptionOutput, c.minChangeOutput]);
    if (remainder < minFeeWithoutSecondOutput) {
        // We cannot even pay the fee for the output(s) we have so far.
        return null;
    }
    if (remainder - minFeeWithSecondOutput < c.minChangeOutput) {
        // The remainder is too small to pay for the end change output. Let's skip it and pay a higher fee.
        return ZERO;
    }
    // let's use as much as we can for fee while leaving enough for fee
    return remainder - minFeeWithSecondOutput;
}
function getFeeOutput(c, startChangeOutput, inscriptionOutput, endChangeOutput) {
    const minFee = getFeeForOutputs(c, [startChangeOutput, inscriptionOutput, endChangeOutput]);
    const remainder = c.total - sum([startChangeOutput, inscriptionOutput, endChangeOutput]);
    if (remainder < minFee) {
        return null;
    }
    return remainder;
}
/**
 * @param inscriptionInput
 * @param search
 * @return a solution that satisfies constraints. If no solution can be found, return `undefined`.
 */
function findOutputLayout(inscriptionInput, search) {
    if (inscriptionInput.ordinals.length !== 1) {
        throw new Error(`unexpected ordinal count ${inscriptionInput.ordinals.length}`);
    }
    if (inscriptionInput.ordinals[0].size() !== ONE) {
        throw new Error(`only single-satoshi inscriptions are supported`);
    }
    const satPos = inscriptionInput.ordinals[0].start;
    const total = inscriptionInput.value;
    const constraints = { ...search, satPos, total };
    const startChangeOutput = getStartChangeOutput(constraints);
    if (startChangeOutput === null) {
        return;
    }
    const inscriptionOutput = getInscriptionOutput(constraints, startChangeOutput);
    if (inscriptionOutput === null) {
        return;
    }
    const endChangeOutput = getEndChangeOutput(constraints, startChangeOutput, inscriptionOutput);
    if (endChangeOutput === null) {
        return;
    }
    const feeOutput = getFeeOutput(constraints, startChangeOutput, inscriptionOutput, endChangeOutput);
    if (feeOutput === null) {
        return;
    }
    const result = toParameters(startChangeOutput, inscriptionOutput, endChangeOutput, feeOutput);
    if (!check(constraints, inscriptionInput, result)) {
        throw new Error(`invalid result`);
    }
    return result;
}
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiT3V0cHV0TGF5b3V0LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vc3JjL091dHB1dExheW91dC50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiO0FBQUE7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7OztHQWdHRzs7QUFrQ0gsMEJBRUM7QUFFRCxvQ0FZQztBQVlELHdEQVVDO0FBcUdELDRDQXFDQztBQTlNRCxNQUFNLElBQUksR0FBRyxNQUFNLENBQUMsQ0FBQyxDQUFDLENBQUM7QUFDdkIsTUFBTSxHQUFHLEdBQUcsTUFBTSxDQUFDLENBQUMsQ0FBQyxDQUFDO0FBRXRCLFNBQVMsR0FBRyxDQUFDLENBQVMsRUFBRSxDQUFTO0lBQy9CLE9BQU8sQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7QUFDdkIsQ0FBQztBQUVELFNBQVMsR0FBRyxDQUFDLENBQVMsRUFBRSxDQUFTO0lBQy9CLE9BQU8sQ0FBQyxHQUFHLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUM7QUFDdkIsQ0FBQztBQUVELFNBQVMsR0FBRyxDQUFDLEdBQWE7SUFDeEIsT0FBTyxHQUFHLENBQUMsTUFBTSxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUMsQ0FBQyxHQUFHLENBQUMsRUFBRSxJQUFJLENBQUMsQ0FBQztBQUMzQyxDQUFDO0FBZ0JELCtDQUErQztBQUMvQyxTQUFnQixPQUFPLENBQUksQ0FBZ0I7SUFDekMsT0FBTyxDQUFDLENBQUMsQ0FBQyxpQkFBaUIsRUFBRSxDQUFDLENBQUMsaUJBQWlCLEVBQUUsQ0FBQyxDQUFDLGtCQUFrQixFQUFFLENBQUMsQ0FBQyxTQUFTLENBQUMsQ0FBQztBQUN2RixDQUFDO0FBRUQs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LGdCQUFnQixDQUFDLEtBQUssQ0FBQztJQUVyQyxNQUFNLFdBQVcsR0FBZ0IsRUFBRSxHQUFHLE1BQU0sRUFBRSxNQUFNLEVBQUUsS0FBSyxFQUFFLENBQUM7SUFFOUQsTUFBTSxpQkFBaUIsR0FBRyxvQkFBb0IsQ0FBQyxXQUFXLENBQUMsQ0FBQztJQUM1RCxJQUFJLGlCQUFpQixLQUFLLElBQUksRUFBRSxDQUFDO1FBQy9CLE9BQU87SUFDVCxDQUFDO0lBQ0QsTUFBTSxpQkFBaUIsR0FBRyxvQkFBb0IsQ0FBQyxXQUFXLEVBQUUsaUJBQWlCLENBQUMsQ0FBQztJQUMvRSxJQUFJLGlCQUFpQixLQUFLLElBQUksRUFBRSxDQUFDO1FBQy9CLE9BQU87SUFDVCxDQUFDO0lBQ0QsTUFBTSxlQUFlLEdBQUcsa0JBQWtCLENBQUMsV0FBVyxFQUFFLGlCQUFpQixFQUFFLGlCQUFpQixDQUFDLENBQUM7SUFDOUYsSUFBSSxlQUFlLEtBQUssSUFBSSxFQUFFLENBQUM7UUFDN0IsT0FBTztJQUNULENBQUM7SUFDRCxNQUFNLFNBQVMsR0FBRyxZQUFZLENBQUMsV0FBVyxFQUFFLGlCQUFpQixFQUFFLGlCQUFpQixFQUFFLGVBQWUsQ0FBQyxDQUFDO0lBQ25HLElBQUksU0FBUyxLQUFLLElBQUksRUFBRSxDQUFDO1FBQ3ZCLE9BQU87SUFDVCxDQUFDO0lBQ0QsTUFBTSxNQUFNLEdBQUcsWUFBWSxDQUFDLGlCQUFpQixFQUFFLGlCQUFpQixFQUFFLGVBQWUsRUFBRSxTQUFTLENBQUMsQ0FBQztJQUM5RixJQUFJLENBQUMsS0FBSyxDQUFDLFdBQVcsRUFBRSxnQkFBZ0IsRUFBRSxNQUFNLENBQUMsRUFBRSxDQUFDO1FBQ2xELE1BQU0sSUFBSSxLQUFLLENBQUMsZ0JBQWdCLENBQUMsQ0FBQztJQUNwQyxDQUFDO0lBQ0QsT0FBTyxNQUFNLENBQUM7QUFDaEIsQ0FBQyIsInNvdXJjZXNDb250ZW50IjpbIi8qXG5cblRoaXMgZmlsZSBjb250YWlucyBjb2RlIGZvciBjcmVhdGluZyBhbiBvdXRwdXQgbGF5b3V0cyBmb3IgdHJhbnNhY3Rpb25zIHRoYXQgcGFzcyBvbiBpbnNjcmlwdGlvbnMuXG5cbldoZW4gcGFzc2luZyBvbiBhbiBpbnNjcmlwdGlvbiwgd2Ugd2FudCB0byBzYXRpc2Z5IGEgZmV3IGNvbnN0cmFpbnRzOlxuXG4qIEFsbCBvdXRwdXRzIHNob3VsZCBiZSBsYXJnZXIgdGhhbiBhIG1pbmltYWwgdmFsdWUgKGR1c3QgbGltaXQpXG4qIFRoZSBzdW0gb2YgYWxsIG91dHB1dCB2YWx1ZXMgbmVlZHMgdG8gYmUgbGVzcyB0aGFuIHRoZSBpbnB1dCB0byBjb3ZlciB0aGUgdHJhbnNhY3Rpb24gZmVlLlxuKiBUaGUgb3V0cHV0IGNvbnRhaW5pbmcgdGhlIGluc2NyaXB0aW9uIHNob3VsZCBiZSBhcyBzbWFsbCBhcyBwb3NzaWJsZSwgYnV0IGxhcmdlIGVub3VnaCB0b1xuICBjb250YWluIHRoZSBpbnNjcmlwdGlvbi5cblxuVG8ga2VlcCB0aGUgaW5zY3JpcHRpb24gb3V0cHV0IHNtYWxsLCB3ZSBjYW4gcGFkIHRoZSBzYXRvc2hpIHJhbmdlIHByZWNlZGluZyBhbmQgZm9sbG93aW5nIHRoZSByYW5nZVxud2l0aCBjaGFuZ2Ugb3V0cHV0cywgd2hpY2ggaGF2ZSBhIG1pbmltYWwgc2l6ZSBhbmQgaW5jdXIgYSBmZWUgY29zdC5cblxuXG5Ccm9hZGx5IHNwZWFraW5nLCB0aGVyZSBhcmUgZm91ciBzY2VuYXJpb3M6XG5cbigxKSBTbWFsbCBpbnNjcmlwdGlvbiBpbnB1dCB0aGF0IGhhcyBqdXN0IGVub3VnaCB2YWx1ZSB0byBwYXkgZm9yIGZlZSBhbmQgYSBzaW5nbGUgaW5zY3JpcHRpb25cbiAgICBvdXRwdXQgKHUwKS4gTm8gcGFkZGluZyBvdXRwdXRzLlxuICAgIOKUjOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUrOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUkFxuICAgIOKUgiAgICAgICAg4pSCIHUwICAgICDilIJcbiAgICDilIIgICAgICByIOKUvCAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilJzilIDilIDilIDilIDilIDilIDilIDilIDilJhcbiAgICDilIIgICAgICAgIOKUgiBmZWVcbiAgICDilJTilIDilIDilIDilIDilIDilIDilIDilIDilJhcblxuXG4oMikgTGFyZ2UgaW5zY3JpcHRpb24gaW5wdXQgd2l0aCBpbnNjcmlwdGlvbiBjbG9zZSB0byBzdGFydCBvZiBpbnB1dC5cbiAgICBJbnNjcmlwdGlvbiBvdXRwdXQgZm9sbG93ZWQgYnkgY2hhbmdlIG91dHB1dCAodTEpIHBhZGRpbmcgdGhlIHJlbWFpbmluZyB2YWx1ZS5cblxuICAgIOKUjOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUrOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUkFxuICAgIOKUgiAgICAgICAg4pSCIHUwICAgICDilIJcbiAgICDilIIgICAgICByIOKUvCAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilJzilIDilIDilIDilIDilIDilIDilIDilIDilKRcbiAgICDilIIgICAgICAgIOKUgiB1MSAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilJzilIDilIDilIDilIDilIDilIDilIDilIDilJhcbiAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCIGZlZVxuICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSU4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSYXG5cblxuKDMpIExhcmdlIGluc2NyaXB0aW9uIGlucHV0IHdpdGggaW5zY3JpcHRpb24gY2xvc2UgdG8gZW5kIG9mIGlucHV0LlxuICAgIENoYW5nZSBvdXRwdXQgcGFkZGluZyBzdGFydCBmb2xsb3dlZCBieSBpbnNjcmlwdGlvbiBvdXRwdXQuXG5cbiAgICDilIzilIDilIDilIDilIDilIDilIDilIDilIDilKzilIDilIDilIDilIDilIDilIDilIDilIDilJBcbiAgICDilIIgICAgICAgIOKUgiB1MCAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUnOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUpFxuICAgIOKUgiAgICAgIHIg4pS8ICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiB1MSAgICAg4pSCXG4gICAg4pSCICAgICAgICDilJzilIDilIDilIDilIDilIDilIDilIDilIDilJhcbiAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCIGZlZVxuICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSU4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSYXG5cblxuKDQpIExhcmdlIGluc2NyaXB0aW9uIGlucHV0IHdpdGggaW5zY3JpcHRpb24gaW4gdGhlIG1pZGRsZS5cbiAgICBJbnNjcmlwdGlvbiBpbnB1dCAodTEpIHdpdGggcGFkZGluZyBvbiBib3RoIHNpZGVzICh1MCBhbmQgdTIpXG5cbiAgICDilIzilIDilIDilIDilIDilIDilIDilIDilIDilKzilIDilIDilIDilIDilIDilIDilIDilIDilJBcbiAgICDilIIgICAgICAgIOKUgiB1MCAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSc4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSA4pSkXG4gICAg4pSCICAgICAgICDilIIgdTEgICAgIOKUglxuICAgIOKUgiAgICAgIHIg4pS8ICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUnOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUpFxuICAgIOKUgiAgICAgICAg4pSCIHUyICAgICDilIJcbiAgICDilIIgICAgICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgICAgICAgIOKUglxuICAgIOKUgiAgICAgICAg4pSCICAgICAgICDilIJcbiAgICDilIIgICAgICAgIOKUnOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUgOKUmFxuICAgIOKUgiAgICAgICAg4pSCXG4gICAg4pSCICAgICAgICDilIIgZmVlXG4gICAg4pSCICAgICAgICDilIJcbiAgICDilJTilIDilIDilIDilIDilIDilIDilIDilIDilJhcbiAqL1xuXG5pbXBvcnQgeyBPcmRPdXRwdXQgfSBmcm9tICcuL09yZE91dHB1dCc7XG5cbmNvbnN0IFpFUk8gPSBCaWdJbnQoMCk7XG5jb25zdCBPTkUgPSBCaWdJbnQoMSk7XG5cbmZ1bmN0aW9uIG1heChhOiBiaWdpbnQsIGI6IGJpZ2ludCk6IGJpZ2ludCB7XG4gIHJldHVybiBhIDwgYiA/IGIgOiBhO1xufVxuXG5mdW5jdGlvbiBtaW4oYTogYmlnaW50LCBiOiBiaWdpbnQpOiBiaWdpbnQge1xuICByZXR1cm4gYSA8IGIgPyBhIDogYjtcbn1cblxuZnVuY3Rpb24gc3VtKGFycjogYmlnaW50W10pOiBiaWdpbnQge1xuICByZXR1cm4gYXJyLnJlZHVjZSgoYSwgYikgPT4gYSArIGIsIFpFUk8pO1xufVxuXG4vKipcbiAqIEEgcmFuZ2UgY29uc3RyYWludFxuICovXG50eXBlIFBhcmFtZXRlcnM8VD4gPSB7XG4gIC8qKiBQYWRkaW5nIHByZWNlZGluZyB0aGUgaW5zY3JpcHRpb24gb3V0cHV0ICovXG4gIGZpcnN0Q2hhbmdlT3V0cHV0OiBUO1xuICAvKiogVGhlIGluc2NyaXB0aW9uIG91dHB1dCB0aGF0IHdpbGwgaW5oZXJpdCB0aGUgaW5wdXQgaW5zY3JpcHRpb24gKi9cbiAgaW5zY3JpcHRpb25PdXRwdXQ6IFQ7XG4gIC8qKiBQYWRkaW5nIGZvbGxvd2luZyB0aGUgaW5zY3JpcHRpb24gb3V0cHV0ICovXG4gIHNlY29uZENoYW5nZU91dHB1dDogVDtcbiAgLyoqIE5vdCBhIHJlYWwgb3V0cHV0LCB1c2VkIG9ubHkgdG8gc2ltcGxpZnkgY2FsY3VsYXRpb25zICovXG4gIGZlZU91dHB1dDogVDtcbn07XG5cbi8qKiBAcmV0dXJuIGNhbm9uaWNhbCBzZXF1ZW5jZSBvZiBwYXJhbWV0ZXJzICovXG5leHBvcnQgZnVuY3Rpb24gdG9BcnJheTxUPihwOiBQYXJhbWV0ZXJzPFQ+KTogW1QsIFQsIFQsIFRdIHtcbiAgcmV0dXJuIFtwLmZpcnN0Q2hhbmdlT3V0cHV0LCBwLmluc2NyaXB0aW9uT3V0cHV0LCBwLnNlY29uZENoYW5nZU91dHB1dCwgcC5mZWVPdXRwdXRdO1xufVxuXG5leHBvcnQgZnVuY3Rpb24gdG9QYXJhbWV0ZXJzPFQ+KFxuICBmaXJzdENoYW5nZU91dHB1dDogVCxcbiAgaW5zY3JpcHRpb25PdXRwdXQ6IFQsXG4gIHNlY29uZENoYW5nZU91dHB1dDogVCxcbiAgZmVlT3V0cHV0OiBUXG4pOiBQYXJhbWV0ZXJzPFQ+IHtcbiAgcmV0dXJuIHtcbiAgICBmaXJzdENoYW5nZU91dHB1dCxcbiAgICBpbnNjcmlwdGlvbk91dHB1dCxcbiAgICBzZWNvbmRDaGFuZ2VPdXRwdXQsXG4gICAgZmVlT3V0cHV0LFxuICB9O1xufVxuXG4vKiogQSBmaW5pc2hlZCBvdXRwdXQgbGF5b3V0ICovXG5leHBvcnQgdHlwZSBPdXRwdXRMYXlvdXQgPSBQYXJhbWV0ZXJzPGJpZ2ludD47XG5cbi8qKlxuICogVHJhbnNsYXRlcyBhIGxheW91dCBpbnRvIE9yZE91dHB1dHMuIEFic2VudCBvdXRwdXRzIGFyZSBzZXQgdG8gYG51bGxgLlxuICpcbiAqIEBwYXJhbSBpbnNjcmlwdGlvbklucHV0XG4gKiBAcGFyYW0gbGF5b3V0XG4gKiBAcmV0dXJuIE9yZE91dHB1dHMgZm9yIGxheW91dFxuICovXG5leHBvcnQgZnVuY3Rpb24gZ2V0T3JkT3V0cHV0c0ZvckxheW91dChcbiAgaW5zY3JpcHRpb25JbnB1dDogT3JkT3V0cHV0LFxuICBsYXlvdXQ6IE91dHB1dExheW91dFxuKTogUGFyYW1ldGVyczxPcmRPdXRwdXQgfCBudWxsPiB7XG4gIGNvbnN0IG91dHB1dHMgPSBpbnNjcmlwdGlvbklucHV0LnNwbGl0QWxsV2l0aFBhcmFtcyh0b0FycmF5KGxheW91dCksIHsgZXhhY3Q6IHRydWUsIGFsbG93WmVybzogdHJ1ZSB9KTtcbiAgaWYgKG91dHB1dHMubGVuZ3RoICE9PSA0KSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKGB1bmV4cGVjdGVkIHJlc3VsdGApO1xuICB9XG4gIHR5cGUgVCA9IE9yZE91dHB1dCB8IG51bGw7XG4gIHJldHVybiB0b1BhcmFtZXRlcnMoLi4uKG91dHB1dHMgYXMgW1QsIFQsIFQsIFRdKSk7XG59XG5cbi8qKlxuICogQHBhcmFtIGNvbnN0cmFpbnRzXG4gKiBAcGFyYW0gaW5zY3JpcHRpb25JbnB1dFxuICogQHBhcmFtIGxheW91dFxuICogQHJldHVybiB0cnVlIGlmZiBsYXlvdXQgc2F0aXNmaWVzIGNvbnN0cmFpbnRzXG4gKi9cbmZ1bmN0aW9uIGNoZWNrKGNvbnN0cmFpbnRzOiBDb25zdHJhaW50cywgaW5zY3JpcHRpb25JbnB1dDogT3JkT3V0cHV0LCBsYXlvdXQ6IE91dHB1dExheW91dCk6IGJvb2xlYW4ge1xuICBpZiAoXG4gICAgKGxheW91dC5maXJzdENoYW5nZU91dHB1dCA9PT0gWkVSTyB8fCBjb25zdHJhaW50cy5taW5DaGFuZ2VPdXRwdXQgPD0gbGF5b3V0LmZpcnN0Q2hhbmdlT3V0cHV0KSAmJlxuICAgIChsYXlvdXQuc2Vjb25kQ2hhbmdlT3V0cHV0ID09PSBaRVJPIHx8IGNvbnN0cmFpbnRzLm1pbkNoYW5nZU91dHB1dCA8PSBsYXlvdXQuc2Vjb25kQ2hhbmdlT3V0cHV0KSAmJlxuICAgIGNvbnN0cmFpbnRzLm1pbkluc2NyaXB0aW9uT3V0cHV0IDw9IGxheW91dC5pbnNjcmlwdGlvbk91dHB1dCAmJlxuICAgIGxheW91dC5pbnNjcmlwdGlvbk91dHB1dCA8PSBjb25zdHJhaW50cy5tYXhJbnNjcmlwdGlvbk91dHB1dCAmJlxuICAgIGdldEZlZUZvck91dHB1dHMoY29uc3RyYWludHMsIFtsYXlvdXQuZmlyc3RDaGFuZ2VPdXRwdXQsIGxheW91dC5pbnNjcmlwdGlvbk91dHB1dCwgbGF5b3V0LnNlY29uZENoYW5nZU91dHB1dF0pIDw9XG4gICAgICBsYXlvdXQuZmVlT3V0cHV0ICYmXG4gICAgc3VtKHRvQXJyYXkobGF5b3V0KSkgPT09IGluc2NyaXB0aW9uSW5wdXQudmFsdWVcbiAgKSB7XG4gICAgLyogbWFrZSBzdXJlIGluc2NyaXB0aW9uIGFjdHVhbGx5IGxpZXMgb24gdGhlIGluc2NyaXB0aW9uT3V0cHV0ICovXG4gICAgY29uc3Qgb3V0cHV0cyA9IGdldE9yZE91dHB1dHNGb3JMYXlvdXQoaW5zY3JpcHRpb25JbnB1dCwgbGF5b3V0KTtcbiAgICByZXR1cm4gb3V0cHV0cy5pbnNjcmlwdGlvbk91dHB1dD8ub3JkaW5hbHMubGVuZ3RoID09PSAxO1xuICB9XG5cbiAgcmV0dXJuIGZhbHNlO1xufVxuXG4vKipcbiAqIEhpZ2gtbGV2ZWwgY29uc3RyYWludHMgZm9yIG91dHB1dCBsYXlvdXRcbiAqL1xuZXhwb3J0IHR5cGUgQ29uc3RyYWludHMgPSB7XG4gIG1pbkNoYW5nZU91dHB1dDogYmlnaW50O1xuICBtaW5JbnNjcmlwdGlvbk91dHB1dDogYmlnaW50O1xuICBtYXhJbnNjcmlwdGlvbk91dHB1dDogYmlnaW50O1xuICBmZWVGaXhlZDogYmlnaW50O1xuICBmZWVQZXJPdXRwdXQ6IGJpZ2ludDtcbiAgc2F0UG9zOiBiaWdpbnQ7XG4gIHRvdGFsOiBiaWdpbnQ7XG59O1xuXG5mdW5jdGlvbiBnZXRGZWVGb3JPdXRwdXRzKHA6IHsgZmVlUGVyT3V0cHV0OiBiaWdpbnQ7IGZlZUZpeGVkOiBiaWdpbnQgfSwgb3V0cHV0czogYmlnaW50W10pOiBiaWdpbnQge1xuICByZXR1cm4gb3V0cHV0cy5yZWR1Y2UoKHN1bSwgb1ZhbHVlKTogYmlnaW50ID0+IHN1bSArIChvVmFsdWUgPT09IFpFUk8gPyBaRVJPIDogcC5mZWVQZXJPdXRwdXQpLCBwLmZlZUZpeGVkKTtcbn1cbmZ1bmN0aW9uIGdldFN0YXJ0Q2hhbmdlT3V0cHV0KGM6IENvbnN0cmFpbnRzKTogYmlnaW50IHwgbnVsbCB7XG4gIC8vIHdlIGRvbid0IG5lZWQgYSBjaGFuZ2UgcGFkZGluZyBvdXRwdXRcbiAgaWYgKGMuc2F0UG9zIDwgYy5tYXhJbnNjcmlwdGlvbk91dHB1dCkge1xuICAgIHJldHVybiBaRVJPO1xuICB9XG4gIGlmIChjLm1pbkNoYW5nZU91dHB1dCA8PSBjLnNhdFBvcykge1xuICAgIHJldHVybiBjLnNhdFBvcztcbiAgfVxuICByZXR1cm4gbnVsbDtcbn1cblxuZnVuY3Rpb24gZ2V0SW5zY3JpcHRpb25PdXRwdXQoYzogQ29uc3RyYWludHMsIHN0YXJ0Q2hhbmdlT3V0cHV0OiBiaWdpbnQpOiBiaWdpbnQgfCBudWxsIHtcbiAgY29uc3QgcmVzdWx0ID0gbWluKGMubWF4SW5zY3JpcHRpb25PdXRwdXQsIG1heChjLm1pbkluc2NyaXB0aW9uT3V0cHV0LCBjLnNhdFBvcyAtIHN0YXJ0Q2hhbmdlT3V0cHV0ICsgT05FKSk7XG4gIGlmIChjLnNhdFBvcyA8IHN0YXJ0Q2hhbmdlT3V0cHV0IHx8IHN0YXJ0Q2hhbmdlT3V0cHV0ICsgcmVzdWx0IDwgYy5zYXRQb3MpIHtcbiAgICByZXR1cm4gbnVsbDtcbiAgfVxuICAvLyBpZiBpcyBub3Qgd29ydGggY3JlYXRpbmcgYW4gZW5kIGNoYW5nZSBvdXRwdXQsIGxldCdzIG1heGltaXplIHRoZSBpbnNjcmlwdGlvbiBvdXRwdXRcbiAgaWYgKGdldEVuZENoYW5nZU91dHB1dChjLCBzdGFydENoYW5nZU91dHB1dCwgcmVzdWx0KSA9PT0gWkVSTykge1xuICAgIGNvbnN0IHJlbWFpbmRlciA9IGMudG90YWwgLSBzdGFydENoYW5nZU91dHB1dCAtIGdldEZlZUZvck91dHB1dHMoYywgW3N0YXJ0Q2hhbmdlT3V0cHV0LCByZXN1bHRdKTtcbiAgICByZXR1cm4gbWluKHJlbWFpbmRlciwgYy5tYXhJbnNjcmlwdGlvbk91dHB1dCk7XG4gIH1cbiAgcmV0dXJuIHJlc3VsdDtcbn1cblxuZnVuY3Rpb24gZ2V0RW5kQ2hhbmdlT3V0cHV0KGM6IENvbnN0cmFpbnRzLCBzdGFydENoYW5nZU91dHB1dDogYmlnaW50LCBpbnNjcmlwdGlvbk91dHB1dDogYmlnaW50KTogYmlnaW50IHwgbnVsbCB7XG4gIGNvbnN0IHJlbWFpbmRlciA9IGMudG90YWwgLSBzdW0oW3N0YXJ0Q2hhbmdlT3V0cHV0LCBpbnNjcmlwdGlvbk91dHB1dF0pO1xuICBjb25zdCBtaW5GZWVXaXRob3V0U2Vjb25kT3V0cHV0ID0gZ2V0RmVlRm9yT3V0cHV0cyhjLCBbc3RhcnRDaGFuZ2VPdXRwdXQsIGluc2NyaXB0aW9uT3V0cHV0XSk7XG4gIGNvbnN0IG1pbkZlZVdpdGhTZWNvbmRPdXRwdXQgPSBnZXRGZWVGb3JPdXRwdXRzKGMsIFtzdGFydENoYW5nZU91dHB1dCwgaW5zY3JpcHRpb25PdXRwdXQsIGMubWluQ2hhbmdlT3V0cHV0XSk7XG4gIGlmIChyZW1haW5kZXIgPCBtaW5GZWVXaXRob3V0U2Vjb25kT3V0cHV0KSB7XG4gICAgLy8gV2UgY2Fubm90IGV2ZW4gcGF5IHRoZSBmZWUgZm9yIHRoZSBvdXRwdXQocykgd2UgaGF2ZSBzbyBmYXIuXG4gICAgcmV0dXJuIG51bGw7XG4gIH1cbiAgaWYgKHJlbWFpbmRlciAtIG1pbkZlZVdpdGhTZWNvbmRPdXRwdXQgPCBjLm1pbkNoYW5nZU91dHB1dCkge1xuICAgIC8vIFRoZSByZW1haW5kZXIgaXMgdG9vIHNtYWxsIHRvIHBheSBmb3IgdGhlIGVuZCBjaGFuZ2Ugb3V0cHV0LiBMZXQncyBza2lwIGl0IGFuZCBwYXkgYSBoaWdoZXIgZmVlLlxuICAgIHJldHVybiBaRVJPO1xuICB9XG4gIC8vIGxldCdzIHVzZSBhcyBtdWNoIGFzIHdlIGNhbiBmb3IgZmVlIHdoaWxlIGxlYXZpbmcgZW5vdWdoIGZvciBmZWVcbiAgcmV0dXJuIHJlbWFpbmRlciAtIG1pbkZlZVdpdGhTZWNvbmRPdXRwdXQ7XG59XG5cbmZ1bmN0aW9uIGdldEZlZU91dHB1dChcbiAgYzogQ29uc3RyYWludHMsXG4gIHN0YXJ0Q2hhbmdlT3V0cHV0OiBiaWdpbnQsXG4gIGluc2NyaXB0aW9uT3V0cHV0OiBiaWdpbnQsXG4gIGVuZENoYW5nZU91dHB1dDogYmlnaW50XG4pOiBiaWdpbnQgfCBudWxsIHtcbiAgY29uc3QgbWluRmVlID0gZ2V0RmVlRm9yT3V0cHV0cyhjLCBbc3RhcnRDaGFuZ2VPdXRwdXQsIGluc2NyaXB0aW9uT3V0cHV0LCBlbmRDaGFuZ2VPdXRwdXRdKTtcbiAgY29uc3QgcmVtYWluZGVyID0gYy50b3RhbCAtIHN1bShbc3RhcnRDaGFuZ2VPdXRwdXQsIGluc2NyaXB0aW9uT3V0cHV0LCBlbmRDaGFuZ2VPdXRwdXRdKTtcbiAgaWYgKHJlbWFpbmRlciA8IG1pbkZlZSkge1xuICAgIHJldHVybiBudWxsO1xuICB9XG4gIHJldHVybiByZW1haW5kZXI7XG59XG5cbi8qKlxuICogQHBhcmFtIGluc2NyaXB0aW9uSW5wdXRcbiAqIEBwYXJhbSBzZWFyY2hcbiAqIEByZXR1cm4gYSBzb2x1dGlvbiB0aGF0IHNhdGlzZmllcyBjb25zdHJhaW50cy4gSWYgbm8gc29sdXRpb24gY2FuIGJlIGZvdW5kLCByZXR1cm4gYHVuZGVmaW5lZGAuXG4gKi9cbmV4cG9ydCBmdW5jdGlvbiBmaW5kT3V0cHV0TGF5b3V0KFxuICBpbnNjcmlwdGlvbklucHV0OiBPcmRPdXRwdXQsXG4gIHNlYXJjaDogT21pdDxDb25zdHJhaW50cywgJ3NhdFBvcycgfCAndG90YWwnPlxuKTogT3V0cHV0TGF5b3V0IHwgdW5kZWZpbmVkIHtcbiAgaWYgKGluc2NyaXB0aW9uSW5wdXQub3JkaW5hbHMubGVuZ3RoICE9PSAxKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKGB1bmV4cGVjdGVkIG9yZGluYWwgY291bnQgJHtpbnNjcmlwdGlvbklucHV0Lm9yZGluYWxzLmxlbmd0aH1gKTtcbiAgfVxuICBpZiAoaW5zY3JpcHRpb25JbnB1dC5vcmRpbmFsc1swXS5zaXplKCkgIT09IE9ORSkge1xuICAgIHRocm93IG5ldyBFcnJvcihgb25seSBzaW5nbGUtc2F0b3NoaSBpbnNjcmlwdGlvbnMgYXJlIHN1cHBvcnRlZGApO1xuICB9XG5cbiAgY29uc3Qgc2F0UG9zID0gaW5zY3JpcHRpb25JbnB1dC5vcmRpbmFsc1swXS5zdGFydDtcbiAgY29uc3QgdG90YWwgPSBpbnNjcmlwdGlvbklucHV0LnZhbHVlO1xuXG4gIGNvbnN0IGNvbnN0cmFpbnRzOiBDb25zdHJhaW50cyA9IHsgLi4uc2VhcmNoLCBzYXRQb3MsIHRvdGFsIH07XG5cbiAgY29uc3Qgc3RhcnRDaGFuZ2VPdXRwdXQgPSBnZXRTdGFydENoYW5nZU91dHB1dChjb25zdHJhaW50cyk7XG4gIGlmIChzdGFydENoYW5nZU91dHB1dCA9PT0gbnVsbCkge1xuICAgIHJldHVybjtcbiAgfVxuICBjb25zdCBpbnNjcmlwdGlvbk91dHB1dCA9IGdldEluc2NyaXB0aW9uT3V0cHV0KGNvbnN0cmFpbnRzLCBzdGFydENoYW5nZU91dHB1dCk7XG4gIGlmIChpbnNjcmlwdGlvbk91dHB1dCA9PT0gbnVsbCkge1xuICAgIHJldHVybjtcbiAgfVxuICBjb25zdCBlbmRDaGFuZ2VPdXRwdXQgPSBnZXRFbmRDaGFuZ2VPdXRwdXQoY29uc3RyYWludHMsIHN0YXJ0Q2hhbmdlT3V0cHV0LCBpbnNjcmlwdGlvbk91dHB1dCk7XG4gIGlmIChlbmRDaGFuZ2VPdXRwdXQgPT09IG51bGwpIHtcbiAgICByZXR1cm47XG4gIH1cbiAgY29uc3QgZmVlT3V0cHV0ID0gZ2V0RmVlT3V0cHV0KGNvbnN0cmFpbnRzLCBzdGFydENoYW5nZU91dHB1dCwgaW5zY3JpcHRpb25PdXRwdXQsIGVuZENoYW5nZU91dHB1dCk7XG4gIGlmIChmZWVPdXRwdXQgPT09IG51bGwpIHtcbiAgICByZXR1cm47XG4gIH1cbiAgY29uc3QgcmVzdWx0ID0gdG9QYXJhbWV0ZXJzKHN0YXJ0Q2hhbmdlT3V0cHV0LCBpbnNjcmlwdGlvbk91dHB1dCwgZW5kQ2hhbmdlT3V0cHV0LCBmZWVPdXRwdXQpO1xuICBpZiAoIWNoZWNrKGNvbnN0cmFpbnRzLCBpbnNjcmlwdGlvbklucHV0LCByZXN1bHQpKSB7XG4gICAgdGhyb3cgbmV3IEVycm9yKGBpbnZhbGlkIHJlc3VsdGApO1xuICB9XG4gIHJldHVybiByZXN1bHQ7XG59XG4iXX0=

Выполнить команду


Для локальной разработки. Не используйте в интернете!