"use strict";
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
    if (k2 === undefined) k2 = k;
    Object.defineProperty(o, k2, { enumerable: true, get: function() { return m[k]; } });
}) : (function(o, m, k, k2) {
    if (k2 === undefined) k2 = k;
    o[k2] = m[k];
}));
var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
    Object.defineProperty(o, "default", { enumerable: true, value: v });
}) : function(o, v) {
    o["default"] = v;
});
var __importStar = (this && this.__importStar) || function (mod) {
    if (mod && mod.__esModule) return mod;
    var result = {};
    if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
    __setModuleDefault(result, mod);
    return result;
};
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());
    });
};
var __importDefault = (this && this.__importDefault) || function (mod) {
    return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
const bignumber_js_1 = __importDefault(require("bignumber.js"));
const sinon_1 = __importDefault(require("sinon"));
const internal_1 = require("../../../../internal");
const mocks_1 = require("../../../../testUtils/mocks");
const types_1 = require("../../../../types");
const utils_1 = require("../../../../types/utils");
const utilsConversionModule = __importStar(require("../../../../utils/conversion"));
const Offerings_1 = require("../Offerings");
jest.mock('~/api/entities/Asset', require("../../../../testUtils/mocks/entities").mockAssetModule('~/api/entities/Asset'));
jest.mock('~/api/entities/Offering', require("../../../../testUtils/mocks/entities").mockOfferingModule('~/api/entities/Offering'));
jest.mock('~/base/Procedure', require("../../../../testUtils/mocks/procedure").mockProcedureModule('~/base/Procedure'));
describe('Offerings class', () => {
    let ticker;
    let asset;
    let context;
    let offerings;
    beforeAll(() => {
        mocks_1.entityMockUtils.initMocks();
        mocks_1.dsMockUtils.initMocks();
        mocks_1.procedureMockUtils.initMocks();
        ticker = 'SOME_ASSET';
    });
    beforeEach(() => {
        context = mocks_1.dsMockUtils.getContextInstance();
        asset = mocks_1.entityMockUtils.getAssetInstance({ ticker });
        offerings = new Offerings_1.Offerings(asset, context);
    });
    afterEach(() => {
        mocks_1.entityMockUtils.reset();
        mocks_1.dsMockUtils.reset();
        mocks_1.procedureMockUtils.reset();
    });
    afterAll(() => {
        mocks_1.dsMockUtils.cleanup();
        mocks_1.procedureMockUtils.cleanup();
    });
    test('should extend namespace', () => {
        expect(Offerings_1.Offerings.prototype instanceof internal_1.Namespace).toBe(true);
    });
    describe('method: launch', () => {
        afterAll(() => {
            sinon_1.default.restore();
        });
        test('should prepare the procedure with the correct arguments and context, and return the resulting transaction queue', () => __awaiter(void 0, void 0, void 0, function* () {
            const expectedQueue = 'someQueue';
            const args = {
                offeringPortfolio: 'otherDid',
                raisingCurrency: 'USD',
                raisingPortfolio: 'someDid',
                name: 'someName',
                tiers: [],
                minInvestment: new bignumber_js_1.default(100),
            };
            mocks_1.procedureMockUtils
                .getPrepareStub()
                .withArgs({ args: Object.assign({ ticker }, args), transformer: undefined }, context)
                .resolves(expectedQueue);
            const queue = yield offerings.launch(args);
            expect(queue).toBe(expectedQueue);
        }));
    });
    describe('method: getOne', () => {
        test('should return the requested Offering', () => __awaiter(void 0, void 0, void 0, function* () {
            mocks_1.entityMockUtils.configureMocks({
                offeringOptions: {
                    ticker,
                },
            });
            const id = new bignumber_js_1.default(1);
            const result = yield offerings.getOne({ id });
            expect(result.id).toEqual(id);
        }));
        test('should throw an error if the Offering does not exist', () => {
            mocks_1.entityMockUtils.configureMocks({
                offeringOptions: {
                    exists: false,
                },
            });
            const id = new bignumber_js_1.default(1);
            return expect(offerings.getOne({ id })).rejects.toThrow('The Offering does not exist');
        });
    });
    describe('method: get', () => {
        let rawTicker;
        let rawName;
        let stringToTickerStub;
        let fundraiserToOfferingDetailsStub;
        let details;
        let fundraisers;
        beforeAll(() => {
            rawTicker = mocks_1.dsMockUtils.createMockTicker(ticker);
            stringToTickerStub = sinon_1.default.stub(utilsConversionModule, 'stringToTicker');
            fundraiserToOfferingDetailsStub = sinon_1.default.stub(utilsConversionModule, 'fundraiserToOfferingDetails');
            const creator = mocks_1.entityMockUtils.getIdentityInstance();
            const name = 'someSto';
            rawName = mocks_1.dsMockUtils.createMockFundraiserName(name);
            const offeringPortfolio = mocks_1.entityMockUtils.getDefaultPortfolioInstance();
            const raisingPortfolio = mocks_1.entityMockUtils.getDefaultPortfolioInstance();
            const venue = mocks_1.entityMockUtils.getVenueInstance();
            const raisingCurrency = 'USD';
            const now = new Date();
            const start = new Date(now.getTime() + 70000);
            const end = new Date(start.getTime() + 70000);
            const minInvestment = new bignumber_js_1.default(100);
            const tiers = [
                {
                    amount: new bignumber_js_1.default(1000),
                    price: new bignumber_js_1.default(50),
                    remaining: new bignumber_js_1.default(300),
                },
            ];
            details = [
                {
                    creator,
                    name,
                    offeringPortfolio,
                    raisingPortfolio,
                    raisingCurrency,
                    start,
                    end,
                    tiers,
                    minInvestment,
                    venue,
                    status: {
                        sale: types_1.OfferingSaleStatus.Closed,
                        timing: types_1.OfferingTimingStatus.Started,
                        balance: types_1.OfferingBalanceStatus.Available,
                    },
                    totalAmount: tiers[0].amount,
                    totalRemaining: tiers[0].remaining,
                },
                {
                    creator,
                    name,
                    offeringPortfolio,
                    raisingPortfolio,
                    raisingCurrency,
                    start,
                    end,
                    tiers,
                    minInvestment,
                    venue,
                    status: {
                        sale: types_1.OfferingSaleStatus.Live,
                        timing: types_1.OfferingTimingStatus.Started,
                        balance: types_1.OfferingBalanceStatus.Available,
                    },
                    totalAmount: tiers[0].amount,
                    totalRemaining: tiers[0].remaining,
                },
            ];
            fundraisers = [
                mocks_1.dsMockUtils.createMockFundraiser({
                    creator: mocks_1.dsMockUtils.createMockIdentityId(creator.did),
                    /* eslint-disable @typescript-eslint/naming-convention */
                    offering_portfolio: mocks_1.dsMockUtils.createMockPortfolioId({
                        did: mocks_1.dsMockUtils.createMockIdentityId(offeringPortfolio.owner.did),
                        kind: mocks_1.dsMockUtils.createMockPortfolioKind('Default'),
                    }),
                    raising_portfolio: mocks_1.dsMockUtils.createMockPortfolioId({
                        did: mocks_1.dsMockUtils.createMockIdentityId(raisingPortfolio.owner.did),
                        kind: mocks_1.dsMockUtils.createMockPortfolioKind('Default'),
                    }),
                    offering_asset: rawTicker,
                    raising_asset: mocks_1.dsMockUtils.createMockTicker(raisingCurrency),
                    venue_id: mocks_1.dsMockUtils.createMockU64(venue.id),
                    tiers: [
                        mocks_1.dsMockUtils.createMockFundraiserTier({
                            total: mocks_1.dsMockUtils.createMockBalance(tiers[0].amount),
                            price: mocks_1.dsMockUtils.createMockBalance(tiers[0].price),
                            remaining: mocks_1.dsMockUtils.createMockBalance(tiers[0].remaining),
                        }),
                    ],
                    start: mocks_1.dsMockUtils.createMockMoment(new bignumber_js_1.default(start.getTime())),
                    end: mocks_1.dsMockUtils.createMockOption(mocks_1.dsMockUtils.createMockMoment(new bignumber_js_1.default(end.getTime()))),
                    minimum_investment: mocks_1.dsMockUtils.createMockBalance(minInvestment),
                    status: mocks_1.dsMockUtils.createMockFundraiserStatus('Closed'),
                }),
                mocks_1.dsMockUtils.createMockFundraiser({
                    creator: mocks_1.dsMockUtils.createMockIdentityId(creator.did),
                    /* eslint-disable @typescript-eslint/naming-convention */
                    offering_portfolio: mocks_1.dsMockUtils.createMockPortfolioId({
                        did: mocks_1.dsMockUtils.createMockIdentityId(offeringPortfolio.owner.did),
                        kind: mocks_1.dsMockUtils.createMockPortfolioKind('Default'),
                    }),
                    raising_portfolio: mocks_1.dsMockUtils.createMockPortfolioId({
                        did: mocks_1.dsMockUtils.createMockIdentityId(raisingPortfolio.owner.did),
                        kind: mocks_1.dsMockUtils.createMockPortfolioKind('Default'),
                    }),
                    offering_asset: rawTicker,
                    raising_asset: mocks_1.dsMockUtils.createMockTicker(raisingCurrency),
                    venue_id: mocks_1.dsMockUtils.createMockU64(venue.id),
                    tiers: [
                        mocks_1.dsMockUtils.createMockFundraiserTier({
                            total: mocks_1.dsMockUtils.createMockBalance(tiers[0].amount),
                            price: mocks_1.dsMockUtils.createMockBalance(tiers[0].price),
                            remaining: mocks_1.dsMockUtils.createMockBalance(tiers[0].remaining),
                        }),
                    ],
                    start: mocks_1.dsMockUtils.createMockMoment(new bignumber_js_1.default(start.getTime())),
                    end: mocks_1.dsMockUtils.createMockOption(mocks_1.dsMockUtils.createMockMoment(new bignumber_js_1.default(end.getTime()))),
                    minimum_investment: mocks_1.dsMockUtils.createMockBalance(minInvestment),
                    status: mocks_1.dsMockUtils.createMockFundraiserStatus('Live'),
                }),
            ];
        });
        beforeEach(() => {
            stringToTickerStub.withArgs(ticker, context).returns(rawTicker);
            fundraiserToOfferingDetailsStub
                .withArgs(fundraisers[0], rawName, context)
                .returns(details[0]);
            fundraiserToOfferingDetailsStub
                .withArgs(fundraisers[1], rawName, context)
                .returns(details[1]);
            mocks_1.dsMockUtils.createQueryStub('sto', 'fundraisers', {
                entries: [
                    utils_1.tuple([rawTicker, mocks_1.dsMockUtils.createMockU64(new bignumber_js_1.default(1))], mocks_1.dsMockUtils.createMockOption(fundraisers[0])),
                    utils_1.tuple([rawTicker, mocks_1.dsMockUtils.createMockU64(new bignumber_js_1.default(2))], mocks_1.dsMockUtils.createMockOption(fundraisers[1])),
                ],
            });
            mocks_1.dsMockUtils.createQueryStub('sto', 'fundraiserNames', {
                entries: [
                    utils_1.tuple([rawTicker, mocks_1.dsMockUtils.createMockU64(new bignumber_js_1.default(1))], rawName),
                    utils_1.tuple([rawTicker, mocks_1.dsMockUtils.createMockU64(new bignumber_js_1.default(2))], rawName),
                ],
            });
        });
        afterAll(() => {
            sinon_1.default.restore();
        });
        test('should return all Offerings associated to the Asset', () => __awaiter(void 0, void 0, void 0, function* () {
            const result = yield offerings.get();
            expect(result[0].offering.id).toEqual(new bignumber_js_1.default(1));
            expect(result[0].details).toEqual(details[0]);
            expect(result[1].offering.id).toEqual(new bignumber_js_1.default(2));
            expect(result[1].details).toEqual(details[1]);
            expect(result.length).toBe(2);
        }));
        test('should return Offerings associated to the Asset filtered by status', () => __awaiter(void 0, void 0, void 0, function* () {
            const result = yield offerings.get({
                status: {
                    sale: types_1.OfferingSaleStatus.Live,
                    timing: types_1.OfferingTimingStatus.Started,
                    balance: types_1.OfferingBalanceStatus.Available,
                },
            });
            expect(result[0].offering.id).toEqual(new bignumber_js_1.default(2));
            expect(result[0].details).toEqual(details[1]);
            expect(result.length).toBe(1);
        }));
    });
});
//# sourceMappingURL=Offerings.js.map