2 # -*- encoding: utf-8; py-indent-offset: 4 -*-
3 # +------------------------------------------------------------------+
4 # | ____ _ _ __ __ _ __ |
5 # | / ___| |__ ___ ___| | __ | \/ | |/ / |
6 # | | | | '_ \ / _ \/ __| |/ / | |\/| | ' / |
7 # | | |___| | | | __/ (__| < | | | | . \ |
8 # | \____|_| |_|\___|\___|_|\_\___|_| |_|_|\_\ |
10 # | Copyright Mathias Kettner 2014 mk@mathias-kettner.de |
11 # +------------------------------------------------------------------+
13 # This file is part of Check_MK.
14 # The official homepage is at http://mathias-kettner.de/check_mk.
16 # check_mk is free software; you can redistribute it and/or modify it
17 # under the terms of the GNU General Public License as published by
18 # the Free Software Foundation in version 2. check_mk is distributed
19 # in the hope that it will be useful, but WITHOUT ANY WARRANTY; with-
20 # out even the implied warranty of MERCHANTABILITY or FITNESS FOR A
21 # PARTICULAR PURPOSE. See the GNU General Public License for more de-
22 # tails. You should have received a copy of the GNU General Public
23 # License along with GNU Make; see the file COPYING. If not, write
24 # to the Free Software Foundation, Inc., 51 Franklin St, Fifth Floor,
25 # Boston, MA 02110-1301 USA.
28 # MSSQL_SQLEXPRESS1 test123 1331207325
31 # MSSQL_SQL0x2 master 2016-07-08 20:20:27
32 # MSSQL_SQL0x2 model 2016-07-08 20:20:28
33 # MSSQL_SQL0x2 model 2016-07-12 09:09:42
34 # MSSQL_SQL0x2 model 2016-07-11 20:20:07
35 # MSSQL_SQL0x2 msdb 2016-07-08 20:20:43
36 # MSSQL_SQL0x2 msdb 2016-07-11 20:20:07
39 # MSSQL_SQL0x3 master 2016-07-08 20:20:27 D
40 # MSSQL_SQL0x3 model 2016-07-08 20:20:28 D
41 # MSSQL_SQL0x3 model 2016-07-12 09:09:42 L
42 # MSSQL_SQL0x3 model 2016-07-11 20:20:07 I
43 # MSSQL_SQL0x3 msdb 2016-07-08 20:20:43 D
44 # MSSQL_SQL0x3 msdb 2016-07-11 20:20:07 I
46 # <<<mssql_backup:sep(124)>>>
47 # MSSQL_SQL0x4|master|2016-07-08 20:20:27|D
48 # MSSQL_SQL0x4|model|2016-07-08 20:20:28|D
49 # MSSQL_SQL0x4|model|2016-07-12 09:09:42|L
50 # MSSQL_SQL0x4|model|2016-07-11 20:20:07|I
51 # MSSQL_SQL0x4|msdb|2016-07-08 20:20:43|D
52 # MSSQL_SQL0x4|msdb|2016-07-11 20:20:07|I
54 discovery_mssql_backup
= []
56 factory_settings
["mssql_backup_default_levels"] = {
57 "database": (None, None),
58 "database_diff": (None, None),
60 "file_or_filegroup": (None, None),
61 "file_diff": (None, None),
62 "partial": (None, None),
63 "partial_diff": (None, None),
64 "unspecific": (None, None),
68 def parse_mssql_backup(info
):
69 def _parse_date_and_time(b_date
, b_time
):
73 return time
.mktime(time
.strptime("%s %s" % (b_date
, b_time
), '%Y-%m-%d %H:%M:%S'))
81 "F": "file or filegroup",
89 Backup
= collections
.namedtuple("Backup", ["timestamp", "type", "state"])
93 # handle one special case where spaces are in date/time:
94 if len(line
) == 4 and " " in line
[2]:
95 line
= line
[:2] + line
[2].split(" ") + line
[3:]
98 line
+= [None] * (6 - len(line
))
100 inst
, tablespace
, b_date
, b_time
, b_type
, b_state
= line
101 timestamp
= _parse_date_and_time(b_date
, b_time
)
103 item
= "%s %s" % (inst
, tablespace
)
104 backup
= Backup(timestamp
, map_backup_types
.get(b_type
), b_state
or "")
105 parsed
.setdefault(item
, []).append(backup
)
110 def inventory_mssql_backup(parsed
):
111 discovery_mode
= _mssql_backup_discovery_mode()
112 if discovery_mode
!= "summary":
114 for db_name
in parsed
:
118 def _mssql_backup_discovery_mode():
119 rules
= host_extra_conf(host_name(), discovery_mssql_backup
)
121 return rules
[0]['mode']
122 except (IndexError, KeyError):
123 return "summary" # default, comp. to older versions
126 def check_mssql_backup(item
, params
, parsed
):
127 data
= parsed
.get(item
)
129 # Assume general connection problem to the database, which is reported
130 # by the "X Instance" service and skip this check.
131 raise MKCounterWrapped("Failed to connect to database")
133 if not isinstance(params
, dict):
134 params
= {"database": params
}
137 if backup
.state
== "no backup found":
138 yield params
.get("not_found", 1), "No backup found"
140 if backup
.state
.startswith("ERROR: "):
141 yield 2, backup
.state
[7:]
143 if backup
.type is None:
144 backup_type_var
= "database"
146 backup_type_info
= "[database]"
148 backup_type_var
= backup
.type.strip().replace(" ", "_")
149 perfkey
= "backup_age_%s" % backup_type_var
150 backup_type_info
= "[%s]" % backup
.type
151 state
, infotext
, perfdata
=\
152 _check_mssql_backup(backup
, params
.get(backup_type_var
, (None, None)), perfkey
)
153 yield state
, "%s %s" % (backup_type_info
, infotext
), perfdata
156 def _check_mssql_backup(backup
, levels
, perfkey
):
158 age_warn
, age_crit
= levels
159 sec_ago
= time
.time() - backup
.timestamp
160 if age_crit
is not None and sec_ago
>= age_crit
:
162 elif age_warn
is not None and sec_ago
>= age_warn
:
165 infotext
= 'Last backup was at %s (%s ago)' % (time
.strftime(
166 '%Y-%m-%d %H:%M:%S', time
.localtime(backup
.timestamp
)), get_age_human_readable(sec_ago
))
169 infotext
+= " (warn/crit at %s/%s)" % (get_age_human_readable(age_warn
),
170 get_age_human_readable(age_crit
))
172 return state
, infotext
, [(perfkey
, sec_ago
, age_warn
, age_crit
)]
175 check_info
['mssql_backup'] = {
176 'parse_function': parse_mssql_backup
,
177 'check_function': check_mssql_backup
,
178 'inventory_function': inventory_mssql_backup
,
179 'service_description': 'MSSQL %s Backup',
180 'has_perfdata': True,
181 'group': 'mssql_backup',
182 'default_levels_variable': 'mssql_backup_default_levels',
186 # .--single--------------------------------------------------------------.
188 # | ___(_)_ __ __ _| | ___ |
189 # | / __| | '_ \ / _` | |/ _ \ |
190 # | \__ \ | | | | (_| | | __/ |
191 # | |___/_|_| |_|\__, |_|\___| |
193 # '----------------------------------------------------------------------'
196 def _mssql_backup_per_type_item(db_name
, backup
):
197 if backup
.type is None:
198 return "%s UNKNOWN" % db_name
199 return "%s %s" % (db_name
, backup
.type.title())
202 def inventory_mssql_backup_per_type(parsed
):
203 discovery_mode
= _mssql_backup_discovery_mode()
204 if discovery_mode
!= "per_type":
206 for db_name
, attrs
in parsed
.iteritems():
208 yield _mssql_backup_per_type_item(db_name
, backup
), {}
211 def check_mssql_backup_per_type(item
, params
, parsed
):
212 for db_name
, attrs
in parsed
.iteritems():
214 if item
== _mssql_backup_per_type_item(db_name
, backup
):
215 return _check_mssql_backup(backup
, params
.get("levels", (None, None)), "backup_age")
216 # Assume general connection problem to the database, which is reported
217 # by the "X Instance" service and skip this check.
218 raise MKCounterWrapped("Failed to connect to database")
221 check_info
['mssql_backup.per_type'] = {
222 'check_function': check_mssql_backup_per_type
,
223 'inventory_function': inventory_mssql_backup_per_type
,
224 'service_description': 'MSSQL %s Backup',
225 'has_perfdata': True,
226 'group': 'mssql_backup_per_type',