]> git.maquefel.me Git - brevno-suite/hugo/commitdiff
Support, but warn, about top level language custom params
authorBjørn Erik Pedersen <bjorn.erik.pedersen@gmail.com>
Wed, 17 May 2023 14:29:06 +0000 (16:29 +0200)
committerBjørn Erik Pedersen <bjorn.erik.pedersen@gmail.com>
Wed, 17 May 2023 20:13:29 +0000 (22:13 +0200)
Updates #10947

common/maps/params.go
common/maps/params_test.go
config/allconfig/allconfig.go
hugolib/config_test.go

index eb60fbbfc94c78f60a27c399fe0cbced73f01223..a3e607b8935f11f8b04eafa561e35359139110c4 100644 (file)
@@ -70,7 +70,7 @@ func (p Params) IsZero() bool {
        }
 
        for k := range p {
-               return k == mergeStrategyKey
+               return k == MergeStrategyKey
        }
 
        return false
@@ -103,7 +103,7 @@ func (p Params) merge(ps ParamsMergeStrategy, pp Params) {
 
        for k, v := range pp {
 
-               if k == mergeStrategyKey {
+               if k == MergeStrategyKey {
                        continue
                }
                vv, found := p[k]
@@ -124,7 +124,7 @@ func (p Params) merge(ps ParamsMergeStrategy, pp Params) {
 
 // For internal use.
 func (p Params) GetMergeStrategy() (ParamsMergeStrategy, bool) {
-       if v, found := p[mergeStrategyKey]; found {
+       if v, found := p[MergeStrategyKey]; found {
                if s, ok := v.(ParamsMergeStrategy); ok {
                        return s, true
                }
@@ -134,8 +134,8 @@ func (p Params) GetMergeStrategy() (ParamsMergeStrategy, bool) {
 
 // For internal use.
 func (p Params) DeleteMergeStrategy() bool {
-       if _, found := p[mergeStrategyKey]; found {
-               delete(p, mergeStrategyKey)
+       if _, found := p[MergeStrategyKey]; found {
+               delete(p, MergeStrategyKey)
                return true
        }
        return false
@@ -148,7 +148,7 @@ func (p Params) SetMergeStrategy(s ParamsMergeStrategy) {
        default:
                panic(fmt.Sprintf("invalid merge strategy %q", s))
        }
-       p[mergeStrategyKey] = s
+       p[MergeStrategyKey] = s
 }
 
 func getNested(m map[string]any, indices []string) (any, string, map[string]any) {
@@ -242,7 +242,7 @@ const (
        // Add new keys, merge existing.
        ParamsMergeStrategyDeep ParamsMergeStrategy = "deep"
 
-       mergeStrategyKey = "_merge"
+       MergeStrategyKey = "_merge"
 )
 
 // CleanConfigStringMapString removes any processing instructions from m,
@@ -251,13 +251,13 @@ func CleanConfigStringMapString(m map[string]string) map[string]string {
        if m == nil || len(m) == 0 {
                return m
        }
-       if _, found := m[mergeStrategyKey]; !found {
+       if _, found := m[MergeStrategyKey]; !found {
                return m
        }
        // Create a new map and copy all the keys except the merge strategy key.
        m2 := make(map[string]string, len(m)-1)
        for k, v := range m {
-               if k != mergeStrategyKey {
+               if k != MergeStrategyKey {
                        m2[k] = v
                }
        }
@@ -270,13 +270,13 @@ func CleanConfigStringMap(m map[string]any) map[string]any {
        if m == nil || len(m) == 0 {
                return m
        }
-       if _, found := m[mergeStrategyKey]; !found {
+       if _, found := m[MergeStrategyKey]; !found {
                return m
        }
        // Create a new map and copy all the keys except the merge strategy key.
        m2 := make(map[string]any, len(m)-1)
        for k, v := range m {
-               if k != mergeStrategyKey {
+               if k != MergeStrategyKey {
                        m2[k] = v
                }
                switch v2 := v.(type) {
@@ -313,7 +313,7 @@ func PrepareParams(m Params) {
        for k, v := range m {
                var retyped bool
                lKey := strings.ToLower(k)
-               if lKey == mergeStrategyKey {
+               if lKey == MergeStrategyKey {
                        v = toMergeStrategy(v)
                        retyped = true
                } else {
index 7e1dbbae7febb993bde18a8d3f1a97aa72ff83d6..578b2a576e9de13f66ef1e77dd25ce485a2d9fe6 100644 (file)
@@ -75,7 +75,7 @@ func TestParamsSetAndMerge(t *testing.T) {
 
        createParamsPair := func() (Params, Params) {
                p1 := Params{"a": "av", "c": "cv", "nested": Params{"al2": "al2v", "cl2": "cl2v"}}
-               p2 := Params{"b": "bv", "a": "abv", "nested": Params{"bl2": "bl2v", "al2": "al2bv"}, mergeStrategyKey: ParamsMergeStrategyDeep}
+               p2 := Params{"b": "bv", "a": "abv", "nested": Params{"bl2": "bl2v", "al2": "al2bv"}, MergeStrategyKey: ParamsMergeStrategyDeep}
                return p1, p2
        }
 
@@ -92,7 +92,7 @@ func TestParamsSetAndMerge(t *testing.T) {
                        "bl2": "bl2v",
                },
                "b":              "bv",
-               mergeStrategyKey: ParamsMergeStrategyDeep,
+               MergeStrategyKey: ParamsMergeStrategyDeep,
        })
 
        p1, p2 = createParamsPair()
index 6731b9003f6140d3b5c2dc831dae3697527cd115..a519147725330d2f18a98829a53dff30a5be8605 100644 (file)
@@ -63,6 +63,31 @@ type InternalConfig struct {
        LiveReloadPort    int
 }
 
+// All non-params config keys for language.
+var configLanguageKeys map[string]bool
+
+func init() {
+       skip := map[string]bool{
+               "internal":   true,
+               "c":          true,
+               "rootconfig": true,
+       }
+       configLanguageKeys = make(map[string]bool)
+       addKeys := func(v reflect.Value) {
+               for i := 0; i < v.NumField(); i++ {
+                       name := strings.ToLower(v.Type().Field(i).Name)
+                       if skip[name] {
+                               continue
+                       }
+                       configLanguageKeys[name] = true
+               }
+       }
+       addKeys(reflect.ValueOf(Config{}))
+       addKeys(reflect.ValueOf(RootConfig{}))
+       addKeys(reflect.ValueOf(config.CommonDirs{}))
+       addKeys(reflect.ValueOf(langs.LanguageConfig{}))
+}
+
 type Config struct {
        // For internal use only.
        Internal InternalConfig `mapstructure:"-" json:"-"`
@@ -328,7 +353,7 @@ type ConfigCompiled struct {
        Clock             time.Time
 
        // This is set to the last transient error found during config compilation.
-       // With themes/modules we compule the configuration in multiple passes, and
+       // With themes/modules we compute the configuration in multiple passes, and
        // errors with missing output format definitions may resolve itself.
        transientErr error
 }
@@ -659,7 +684,30 @@ func FromLoadConfigResult(fs afero.Fs, res config.LoadConfigResult) (*Configs, e
                var differentRootKeys []string
                switch x := v.(type) {
                case maps.Params:
+                       var params maps.Params
+                       pv, found := x["params"]
+                       if found {
+                               params = pv.(maps.Params)
+                       } else {
+                               params = maps.Params{
+                                       maps.MergeStrategyKey: maps.ParamsMergeStrategyDeep,
+                               }
+                               x["params"] = params
+                       }
+
                        for kk, vv := range x {
+                               if kk == "_merge" {
+                                       continue
+                               }
+                               if kk != maps.MergeStrategyKey && !configLanguageKeys[kk] {
+                                       // This should have been placed below params.
+                                       // We accidently allowed it in the past, so we need to support it a little longer,
+                                       // But log a warning.
+                                       if _, found := params[kk]; !found {
+                                               helpers.Deprecated(fmt.Sprintf("config: languages.%s.%s: custom params on the language top level", k, kk), fmt.Sprintf("Put the value below [languages.%s.params]. See See https://gohugo.io/content-management/multilingual/#changes-in-hugo-01120", k), false)
+                                               params[kk] = vv
+                                       }
+                               }
                                if kk == "baseurl" {
                                        // baseURL configure don the language level is a multihost setup.
                                        isMultiHost = true
index e27068da6997ab279aebfe77a68c45497d10cf3e..1baaf71963c97fbe9b7b57893da90442ace55b76 100644 (file)
@@ -778,6 +778,43 @@ Home.
 
 }
 
+func TestConfigParamSetOnLanguageLevel(t *testing.T) {
+       t.Parallel()
+
+       files := `
+-- hugo.toml --
+disableKinds = ["taxonomy", "term", "RSS", "sitemap", "robotsTXT"]
+[languages]
+[languages.en]
+title = "English Title"
+thisIsAParam = "thisIsAParamValue"
+[languages.en.params]
+myparam = "enParamValue"
+[languages.sv]
+title = "Svensk Title"
+[languages.sv.params]
+myparam = "svParamValue"
+-- layouts/index.html --
+MyParam: {{ site.Params.myparam }}
+ThisIsAParam: {{ site.Params.thisIsAParam }}
+
+
+`
+
+       b, err := NewIntegrationTestBuilder(
+               IntegrationTestConfig{
+                       T:           t,
+                       TxtarString: files,
+               },
+       ).BuildE()
+
+       b.Assert(err, qt.IsNil)
+       b.AssertFileContent("public/index.html", `              
+MyParam: enParamValue
+ThisIsAParam: thisIsAParamValue        
+`)
+}
+
 func TestReproCommentsIn10947(t *testing.T) {
        t.Parallel()
 
@@ -817,7 +854,9 @@ title: "My Swedish Section"
                },
        ).Build()
 
-       b.Assert(b.H.Log.LogCounters().WarnCounter.Count(), qt.Equals, uint64(2))
+       {
+               b.Assert(b.H.Log.LogCounters().WarnCounter.Count(), qt.Equals, uint64(2))
+       }
        b.AssertFileContent("public/index.html", `
 AllPages: 4|
 Sections: true|