0002-maarch-implement-sending-a-response-27814.patch
setup.py | ||
---|---|---|
103 | 103 |
'django-haystack<2.8', |
104 | 104 |
'django-reversion>=2.0', |
105 | 105 |
'django-taggit', |
106 |
'djangorestframework>=3.3, <3.7', |
|
106 | 107 |
'requests', |
107 | 108 |
'whoosh', |
108 | 109 |
'XStatic-Select2', |
tests/test_source_maarch.py | ||
---|---|---|
18 | 18 | |
19 | 19 |
import pytest |
20 | 20 | |
21 |
from django.contrib.auth.models import User |
|
22 | ||
21 | 23 |
from httmock import urlmatch, HTTMock |
22 | 24 | |
23 | 25 | |
... | ... | |
153 | 155 |
PDF_MOCK = '%PDF-1.4 ...' |
154 | 156 | |
155 | 157 | |
156 |
def test_feed(app, maarch, wcs, user): |
|
158 |
def test_feed(settings, app, maarch, wcs, user):
|
|
157 | 159 |
import base64 |
158 | 160 |
from django.core.management import call_command |
159 | 161 |
from django.contrib.contenttypes.models import ContentType |
... | ... | |
241 | 243 |
] |
242 | 244 |
} |
243 | 245 | |
246 |
# verify we can answer |
|
247 |
maarch.clear() |
|
248 |
app.set_user(None) |
|
249 |
user = User.objects.create(username='test') |
|
250 |
user.set_password('test') |
|
251 |
user.save() |
|
252 |
# verify authentication error |
|
253 |
response = app.post_json('/api/mail/response/', params={}, status=401) |
|
254 |
app.authorization = ('Basic', ('test', 'test')) |
|
255 |
# verify serializer error |
|
256 |
response = app.post_json('/api/mail/response/', params={}, status=400) |
|
257 |
assert response.json['err'] == 1 |
|
258 |
# verify error when maarch feed is not configured |
|
259 |
settings.MAARCH_FEED['ENABLE'] = False |
|
260 |
response = app.post_json('/api/mail/response/', |
|
261 |
params={'mail_id': 'maarch-1', 'content': 'coucou'}, |
|
262 |
status=200) |
|
263 |
assert response.json['err'] == 1 |
|
264 |
assert response.json['err_desc'] == 'maarch is unconfigured' |
|
265 |
settings.MAARCH_FEED['ENABLE'] = True |
|
266 |
# verify error when mail_id is unknown |
|
267 |
response = app.post_json('/api/mail/response/', |
|
268 |
params={'mail_id': 'maarch-231', 'content': 'coucou'}, |
|
269 |
status=404) |
|
270 |
assert response.json['err'] == 1 |
|
271 | ||
272 |
# successfull call |
|
273 |
maarch.responses.append({}) |
|
274 |
with maarch.ctx_manager: |
|
275 |
response = app.post_json('/api/mail/response/', |
|
276 |
params={'mail_id': 'maarch-1', 'content': 'coucou'}, |
|
277 |
status=200) |
|
278 |
assert maarch.requests[0][3] == { |
|
279 |
'historyMessage': 'coucou', |
|
280 |
'resId': [1], |
|
281 |
'status': 'GRC_RESPONSE', |
|
282 |
} |
|
283 | ||
244 | 284 | |
245 | 285 |
def test_command_is_noop(): |
246 | 286 |
from django.core.management import call_command |
welco/settings.py | ||
---|---|---|
227 | 227 |
# ex: FLAVOURS = ['alfortville'] |
228 | 228 |
FLAVOURS = [] |
229 | 229 | |
230 |
REST_FRAMEWORK = {} |
|
231 |
REST_FRAMEWORK['DEFAULT_AUTHENTICATION_CLASSES'] = ['rest_framework.authentication.BasicAuthentication'] |
|
232 | ||
230 | 233 |
local_settings_file = os.environ.get('WELCO_SETTINGS_FILE', |
231 | 234 |
os.path.join(os.path.dirname(__file__), 'local_settings.py')) |
232 | 235 |
if os.path.exists(local_settings_file): |
welco/sources/mail/urls.py | ||
---|---|---|
17 | 17 |
from django.conf.urls import url |
18 | 18 | |
19 | 19 |
from .views import (viewer, feeder, qualification_save, edit_note, note, |
20 |
reject, mail_count) |
|
20 |
reject, mail_count, mail_response)
|
|
21 | 21 | |
22 | 22 |
urlpatterns = [ |
23 | 23 |
url('viewer/$', viewer, name='mail-viewer'), |
... | ... | |
27 | 27 |
url(r'^ajax/mail/edit-note/$', edit_note, name='mail-edit-note'), |
28 | 28 |
url(r'^ajax/mail/note/(?P<pk>\w+)$', note, name='mail-note'), |
29 | 29 |
url(r'^ajax/count/mail/$', mail_count, name='mail-count'), |
30 |
url(r'^api/mail/response/$', mail_response, name='mail-api-response'), |
|
30 | 31 |
] |
welco/sources/mail/utils.py | ||
---|---|---|
16 | 16 | |
17 | 17 |
from django.conf import settings |
18 | 18 | |
19 |
from .maarch import MaarchCourrier |
|
19 |
from .maarch import MaarchCourrier, MaarchError
|
|
20 | 20 | |
21 | 21 | |
22 | 22 |
class WelcoMaarchCourrier(MaarchCourrier): |
23 | 23 |
def __init__(self, url, username, password, grc_status, |
24 | 24 |
grc_received_status, grc_send_status, grc_refused_status, |
25 |
batch_size=10): |
|
25 |
grc_response_status, batch_size=10):
|
|
26 | 26 |
super(WelcoMaarchCourrier, self).__init__(url, username, password) |
27 | 27 |
self.grc_status = grc_status |
28 | 28 |
self.grc_received_status = grc_received_status |
29 | 29 |
self.grc_send_status = grc_send_status |
30 | 30 |
self.grc_refused_status = grc_refused_status |
31 |
self.grc_response_status = grc_response_status |
|
31 | 32 |
self.batch_size = batch_size |
32 | 33 | |
33 | 34 |
def get_mails(self): |
... | ... | |
53 | 54 |
mail = self.Courrier(self, pk=mail_pk) |
54 | 55 |
self.update_status([mail], self.grc_refused_status) |
55 | 56 | |
57 |
def set_grc_response_status(self, mail_pk, history_message): |
|
58 |
mail = self.Courrier(self, pk=mail_pk) |
|
59 |
self.update_status([mail], self.grc_response_status, history_message) |
|
60 | ||
56 | 61 | |
57 | 62 |
def get_maarch(): |
58 | 63 |
config = getattr(settings, 'MAARCH_FEED', {}) |
... | ... | |
68 | 73 |
grc_status=config.get('STATUS_GRC', 'GRC'), |
69 | 74 |
grc_received_status=config.get('STATUS_RECEIVED', 'GRC_TRT'), |
70 | 75 |
grc_send_status=config.get('STATUS_SEND', 'GRCSENT'), |
71 |
grc_refused_status=config.get('STATUS_REFUSED', 'GRCREFUSED')) |
|
76 |
grc_refused_status=config.get('STATUS_REFUSED', 'GRCREFUSED'), |
|
77 |
grc_response_status=config.get('STATUS_REFUSED', 'GRC_RESPONSE')) |
|
72 | 78 |
welco/sources/mail/views.py | ||
---|---|---|
29 | 29 |
from django.views.generic import TemplateView |
30 | 30 |
from django.db.transaction import atomic |
31 | 31 | |
32 |
from rest_framework import authentication, serializers, permissions, status |
|
33 |
from rest_framework.generics import GenericAPIView |
|
34 |
from rest_framework.response import Response |
|
35 | ||
32 | 36 |
from welco.utils import response_for_json |
33 | 37 | |
34 | 38 |
from .models import Mail |
35 | 39 |
from .forms import MailQualificationForm |
36 |
from .utils import get_maarch |
|
40 |
from .utils import get_maarch, MaarchError
|
|
37 | 41 | |
38 | 42 | |
39 | 43 |
logger = logging.getLogger(__name__) |
... | ... | |
149 | 153 |
def mail_count(request, *args, **kwargs): |
150 | 154 |
count = Mail.objects.exclude(status__startswith='done-').count() |
151 | 155 |
return response_for_json(request, {'count': count}) |
156 | ||
157 | ||
158 |
class NotificationSerializer(serializers.Serializer): |
|
159 |
mail_id = serializers.CharField() |
|
160 |
content = serializers.CharField() |
|
161 | ||
162 | ||
163 |
class MailResponseAPIView(GenericAPIView): |
|
164 |
permission_classes = (permissions.IsAuthenticated,) |
|
165 |
serializer_class = NotificationSerializer |
|
166 | ||
167 |
def post(self, request, *args, **kwargs): |
|
168 |
serializer = self.get_serializer(data=request.data) |
|
169 |
if not serializer.is_valid(): |
|
170 |
response = {'err': 1, 'err_desc': serializer.errors} |
|
171 |
return Response(response, status.HTTP_400_BAD_REQUEST) |
|
172 |
mail_id = serializer.validated_data['mail_id'] |
|
173 |
content = serializer.validated_data['content'] |
|
174 |
# for now, we only support maarch |
|
175 |
if not mail_id.startswith('maarch-'): |
|
176 |
response = {'err': 1, 'err_desc': 'only maarch is supported'} |
|
177 |
return Response(response) |
|
178 |
mail = Mail.objects.filter(external_id=mail_id).first() |
|
179 |
if not mail: |
|
180 |
response = {'err': 1, 'err_desc': 'unknown mail_id'} |
|
181 |
return Response(response, status.HTTP_404_NOT_FOUND) |
|
182 |
return self.maarch_response(mail, content) |
|
183 | ||
184 |
def maarch_response(self, mail, content): |
|
185 |
maarch = get_maarch() |
|
186 |
if not maarch: |
|
187 |
return Response({'err': 1, 'err_desc': 'maarch is unconfigured'}) |
|
188 |
mail_pk = int(mail.external_id.split('-', 1)[1]) |
|
189 |
try: |
|
190 |
maarch.set_grc_response_status(mail_pk, content) |
|
191 |
except MaarchError as e: |
|
192 |
return Response({'err': 1, 'err_desc': str(e)}) |
|
193 |
return Response({'err': 0}) |
|
194 | ||
195 |
mail_response = MailResponseAPIView.as_view() |
|
152 |
- |