"use strict";

var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");

Object.defineProperty(exports, "__esModule", {
  value: true
});
exports.default = void 0;

var _util = require("@polkadot/util");

var _Enum = _interopRequireDefault(require("../codec/Enum"));

var _Struct = _interopRequireDefault(require("../codec/Struct"));

var _MagicNumber = _interopRequireDefault(require("./MagicNumber"));

var _v = _interopRequireDefault(require("./v2"));

var _v2 = _interopRequireDefault(require("./v3"));

var _v3 = _interopRequireDefault(require("./v4"));

var _v4 = _interopRequireDefault(require("./v5"));

var _v5 = _interopRequireDefault(require("./v6"));

var _v6 = _interopRequireDefault(require("./v7"));

var _v7 = _interopRequireDefault(require("./v8"));

var _toV = _interopRequireDefault(require("./v0/toV1"));

var _toV2 = _interopRequireDefault(require("./v1/toV2"));

var _toV3 = _interopRequireDefault(require("./v2/toV3"));

var _toV4 = _interopRequireDefault(require("./v3/toV4"));

var _toV5 = _interopRequireDefault(require("./v4/toV5"));

var _toV6 = _interopRequireDefault(require("./v5/toV6"));

var _toV7 = _interopRequireDefault(require("./v6/toV7"));

var _toV8 = _interopRequireDefault(require("./v7/toV8"));

var _util2 = require("./util");

// Copyright 2017-2019 @polkadot/types authors & contributors
// This software may be modified and distributed under the terms
// of the Apache-2.0 license. See the LICENSE file for details.
class MetadataEnum extends _Enum.default {
  constructor(value, index) {
    super({
      V0: 'MetadataV0',
      // once rolled-out, can replace this with MetadataDeprecated
      V1: 'MetadataV1',
      // once rolled-out, can replace this with MetadataDeprecated
      V2: _v.default,
      // once rolled-out, can replace this with MetadataDeprecated
      V3: _v2.default,
      // once rolled-out, can replace this with MetadataDeprecated
      V4: _v3.default,
      // once rolled-out, can replace this with MetadataDeprecated
      V5: _v4.default,
      // once rolled-out, can replace this with MetadataDeprecated
      V6: _v5.default,
      // once rolled-out, can replace this with MetadataDeprecated
      V7: _v6.default,
      // once rolled-out, can replace this with MetadataDeprecated
      V8: _v7.default
    }, value, index);
  }
  /**
   * @description Returns the wrapped values as a V0 object
   */


