Skip to content

Commit c3890e0

Browse files
authored
Merge pull request LokiExtensions#10 from integer-net/4/custom-fields-2
LokiExtensions#4 [fix] Custom fields configured via layout xml file are not appearing in the form
2 parents 5212115 + c55504c commit c3890e0

1 file changed

Lines changed: 116 additions & 59 deletions

File tree

Form/FieldResolver.php

Lines changed: 116 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -19,92 +19,149 @@ public function __construct(
1919
public function resolve(FormRepository $formRepository, array $fieldDefinitions): array
2020
{
2121
$resourceModel = $formRepository->getResourceModel();
22-
if (!$resourceModel) {
22+
23+
if ($resourceModel === null) {
2324
return [];
2425
}
2526

26-
$fields = [];
27-
$tableColumns = $resourceModel->getConnection()->describeTable($resourceModel->getMainTable());
27+
$tableColumns = $this->getTableColumns($resourceModel);
28+
$fieldColumns = $this->mergeTableAndExtraColumns(
29+
$tableColumns,
30+
$fieldDefinitions
31+
);
2832

29-
foreach ($tableColumns as $tableColumn) {
30-
$columnName = $tableColumn['COLUMN_NAME'];
31-
$fieldType = $this->getFieldTypeCodeFromColumn($formRepository, $tableColumn);
32-
if ($columnName === $resourceModel->getIdFieldName()) {
33-
$fieldType = 'view';
34-
}
33+
$fields = $this->buildFields(
34+
$formRepository,
35+
$tableColumns,
36+
$fieldColumns,
37+
$fieldDefinitions
38+
);
3539

36-
$fieldLabel = $this->getLabelByColumn($tableColumn['COLUMN_NAME']);
37-
$code = $tableColumn['COLUMN_NAME'];
40+
$this->sortFieldsBySortOrder($fields);
3841

39-
if (empty($fieldType)) {
40-
$fieldType = 'input';
41-
}
42+
return $fields;
43+
}
4244

43-
$block = $this->layout->createBlock(Template::class);
44-
$fieldData = [
45-
'field_type' => $fieldType,
46-
'code' => $code,
47-
'label' => $fieldLabel,
48-
'required' => false,
49-
'sort_order' => 0,
50-
'field_attributes' => [],
51-
'label_attributes' => [],
52-
];
53-
54-
if (array_key_exists($columnName, $fieldDefinitions)) {
55-
$fieldDefinition = (array)$fieldDefinitions[$columnName];
56-
$fieldData = array_merge($fieldData, $fieldDefinition);
57-
}
45+
private function getTableColumns(object $resourceModel): array
46+
{
47+
return $resourceModel
48+
->getConnection()
49+
->describeTable($resourceModel->getMainTable());
50+
}
5851

59-
$fields[$code] = $this->fieldFactory->create(
60-
$block,
61-
$fieldData,
52+
private function mergeTableAndExtraColumns(
53+
array $tableColumns,
54+
array $fieldDefinitions
55+
): array {
56+
$tableColumnNames = array_keys($tableColumns);
57+
58+
$extraFieldDefinitions = array_filter(
59+
$fieldDefinitions,
60+
static fn (array $definition, string $fieldCode): bool =>
61+
!in_array($fieldCode, $tableColumnNames, true),
62+
ARRAY_FILTER_USE_BOTH
63+
);
64+
65+
return array_merge($tableColumns, $extraFieldDefinitions);
66+
}
67+
68+
private function buildFields(
69+
FormRepository $formRepository,
70+
array $tableColumns,
71+
array $fieldColumns,
72+
array $fieldDefinitions
73+
): array {
74+
$fields = [];
75+
76+
foreach ($fieldColumns as $fieldCode => $definition) {
77+
$columnData = $this->buildBaseColumnData(
78+
$formRepository,
79+
$tableColumns,
80+
$fieldCode
6281
);
63-
}
6482

65-
uasort($fields, function (Field $field1, Field $field2) {
66-
return $field1->getSortOrder() <=> $field2->getSortOrder();
67-
});
83+
if (array_key_exists($fieldCode, $fieldDefinitions)) {
84+
$columnData = array_merge(
85+
$columnData,
86+
$fieldDefinitions[$fieldCode]
87+
);
88+
}
89+
90+
$fields[$fieldCode] = $this->createField($columnData);
91+
}
6892

6993
return $fields;
7094
}
7195

72-
private function getFieldTypeCodeFromColumn(FormRepository $formRepository, array $tableColumn): false|string
73-
{
74-
if ($tableColumn['COLUMN_NAME'] === $formRepository->getPrimaryKey()) {
75-
return 'view';
76-
}
96+
private function buildBaseColumnData(
97+
FormRepository $formRepository,
98+
array $tableColumns,
99+
string $fieldCode
100+
): array {
101+
$columnData = ['code' => $fieldCode];
77102

78-
if (in_array($tableColumn['DATA_TYPE'], ['datetime'])) {
79-
return 'datetime';
103+
if (!array_key_exists($fieldCode, $tableColumns)) {
104+
return $columnData;
80105
}
81106

82-
if (in_array($tableColumn['DATA_TYPE'], ['date'])) {
83-
return 'date';
84-
}
107+
$tableColumn = $tableColumns[$fieldCode];
108+
$fieldType = $this->resolveFieldType(
109+
$formRepository,
110+
$tableColumn
111+
);
112+
113+
return array_merge($columnData, [
114+
'field_type' => $fieldType ?: 'input',
115+
'label' => $this->getLabelByColumn($tableColumn['COLUMN_NAME']),
116+
'required' => false,
117+
'sort_order' => 0,
118+
'field_attributes' => [],
119+
'label_attributes' => [],
120+
]);
121+
}
85122

86-
if (in_array($tableColumn['DATA_TYPE'], ['tinyint'])) {
87-
return 'switch';
88-
}
123+
private function createField(array $columnData): Field
124+
{
125+
return $this->fieldFactory->create(
126+
$this->layout->createBlock(Template::class),
127+
$columnData,
128+
);
129+
}
89130

90-
if (in_array($tableColumn['DATA_TYPE'], ['int'])) {
91-
return 'number';
92-
}
131+
private function sortFieldsBySortOrder(array &$fields): void
132+
{
133+
uasort(
134+
$fields,
135+
static fn (Field $a, Field $b): int =>
136+
$a->getSortOrder() <=> $b->getSortOrder()
137+
);
138+
}
93139

94-
if (in_array($tableColumn['DATA_TYPE'], ['varchar', 'text', 'smalltext', 'mediumtext'])) {
95-
return 'input';
140+
private function resolveFieldType(
141+
FormRepository $formRepository,
142+
array $tableColumn
143+
): false|string {
144+
if ($tableColumn['COLUMN_NAME'] === $formRepository->getPrimaryKey()) {
145+
return 'view';
96146
}
97147

98-
return false;
148+
return match ($tableColumn['DATA_TYPE']) {
149+
'datetime' => 'datetime',
150+
'date' => 'date',
151+
'tinyint' => 'switch',
152+
'int' => 'number',
153+
'varchar', 'text', 'smalltext', 'mediumtext' => 'input',
154+
default => false,
155+
};
99156
}
100157

101158
private function getLabelByColumn(string $columnName): string
102159
{
103-
$label = (string)__($columnName);
104-
if ($label !== $columnName) {
105-
return $label;
160+
$translated = (string) __($columnName);
161+
if ($translated !== $columnName) {
162+
return $translated;
106163
}
107164

108-
return ucfirst(str_replace('_', ' ', $label));
165+
return ucfirst(str_replace('_', ' ', $columnName));
109166
}
110167
}

0 commit comments

Comments
 (0)