I've started on twig recently and now i'm faced with the issue that I want to group an array based on multiple common key.
My current array is this: (JSON style)
{
"attribute_groups": [
{
"attribute_group_id": "1",
"name": "Atribute Group #1",
"attribute": [
{
"attribute_id": "101",
"name": "Attrib1",
"value": "Val1",
"subgroup": "SubGroup A"
},
{
"attribute_id": "102",
"name": "Attrib2",
"value": "Val2",
"subgroup": "SubGroup B"
},
{
"attribute_id": "103",
"name": "Attrib3",
"value": "Val3",
"subgroup": "SubGroup A"
},
{
"attribute_id": "104",
"name": "Attrib4",
"value": "Val4",
"subgroup": "SubGroup B"
}
]
},
{
"attribute_group_id": "2",
"name": "Atribute Group #2",
"attribute": [
{
"attribute_id": "201",
"name": "Attrib5",
"value": "Val5",
"subgroup": "SubGroup A"
},
{
"attribute_id": "202",
"name": "Attrib6",
"value": "Val6",
"subgroup": "SubGroup C"
},
{
"attribute_id": "203",
"name": "Attrib7",
"value": "Val7",
"subgroup": "SubGroup A"
},
{
"attribute_id": "204",
"name": "Attrib8",
"value": "Val8",
"subgroup": "SubGroup C"
}
]
}
]
}
With basic twig for loop i can
{% for attribute_group in attribute_groups %}
This is group: {{ attribute_group.name }}
{% for attribute in attribute_group.attribute %}
Attribute {{ attribute.name }} has value: {{ attribute.value }}
{% endfor %}
{% endfor %}
And output would show attributes grouped by main group:
This is group: Atribute Group #1
Attribute Attrib1 has value: Val1
Attribute Attrib2 has value: Val2
Attribute Attrib3 has value: Val3
Attribute Attrib4 has value: Val4
This is group: Atribute Group #2
Attribute Attrib5 has value: Val5
Attribute Attrib6 has value: Val6
Attribute Attrib7 has value: Val7
Attribute Attrib8 has value: Val8
As TWIGfiddled: https://twigfiddle.com/cow2ax
Now i would like to have an additional subgrouping by "subgroup" key like:
This is group: Atribute Group #1
SubGroup A has attribues:
Attribute Attrib1 has value: Val1
Attribute Attrib3 has value: Val3
SubGroup B has attribues:
Attribute Attrib2 has value: Val2
Attribute Attrib4 has value: Val4
This is group: Atribute Group #2
SubGroup A has attribues:
Attribute Attrib5 has value: Val5
Attribute Attrib7 has value: Val7
SubGroup C has attribues:
Attribute Attrib6 has value: Val6
Attribute Attrib8 has value: Val8
How to achieve such subsorting/subgrouping ?
I've found How to add values of same names in a row in an HTML Table but i cannot wrap my brain around it :|
CodePudding user response:
Disclaimer
As said and already mentioned in the linked answer(s), these are things that shouldn't be done in twig
itself. It's better to move this logic to the controller or at least use a twig extension in which you then can group everything you want more easily.
More information about why you shouldn't do this inside a template can be found here
Here is the reworked snippet for your grouping. I've already gave my two cents in the linked questions on how this works, so please read those questions/answers as well if you want more details on how this snippet "works"
{% set subgroups = {} %}
{% for attribute_group in attribute_groups %}
{% set subgroups = subgroups|merge({ ('_'~attribute_group.attribute_group_id): {},}) %}
{% for attribute in attribute_group.attribute %}
{% if not subgroups['_'~attribute_group.attribute_group_id][attribute.subgroup] is defined %}
{% set subgroups = subgroups|merge({
('_'~attribute_group.attribute_group_id): subgroups['_'~attribute_group.attribute_group_id]|merge({(attribute.subgroup):{},}),
}) %}
{% endif %}
{% set subgroups = subgroups|merge({
('_'~attribute_group.attribute_group_id): subgroups['_'~attribute_group.attribute_group_id]|merge({(attribute.subgroup): subgroups['_'~attribute_group.attribute_group_id][attribute.subgroup]|merge([ attribute, ]),}),
}) %}
{% endfor %}
{% endfor %}
{% for attribute_group in attribute_groups %}
{{ attribute_group.name }}
{% for key, attributes in subgroups['_'~attribute_group.attribute_group_id] %}
{{ key }}
=============
{% for attribute in attributes %}
{{ attribute.value }}
{% endfor %}
=============
{% endfor %}
{% endfor %}