Passed
Push — master ( 698671...851994 )
by Tony
40:30 queued 28:04
created

AlertRules   A

Complexity

Total Complexity 23

Size/Duplication

Total Lines 87
Duplicated Lines 0 %

Importance

Changes 1
Bugs 0 Features 0
Metric Value
wmc 23
eloc 63
c 1
b 0
f 0
dl 0
loc 87
rs 10

1 Method

Rating   Name   Duplication   Size   Complexity  
F runRules() 0 85 23
1
<?php
2
/**
3
 * AlertRules.php
4
 *
5
 * Extending the built in logging to add an event logger function
6
 *
7
 * This program is free software: you can redistribute it and/or modify
8
 * it under the terms of the GNU General Public License as published by
9
 * the Free Software Foundation, either version 3 of the License, or
10
 * (at your option) any later version.
11
 *
12
 * This program is distributed in the hope that it will be useful,
13
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
14
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.See the
15
 * GNU General Public License for more details.
16
 *
17
 * You should have received a copy of the GNU General Public License
18
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
19
 *
20
 * Original Code:
21
 * @author Daniel Preussker <[email protected]>
22
 * @copyright 2014 f0o, LibreNMS
23
 * @license GPL
24
 * @package LibreNMS
25
 * @subpackage Alerts
26
 *
27
 * Modeified by:
28
 * @package    LibreNMS
29
 * @link       http://librenms.org
30
 * @copyright  2019 KanREN, Inc.
31
 * @author     Heath Barnhart <[email protected]>
32
 */
33
34
namespace LibreNMS\Alert;
35
36
use App\Models\Device;
37
use LibreNMS\Alert\AlertUtil;
38
use LibreNMS\Alert\AlertDB;
39
40
class AlertRules
41
{
42
    public function runRules($device_id)
43
    {
44
45
        //Check to see if under maintenance
46
        if (AlertUtil::isMaintenance($device_id) > 0) {
47
            echo "Under Maintenance, Skipping alerts.\r\n";
48
            return false;
49
        }
50
        //Checks each rule.
51
        foreach (AlertUtil::getRules($device_id) as $rule) {
52
            c_echo('Rule %p#'.$rule['id'].' (' . $rule['name'] . '):%n ');
53
            $extra = json_decode($rule['extra'], true);
54
            if (isset($extra['invert'])) {
55
                $inv = (bool) $extra['invert'];
56
            } else {
57
                $inv = false;
58
            }
59
            d_echo(PHP_EOL);
60
            if (empty($rule['query'])) {
61
                $rule['query'] = AlertDB::genSQL($rule['rule'], $rule['builder']);
62
            }
63
            $sql = $rule['query'];
64
            $qry = dbFetchRows($sql, array($device_id));
65
            $cnt = count($qry);
66
            for ($i = 0; $i < $cnt; $i++) {
67
                if (isset($qry[$i]['ip'])) {
68
                    $qry[$i]['ip'] = inet6_ntop($qry[$i]['ip']);
69
                }
70
            }
71
            $s = sizeof($qry);
72
            if ($s == 0 && $inv === false) {
73
                $doalert = false;
74
            } elseif ($s > 0 && $inv === false) {
75
                $doalert = true;
76
            } elseif ($s == 0 && $inv === true) {
77
                $doalert = true;
78
            } else {
79
                $doalert = false;
80
            }
81
82
            $current_state = dbFetchCell("SELECT state FROM alerts WHERE rule_id = ? AND device_id = ? ORDER BY id DESC LIMIT 1", [$rule['id'], $device_id]);
83
            if ($doalert) {
84
                if ($current_state == 2) {
85
                    c_echo('Status: %ySKIP');
86
                } elseif ($current_state >= 1) {
87
                    c_echo('Status: %bNOCHG');
88
                    // NOCHG here doesn't mean no change full stop. It means no change to the alert state
89
                    // So we update the details column with any fresh changes to the alert output we might have.
90
                    $alert_log = dbFetchRow('SELECT alert_log.id, alert_log.details FROM alert_log,alert_rules WHERE alert_log.rule_id = alert_rules.id && alert_log.device_id = ? && alert_log.rule_id = ? && alert_rules.disabled = 0
91
     ORDER BY alert_log.id DESC LIMIT 1', array($device_id, $rule['id']));
92
                    $details = [];
93
                    if (!empty($alert_log['details'])) {
94
                         $details = json_decode(gzuncompress($alert_log['details']), true);
95
                    }
96
                    $details['contacts'] = AlertUtil::getContacts($qry);
97
                    $details['rule']     = $qry;
98
                    $details             = gzcompress(json_encode($details), 9);
99
                    dbUpdate(array('details' => $details), 'alert_log', 'id = ?', array($alert_log['id']));
100
                } else {
101
                    $extra = gzcompress(json_encode(array('contacts' => AlertUtil::getContacts($qry), 'rule'=>$qry)), 9);
102
                    if (dbInsert(['state' => 1, 'device_id' => $device_id, 'rule_id' => $rule['id'], 'details' => $extra], 'alert_log')) {
103
                        if (is_null($current_state)) {
104
                            dbInsert(array('state' => 1, 'device_id' => $device_id, 'rule_id' => $rule['id'], 'open' => 1,'alerted' => 0), 'alerts');
105
                        } else {
106
                            dbUpdate(['state' => 1, 'open' => 1], 'alerts', 'device_id = ? && rule_id = ?', [$device_id, $rule['id']]);
107
                        }
108
                        c_echo(PHP_EOL . 'Status: %rALERT');
109
                    }
110
                }
111
            } else {
112
                if (!is_null($current_state) && $current_state == 0) {
113
                    c_echo('Status: %bNOCHG');
114
                } else {
115
                    if (dbInsert(['state' => 0, 'device_id' => $device_id, 'rule_id' => $rule['id']], 'alert_log')) {
116
                        if (is_null($current_state)) {
117
                            dbInsert(['state' => 0, 'device_id' => $device_id, 'rule_id' => $rule['id'], 'open' => 1, 'alerted' => 0], 'alerts');
118
                        } else {
119
                            dbUpdate(['state' => 0, 'open' => 1, 'note' => ''], 'alerts', 'device_id = ? && rule_id = ?', [$device_id, $rule['id']]);
120
                        }
121
122
                        c_echo(PHP_EOL . 'Status: %gOK');
123
                    }
124
                }
125
            }
126
            c_echo('%n' . PHP_EOL);
127
        }
128
    }
129
}
130