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
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
|
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
# Plugin to monitor nextcloud external api statistics
# * user activity
# * db size
# * share count
# * available app updates
#
# Parameters understood:
# config (required)
# autoconf (optional - used by munin-config)
# Magic markers - optional - used by installation scripts and
# munin-config:
#
# #%# family=manual
# #%# capabilities=autoconf
import requests
import sys
import os
import re
class NextcloudMultiGraph:
def config(self):
config = {
'users': [
'multigraph nextcloud_users',
'graph_title Nextcloud User Activity',
'graph_args --base 1024 -l 0',
'graph_printf %.0lf',
'graph_vlabel connected users',
'graph_info graph showing the number of connected user',
'graph_category nextcloud',
'last5minutes.label last 5 minutes',
'last5minutes.info users connected in the last 5 minutes',
'last1hour.label last hour',
'last1hour.info users connected in the last hour',
'last24hours.label last 24 hours',
'last24hours.info users connected in the last 24 hours'
],
'shares': [
'multigraph nextcloud_shares',
'graph_title Nextcloud Shares',
'graph_args --base 1024 -l 0',
'graph_vlabel number of shares',
'graph_info graph showing the number of shares',
'graph_category nextcloud',
'num_fed_shares_received.label federated shares recieved',
'num_fed_shares_received.info current total of federated shares recieved',
'num_fed_shares_sent.label federated shares sent',
'num_fed_shares_sent.info current total of federated shares sent',
'num_shares.label total number of shares',
'num_shares.info current over all total of shares',
'num_shares_groups.label group shares',
'num_shares_groups.info current total of group shares',
'num_shares_link.label link shares',
'num_shares_link.info current total of shares through a link',
'num_shares_link_no_password.label link shares without a password',
'num_shares_link_no_password.info current total of shares through a link without a password protection',
'num_shares_user.label user shares',
'num_shares_user.info current total of user shares'
],
'dbsize': [
'multigraph nextcloud_dbsize',
'graph_title Nextcloud Database Size',
'graph_args --base 1024 -l 0',
'graph_vlabel size in byte',
'graph_info graph showing the database size in byte',
'graph_category nextcloud',
'db_size.label database size in byte',
'db_size.info users connected in the last 5 minutes',
'db_size.draw AREA',
],
'available_updates': [
'multigraph nextcloud_available_updates',
'graph_title Nextcloud available App updates',
'graph_args --base 1024 -l 0',
'graph_vlabel updates available',
'graph_info graph showing the number of available app updates',
'graph_category nextcloud',
'num_updates_available.label available app updates',
'num_updates_available.info number of available app updates',
]
}
return config
def get_data(self, api_response):
data ={
'nextcloud_users': [],
'nextcloud_shares': [],
'nextcloud_dbsize': [],
'nextcloud_available_updates': []
}
users = api_response['ocs']['data']['activeUsers']
shares = api_response['ocs']['data']['nextcloud']['shares']
dbsize = api_response['ocs']['data']['server']['database']['size']
data['nextcloud_users'].append('multigraph nextcloud_users')
for key in users.keys():
data['nextcloud_users'].append(str(key) + ".value " + str(users[key]))
# use regex to remove permission stats from api response
reg = re.compile("num.*")
share_keys = shares.keys()
sharelist = list(filter(reg.match, share_keys))
data['nextcloud_shares'].append('multigraph nextcloud_shares')
for key in sharelist:
data['nextcloud_shares'].append(str(key) + ".value " + str(shares[key]))
data['nextcloud_dbsize'].append('multigraph nextcloud_dbsize')
data['nextcloud_dbsize'].append('db_size.value %s' % dbsize)
# precaution for Nextcloud versions prior to version 14
try:
num_updates_available = api_response['ocs']['data']['nextcloud']['system']['apps']['num_updates_available']
data['nextcloud_available_updates'].append('multigraph nextcloud_available_updates')
data['nextcloud_available_updates'].append('num_updates_available.value %s' % num_updates_available)
except KeyError:
return False
return data
def run(self):
# read the configuration from munin environment
URL = os.environ['url']
auth = (os.environ['username'], os.environ['password'])
# init requests session with specific header and credentials
with requests.Session() as s:
s.auth = auth
s.headers.update({'Accept': 'application/json'})
s.stream = False
# request data from api
r = s.get(URL)
# if status code is successful close connection and continue
if r.status_code == 200:
s.close()
api_response = r.json()
result = self.get_data(api_response)
for key in result.keys():
print('\n'.join(result[key]))
elif r.status_code == 996:
print('server error')
elif r.status_code == 997:
print('not authorized')
elif r.status_code == 998:
print('not found')
else:
print('unknown error')
def main(self):
if (sys.argv.__len__() == 2) and (sys.argv[1] == "config"):
for key in self.config().keys():
print('\n'.join(self.config()[key]))
try:
if os.environ['MUNIN_CAP_DIRTYCONFIG'] == '1':
self.run()
except KeyError:
pass
elif (sys.argv.__len__() == 2) and (sys.argv[1] == 'autoconf'):
# check host if env variables are set
try:
if None not in {os.environ['url'], os.environ['username'], os.environ['password']}:
print('yes')
except KeyError:
print('no env configuration options are missing')
else:
self.run()
if __name__ == "__main__":
NextcloudMultiGraph().main()
quit(0)
|