Is your feature request related to a problem? Please describe.
SecondaryVisibilityWritingMode in common/dynamicconfig/constants.go is declared with NewGlobalTypedSettingWithConverter and convertStringEnum([]string{"off", "on", "dual"}). convertStringEnum lives in common/dynamicconfig/collection.go. That converter checks values loaded later from dynamic config, but the constructor stores the default "off" without checking that it is one of the allowed values. A typo in the default would still register.
It is also a one-off. The next string-enum setting would copy the same generic constructor call instead of using a named setting kind like NewGlobalStringSetting.
Describe the solution you'd like
Add StringEnum as a dynamic config setting type, with a constructor such as NewGlobalStringEnumSetting, following cmd/tools/gendynamicconfig. The constructor should take the allowed values and the default, reject a default that is not one of those values, and use convertStringEnum for values loaded later. Switch SecondaryVisibilityWritingMode in common/dynamicconfig/constants.go over to it:
// common/dynamicconfig/constants.go
SecondaryVisibilityWritingMode = NewGlobalStringEnumSetting(
"system.secondaryVisibilityWritingMode",
[]string{"off", "on", "dual"},
"off",
`SecondaryVisibilityWritingMode is key for how to write to secondary visibility`,
)
common/dynamicconfig/setting_gen.go is generated by cmd/tools/gendynamicconfig (common/dynamicconfig/setting.go has the go:generate line), so this belongs in the generator rather than a hand edit of that file. The type list is in cmd/tools/gendynamicconfig/main.go, and the constructor template is cmd/tools/gendynamicconfig/dynamic_config.tmpl. Existing constructors are (key, default, description) with a fixed converter. A string enum needs (key, allowed values, default, description), because the converter is convertStringEnum(allowed). The template needs a special case for that signature.
Describe alternatives you've considered
Leave the call site in common/dynamicconfig/constants.go on NewGlobalTypedSettingWithConverter. That already enforces the allowed values when config is loaded, which is what #12184 shipped. It does not check the default, and it does not give the next string-enum setting a reusable constructor.
Additional context
Follow-up to #12184, from #12184 (comment).
Is your feature request related to a problem? Please describe.
SecondaryVisibilityWritingModeincommon/dynamicconfig/constants.gois declared withNewGlobalTypedSettingWithConverterandconvertStringEnum([]string{"off", "on", "dual"}).convertStringEnumlives incommon/dynamicconfig/collection.go. That converter checks values loaded later from dynamic config, but the constructor stores the default"off"without checking that it is one of the allowed values. A typo in the default would still register.It is also a one-off. The next string-enum setting would copy the same generic constructor call instead of using a named setting kind like
NewGlobalStringSetting.Describe the solution you'd like
Add
StringEnumas a dynamic config setting type, with a constructor such asNewGlobalStringEnumSetting, followingcmd/tools/gendynamicconfig. The constructor should take the allowed values and the default, reject a default that is not one of those values, and useconvertStringEnumfor values loaded later. SwitchSecondaryVisibilityWritingModeincommon/dynamicconfig/constants.goover to it:common/dynamicconfig/setting_gen.gois generated bycmd/tools/gendynamicconfig(common/dynamicconfig/setting.gohas thego:generateline), so this belongs in the generator rather than a hand edit of that file. The type list is incmd/tools/gendynamicconfig/main.go, and the constructor template iscmd/tools/gendynamicconfig/dynamic_config.tmpl. Existing constructors are(key, default, description)with a fixed converter. A string enum needs(key, allowed values, default, description), because the converter isconvertStringEnum(allowed). The template needs a special case for that signature.Describe alternatives you've considered
Leave the call site in
common/dynamicconfig/constants.goonNewGlobalTypedSettingWithConverter. That already enforces the allowed values when config is loaded, which is what #12184 shipped. It does not check the default, and it does not give the next string-enum setting a reusable constructor.Additional context
Follow-up to #12184, from #12184 (comment).