Revision c8a38c0e

b/snf-astakos-app/astakos/admin/admin_urls.py
1
# Copyright 2013 GRNET S.A. All rights reserved.
2
#
3
# Redistribution and use in source and binary forms, with or
4
# without modification, are permitted provided that the following
5
# conditions are met:
6
#
7
#   1. Redistributions of source code must retain the above
8
#      copyright notice, this list of conditions and the following
9
#      disclaimer.
10
#
11
#   2. Redistributions in binary form must reproduce the above
12
#      copyright notice, this list of conditions and the following
13
#      disclaimer in the documentation and/or other materials
14
#      provided with the distribution.
15
#
16
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
# POSSIBILITY OF SUCH DAMAGE.
28
#
29
# The views and conclusions contained in the software and
30
# documentation are those of the authors and should not be
31
# interpreted as representing official policies, either expressed
32
# or implied, of GRNET S.A.
33

  
34
from django.conf.urls import url, patterns
35

  
36
from astakos.admin import views
37
from django.http import Http404
38

  
39

  
40
def index(request):
41
    raise Http404
42

  
43

  
44
urlpatterns = patterns(
45
    '',
46
    url(r'^$', index),
47
    url(r'^stats$', views.get_public_stats),
48
    url(r'^stats/detail$', views.get_astakos_stats),
49
)
b/snf-astakos-app/astakos/admin/stats.py
1
# Copyright 2013 GRNET S.A. All rights reserved.
2
#
3
# Redistribution and use in source and binary forms, with or
4
# without modification, are permitted provided that the following
5
# conditions are met:
6
#
7
#   1. Redistributions of source code must retain the above
8
#      copyright notice, this list of conditions and the following
9
#      disclaimer.
10
#
11
#   2. Redistributions in binary form must reproduce the above
12
#      copyright notice, this list of conditions and the following
13
#      disclaimer in the documentation and/or other materials
14
#      provided with the distribution.
15
#
16
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
# POSSIBILITY OF SUCH DAMAGE.
28
#
29
# The views and conclusions contained in the software and
30
# documentation are those of the authors and should not be
31
# interpreted as representing official policies, either expressed
32
# or implied, of GRNET S.A.
33
import datetime
34
from django.conf import settings
35
from django.db.models import Sum
36

  
37
from astakos.im.models import AstakosUser, Resource
38
from astakos.quotaholder_app.models import Holding
39

  
40

  
41
def get_public_stats():
42
    users = AstakosUser.objects.all()
43
    active = users.filter(is_active=True)
44
    return {"users": {"total": users.count(),
45
                      "active": active.count()}}
46

  
47

  
48
def get_astakos_stats():
49
    stats = {"datetime": datetime.datetime.now().strftime("%c")}
50

  
51
    resources = Resource.objects.values_list("name", flat=True)
52

  
53
    users = AstakosUser.objects.all()
54
    verified = users.filter(email_verified=True)
55
    active = users.filter(is_active=True)
56

  
57
    user_stats = {}
58
    user_stats["total"] = {"total": users.count(),
59
                           "verified": verified.count(),
60
                           "active": active.count(),
61
                           "usage": {}}
62

  
63
    for resource in resources:
64
        usage = Holding.objects.filter(resource=resource)\
65
                               .aggregate(summ=Sum("usage_max"))
66
        user_stats["total"]["usage"][resource] = int(usage["summ"])
67

  
68
    for provider in settings.ASTAKOS_IM_MODULES:
69

  
70
        users = AstakosUser.objects.filter(auth_providers__module=provider)
71
        verified = users.filter(email_verified=True)
72
        active = users.filter(is_active=True)
73

  
74
        user_stats[provider] = {"total": users.count(),
75
                                "verified": verified.count(),
76
                                "active": active.count(),
77
                                "usage": {}}
78

  
79
        users_uuids = users.values_list("uuid", flat=True)
80
        for resource in resources:
81
            usage = Holding.objects\
82
                           .filter(holder__in=users_uuids, resource=resource)\
83
                           .aggregate(summ=Sum("usage_max"))
84
            user_stats[provider]["usage"][resource] = int(usage["summ"])
85

  
86
    stats["users"] = user_stats
87

  
88
    return stats
