Merge branches

This commit is contained in:
Pieter Vander Vennet 2024-05-13 18:55:54 +02:00
commit bae90d50bc
304 changed files with 49983 additions and 31589 deletions

View file

@ -258,11 +258,11 @@ export class ExpandRewrite<T> extends Conversion<T | RewritableConfigJson<T>, T[
}
}
let renderings = Array.isArray(rewrite.renderings)
const renderings = Array.isArray(rewrite.renderings)
? rewrite.renderings
: [rewrite.renderings]
for (let i = 0; i < keysToRewrite.into.length; i++) {
let ts: T[] = <T[]>Utils.Clone(renderings)
const ts: T[] = <T[]>Utils.Clone(renderings)
for (const tx of ts) {
let t = <T>tx
const sourceKeysToIgnore: string[] = []

View file

@ -161,7 +161,9 @@ class ExpandTagRendering extends Conversion<
private readonly _options: {
/* If true, will copy the 'osmSource'-tags into the condition */
applyCondition?: true | boolean
noHardcodedStrings?: false | boolean
noHardcodedStrings?: false | boolean,
addToContext?: false | boolean
}
constructor(
@ -169,11 +171,13 @@ class ExpandTagRendering extends Conversion<
self: LayerConfigJson,
options?: {
applyCondition?: true | boolean
noHardcodedStrings?: false | boolean
noHardcodedStrings?: false | boolean,
// If set, a question will be added to the 'sharedTagRenderings'. Should only be used for 'questions.json'
addToContext?: false | boolean
}
) {
super(
"Converts a tagRenderingSpec into the full tagRendering, e.g. by substituting the tagRendering by the shared-question",
"Converts a tagRenderingSpec into the full tagRendering, e.g. by substituting the tagRendering by the shared-question and reusing the builtins",
[],
"ExpandTagRendering"
)
@ -204,8 +208,17 @@ class ExpandTagRendering extends Conversion<
if (typeof tr === "string" || tr["builtin"] !== undefined) {
const stable = this.convert(tr, ctx.inOperation("recursive_resolve"))
result.push(...stable)
if(this._options?.addToContext){
for (const tr of stable) {
this._state.tagRenderings?.set(tr.id, tr)
}
}
} else {
result.push(tr)
if(this._options?.addToContext){
this._state.tagRenderings?.set(tr["id"], <QuestionableTagRenderingConfigJson> tr)
}
}
}
@ -220,7 +233,7 @@ class ExpandTagRendering extends Conversion<
}
const result: TagRenderingConfigJson[] = []
for (const tagRenderingConfigJson of direct) {
let nm: string | string[] | undefined = tagRenderingConfigJson["builtin"]
const nm: string | string[] | undefined = tagRenderingConfigJson["builtin"]
if (nm !== undefined) {
let indirect: TagRenderingConfigJson[]
if (typeof nm === "string") {
@ -1261,12 +1274,14 @@ export class AutoTitleIcon extends DesugaringStep<LayerConfigJson> {
}
export class PrepareLayer extends Fuse<LayerConfigJson> {
constructor(state: DesugaringContext) {
constructor(state: DesugaringContext, options?: {addTagRenderingsToContext?: false | boolean}) {
super(
"Fully prepares and expands a layer for the LayerConfig.",
new On("tagRenderings", new Each(new RewriteSpecial())),
new On("tagRenderings", new Concat(new ExpandRewrite()).andThenF(Utils.Flatten)),
new On("tagRenderings", (layer) => new Concat(new ExpandTagRendering(state, layer))),
new On("tagRenderings", (layer) => new Concat(new ExpandTagRendering(state, layer, {
addToContext: options?.addTagRenderingsToContext ?? false
}))),
new On("tagRenderings", new Each(new DetectInline())),
new AddQuestionBox(),
new AddEditingElements(state),

View file

@ -562,6 +562,65 @@ export class DetectNonErasedKeysInMappings extends DesugaringStep<QuestionableTa
}
}
export class DetectMappingsShadowedByCondition extends DesugaringStep<TagRenderingConfigJson> {
private readonly _forceError: boolean
constructor(forceError: boolean = false) {
super("Checks that, if the tagrendering has a condition, that a mapping is not contradictory to it, i.e. that there are no dead mappings", [], "DetectMappingsShadowedByCondition")
this._forceError = forceError
}
/**
*
* const validator = new DetectMappingsShadowedByCondition(true)
* const ctx = ConversionContext.construct([],["test"])
* validator.convert({
* condition: "count>0",
* mappings:[
* {
* if: "count=0",
* then:{
* en: "No count"
* }
* }
* ]
* }, ctx)
* ctx.hasErrors() // => true
*/
convert(json: TagRenderingConfigJson, context: ConversionContext): TagRenderingConfigJson {
if(!json.condition && !json.metacondition){
return json
}
if(!json.mappings || json.mappings?.length ==0){
return json
}
let conditionJson = json.condition ?? json.metacondition
if(json.condition !== undefined && json.metacondition !== undefined){
conditionJson = {and: [json.condition, json.metacondition]}
}
const condition = TagUtils.Tag(conditionJson, context.path.join("."))
for (let i = 0; i < json.mappings.length; i++){
const mapping = json.mappings[i]
const tagIf = TagUtils.Tag(mapping.if, context.path.join("."))
const optimized = new And([tagIf, condition]).optimize()
if(optimized === false){
const msg = ("Detected a conflicting mapping and condition. The mapping requires tags " + tagIf.asHumanString() + ", yet this can never happen because the set condition requires " + condition.asHumanString())
const ctx = context.enters("mappings", i)
if (this._forceError) {
ctx.err(msg)
} else {
ctx.warn(msg)
}
}
}
return undefined
}
}
export class DetectShadowedMappings extends DesugaringStep<TagRenderingConfigJson> {
private readonly _calculatedTagNames: string[]
@ -1088,6 +1147,8 @@ export class ValidateTagRenderings extends Fuse<TagRenderingConfigJson> {
"Various validation on tagRenderingConfigs",
new MiscTagRenderingChecks(),
new DetectShadowedMappings(layerConfig),
new DetectMappingsShadowedByCondition(),
new DetectConflictingAddExtraTags(),
// TODO enable new DetectNonErasedKeysInMappings(),
new DetectMappingsWithImages(doesImageExist),