"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.schemaKeywords = void 0; const applicability_1 = require("./applicability"); const dataType_1 = require("./dataType"); const defaults_1 = require("./defaults"); const keyword_1 = require("./keyword"); const util_1 = require("../util"); const _1 = require("."); const codegen_1 = require("../codegen"); const names_1 = require("../names"); function schemaKeywords(it, types, typeErrors, errsCount) { const { gen, schema, data, allErrors, opts, self } = it; const { RULES } = self; if (schema.$ref && (opts.ignoreKeywordsWithRef || !util_1.schemaHasRulesButRef(schema, RULES))) { gen.block(() => keyword_1.keywordCode(it, "$ref", RULES.all.$ref.definition)); // TODO typecast return; } if (!opts.jtd) checkStrictTypes(it, types); gen.block(() => { for (const group of RULES.rules) groupKeywords(group); groupKeywords(RULES.post); }); function groupKeywords(group) { if (!applicability_1.shouldUseGroup(schema, group)) return; if (group.type) { gen.if(dataType_1.checkDataType(group.type, data, opts.strict)); iterateKeywords(it, group); if (types.length === 1 && types[0] === group.type && typeErrors) { gen.else(); dataType_1.reportTypeError(it); } gen.endIf(); } else { iterateKeywords(it, group); } // TODO make it "ok" call? if (!allErrors) gen.if(codegen_1._ `${names_1.default.errors} === ${errsCount || 0}`); } } exports.schemaKeywords = schemaKeywords; function iterateKeywords(it, group) { const { gen, schema, opts: { useDefaults }, } = it; if (useDefaults) defaults_1.assignDefaults(it, group.type); gen.block(() => { for (const rule of group.rules) { if (applicability_1.shouldUseRule(schema, rule)) { keyword_1.keywordCode(it, rule.keyword, rule.definition, group.type); } } }); } function checkStrictTypes(it, types) { if (it.schemaEnv.meta || !it.opts.strictTypes) return; checkContextTypes(it, types); if (!it.opts.allowUnionTypes) checkMultipleTypes(it, types); checkKeywordTypes(it, it.dataTypes); } function checkContextTypes(it, types) { if (!types.length) return; if (!it.dataTypes.length) { it.dataTypes = types; return; } types.forEach((t) => { if (!includesType(it.dataTypes, t)) { strictTypesError(it, `type "${t}" not allowed by context "${it.dataTypes.join(",")}"`); } }); it.dataTypes = it.dataTypes.filter((t) => includesType(types, t)); } function checkMultipleTypes(it, ts) { if (ts.length > 1 && !(ts.length === 2 && ts.includes("null"))) { strictTypesError(it, "use allowUnionTypes to allow union type keyword"); } } function checkKeywordTypes(it, ts) { const rules = it.self.RULES.all; for (const keyword in rules) { const rule = rules[keyword]; if (typeof rule == "object" && applicability_1.shouldUseRule(it.schema, rule)) { const { type } = rule.definition; if (type.length && !type.some((t) => hasApplicableType(ts, t))) { strictTypesError(it, `missing type "${type.join(",")}" for keyword "${keyword}"`); } } } } function hasApplicableType(schTs, kwdT) { return schTs.includes(kwdT) || (kwdT === "number" && schTs.includes("integer")); } function includesType(ts, t) { return ts.includes(t) || (t === "integer" && ts.includes("number")); } function strictTypesError(it, msg) { const schemaPath = it.schemaEnv.baseId + it.errSchemaPath; msg += ` at "${schemaPath}" (strictTypes)`; _1.checkStrictMode(it, msg, it.opts.strictTypes); } //# sourceMappingURL=iterate.js.map