b/snf-astakos-app/astakos/admin/views.py
1
# Copyright 2013 GRNET S.A. All rights reserved.
2
#
3
# Redistribution and use in source and binary forms, with or
4
# without modification, are permitted provided that the following
5
# conditions are met:
6
#
7
#   1. Redistributions of source code must retain the above
8
#      copyright notice, this list of conditions and the following
9
#      disclaimer.
10
#
11
#   2. Redistributions in binary form must reproduce the above
12
#      copyright notice, this list of conditions and the following
13
#      disclaimer in the documentation and/or other materials
14
#      provided with the distribution.
15
#
16
# THIS SOFTWARE IS PROVIDED BY GRNET S.A. ``AS IS'' AND ANY EXPRESS
17
# OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
18
# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19
# PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL GRNET S.A OR
20
# CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
21
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
22
# LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
23
# USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
24
# AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
25
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
26
# ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27
# POSSIBILITY OF SUCH DAMAGE.
28
#
29
# The views and conclusions contained in the software and
30
# documentation are those of the authors and should not be
31
# interpreted as representing official policies, either expressed
32
# or implied, of GRNET S.A.
33

  
34
import logging
35
from django import http
36
from django.utils import simplejson as json
37
from snf_django.lib import api
38
from astakos.im import settings
39

  
40
from astakos.admin import stats
41

  
42
logger = logging.getLogger(__name__)
43

  
44
PERMITTED_GROUPS = settings.ADMIN_STATS_PERMITTED_GROUPS
45

  
46

  
47
@api.api_method(http_method='GET', user_required=False, token_required=False,
48
                logger=logger, serializations=['json'])
49
@api.allow_jsonp()
50
def get_public_stats(request):
51
    _stats = stats.get_public_stats()
52
    data = json.dumps(_stats)
53
    return http.HttpResponse(data, status=200, content_type='application/json')
54

  
55

  
56
@api.api_method(http_method='GET', user_required=True, token_required=True,
57
                logger=logger, serializations=['json'])
58
@api.user_in_groups(permitted_groups=PERMITTED_GROUPS,
59
                    logger=logger)
60
def get_astakos_stats(request):
61
    _stats = stats.get_astakos_stats()
62
    data = json.dumps(_stats)
63
    return http.HttpResponse(data, status=200, content_type='application/json')
b/snf-astakos-app/astakos/api/services.py
85 85
             'publicURL': None},
86 86
        ],
87 87
    },
88

  
89
    'astakos_admin': {
90
        'type': 'astakos_admin',
91
        'component': 'astakos',
92
        'prefix': 'admin',
93
        'public': False,
94
        'endpoints': [
95
            {'versionId': '',
96
             'publicURL': None},
97
        ],
98
    },
88 99
}
b/snf-astakos-app/astakos/im/management/commands/stats-astakos.py
30 30
# documentation are those of the authors and should not be
31 31
# interpreted as representing official policies, either expressed
32 32
# or implied, of GRNET S.A.
33

  
34

  
35
import datetime
36 33
import json
37 34
import string
38

  
39 35
#from optparse import make_option
40 36

  
41
from django.conf import settings
42
from snf_django.management.utils import pprint_table
43

  
44 37
from snf_django.management.commands import SynnefoCommand, CommandError
45
from astakos.im.models import AstakosUser, Resource
46
from astakos.quotaholder_app.models import Holding
47
from django.db.models import Sum
38
from snf_django.management.utils import pprint_table
39
#from astakos.im.models import AstakosUser, Resource
40
#from astakos.quotaholder_app.models import Holding
41
from astakos.admin import stats as statistics
48 42

  
49 43

  
50 44
class Command(SynnefoCommand):
......
55 49
    )
56 50

  
57 51
    def handle(self, *args, **options):
58
        stats = get_astakos_stats()
52
        stats = statistics.get_astakos_stats()
59 53

  
60 54
        output_format = options["output_format"]
61 55
        if output_format == "json":
......
67 61
                               output_format)
68 62

  
69 63

  
70
def get_astakos_stats():
71
    stats = {"datetime": datetime.datetime.now().strftime("%c")}
72

  
73
    resources = Resource.objects.values_list("name", flat=True)
74

  
75
    users = AstakosUser.objects.all()
76
    verified = users.filter(email_verified=True)
77
    active = users.filter(is_active=True)
78

  
79
    user_stats = {}
80
    user_stats["total"] = {"total": users.count(),
81
                           "verified": verified.count(),
82
                           "active": active.count(),
83
                           "usage": {}}
84

  
85
    for resource in resources:
