Skip to content

Commit b31ae11

Browse files
author
Maria Vatasoiu
committed
feat(form): Implements feature for issue #1699
1 parent e0a1b07 commit b31ae11

File tree

10 files changed

+144
-18
lines changed

10 files changed

+144
-18
lines changed

caluma/caluma_core/models.py

+3-4
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,10 @@ def _history_user_getter(historical_instance):
1010

1111
def _history_user_setter(historical_instance, user):
1212
request = getattr(HistoricalRecords.thread, "request", None)
13-
user = None
13+
user = "AnonymousUser"
1414
if request is not None:
15-
user = request.user.username
16-
if request.user.__class__.__name__ == "AnonymousUser":
17-
user = "AnonymousUser"
15+
if hasattr(request, "user"):
16+
user = request.user.username
1817
historical_instance.history_user_id = user
1918

2019

+63
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,63 @@
1+
import pytest
2+
from django.urls import reverse
3+
from rest_framework.status import HTTP_201_CREATED
4+
5+
6+
@pytest.mark.parametrize("question__type", ["files"])
7+
def test_minio_callback_view(transactional_db, client, answer, minio_mock, settings):
8+
file = answer.files.first()
9+
data = {
10+
"EventName": "s3:ObjectCreated:Put",
11+
"Key": "caluma-media/218b2504-1736-476e-9975-dc5215ef4f01_test.png",
12+
"Records": [
13+
{
14+
"eventVersion": "2.0",
15+
"eventSource": "minio:s3",
16+
"awsRegion": "",
17+
"eventTime": "2020-07-17T06:38:23.221Z",
18+
"eventName": "s3:ObjectCreated:Put",
19+
"userIdentity": {"principalId": "minio"},
20+
"requestParameters": {
21+
"accessKey": "minio",
22+
"region": "",
23+
"sourceIPAddress": "172.20.0.1",
24+
},
25+
"responseElements": {
26+
"x-amz-request-id": "162276DB8350E531",
27+
"x-minio-deployment-id": "5db7c8da-79cb-4d3a-8d40-189b51ca7aa6",
28+
"x-minio-origin-endpoint": "http://172.20.0.2:9000",
29+
},
30+
"s3": {
31+
"s3SchemaVersion": "1.0",
32+
"configurationId": "Config",
33+
"bucket": {
34+
"name": "caluma-media",
35+
"ownerIdentity": {"principalId": "minio"},
36+
"arn": "arn:aws:s3:::caluma-media",
37+
},
38+
"object": {
39+
"key": "{file_id}_name".format(file_id=file.id),
40+
"size": 299758,
41+
"eTag": "af1421c17294eed533ec99eb82b468fb",
42+
"contentType": "application/pdf",
43+
"userMetadata": {"content-variant": "application/pdf"},
44+
"versionId": "1",
45+
"sequencer": "162276DB83A9F895",
46+
},
47+
},
48+
"source": {
49+
"host": "172.20.0.1",
50+
"port": "",
51+
"userAgent": "Mozilla/5.0 (X11; Linux x86_64) AppleWebKit/537.36 (KHTML, like Gecko) QtWebEngine/5.15.0 Chrome/80.0.3987.163 Safari/537.36",
52+
},
53+
}
54+
],
55+
}
56+
57+
assert file.is_draft is True
58+
response = client.post(
59+
reverse("minio-callback"), data=data, content_type="application/json"
60+
)
61+
file.refresh_from_db()
62+
assert file.is_draft is False
63+
assert response.status_code == HTTP_201_CREATED

caluma/caluma_core/urls.py

+4-2
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
from django.conf import settings
22
from django.urls import re_path
33

4-
from caluma.caluma_core import views
4+
from caluma.caluma_core import views as core_views
5+
from caluma.caluma_form import views as form_views
56
from caluma.caluma_user.views import AuthenticationGraphQLView
67

78
urlpatterns = [
@@ -10,5 +11,6 @@
1011
AuthenticationGraphQLView.as_view(graphiql=settings.DEBUG),
1112
name="graphql",
1213
),
13-
re_path("healthz/?", views.health_check_status, name="healthz"),
14+
re_path("healthz/?", core_views.health_check_status, name="healthz"),
15+
re_path("minio-callback/?", form_views.minio_callback_view, name="minio-callback"),
1416
]
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
# Generated by Django 3.2.19 on 2023-07-20 12:17
2+
3+
from django.db import migrations, models
4+
5+
6+
class Migration(migrations.Migration):
7+
dependencies = [
8+
("caluma_form", "0046_file_answer_reverse_keys"),
9+
]
10+
11+
operations = [
12+
migrations.AddField(
13+
model_name="file",
14+
name="is_draft",
15+
field=models.BooleanField(default=True),
16+
),
17+
migrations.AddField(
18+
model_name="historicalfile",
19+
name="is_draft",
20+
field=models.BooleanField(default=True),
21+
),
22+
]

