diff --git a/layouts/partials/decap-cms/functions/compute-definition.html b/layouts/partials/decap-cms/functions/compute-definition.html new file mode 100644 index 0000000..6240d79 --- /dev/null +++ b/layouts/partials/decap-cms/functions/compute-definition.html @@ -0,0 +1,26 @@ +{{- $definitions := .definitions -}} +{{- $name := .name -}} +{{- $def := $definitions.Get $name -}} +{{- $extends := default slice (index $def "_extends") -}} +{{- if not (reflect.IsSlice $extends) }} + {{- errorf "[decap-cms] %q _extends is not an array." $name }} +{{- end }} +{{- $merging := slice -}} +{{- range $extends -}} + {{- $parentName := . -}} + {{- with $definitions.Get $parentName -}} + {{- $parent := . -}} + {{/* Handle nested extends. */}} + {{- with index $parent "_extends" -}} + {{- partial "decap-cms/functions/compute-definition" (dict "definitions" $definitions "name" $parentName) -}} + {{- end -}} + {{- $merging = $merging | append ($definitions.Get $parentName) -}} + {{- else -}} + {{- errorf "[decap-cms] no such extensible config: %s" $name -}} + {{- end -}} +{{- end -}} +{{/* Override with the computed definition. */}} +{{- with $merging -}} + {{- $def = partial "decap-cms/functions/deep-merge" (. | append $def) -}} + {{- $definitions.Set $name $def.Values -}} +{{- end -}} diff --git a/layouts/partials/decap-cms/functions/config.html b/layouts/partials/decap-cms/functions/config.html index 7f03c5a..fadc8c3 100644 --- a/layouts/partials/decap-cms/functions/config.html +++ b/layouts/partials/decap-cms/functions/config.html @@ -11,12 +11,10 @@ {{- $config.Set $key (index $params $key) -}} {{- end -}} {{- end -}} -{{- $configs := default dict (index $params "_configs") -}} - +{{- $definitions := partial "decap-cms/functions/definitions" (default dict (index $params "_configs")) }} {{/* Transform collections. */}} {{- with index $params "collections" -}} - {{- range . -}} - {{- $collection := . -}} + {{- range $collectionName, $collection := . -}} {{- with $collection.fields -}} {{- if reflect.IsSlice . -}} {{- $fields := dict -}} @@ -30,23 +28,20 @@ {{/* Extends configurations. */}} {{- $extends := slice -}} {{- with index $collection "_extends" -}} + {{- if not (reflect.IsSlice .) }} + {{- errorf "[decap-cms] %q _extends is not an array." $collectionName }} + {{- end }} {{- range $weight, $extendName := . -}} - {{- with index $configs . -}} + {{- with index $definitions . -}} {{/* Assign the weight to fields for sorting. */}} {{- $extend := . -}} {{- with $extend.fields -}} - {{- $isMap := reflect.IsMap . }} - {{- range $name, $field := . -}} - {{- $field = merge $field (dict "_weight" (add $weight 1)) -}} - {{- if not $isMap }} - {{- $name = $field.name }} - {{- end }} - {{- $extend = merge $extend (dict "fields" (dict $name $field)) -}} - {{- end -}} + {{- $fields := partial "decap-cms/functions/format-fields" . -}} + {{- $extend = merge $extend (dict "fields" $fields) -}} {{- end -}} {{- $extends = $extends | append $extend -}} {{- else -}} - {{- warnf "[decap-cms] no such extendable configuration: %s." . -}} + {{- errorf "[decap-cms] no such extendable configuration: %s." . -}} {{- end -}} {{- end -}} {{- end -}} diff --git a/layouts/partials/decap-cms/functions/deep-merge.html b/layouts/partials/decap-cms/functions/deep-merge.html index f51ca26..7c16faf 100644 --- a/layouts/partials/decap-cms/functions/deep-merge.html +++ b/layouts/partials/decap-cms/functions/deep-merge.html @@ -37,6 +37,22 @@ {{- $rst.Set $key $values }} {{- else }} {{/* Start map merging. */}} + {{- if eq $key "fields" }} + {{/* Calculate fields weight. */}} + {{- $fieldWeight := len $values }} + {{- $fields := newScratch }} + {{- range $fieldName, $field := $items }} + {{- $field = partial "decap-cms/functions/dict2scratch" $field }} + {{- if isset $values $fieldName }} + {{- $field.Delete "_weight" }} + {{- else }} + {{- $fieldWeight = add $fieldWeight 1 }} + {{- $field.Set "_weight" $fieldWeight }} + {{- end }} + {{- $fields.Set $fieldName $field.Values }} + {{- end }} + {{- $items = $fields.Values }} + {{- end }} {{- $rst.Set $key (merge $values $items) }} {{- end }} {{- else }} diff --git a/layouts/partials/decap-cms/functions/definitions.html b/layouts/partials/decap-cms/functions/definitions.html new file mode 100644 index 0000000..bbdf000 --- /dev/null +++ b/layouts/partials/decap-cms/functions/definitions.html @@ -0,0 +1,13 @@ +{{- $definitions := newScratch -}} +{{/* Convert definitions from map to scratch. */}} +{{- range $name, $def := . -}} + {{- with $def.fields -}} + {{- $fields := partial "decap-cms/functions/format-fields" . -}} + {{- $def = merge $def (dict "fields" $fields) -}} + {{- end -}} + {{- $definitions.Set $name $def -}} +{{- end -}} +{{- range $name, $def := . -}} + {{- partial "decap-cms/functions/compute-definition" (dict "definitions" $definitions "name" $name) -}} +{{- end -}} +{{- return $definitions.Values -}} diff --git a/layouts/partials/decap-cms/functions/dict2scratch.html b/layouts/partials/decap-cms/functions/dict2scratch.html index 3add2f1..f80c27b 100644 --- a/layouts/partials/decap-cms/functions/dict2scratch.html +++ b/layouts/partials/decap-cms/functions/dict2scratch.html @@ -1,5 +1,5 @@ {{- $scratch := newScratch }} -{{- range $key, $val := index . 0 }} +{{- range $key, $val := . }} {{- $scratch.Set $key $val }} {{- end }} {{- return $scratch }} diff --git a/layouts/partials/decap-cms/functions/format-fields.html b/layouts/partials/decap-cms/functions/format-fields.html new file mode 100644 index 0000000..1d95f41 --- /dev/null +++ b/layouts/partials/decap-cms/functions/format-fields.html @@ -0,0 +1,17 @@ +{{/* Format fields to add _weight and convert it to map if it's an array. */}} +{{- $fields := newScratch -}} +{{- with . -}} + {{- $isMap := reflect.IsMap . -}} + {{- $weight := 0 -}} + {{- range $name, $field := . -}} + {{- if isset $field "_weight" }} + {{- continue }} + {{- end }} + {{- $field = merge $field (dict "_weight" (add $weight 1)) -}} + {{- if not $isMap -}} + {{- $name = $field.name -}} + {{- end -}} + {{- $fields.Set $name $field -}} + {{- end -}} +{{- end -}} +{{- return $fields.Values -}}