ColumnFactory   A
last analyzed

Complexity

Total Complexity 9

Size/Duplication

Total Lines 72
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 5

Importance

Changes 0
Metric Value
wmc 9
lcom 1
cbo 5
dl 0
loc 72
rs 10
c 0
b 0
f 0

5 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 6 1
A resolveLayers() 0 21 3
A createCell() 0 14 2
A createHeader() 0 7 1
A resolveOptions() 0 15 2
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Psi\Component\Grid;
6
7
use Psi\Component\Grid\View\Cell;
8
use Psi\Component\Grid\View\Header;
9
use Symfony\Component\OptionsResolver\OptionsResolver;
10
11
class ColumnFactory
12
{
13
    private $registry;
14
15
    public function __construct(
16
        ColumnRegistry $registry
17
18
    ) {
19
        $this->registry = $registry;
20
    }
21
22
    public function createCell(string $columnName, string $typeName, $data, array $options): Cell
23
    {
24
        $column = $this->registry->get($typeName);
25
26
        $layers = $this->resolveLayers($column);
27
        $options = $this->resolveOptions($layers, $column, $columnName, $options);
28
        $cell = new Cell($data, $options['cell_template']);
29
30
        foreach ($layers as $column) {
31
            $column->buildCell($cell, $options);
32
        }
33
34
        return $cell;
35
    }
36
37
    public function createHeader(GridContext $gridContext, string $columnName, string $typeName, array $options): Header
38
    {
39
        $column = $this->registry->get($typeName);
40
        $options = $this->resolveOptions($this->resolveLayers($column), $column, $columnName, $options);
41
42
        return new Header($gridContext, $options['header_template'], $options['column_name'], $options['label'], $options['sort_field']);
43
    }
44
45
    private function resolveOptions(array $layers, ColumnInterface $column, string $columnName, array $options)
46
    {
47
        $resolver = new OptionsResolver();
48
        $resolver->setDefault('column_name', $columnName);
49
        $resolver->setDefault('label', $columnName);
50
        $resolver->setDefault('sort_field', null);
51
        $resolver->setDefault('cell_template', $column->getCellTemplate());
52
        $resolver->setDefault('header_template', 'Header');
53
54
        foreach ($layers as $column) {
55
            $column->configureOptions($resolver);
56
        }
57
58
        return $resolver->resolve($options);
59
    }
60
61
    private function resolveLayers(ColumnInterface $column)
62
    {
63
        $layers = [$column];
64
        $seen = [spl_object_hash($column) => true];
65
66
        while (null !== $parentType = $column->getParent()) {
67
            $parent = $this->registry->get($parentType);
68
69
            if (isset($seen[spl_object_hash($parent)])) {
70
                throw new \RuntimeException(sprintf(
71
                    'Circular reference detected on class "%s"',
72
                    get_class($parent)
73
                ));
74
            }
75
76
            $layers[] = $parent;
77
            $column = $parent;
78
        }
79
80
        return array_reverse($layers);
81
    }
82
}
83