* Returns normalized and compiled rule for processing. * @param {string} path current path * @param {RuleSetRule} rule the raw rule provided by user * @param {References} refs references * @returns {CompiledRule} normalized and compiled rule for processing
(path, rule, refs)
| 241 | * @returns {CompiledRule} normalized and compiled rule for processing |
| 242 | */ |
| 243 | compileRule(path, rule, refs) { |
| 244 | /** @type {UnhandledProperties} */ |
| 245 | const unhandledProperties = new Set( |
| 246 | Object.keys(rule).filter( |
| 247 | (key) => rule[/** @type {keyof RuleSetRule} */ (key)] !== undefined |
| 248 | ) |
| 249 | ); |
| 250 | |
| 251 | /** @type {CompiledRule} */ |
| 252 | const compiledRule = { |
| 253 | conditions: [], |
| 254 | effects: [], |
| 255 | rules: undefined, |
| 256 | oneOf: undefined |
| 257 | }; |
| 258 | |
| 259 | this.hooks.rule.call(path, rule, unhandledProperties, compiledRule, refs); |
| 260 | |
| 261 | if (unhandledProperties.has("rules")) { |
| 262 | unhandledProperties.delete("rules"); |
| 263 | const rules = rule.rules; |
| 264 | if (!Array.isArray(rules)) { |
| 265 | throw this.error(path, rules, "Rule.rules must be an array of rules"); |
| 266 | } |
| 267 | compiledRule.rules = this.compileRules(`${path}.rules`, rules, refs); |
| 268 | } |
| 269 | |
| 270 | if (unhandledProperties.has("oneOf")) { |
| 271 | unhandledProperties.delete("oneOf"); |
| 272 | const oneOf = rule.oneOf; |
| 273 | if (!Array.isArray(oneOf)) { |
| 274 | throw this.error(path, oneOf, "Rule.oneOf must be an array of rules"); |
| 275 | } |
| 276 | compiledRule.oneOf = this.compileRules(`${path}.oneOf`, oneOf, refs); |
| 277 | } |
| 278 | |
| 279 | if (unhandledProperties.size > 0) { |
| 280 | throw this.error( |
| 281 | path, |
| 282 | rule, |
| 283 | `Properties ${[...unhandledProperties].join(", ")} are unknown` |
| 284 | ); |
| 285 | } |
| 286 | |
| 287 | return compiledRule; |
| 288 | } |
| 289 | |
| 290 | /** |
| 291 | * Returns compiled condition. |
no test coverage detected