Passed
Pull Request — master (#13)
by Jesús
02:13
created

TransactionMessage::groupedSegmentsNotEmpty()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 1
c 0
b 0
f 0
nc 1
nop 1
dl 0
loc 3
rs 10
ccs 2
cts 2
cp 1
crap 1
1
<?php
2
3
declare(strict_types=1);
4
5
namespace EdifactParser;
6
7
use EdifactParser\Segments\SegmentInterface;
8
use EdifactParser\Segments\UNHMessageHeader;
9
use EdifactParser\Segments\UNTMessageFooter;
10
11
/** @psalm-immutable */
12
final class TransactionMessage
13
{
14
    /** @var array<string, array<string,SegmentInterface>> */
15
    private array $groupedSegments;
16
17
    /**
18
     * A transaction message starts with the "UNHMessageHeader" segment and finalizes with
19
     * the "UNTMessageFooter" segment, this process is repeated for each pair of segments.
20
     *
21
     * @psalm-pure
22
     * @psalm-return list<TransactionMessage>
23
     */
24 9
    public static function groupSegmentsByMessage(SegmentInterface...$segments): array
25
    {
26 9
        $messages = [];
27 9
        $groupedSegments = [];
28
29 9
        foreach ($segments as $segment) {
30 9
            if ($segment instanceof UNHMessageHeader) {
31 9
                $groupedSegments = [];
32
            }
33
34 9
            $groupedSegments[] = $segment;
35
36 9
            if ($segment instanceof UNTMessageFooter
37 9
                && self::groupedSegmentsNotEmpty($groupedSegments)
38
            ) {
39 8
                $messages[] = self::groupSegmentsByName(...$groupedSegments);
40
            }
41
        }
42
43 9
        return array_values(
44
            array_filter($messages, static function (self $m) {
45 8
                return !empty($m->segmentByName(UNHMessageHeader::class));
46 9
            })
47
        );
48
    }
49
50
    /** @param array<string, array<string,SegmentInterface>> $groupedSegments */
51 8
    public function __construct(array $groupedSegments)
52
    {
53 8
        $this->groupedSegments = $groupedSegments;
54 8
    }
55
56 8
    public function segmentByName(string $name): array
57
    {
58 8
        return $this->groupedSegments[$name] ?? [];
59
    }
60
61
    /**
62
     * We add automatically all items to the $groupedSegments array in the loop,
63
     * one message is made of "UNHMessageHeader" and "UNTMessageFooter" segments.
64
     * So the minimum messages are two, only one segment is not possible.
65
     * @psalm-pure
66
     */
67 9
    private static function groupedSegmentsNotEmpty(array $groupedSegments): bool
68
    {
69 9
        return count($groupedSegments) > 1;
70
    }
71
72
    /** @psalm-pure */
73 8
    private static function groupSegmentsByName(SegmentInterface...$segments): self
74
    {
75 8
        $return = [];
76
77 8
        foreach ($segments as $s) {
78 8
            $return[$s->tag()] ??= [];
79 8
            $return[$s->tag()][$s->subId()] = $s;
80
        }
81
82 8
        return new self($return);
83
    }
84
}
85