  get asV0() {
    (0, _util.assert)(this.isV0, "Cannot convert '".concat(this.type, "' via asV0"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V1 object
   */


  get asV1() {
    (0, _util.assert)(this.isV1, "Cannot convert '".concat(this.type, "' via asV1"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V2 object
   */


  get asV2() {
    (0, _util.assert)(this.isV2, "Cannot convert '".concat(this.type, "' via asV2"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V3 object
   */


  get asV3() {
    (0, _util.assert)(this.isV3, "Cannot convert '".concat(this.type, "' via asV3"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V4 object
   */


  get asV4() {
    (0, _util.assert)(this.isV4, "Cannot convert '".concat(this.type, "' via asV4"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V5 object
   */


  get asV5() {
    (0, _util.assert)(this.isV5, "Cannot convert '".concat(this.type, "' via asV5"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V6 object
   */


  get asV6() {
    (0, _util.assert)(this.isV6, "Cannot convert '".concat(this.type, "' via asV6"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V7 object
   */


  get asV7() {
    (0, _util.assert)(this.isV7, "Cannot convert '".concat(this.type, "' via asV7"));
    return this.value;
  }
  /**
   * @description Returns the wrapped values as a V8 object
   */


  get asV8() {
    (0, _util.assert)(this.isV8, "Cannot convert '".concat(this.type, "' via asV8"));
    return this.value;
  }
  /**
   * @description `true` if Deprecated
   */


  get isDeprecated() {
    return this.type === 'MetadataDeprectated';
  }
  /**
   * @description `true` if V0
   */


  get isV0() {
    return this.type === 'V0';
  }
  /**
   * @description `true` if V1
   */


  get isV1() {
    return this.type === 'V1';
  }
  /**
   * @description `true` if V2
   */


  get isV2() {
    return this.type === 'V2';
  }
  /**
   * @description `true` if V3
   */


  get isV3() {
    return this.type === 'V3';
  }
  /**
   * @description `true` if V4
   */


  get isV4() {
    return this.type === 'V4';
  }
  /**
   * @description `true` if V5
   */


  get isV5() {
    return this.type === 'V5';
  }
  /**
   * @description `true` if V6
   */


  get isV6() {
    return this.type === 'V6';
  }
  /**
   * @description `true` if V7
   */


  get isV7() {
    return this.type === 'V7';
  }
  /**
   * @description `true` if V8
   */


  get isV8() {
    return this.type === 'V8';
  }

}
/**
 * @name MetadataVersioned
 * @description
 * The versioned runtime metadata as a decoded structure
 */


class MetadataVersioned extends _Struct.default {
  constructor(value) {
    super({
      magicNumber: _MagicNumber.default,
      metadata: MetadataEnum
    }, value);
    this._converted = new Map();
  }

  assertVersion(version) {
    (0, _util.assert)(this.version <= version, "Cannot convert metadata from v".concat(this.version, " to v").concat(version));
    return this.version === version;
  }

  getVersion(version, fromPrev) {
    const asCurr = "asV".concat(version);
    const asPrev = "asV".concat(version - 1);

    if (this.assertVersion(version)) {
      return this.metadata[asCurr];
    }

    if (!this._converted.has(version)) {
      this._converted.set(version, fromPrev(this[asPrev]));
    }

    return this._converted.get(version);
  }
  /**
   * @description Returns the wrapped metadata as a limited calls-only (latest) version
   */


  get asCallsOnly() {
    return new MetadataVersioned({
      magicNumber: this.magicNumber,
      metadata: new MetadataEnum((0, _util2.toCallsOnly)(this.asLatest), this.version)
    });
  }
  /**
   * @description Returns the wrapped metadata as a V0 object
   */


  get asV0() {
    this.assertVersion(0);
    return this.metadata.asV0;
  }
  /**
   * @description Returns the wrapped values as a V1 object
   */


  get asV1() {
    return this.getVersion(1, _toV.default);
  }
  /**
   * @description Returns the wrapped values as a V2 object
   */


  get asV2() {
    return this.getVersion(2, _toV2.default);
  }
  /**
   * @description Returns the wrapped values as a V3 object
   */


  get asV3() {
    return this.getVersion(3, _toV3.default);
  }
  /**
   * @description Returns the wrapped values as a V4 object
   */


  get asV4() {
    return this.getVersion(4, _toV4.default);
  }
  /**
   * @description Returns the wrapped values as a V5 object
   */


  get asV5() {
    return this.getVersion(5, _toV5.default);
  }
  /**
   * @description Returns the wrapped values as a V6 object
   */


  get asV6() {
    return this.getVersion(6, _toV6.default);
  }
  /**
   * @description Returns the wrapped values as a V7 object
   */


  get asV7() {
    return this.getVersion(7, _toV7.default);
  }
  /**
   * @description Returns the wrapped values as a V8 object
   */


  get asV8() {
    return this.getVersion(8, _toV8.default);
  }
  /**
   * @description Returns the wrapped values as a latest version object
   */


  get asLatest() {
    return this.asV8;
  }
  /**
   * @description
   */


  get magicNumber() {
    return this.get('magicNumber');
  }
  /**
   * @description the metadata wrapped
   */


  get metadata() {
    return this.get('metadata');
  }
  /**
   * @description the metadata version this structure represents
   */


  get version() {
    return this.metadata.index;
  }

  getUniqTypes(throwError) {
    return (0, _util2.getUniqTypes)(this.asLatest, throwError);
  }

}

exports.default = MetadataVersioned;