caluma/caluma_form/models.py

+1
Original file line numberDiff line numberDiff line change
@@ -608,6 +608,7 @@ class File(core_models.UUIDModel):
608608
answer = models.ForeignKey(
609609
Answer, on_delete=models.CASCADE, related_name="files", null=True, default=None
610610
)
611+
is_draft = models.BooleanField(default=True)
611612

612613
@_ignore_missing_file
613614
def _move_blob(self):

caluma/caluma_form/tests/__snapshots__/test_history.ambr

+2-2
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@
2828
dict({
2929
'node': dict({
3030
'__typename': 'HistoricalStringAnswer',
31-
'historyUserId': 'AnonymousUser',
31+
'historyUserId': None,
3232
'value': 'first anon - revision 3',
3333
}),
3434
}),
@@ -48,7 +48,7 @@
4848
dict({
4949
'node': dict({
5050
'__typename': 'HistoricalStringAnswer',
51-
'historyUserId': 'AnonymousUser',
51+
'historyUserId': None,
5252
'value': 'second anon - revision 4',
5353
}),
5454
}),

caluma/caluma_form/tests/test_history.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -63,7 +63,7 @@ def test_history(db, question, document, schema_executor, admin_schema_executor)
6363
)
6464
assert history[1].value == "dolor"
6565

66-
assert history[0].history_user == "AnonymousUser"
66+
assert history[0].history_user is None
6767
assert history[0].value == "sit"
6868

6969

caluma/caluma_form/views.py

+34
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
import json
2+
3+
from django.conf import settings
4+
from django.http import HttpResponse
5+
from django.views.decorators.http import require_http_methods
6+
from rest_framework.status import HTTP_200_OK, HTTP_201_CREATED, HTTP_400_BAD_REQUEST
7+
8+
from caluma.caluma_form.models import File
9+
10+
11+
@require_http_methods(["HEAD", "POST"])
12+
def minio_callback_view(request):
13+
status = HTTP_200_OK
14+
if request.method == "HEAD":
15+
return HttpResponse(status=status)
16+
17+
data = json.loads(request.body.decode("utf-8"))
18+
19+
for record in data["Records"]:
20+
bucket_name = record["s3"]["bucket"]["name"]
21+
if not bucket_name == settings.MINIO_STORAGE_MEDIA_BUCKET_NAME:
22+
continue
23+
24+
file_pk = record["s3"]["object"]["key"].split("_")[0]
25+
try:
26+
file = File.objects.get(pk=file_pk)
27+
except File.DoesNotExist:
28+
return HttpResponse(status=HTTP_400_BAD_REQUEST)
29+
30+
file.is_draft = False
31+
file.save()
32+
status = HTTP_201_CREATED
33+
34+
return HttpResponse(status=status)

caluma/caluma_logging/middleware.py

+13-9
Original file line numberDiff line numberDiff line change
@@ -22,17 +22,21 @@ def __call__(self, request):
2222
try:
2323
doc = parser.parse(body["query"])
2424
visitor.visit(doc, vis)
25-
except GraphQLSyntaxError:
25+
except (GraphQLSyntaxError, KeyError):
2626
pass
2727

28-
AccessLog.objects.create(
29-
username=request.user.username,
30-
query=body.get("query"),
31-
variables=body.get("variables"),
32-
status_code=response.status_code,
33-
has_error=response.status_code >= 400,
34-
**vis.values,
35-
)
28+
try:
29+
AccessLog.objects.create(
30+
username=request.user.username,
31+
query=body.get("query"),
32+
variables=body.get("variables"),
33+
status_code=response.status_code,
34+
has_error=response.status_code >= 400,
35+
**vis.values,
36+
)
37+
except AttributeError:
38+
pass
39+
# create might fail if the request has no user.
3640

3741
return response
3842

caluma/tests/__snapshots__/test_schema.ambr

+1
Original file line numberDiff line numberDiff line change
@@ -1104,6 +1104,7 @@
11041104
id: ID!
11051105
name: String!
11061106
answer: FilesAnswer
1107+
isDraft: Boolean!
11071108
uploadUrl: String
11081109
downloadUrl: String
11091110
metadata: GenericScalar

0 commit comments

Comments
 (0)