"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var ts = require("./typesystem");
var ms = require("./metainfo");
var typesystem_1 = require("./typesystem");
var restrictions_1 = require("./restrictions");
var metainfo_1 = require("./metainfo");
var metainfo_2 = require("./metainfo");
var restrictions_2 = require("./restrictions");
var FacetPrototype = /** @class */ (function () {
    function FacetPrototype(_construct, _constructWithValue) {
        this._construct = _construct;
        this._constructWithValue = _constructWithValue;
    }
    FacetPrototype.prototype.isSimple = function () {
        return this._constructWithValue != null;
    };
    FacetPrototype.prototype.newInstance = function () {
        return this._construct();
    };
    FacetPrototype.prototype.createWithValue = function (v) {
        return this._constructWithValue(v);
    };
    FacetPrototype.prototype.isApplicable = function (t) {
        var instance = this.newInstance();
        var requiredType = instance.requiredType();
        var requiredTypes = instance.requiredTypes();
        if (requiredTypes && requiredTypes.length > 0) {
            return requiredTypes.some(function (currentRType) { return t.isSubTypeOf(currentRType); });
        }
        else {
            return t.isSubTypeOf(requiredType);
        }
    };
    FacetPrototype.prototype.isInheritable = function () {
        return this.newInstance().isInheritable();
    };
    FacetPrototype.prototype.isConstraint = function () {
        return this.newInstance() instanceof ts.Constraint;
    };
    FacetPrototype.prototype.isMeta = function () {
        return !this.isConstraint();
    };
    FacetPrototype.prototype.name = function () {
        return this.newInstance().facetName();
    };
    return FacetPrototype;
}());
exports.FacetPrototype = FacetPrototype;
var Registry = /** @class */ (function () {
    function Registry() {
        var _this = this;
        this.constraints = [
            new FacetPrototype(function () { return new restrictions_1.MinProperties(1); }, function (x) { return new restrictions_1.MinProperties(x); }),
            new FacetPrototype(function () { return new restrictions_1.MaxProperties(1); }, function (x) { return new restrictions_1.MaxProperties(x); }),
            new FacetPrototype(function () { return new restrictions_1.MinItems(1); }, function (x) { return new restrictions_1.MinItems(x); }),
            new FacetPrototype(function () { return new restrictions_1.MaxItems(1); }, function (x) { return new restrictions_1.MaxItems(x); }),
            new FacetPrototype(function () { return new restrictions_1.MinLength(1); }, function (x) { return new restrictions_1.MinLength(x); }),
            new FacetPrototype(function () { return new restrictions_1.MaxLength(1); }, function (x) { return new restrictions_1.MaxLength(x); }),
            new FacetPrototype(function () { return new restrictions_1.Minimum(1); }, function (x) { return new restrictions_1.Minimum(x); }),
            new FacetPrototype(function () { return new restrictions_2.MultipleOf(1); }, function (x) { return new restrictions_2.MultipleOf(x); }),
            new FacetPrototype(function () { return new restrictions_1.Maximum(1); }, function (x) { return new restrictions_1.Maximum(x); }),
            new FacetPrototype(function () { return new restrictions_1.Enum([""]); }, function (x) { return new restrictions_1.Enum(x); }),
            new FacetPrototype(function () { return new restrictions_1.Pattern("."); }, function (x) { return new restrictions_1.Pattern(x); }),
            new FacetPrototype(function () { return new restrictions_1.Format(""); }, function (x) { return new restrictions_1.Format(x); }),
            new FacetPrototype(function () { return new restrictions_1.PropertyIs("x", ts.ANY); }, null),
            new FacetPrototype(function () { return new restrictions_1.AdditionalPropertyIs(ts.ANY); }, null),
            new FacetPrototype(function () { return new restrictions_1.MapPropertyIs(".", ts.ANY); }, null),
            new FacetPrototype(function () { return new restrictions_1.HasProperty("x"); }, null),
            new FacetPrototype(function () { return new restrictions_1.UniqueItems(true); }, function (x) { return new restrictions_1.UniqueItems(x); }),
            new FacetPrototype(function () { return new restrictions_1.ComponentShouldBeOfType(ts.ANY); }, null),
            new FacetPrototype(function () { return new restrictions_1.KnownPropertyRestriction(false); }, function (x) { return new restrictions_1.KnownPropertyRestriction(x); }),
            new FacetPrototype(function () { return new restrictions_1.FileTypes([""]); }, function (x) { return new restrictions_1.FileTypes(x); }),
        ];
        this.meta = [
            new FacetPrototype(function () { return new ms.Discriminator("kind"); }, function (x) { return new ms.Discriminator(x); }),
            new FacetPrototype(function () { return new ms.DiscriminatorValue("x"); }, function (x) { return new ms.DiscriminatorValue(x); }),
            new FacetPrototype(function () { return new metainfo_1.Default(""); }, function (x) { return new metainfo_1.Default(x); }),
            //new FacetPrototype(()=>new Usage(""), (x)=>new Usage(x)),//X
            new FacetPrototype(function () { return new metainfo_1.Example(""); }, function (x) { return new metainfo_1.Example(x); }),
            new FacetPrototype(function () { return new metainfo_2.Required(true); }, function (x) { return new metainfo_2.Required(x); }),
            new FacetPrototype(function () { return new ms.Examples({}); }, function (x) { return new ms.Examples(x); }),
            new FacetPrototype(function () { return new metainfo_1.Description(""); }, function (x) { return new metainfo_1.Description(x); }),
            new FacetPrototype(function () { return new metainfo_1.DisplayName(""); }, function (x) { return new metainfo_1.DisplayName(x); }),
            new FacetPrototype(function () { return new typesystem_1.Abstract(); }, function (x) { return new typesystem_1.Abstract(); }),
            new FacetPrototype(function () { return new typesystem_1.Polymorphic(); }, function (x) { return new typesystem_1.Polymorphic(); }),
            new FacetPrototype(function () { return new metainfo_2.XMLInfo({}); }, function (x) { return new metainfo_2.XMLInfo(x); }),
            new FacetPrototype(function () { return new metainfo_2.AllowedTargets({}); }, function (x) { return new metainfo_2.AllowedTargets(x); }),
            new FacetPrototype(function () { return new metainfo_1.SourceMap({}); }, function (x) { return new metainfo_1.SourceMap(x); }),
            new FacetPrototype(function () { return new metainfo_1.ParserMetadata({}); }, function (x) { return new metainfo_1.ParserMetadata(x); })
        ];
        this.known = {};
        this.allPrototypes().forEach(function (x) { return _this.known[x.name()] = x; });
    }
    Registry.prototype.allPrototypes = function () {
        return this.meta.concat(this.constraints);
    };
    Registry.prototype.buildFacet = function (n, value) {
        if (this.known.hasOwnProperty(n) && this.known[n].isSimple()) {
            return this.known[n].createWithValue(value);
        }
        return null;
    };
    Registry.prototype.facetPrototypeWithName = function (n) {
        if (this.known.hasOwnProperty(n)) {
            return this.known[n];
        }
        return null;
    };
    Registry.prototype.applyableTo = function (t) {
        return this.allPrototypes().filter(function (x) { return x.isApplicable(t); });
    };
    Registry.prototype.allMeta = function () {
        return this.allPrototypes().filter(function (x) { return x.isMeta(); });
    };
    return Registry;
}());
exports.Registry = Registry;
var instance;
function getInstance() {
    if (instance) {
        return instance;
    }
    instance = new Registry();
    return instance;
}
exports.getInstance = getInstance;
//# sourceMappingURL=facetRegistry.js.map