在我的包的 Configuration
中,我定义了以下内容,例如:
$treeBuilder = new TreeBuilder('foo');
$treeBuilder
->getRootNode()
->children()
->arrayNode('foobar')
->scalarPrototype()->end()
->defaultValue([])
->end()
->end()
;
我。例如,包需要 foo.foobar
中的值数组。现在,就我的包而言,这些值取决于应用程序运行的环境。因此,通过环境变量提供此配置值是有意义的。 Since Symfony 3.4可以处理环境变量的值。所以这个数组可以存储在环境变量中的 JSON 编码,然后通过 %env(json:FOO)%
解码。所以不必写
foo:
foobar:
- Lorem
- Ipsum
- Dolor
可以改用
foo:
foobar: '%env(json:FOO)%'
在哪里
FOO=["Lorem","Ipsum","Dolor"]
但是,当尝试这样做时,Symfony 会抛出以下异常:
A dynamic value is not compatible with a "Symfony\Component\Config\Definition\PrototypedArrayNode" node type at path "foo.foobar".
允许数组节点使用此类动态值的正确方法是什么?例如,我是否需要在配置树中实现自己的规范化?
最佳答案
静态yaml配置和'%env(json:FOO)%'
有很大区别: 环境变量的内容在编译时不可用。参见 docs :
You can reference environment variables using the special syntax %env(ENV_VAR_NAME)%. The values of these options are resolved at runtime (only once per request, to not impact performance).
在你的BundleExtension
(在编译时)你的配置值 foobar
将包含类似 env_514deb50f3dcab34_json_FOO_ac251f2b9ef3c85f94a68df880763311
的字符串(而不是真正的数组)。
例如,这意味着您不能有条件地在您的包中加载某些配置。
但是,应该在编译时验证此节点。在 JSON 的情况下,它不能被验证为 scalarNode(...)
,因为包含 JSON 环境处理器。无法将其验证为 arrayNode(...)
,因为 ArrayNode
不支持动态值。
所以你可以跳过验证:
$treeBuilder
->getRootNode()
->children()
->variableNode('foobar')->end()
->end()
;
您还可以在 bundle 中添加两个不同的配置项:静态配置(如 arrayNode)和动态配置(如 variableNode),然后在扩展中检查只定义了其中一个。
PS:看起来不方便。但这些都是很自然的限制,如果我们记得环境变量可以在运行时更改(即在编译容器之后)。
关于php - 交响乐 4 : how to allow dynamic values for array nodes in bundle configuration?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62230270/