1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
|
#!/usr/bin/env python3
# Check openvpn-status.log
# needs status-version 3 set in ovpn config!
import json
import datetime
import dateutil.parser
import sys
import argparse
class Status:
OK = 0
WARNING = 1
CRITICAL = 2
UNKNOWN = 3
@staticmethod
def toString(status):
return (['OK', 'WARNING', 'CRITICAL', 'UNKNOWN'])[status]
def print_perfdata(perfdata):
print('|' ,end='')
for d in perfdata:
print(f'{d}={perfdata[d]}', end=' ')
def set_status(status):
if status > STATUS:
return status
return STATUS
parser = argparse.ArgumentParser(description='check openvpn-status.log')
parser.add_argument(dest='logfile')
parser.add_argument('-c', dest='max_conns', action='store', type=int, default=0)
parser.add_argument('-u', dest='max_conns_per_user', action='store', type=int, default=0)
parser.add_argument('-t', dest='traffic', action='store_true')
args=parser.parse_args()
STATUS = Status.OK
STATUS_STRINGS = []
FILE = args.logfile
DATA={}
PERFDATA={}
file_lines=[]
with open(FILE, 'r') as f:
file_lines = f.readlines()
for l in file_lines:
line_elements = l.split('\t')
title = line_elements[0].strip()
if title not in DATA:
DATA[title] = []
DATA[title].append(list(map(lambda x: x.strip(), line_elements[1:])))
now = datetime.datetime.now()
status_time = dateutil.parser.parse(DATA['TIME'][0][0])
status_age = int((now-status_time).total_seconds())
PERFDATA['statusage'] = status_age
if status_age > 120:
STATUS = set_status(Status.UNKNOWN)
STATUS_STRINGS.append(f'Statusfile is {status_age} seconds old. This should be no more than 60.')
if 'CLIENT_LIST' not in DATA:
DATA['CLIENT_LIST'] = []
if args.max_conns > 0:
clients = ', '.join(list(map(lambda x: x[0], DATA['CLIENT_LIST'])))
clients_cnt = len(DATA['CLIENT_LIST'])
if clients_cnt >= args.max_conns:
STATUS = set_status(Status.CRITICAL)
elif clients_cnt >= (args.max_conns * 0.9):
STATUS = set_status(Status.WARNING)
PERFDATA['clients_cnt'] = f'{clients_cnt};{int(args.max_conns*0.9)};{args.max_conns}'
STATUS_STRINGS.append(f'{clients_cnt} clients logged in ({clients})')
if args.max_conns_per_user > 0:
user_cnts = {}
for u in DATA['CLIENT_LIST']:
uname = u[8]
if uname in user_cnts:
user_cnts[uname] += 1
else:
user_cnts[uname] = 1
for u in user_cnts:
if user_cnts[u] >= args.max_conns_per_user:
STATUS = set_status(Status.CRITICAL)
if user_cnts[u] >= (args.max_conns_per_user * 0.8):
STATUS = set_status(Status.WARNING)
STATUS_STRINGS.append(f'{u} is logged in {user_cnts[u]} times')
PERFDATA[f'user_{u}'] = f'{user_cnts[u]};{int(args.max_conns_per_user * 0.8)};{int(args.max_conns_per_user)}'
if args.traffic:
recv_cnt = 0
sent_cnt = 0
for u in DATA['CLIENT_LIST']:
recv_cnt += int(u[4])
sent_cnt += int(u[5])
PERFDATA['recieved_bytes'] = f'{recv_cnt}B'
PERFDATA['sent_bytes'] = f'{sent_cnt}B'
print(f'OpenVPN {Status.toString(STATUS)}')
for s in STATUS_STRINGS:
print(s)
print_perfdata(PERFDATA)
|