Проверка конфигурации Symfony ключей в парах ключ-значение в узле прототипа

В Symfony 2.8, учитывая этот конфигурационный блок YAML

my_bundle:
profiles:
'abc': 123
'def: 456
'...': ...

Как я могу проверить ключи в значениях ключей под профилями непустой строки?

В этом случае ‘abc’ и ‘def’ являются просто примерами, они произвольны, их нельзя предопределить.

Вот мой файл конфигурации —

->arrayNode('profiles')
->isRequired()
->requiresAtLeastOneElement()
->useAttributeAsKey('name')
->prototype('integer')
->min(0)
->end()
->end()

Проблема в

my_bundle:
profiles:
123
456

действительно, когда я не хочу, чтобы это было.

Я не смог найти простой встроенный способ проверки ключей массивов-прототипов.

Возможные решения

Один: Кажется что я мог сделать массив массивов

my_bundle:
profiles:
-
name: abc
value: 123
-
name: def
value: 456

с

->arrayNode('profiles')
->isRequired()
->useAttributeAsKey('name')
->requiresAtLeastOneElement()
->prototype('array')
->children()
->scalarNode('name')
->isRequired()
->cannotBeEmpty()
->validate()
->ifTrue(
function($s) {
return !is_string($s);
}
)
->thenInvalid('Profile key must be a non-empty string')
->end()
->end()
->integerNode('value')
->isRequired()
->min(0)
->end()
->end()
->end()

но я бы предпочел не делать этого, так как наши клиенты уже имеют оригинальный формат в своей конфигурации, мы можем легче обновить конфигурацию, чем сами файлы конфигурации.

Два: Кажется что я мог сделать # 1 без изменения конфигурации, добавив некоторую нормализацию, чтобы сначала преобразовать старый формат конфигурации в новый формат

->arrayNode('profiles')
->beforeNormalization()
->ifTrue(
function($array) {
$hasSimpleKeyValuePair = false;
foreach ($array as $key => $value) {
if (!is_array($value)) {
$hasSimpleKeyValuePair = true;
break;
}
}

return $hasSimpleKeyValuePair;
}
)
->then(
function($array) {
$newArray = [];
foreach ($array as $key => $value) {
if (!is_array($value)) {
$newArray[] = ['name' => $key, 'value' => $value];
}
}
return $newArray;
}
)
->end()
->isRequired()
->requiresAtLeastOneElement()
->prototype('array')
->children()
->scalarNode('name')
->isRequired()
->cannotBeEmpty()
->validate()
->ifTrue(
function($s) {
return !is_string($s);
}
)
->thenInvalid('Profile key must be a non-empty string')
->end()
->end()
->integerNode('value')
->isRequired()
->min(0)
->end()
->end()
->end()
->end()

но это кажется огромным излишним.

(Эти два параметра также означают, что мне нужно изменить получателей данных профиля, чтобы знать, что вместо использования числа им нужно использовать индекс ключа массива, который указывает на число, $profile[$key]['value'] а не просто $profile[$key]который я Можно я предполагаю)

Три: Кажется что я мог добавить пользовательскую проверку всего блока

->arrayNode('profiles')
->isRequired()
->requiresAtLeastOneElement()
->useAttributeAsKey('name')
->prototype('integer')
->min(0)
->end()
->validate()
->ifTrue(function ($array) {
$notValid = false;
foreach ($array as $key => $value) {
if (!is_string($key) || empty($key)) {
$notValid = true;
break;
}
}

return $notValid;
})
->thenInvalid('Profile keys must be a non-empty string.')
->end()
->end()

это то, чем я сейчас занимаюсь, но все-таки кажется ненужным обычай / хакерство для чего-то, что, я думаю, будет обычным вариантом использования.

Я просто хочу проверить, что я не пропустил какой-то волшебный встроенный способ сделать это с конфигурацией Symfony?

3

Решение

Задача ещё не решена.

Другие решения

Других решений пока нет …

По вопросам рекламы ammmcru@yandex.ru
Adblock
detector