Projet

Général

Profil

0001-provisionning-agent-12910.patch

Serghei Mihai, 06 juillet 2017 19:57

Télécharger (12,5 ko)

Voir les différences:

Subject: [PATCH] provisionning agent (#12910)

 corbo/hobo_agent/__init__.py                       |  0
 corbo/hobo_agent/management/__init__.py            |  0
 corbo/hobo_agent/management/commands/__init__.py   |  0
 .../hobo_agent/management/commands/hobo_notify.py  | 53 +++++++++++++
 debian/debian_config.py                            |  2 +
 tests/conftest.py                                  | 89 ++++++++++++++++++++++
 tests/settings.py                                  |  2 +
 tests/test_notify.py                               | 83 ++++++++++++++++++++
 tox.ini                                            |  2 +
 9 files changed, 231 insertions(+)
 create mode 100644 corbo/hobo_agent/__init__.py
 create mode 100644 corbo/hobo_agent/management/__init__.py
 create mode 100644 corbo/hobo_agent/management/commands/__init__.py
 create mode 100644 corbo/hobo_agent/management/commands/hobo_notify.py
 create mode 100644 tests/settings.py
 create mode 100644 tests/test_notify.py
corbo/hobo_agent/management/commands/hobo_notify.py
1
# corbo - Announces Manager
2
# Copyright (C) 2017 Entr'ouvert
3
#
4
# This program is free software: you can redistribute it and/or modify it
5
# under the terms of the GNU Affero General Public License as published
6
# by the Free Software Foundation, either version 3 of the License, or
7
# (at your option) any later version.
8
#
9
# This program is distributed in the hope that it will be useful,
10
# but WITHOUT ANY WARRANTY; without even the implied warranty of
11
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
# GNU Affero General Public License for more details.
13
#
14
# You should have received a copy of the GNU Affero General Public License
15
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
16

  
17
from django.db.models import Q
18

  
19
from hobo.agent.common.management.commands import hobo_notify
20

  
21
from corbo.models import Subscription
22

  
23
class Command(hobo_notify.Command):
24

  
25
    def process_notification(self, tenant, notification):
26
        super(Command, self).process_notification(tenant, notification)
27
        object_type = notification['objects']['@type']
28
        if object_type != 'user':
29
            return
30
        users = notification['objects']['data']
31
        action = notification['@type']
32
        if notification.get('full'):
33
            uuids = [user['uuid'] for user in users]
34
            Subscription.objects.exclude(Q(uuid__in=uuids)|Q(uuid__isnull=True)|Q(uuid='')).delete()
35

  
36
        for user in users:
37
            for subscription in Subscription.objects.filter(uuid=user['uuid']):
38
                if action == 'provision':
39
                    if subscription.identifier.startswith('mailto:'):
40
                        if user.get('email'):
41
                            subscription.identifier = 'mailto:%s' % user['email']
42
                        else:
43
                            subscription.delete()
44
                            continue
45
                    elif subscription.identifier.startswith('sms:'):
46
                        if user.get('mobile'):
47
                            subscription.identifier = 'sms:%s' % user['mobile']
48
                        else:
49
                            subscription.delete()
50
                            continue
51
                    subscription.save()
52
                elif action == 'deprovision':
53
                    subscription.delete()
debian/debian_config.py
12 12
#
13 13
execfile('/usr/lib/hobo/debian_config_common.py')
14 14

  
15
INSTALLED_APPS = ('corbo.hobo_agent', ) + INSTALLED_APPS
16

  
15 17
#
16 18
# local settings
17 19
#
tests/conftest.py
1 1
import pytest
2 2
import django_webtest
3 3
import copy
4
import tempfile
5
import os
6
import json
7
import shutil
4 8

  
5 9
import django.core.mail.backends.locmem
6 10
from django.core.mail.backends.locmem import EmailBackend as DjangoEmailBackend
11
from django.utils.text import slugify
12

  
13
from corbo.models import Category, Announce, Broadcast, Subscription
14

  
15
CATEGORIES = ('Alerts', 'News')
16

  
17
SUBSCRIBERS = [{'uuid': 'uuid1', 'email': 'foo@example.net', 'mobile': '0102030405'},
18
               {'uuid': 'uuid2', 'email': 'bar@example.net', 'mobile': '0607080900'},
19
               {'uuid': '', 'email': 'john@example.net', 'mobile': '0304050607'},
20
               {'uuid': None, 'email': 'john2@example.net', 'mobile': '0405060708'}]
21

  
7 22

  
8 23

  
9 24
class MockedEmailBackend(object):
......
42 57
    wtm._patch_settings()
43 58
    request.addfinalizer(wtm._unpatch_settings)
44 59
    return django_webtest.DjangoTestApp()
60

  
61

  
62
@pytest.fixture
63
def categories():
64
    categories = []
65
    for category in CATEGORIES:
66
        c, created = Category.objects.get_or_create(name=category, slug=slugify(category))
67
        categories.append(c)
68
    return categories
69

  
70

  
71
@pytest.fixture
72
def subscriptions(categories):
73
    subscriptions = []
74
    for category in categories:
75
        for subscriber in SUBSCRIBERS:
76
            kwargs = {'category': category, 'identifier': 'mailto:%(email)s' % subscriber}
77
            uuid = subscriber['uuid']
78
            if uuid is not None:
79
                kwargs['uuid'] = uuid
80
            subscriptions.append(Subscription.objects.create(**kwargs))
81
            kwargs['identifier'] = 'sms:%(mobile)s' % subscriber
82
            subscriptions.append(Subscription.objects.create(**kwargs))
83
    return subscriptions
84

  
85

  
86
@pytest.fixture
87
def tenant_base(request, settings):
88
    base = tempfile.mkdtemp('corbo-tenant-base')
89
    settings.TENANT_BASE = base
90

  
91
    def fin():
92
        shutil.rmtree(base)
93
    request.addfinalizer(fin)
94
    return base
95

  
96

  
97
@pytest.fixture(scope='function')
98
def tenant(transactional_db, request, tenant_base):
99
    from hobo.multitenant.models import Tenant
100
    base = tenant_base
101

  
102
    @pytest.mark.django_db
103
    def make_tenant(name):
104
        tenant_dir = os.path.join(base, name)
105
        os.mkdir(tenant_dir)
106
        with open(os.path.join(tenant_dir, 'hobo.json'), 'w') as fd:
107
            json.dump({
108
                'variables': {
109
                    'hobo_test_variable': True,
110
                    'other_variable': 'foo',
111
                },
112
                'services': [
113
                    {'slug': 'test',
114
                     'service-id': 'corbo',
115
                     'title': 'Test',
116
                     'this': True,
117
                     'secret_key': '12345',
118
                     'base_url': 'http://%s' % name,
119
                     'saml-sp-metadata-url': 'http://%s/metadata/' % name,
120
                     'variables': {
121
                         'other_variable': 'bar',
122
                     }
123
                    },
124
                    {'slug': 'passerelle',
125
                     'title': 'Webserivces',
126
                     'service-id': 'passerelle',
127
                     'secret_key': 'abcdef',
128
                     'base_url': 'http://passerelle.example.net',
129
                     'saml-sp-metadata-url': 'http://passerelle.example.net/metadata/' },
130
                    ]}, fd)
131
        return Tenant(domain_url=name,
132
                      schema_name=name.replace('-', '_').replace('.', '_'))
133
    return make_tenant('corbo.example.net')
tests/settings.py
1
# Add corbo hobo agent
2
INSTALLED_APPS = ('corbo.hobo_agent', ) + INSTALLED_APPS
tests/test_notify.py
1
import pytest
2
from copy import deepcopy
3
import json
4

  
5
from corbo.models import Subscription
6
from corbo.hobo_agent.management.commands.hobo_notify import Command
7
from django.core.management import call_command
8
from django.db.models import Q
9

  
10
NOTIFICATION = {'@type': 'provision',
11
                'objects': {'@type': 'user',
12
                            'data': [
13
                                {'uuid': 'uuid1', 'email': 'foo1@example.net', 'mobile': '0504030201'},
14
                                {'uuid': 'uuid2', 'email': 'bar1@example.net', 'mobile': '0009080706'},
15
                            ]},
16
                'audience': [],
17
                'full': False
18
}
19

  
20

  
21
def test_notify_provision(tenant, subscriptions):
22
    command = Command()
23
    command.process_notification(tenant, NOTIFICATION)
24
    assert Subscription.objects.count() == len(subscriptions)
25
    for user in NOTIFICATION['objects']['data']:
26
        assert Subscription.objects.filter(uuid=user['uuid'], identifier='mailto:%(email)s' % user).exists()
27
        assert Subscription.objects.filter(uuid=user['uuid'], identifier='sms:%(mobile)s' % user).exists()
28

  
29

  
30
def test_notify_other_provision(tenant, subscriptions):
31
    role_notification = deepcopy(NOTIFICATION)
32
    role_notification['objects']['@type'] = 'role'
33
    command = Command()
34
    command.process_notification(tenant, role_notification)
35
    assert Subscription.objects.count() == len(subscriptions)
36
    for subscription in subscriptions:
37
        assert Subscription.objects.filter(uuid=subscription.uuid, identifier=subscription.identifier)
38

  
39

  
40
def test_notify_deprovision(tenant, subscriptions):
41
    deprovision_notification = deepcopy(NOTIFICATION)
42
    deprovision_notification['@type'] = 'deprovision'
43
    command = Command()
44
    command.process_notification(tenant, deprovision_notification)
45
    for user in deprovision_notification['objects']['data']:
46
        assert not Subscription.objects.filter(uuid=user['uuid']).exists()
47

  
48

  
49
def test_notify_full(tenant, subscriptions):
50
    full_notification = deepcopy(NOTIFICATION)
51
    full_notification['full'] = True
52
    command = Command()
53
    command.process_notification(tenant, full_notification)
54
    # strings empty and null are the same for CharFields
55
    assert Subscription.objects.filter(Q(uuid='')|Q(uuid__isnull=True)).count() == 8
56
    assert Subscription.objects.exclude(Q(uuid='')|Q(uuid__isnull=True)).count() == 8
57
    full_notification['objects']['data'] = []
58
    command.process_notification(tenant, full_notification)
59
    # check all remaining subscriptions have empty uuids
60
    for subscription in Subscription.objects.all():
61
        assert not subscription.uuid
62

  
63

  
64
def test_notify_emails_only(tenant, subscriptions):
65
    email_notification = deepcopy(NOTIFICATION)
66
    for user in email_notification['objects']['data']:
67
        user['mobile'] = None
68
        user['email'] = 'new-%(email)s' % user
69
    command = Command()
70
    command.process_notification(tenant, email_notification)
71
    for user in email_notification['objects']['data']:
72
        assert not Subscription.objects.filter(uuid=user['uuid'], identifier__startswith='sms:').exists()
73

  
74

  
75
def test_notify_mobiles_only(tenant, subscriptions):
76
    mobile_notification = deepcopy(NOTIFICATION)
77
    for user in mobile_notification['objects']['data']:
78
        user['email'] = None
79
        user['mobile'] = '0%(mobile)s' % user
80
    command = Command()
81
    command.process_notification(tenant, mobile_notification)
82
    for user in mobile_notification['objects']['data']:
83
        assert not Subscription.objects.filter(uuid=user['uuid'], identifier__startswith='mailto:').exists()
tox.ini
6 6
  coverage: True
7 7
setenv =
8 8
  DJANGO_SETTINGS_MODULE=corbo.settings
9
  CORBO_SETTINGS_FILE=tests/settings.py
9 10
  coverage: COVERAGE=--junitxml=test_results.xml --cov-report xml --cov=corbo/ --cov-config .coveragerc
10 11
deps =
11 12
  django18: django>=1.8,<1.9
13
  http://git.entrouvert.org/hobo.git/snapshot/hobo-master.tar.gz
12 14
  pytest-cov
13 15
  pytest-django>=3.1.1
14 16
  pytest>=3.0.4
15
-