AbstractOs::getPeakMemoryUsagePercentage()   A
last analyzed

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 1
dl 0
loc 3
rs 10
c 0
b 0
f 0
1
<?php
2
/**
3
 * @package     Cronfig Sysinfo Library
4
 * @link        https://github.com/cronfig/sysinfo
5
 * @license     http://opensource.org/licenses/MIT
6
 */
7
8
namespace Cronfig\Sysinfo;
9
10
/**
11
 * Abstract model of a general Operating System
12
 *
13
 * Class AbstractOs
14
 */
15
abstract class AbstractOs
16
{
17
    const TIMEFRAME_1_MIN = 0;
18
    const TIMEFRAME_5_MIN = 1;
19
    const TIMEFRAME_15_MIN = 2;
20
21
    /**
22
     * Checks whether the system has enough system load and memory for more work to do.
23
     * Less than 90% by default.
24
     *
25
     * @param  int $timeframe
26
     * @param  int $limit In percent
27
     *
28
     * @return bool
29
     */
30
    public function canHandleMore($timeframe, $limit = 90)
31
    {
32
        if ($this->getCurrentMemoryUsagePercentage() >= $limit) {
33
            return false;
34
        }
35
36
        if ($this->getLoadPercentage($timeframe) >= $limit) {
37
            return false;
38
        }
39
40
        return true;
41
    }
42
43
    /**
44
     * Returns the amount of memory allocated to PHP
45
     *
46
     * @return int in bytes
47
     */
48
    public function getCurrentMemoryUsage()
49
    {
50
        $this->requiredFunction('memory_get_usage');
51
52
        return memory_get_usage();
53
    }
54
55
    /**
56
     *  Returns the peak of memory allocated by PHP
57
     *
58
     * @return int in bytes
59
     */
60
    public function getPeakMemoryUsage()
61
    {
62
        $this->requiredFunction('memory_get_peak_usage');
63
64
        return memory_get_peak_usage();
65
    }
66
67
    /**
68
     * Finds out PHP memory limit from php.ini
69
     *
70
     * @return int in bytes
71
     */
72
    public function getMemoryLimit()
73
    {
74
        return $this->getBytesFromPhpIniValue(ini_get('memory_limit'));
75
    }
76
77
    /**
78
     * Finds out max PHP execution time limit from php.ini
79
     *
80
     * @return int in seconds. If set to zero, no time limit is imposed.
81
     */
82
    public function getExecutionTimeLimit()
83
    {
84
        return (int) ini_get('max_execution_time');
85
    }
86
87
    /**
88
     * Calculates current memory usage where 100% is the PHP memory limit
89
     *
90
     * @param int $round
91
     *
92
     * @return float
93
     */
94
    public function getCurrentMemoryUsagePercentage($round = 2)
95
    {
96
        return $this->getPercentage($this->getCurrentMemoryUsage(), $this->getMemoryLimit(), $round);
97
    }
98
99
    /**
100
     * Calculates peak memory usage where 100% is the PHP memory limit
101
     *
102
     * @param int $round
103
     *
104
     * @return float
105
     */
106
    public function getPeakMemoryUsagePercentage($round = 2)
107
    {
108
        return $this->getPercentage($this->getPeakMemoryUsage(), $this->getMemoryLimit(), $round);
109
    }
110
111
    /**
112
     * Returns system load divided by CPU cores to get percentage per core.
113
     * value < 100% means system handles the processes fine
114
     * value > 100% means system is overloaded and some processes are waiting for processing time
115
     *
116
     * @param int $timeframe Use the constats of this class instead of integers
117
     * @param int $round
118
     *
119
     * @return float
120
     */
121
    public function getLoadPercentage($timeframe, $round = 2)
122
    {
123
        return $this->getPercentage($this->getLoad($timeframe), $this->getCoreCount(), $round);
124
    }
125
126
    /**
127
     * Gets system load. Implemented by PHP only on linux based systems.
128
     *
129
     * @param int $timeframe Use the constats of this class instead of integers
130
     *
131
     * @return int
132
     */
133
    public function getLoad($timeframe)
134
    {
135
        $this->requiredFunction('sys_getloadavg');
136
137
        $possibleArguments = [self::TIMEFRAME_1_MIN, self::TIMEFRAME_5_MIN, self::TIMEFRAME_15_MIN];
138
139
        if (!in_array($timeframe, $possibleArguments)) {
140
            throw new \UnexpectedValueException;
141
        }
142
143
        return sys_getloadavg()[$timeframe];
144
    }
145
146
    /**
147
     * Counts free disk percentage
148
     *
149
     * @param int $round
150
     *
151
     * @return float
152
     */
153
    public function getDiskUsagePercentage($round = 2)
154
    {
155
        $this->requiredFunction('disk_total_space')->requiredFunction('disk_free_space');
156
157
        $disktotal = disk_total_space('/');
158
        $diskfree  = disk_free_space('/');
159
160
        return 100 - $this->getPercentage($diskfree, $disktotal, $round);
161
    }
162
163
    /**
164
     * Counts CPU cores of the current system
165
     *
166
     * @return int
167
     */
168
    public function getCoreCount()
169
    {
170
        throw new \BadMethodCallException(__METHOD__.' must be implemented in a child class');
171
    }
172
173
    /**
174
     * Returns name of the current OS
175
     *
176
     * @return string
177
     */
178
    public function getCurrentOsName()
179
    {
180
        $this->requiredFunction('php_uname');
181
        return php_uname('s');
182
    }
183
184
    /**
185
     * Provides optimal timeframe for system load methods based on real execution time
186
     *
187
     * @param int $executionTime in seconds
188
     *
189
     * @return int
190
     */
191
    public function getTimeframeFromExecutionTime($executionTime)
192
    {
193
        $ETInMinutes = $executionTime / 60;
194
195
        if ($ETInMinutes > 10) {
196
            $timeframe = self::TIMEFRAME_15_MIN;
197
        } elseif ($ETInMinutes > 4) {
198
            $timeframe = self::TIMEFRAME_5_MIN;
199
        } else {
200
            $timeframe = self::TIMEFRAME_1_MIN;
201
        }
202
203
        return $timeframe;
204
    }
205
206
    /**
207
     * Helper method which counts percentage and ensures we don't devide by 0
208
     *
209
     * @param double $current
210
     * @param double $limit
211
     * @param int $round
212
     *
213
     * @return float
214
     */
215
    public function getPercentage($current, $limit, $round = 2)
216
    {
217
        if (!$limit) {
218
            return 0;
219
        }
220
221
        return round($current / $limit * 100, $round);
222
    }
223
224
    /**
225
     * Converts shorthand memory notation value to bytes
226
     *
227
     * @param string $val Memory size shorthand notation string
228
     *
229
     * @return int in bytes
230
     */
231
    public function getBytesFromPhpIniValue($val)
232
    {
233
        $val  = trim($val);
234
        $unit = strtolower($val[strlen($val) - 1]);
235
        $val  = (int) substr($val, 0, -1);
236
237
        switch ($unit) {
238
            case 'g':
239
                $val *= 1024;
240
                // no break;
241
            case 'm':
242
                $val *= 1024;
243
                // no break;
244
            case 'k':
245
                $val *= 1024;
246
                // no break;
247
        }
248
249
        return $val;
250
    }
251
252
    /**
253
     * Throws an exception if the function does not exist or is disabled
254
     *
255
     * @param string $name of the required function
256
     *
257
     * @return self
258
     */
259
    public function requiredFunction($name)
260
    {
261
        if (!function_exists($name)) {
262
            throw new \BadFunctionCallException('Function '.$name.' does not exist.');
263
        }
264
265
        if ($this->isFunctionDisabled($name)) {
266
            throw new \BadFunctionCallException('Function '.$name.' is disabled in php.ini.');
267
        }
268
269
        return $this;
270
    }
271
272
    /**
273
     * Check if the function is disabled in php.ini
274
     *
275
     * @param string $name
276
     *
277
     * @return bool
278
     */
279
    public function isFunctionDisabled($name)
280
    {
281
        $disabled = explode(',', ini_get('disable_functions'));
282
        return in_array($name, $disabled);
283
    }
284
}
285