SystemDCollector   A
last analyzed

Complexity

Total Complexity 12

Size/Duplication

Total Lines 146
Duplicated Lines 0 %

Importance

Changes 13
Bugs 0 Features 0
Metric Value
eloc 105
c 13
b 0
f 0
dl 0
loc 146
rs 10
wmc 12

3 Methods

Rating   Name   Duplication   Size   Complexity  
A collect() 0 4 1
B getServices() 0 44 6
A getServiceClassic() 0 32 5
1
<?php
2
3
namespace Startwind\Inventorio\Collector\System\Service;
4
5
use Startwind\Inventorio\Collector\BasicCollector;
6
use Startwind\Inventorio\Exec\Runner;
7
8
class SystemDCollector extends BasicCollector
9
{
10
    protected string $identifier = 'ServerServiceSystemD';
11
12
    private array $systemServices = [
13
        'accounts-daemon',
14
        'console-setup',
15
        'cron',
16
        'dbus',
17
        'keyboard-setup',
18
        'systemd-journal-flush',
19
        'systemd-journald',
20
        'systemd-logind',
21
        'systemd-modules-load',
22
        'systemd-networkd-wait-online',
23
        'systemd-networkd',
24
        'systemd-quotacheck',
25
        'systemd-random-seed',
26
        'systemd-remount-fs',
27
        'systemd-resolved',
28
        'systemd-sysctl',
29
        'systemd-sysusers',
30
        'systemd-timesyncd',
31
        'systemd-tmpfiles-setup-dev',
32
        'systemd-tmpfiles-setup',
33
        'systemd-udev-trigger',
34
        'systemd-udevd',
35
        'systemd-update-utmp',
36
        'systemd-user-sessions',
37
        'ubuntu-fan',
38
        'user-runtime-dir@0',
39
        'user@0',
40
        'console-setup',
41
        'cron',
42
        'dbus',
43
        'finalrd',
44
        'keyboard-setup',
45
        'qemu-guest-agent',
46
        'rsyslog',
47
        'ssh',
48
        'systemd-binfmt',
49
        'systemd-tmpfiles-setup-dev-early',
50
        'snapd.seeded',
51
        'polkit',
52
        'multipathd',
53
        'finalrd',
54
        'cloud-init-local',
55
        'cloud-final',
56
        'cloud-config',
57
        'apport',
58
        'kmod-static-nodes',
59
        'multipathd',
60
        'plymouth-quit-wait',
61
        'plymouth-quit',
62
        'plymouth-read-write',
63
        'serial-getty@ttyS0',
64
        'setvtrgb',
65
        'sysstat',
66
        'blk-availability',
67
        'getty@tty1',
68
    ];
69
70
    public function collect(): array
71
    {
72
        $services = $this->getServices();
73
        return ['services' => $services];
74
    }
75
76
    private function getServices(): array
77
    {
78
        $runner = Runner::getInstance();
79
80
        if (!$runner->commandExists('systemctl')) {
81
            return [];
82
        }
83
84
        $output = $runner->run("systemctl show --type=service --all --no-page --property=Id,Description,LoadState,ActiveState,SubState")->getOutput();
85
86
        if (!$output) {
87
            return $this->getServiceClassic();
88
        }
89
90
        $services = [];
91
        $systemServices = array_flip($this->systemServices);
92
        $blocks = preg_split('/\n(?=Id=)/', trim($output));
93
94
        foreach ($blocks as $block) {
95
            $lines = explode("\n", trim($block));
96
            $data = [];
97
98
            foreach ($lines as $line) {
99
                [$key, $value] = explode('=', $line, 2);
100
                $data[$key] = trim($value);
101
            }
102
103
            if (($data['LoadState'] ?? '') !== 'loaded') {
104
                continue;
105
            }
106
107
            $id = $data['Id'] ?? '';
108
            $service = str_replace('.service', '', $id);
109
110
            $services[$id] = [
111
                'Id' => $id,
112
                'Description' => $data['Description'] ?? '',
113
                'ActiveState' => $data['ActiveState'] ?? '',
114
                'SubState' => $data['SubState'] ?? '',
115
                'SystemService' => isset($systemServices[$service])
116
            ];
117
        }
118
119
        return $services;
120
    }
121
122
    function getServiceClassic(): array
0 ignored issues
show
Best Practice introduced by
It is generally recommended to explicitly declare the visibility for methods.

Adding explicit visibility (private, protected, or public) is generally recommend to communicate to other developers how, and from where this method is intended to be used.

Loading history...
123
    {
124
        $command = "systemctl list-units --type=service --all --no-legend --no-pager | awk '{printf \"%s|%s|%s|%s|\", \$1, \$2, \$3, \$4; for (i=5; i<=NF; i++) printf \$i \" \"; print \"\"}'";
125
126
        $output = Runner::getInstance()->run($command)->getOutput();
127
128
        if ($output === null) return [];
0 ignored issues
show
introduced by
The condition $output === null is always false.
Loading history...
129
130
        $lines = explode("\n", trim($output));
131
        $services = [];
132
133
        $systemServices = array_flip($this->systemServices);
134
135
        foreach ($lines as $line) {
136
            if (empty($line)) continue;
137
            $parts = explode('|', $line);
138
139
            if (count($parts) >= 5) {
140
                $id = trim($parts[0]);
141
                $service = str_replace('.service', '', $id);
142
143
                $services[$id] = [
144
                    'Id' => $service,
145
                    'Description' => trim($parts[4]),
146
                    'ActiveState' => trim($parts[2]),
147
                    'SubState' => trim($parts[3]),
148
                    'SystemService' => isset($systemServices[$service])
149
                ];
150
            }
151
        }
152
153
        return $services;
154
    }
155
}
156