e8eb5c3f0b097ab59dd2b2742138ddba61ca956c
[unfold.git] / activity / __init__.py
1 #
2 # Activity monitor
3 #
4 # Client is authenticated with an API key and a secret
5 # The API key is a 64 chars string (digits and letters) that is passed to the request
6 # The secret is a 64 chars string that is used to sign the request
7 # The generated signature is a SHA256 hes digest
8
9 from __future__ import print_function
10
11 import urllib, urllib2
12 import threading
13 import hmac
14 import hashlib
15 import base64
16 import time
17 import datetime
18 from myslice.configengine import ConfigEngine
19
20 config = ConfigEngine()
21 if config.activity and config.activity.apikey :
22     apikey = config.activity.apikey
23 else :
24     # apikey will be necessary
25     apikey = None
26
27 if config.activity and config.activity.secret :
28     secret = config.activity.secret
29 else :
30     # secret will be necessary
31     secret = None
32
33 if config.activity and config.activity.server :
34     server = config.activity.server
35 else :
36     # default log server
37     server = "http://athos.ipv6.lip6.fr/activity/push/log"
38
39 def logWrite(request, action, message, objects = None):
40     
41     if not apikey :
42         print("===============>> activity: no apikey")
43         return
44     if not secret :
45         print("===============>> activity: no secret")
46         return
47     
48     timestamp = time.mktime(datetime.datetime.today().timetuple())
49     ip = getClientIp(request)
50     log = {
51         "timestamp" : timestamp,
52         "client_ip" : ip,
53         "host"      : request.get_host(),
54         "referrer"  : request.META.get('HTTP_REFERER'),
55         "user"      : request.user,
56         "action"    : action,
57         "message"   : message,
58         "apikey"    : apikey,
59         "signature" : sign(secret, "%s%s%s%s" % (timestamp, ip, request.user, action)),
60         "slice"     : None,
61         "resource"  : None,
62         "resource_type"     : None,
63         "facility"      : None,
64         "testbed"       : None,
65     }
66     
67     if objects is not None:
68         for o in objects :
69             if (o in log) :
70                 log[o] = objects[o]
71     
72     try :
73         result = urllib2.urlopen(server, urllib.urlencode(log))
74         print("===============>> activity: %s <%s> %s" % (action, request.user,message))
75         content = result.read()
76     except urllib2.URLError as e:
77         print("===============>> activity: connection to " + server + " impossible, could not log action")
78         print(e.strerror)
79         print("")
80
81 def log(request, action, message, objects = None):
82     # Create a new thread in Daemon mode to send the log entry
83     t = threading.Thread(target=logWrite, args=(request, action, message, objects))
84     t.setDaemon(True)
85     t.start()
86
87 def getClientIp(request):
88     x_forwarded_for = request.META.get('HTTP_X_FORWARDED_FOR')
89     if x_forwarded_for:
90         ip = x_forwarded_for.split(',')[0]
91     else:
92         ip = request.META.get('REMOTE_ADDR')
93     return ip
94
95 #
96 # sign the request with the secret key
97 def sign(secret, message):
98     return hmac.new(secret, msg=message, digestmod=hashlib.sha256).hexdigest()