86
        usage = Holding.objects.filter(resource=resource)\
87
                               .aggregate(summ=Sum("usage_max"))
88
        user_stats["total"]["usage"][resource] = int(usage["summ"])
89

  
90
    for provider in settings.ASTAKOS_IM_MODULES:
91

  
92
        users = AstakosUser.objects.filter(auth_providers__module=provider)
93
        verified = users.filter(email_verified=True)
94
        active = users.filter(is_active=True)
95

  
96
        user_stats[provider] = {"total": users.count(),
97
                                "verified": verified.count(),
98
                                "active": active.count(),
99
                                "usage": {}}
100

  
101
        users_uuids = users.values_list("uuid", flat=True)
102
        for resource in resources:
103
            usage = Holding.objects\
104
                           .filter(holder__in=users_uuids, resource=resource)\
105
                           .aggregate(summ=Sum("usage_max"))
106
            user_stats[provider]["usage"][resource] = int(usage["summ"])
107

  
108
    stats["users"] = user_stats
109

  
110
    return stats
111

  
112

  
113 64
def columns_from_fields(fields, values):
114 65
    return zip(map(string.lower, fields), [values.get(f, 0) for f in fields])
115 66

  
......
117 68
def pretty_print_stats(stats, stdout):
118 69
    newline = lambda: stdout.write("\n")
119 70

  
120
    datetime = stats.get("datetime")
121
    stdout.write("datetime: %s\n" % datetime)
71
    _datetime = stats.get("datetime")
72
    stdout.write("datetime: %s\n" % _datetime)
122 73
    newline()
123 74

  
124 75
    users = stats.get("users", {})
b/snf-astakos-app/astakos/im/settings.py
21 21
VIEWS_PREFIX = get_path(astakos_services, 'astakos_ui.prefix')
22 22
KEYSTONE_PREFIX = get_path(astakos_services, 'astakos_identity.prefix')
23 23
WEBLOGIN_PREFIX = get_path(astakos_services, 'astakos_weblogin.prefix')
24
ADMIN_PREFIX = get_path(astakos_services, 'astakos_admin.prefix')
24 25

  
25 26
# Set the expiration time of newly created auth tokens
26 27
# to be this many hours after their creation time.
......
207 208
REDIRECT_ALLOWED_SCHEMES = getattr(settings,
208 209
                                   'ASTAKOS_REDIRECT_ALLOWED_SCHEMES',
209 210
                                   ('pithos', 'pithosdev'))
211

  
212
ADMIN_STATS_PERMITTED_GROUPS = getattr(settings,
213
                                       'ASTAKOS_ADMIN_STATS_PERMITTED_GROUPS',
214
                                       ['admin-stats'])
b/snf-astakos-app/astakos/urls.py
34 34
from django.conf.urls import include, patterns
35 35

  
36 36
from astakos.im.settings import (
37
    BASE_PATH, ACCOUNTS_PREFIX, VIEWS_PREFIX, KEYSTONE_PREFIX, WEBLOGIN_PREFIX)
37
    BASE_PATH, ACCOUNTS_PREFIX, VIEWS_PREFIX, KEYSTONE_PREFIX, WEBLOGIN_PREFIX,
38
    ADMIN_PREFIX)
38 39
from snf_django.lib.api.utils import prefix_pattern
39 40
from snf_django.utils.urls import \
40 41
    extend_with_root_redirects, extend_endpoint_with_slash
......
52 53
    (prefix_pattern(ACCOUNTS_PREFIX), include('astakos.api.urls')),
53 54
    (prefix_pattern(KEYSTONE_PREFIX), include('astakos.api.keystone_urls')),
54 55
    (prefix_pattern(WEBLOGIN_PREFIX), include('astakos.im.weblogin_urls')),
56
    (prefix_pattern(ADMIN_PREFIX), include('astakos.admin.admin_urls')),
55 57
)
56 58

  
57 59

  
b/snf-astakos-app/conf/20-snf-astakos-app-settings.conf
136 136
# Migrate existing shibboleth user entries which where previously associated 
137 137
# with EPPN instead of the provided value of REMOTE_ID mod_shib2 header.
138 138
# ASTAKOS_SHIBBOLETH_MIGRATE_EPPN = False
139
#
140
## Astakos groups that have access to '/admin' views.
141
# ASTAKOS_ADMIN_STATS_PERMITTED_GROUPS = ["admin-stats"]

Also available in: Unified diff