Coverage for website/sales/tests/test_api.py: 100.00%
331 statements
« prev ^ index » next coverage.py v7.6.12, created at 2026-06-21 23:59 +0000
« prev ^ index » next coverage.py v7.6.12, created at 2026-06-21 23:59 +0000
1from unittest import mock
3from django.contrib.auth.models import Permission
4from django.contrib.contenttypes.models import ContentType
5from django.test import TestCase
6from django.urls import reverse
7from django.utils import timezone
9from freezegun import freeze_time
10from rest_framework.test import APIClient
12from activemembers.models import Committee, MemberGroupMembership
13from members.models import Member
14from payments.models import Payment
15from payments.services import create_payment
16from sales import payables
17from sales.models.order import Order, OrderItem
18from sales.models.product import Product, ProductList
19from sales.models.shift import Shift
22@freeze_time("2021-01-01")
23class OrderAPITest(TestCase):
24 fixtures = [
25 "members.json",
26 "bank_accounts.json",
27 "member_groups.json",
28 "products.json",
29 ]
31 @classmethod
32 def setUpTestData(cls):
33 """Create the following test data:
35 o0: an empty order
36 o1: an unpaid order of 2 beer
37 o2: an order of 2 soda that doesn't need a payment
38 o3: an unpaid order with 2 beer and 2 wine
39 o4: a paid order with 2 wine
40 o4: a paid order with 2 beer and 2 wine
41 """
42 payables.register()
44 cls.member = Member.objects.filter(last_name="Wiggers").first()
46 cls.beer = Product.objects.get(name="beer")
47 cls.wine = Product.objects.get(name="wine")
48 cls.soda = Product.objects.get(name="soda")
50 cls.normal = ProductList.objects.get(
51 name="normal",
52 )
53 cls.free = ProductList.objects.get(
54 name="free",
55 )
57 cls.shift = Shift.objects.create(
58 start=timezone.now(),
59 end=timezone.now() + timezone.timedelta(hours=1),
60 product_list=cls.normal,
61 selforder=True,
62 )
64 cls.o0 = Order.objects.create(shift=cls.shift)
65 cls.o1 = Order.objects.create(shift=cls.shift)
66 OrderItem.objects.create(
67 order=cls.o1,
68 product=cls.shift.product_list.product_items.get(product=cls.beer),
69 amount=2,
70 )
71 cls.o2 = Order.objects.create(shift=cls.shift)
72 OrderItem.objects.create(
73 order=cls.o2,
74 product=cls.shift.product_list.product_items.get(product=cls.soda),
75 amount=2,
76 )
77 cls.o3 = Order.objects.create(shift=cls.shift)
78 OrderItem.objects.create(
79 order=cls.o3,
80 product=cls.shift.product_list.product_items.get(product=cls.beer),
81 amount=2,
82 )
83 OrderItem.objects.create(
84 order=cls.o3,
85 product=cls.shift.product_list.product_items.get(product=cls.wine),
86 amount=2,
87 )
88 cls.o4 = Order.objects.create(shift=cls.shift)
89 OrderItem.objects.create(
90 order=cls.o4,
91 product=cls.shift.product_list.product_items.get(product=cls.wine),
92 amount=2,
93 )
94 cls.o5 = Order.objects.create(shift=cls.shift)
95 OrderItem.objects.create(
96 order=cls.o5,
97 product=cls.shift.product_list.product_items.get(product=cls.beer),
98 amount=2,
99 )
100 OrderItem.objects.create(
101 order=cls.o5,
102 product=cls.shift.product_list.product_items.get(product=cls.wine),
103 amount=2,
104 )
105 cls.o4.payment = create_payment(
106 cls.o4, processed_by=cls.member, pay_type=Payment.CASH
107 )
108 cls.o4.save()
109 cls.o5.payment = create_payment(
110 cls.o5, processed_by=cls.member, pay_type=Payment.CASH
111 )
112 cls.o5.save()
114 cls.cie = Committee.objects.get(pk=1)
115 MemberGroupMembership.objects.create(group=cls.cie, member=cls.member)
116 content_type = ContentType.objects.get_for_model(Order)
117 permission1 = Permission.objects.get(
118 content_type=content_type, codename="add_order"
119 )
120 permission2 = Permission.objects.get(
121 content_type=content_type, codename="change_order"
122 )
123 permission3 = Permission.objects.get(
124 content_type=content_type, codename="delete_order"
125 )
126 permission4 = Permission.objects.get(
127 content_type=content_type, codename="view_order"
128 )
129 permission5 = Permission.objects.get(
130 content_type=ContentType.objects.get_for_model(Shift), codename="view_shift"
131 )
132 cls.cie.permissions.add(permission1)
133 cls.cie.permissions.add(permission2)
134 cls.cie.permissions.add(permission3)
135 cls.cie.permissions.add(permission4)
136 cls.cie.permissions.add(permission5)
138 def setUp(self):
139 self.client = APIClient()
140 self.client.force_login(self.member)
142 def test_detail_not_logged_in(self):
143 self.client.logout()
144 response = self.client.get(
145 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o0.pk})
146 )
147 self.assertEqual(403, response.status_code)
149 def test_detail_not_authorized__get(self):
150 response = self.client.get(
151 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk})
152 )
153 self.assertEqual(200, response.status_code)
155 self.member.is_superuser = False
156 self.member.save()
158 response = self.client.get(
159 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk})
160 )
161 self.assertEqual(404, response.status_code)
163 self.shift.managers.add(self.cie)
164 self.shift.save()
166 response = self.client.get(
167 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk})
168 )
169 self.assertEqual(200, response.status_code)
171 def test_detail_not_authorized__patch(self):
172 data = {"discount": "0.5"}
174 response = self.client.patch(
175 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk}), data
176 )
177 self.assertEqual(200, response.status_code)
179 self.member.is_superuser = False
180 self.member.save()
182 response = self.client.patch(
183 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk}), data
184 )
185 self.assertEqual(404, response.status_code)
187 self.shift.managers.add(self.cie)
188 self.shift.save()
190 response = self.client.patch(
191 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk}), data
192 )
193 self.assertEqual(200, response.status_code)
195 def test_detail_not_authorized__put(self):
196 data = {"discount": "0.5"}
198 response = self.client.put(
199 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk}), data
200 )
201 self.assertEqual(200, response.status_code)
203 self.member.is_superuser = False
204 self.member.save()
206 response = self.client.put(
207 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk}), data
208 )
209 self.assertEqual(404, response.status_code)
211 self.shift.managers.add(self.cie)
212 self.shift.save()
214 response = self.client.put(
215 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk}), data
216 )
217 self.assertEqual(200, response.status_code)
219 def test_detail_not_authorized__delete(self):
220 response = self.client.delete(
221 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o1.pk})
222 )
223 self.assertEqual(204, response.status_code)
225 self.member.is_superuser = False
226 self.member.save()
228 response = self.client.delete(
229 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o2.pk})
230 )
231 self.assertEqual(404, response.status_code)
233 self.shift.managers.add(self.cie)
234 self.shift.save()
236 response3 = self.client.delete(
237 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": self.o2.pk})
238 )
239 self.assertEqual(204, response3.status_code)
241 def test_list_not_logged_in(self):
242 self.client.logout()
243 response = self.client.get(
244 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk})
245 )
246 self.assertEqual(403, response.status_code)
248 def test_list_not_authorized__get(self):
249 response = self.client.get(
250 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk})
251 )
252 self.assertEqual(200, response.status_code)
254 self.member.is_superuser = False
255 self.member.save()
257 response = self.client.get(
258 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk})
259 )
260 self.assertEqual(403, response.status_code)
262 self.shift.managers.add(self.cie)
263 self.shift.save()
265 response = self.client.get(
266 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk})
267 )
268 self.assertEqual(200, response.status_code)
270 def test_list_not_authorized__post(self):
271 data = {"order_items": [{"product": "beer", "amount": 4}]}
273 response = self.client.post(
274 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk}),
275 data,
276 )
277 self.assertEqual(201, response.status_code)
279 self.member.is_superuser = False
280 self.member.save()
282 response = self.client.post(
283 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk}),
284 data,
285 )
286 self.assertEqual(403, response.status_code)
288 self.shift.managers.add(self.cie)
289 self.shift.save()
291 response = self.client.post(
292 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk}),
293 data,
294 )
295 self.assertEqual(201, response.status_code)
297 def test_create_order(self):
298 self.maxDiff = None
299 with self.subTest("Create new order with single item"):
300 data = {"order_items": [{"product": "beer", "amount": 4}]}
301 response = self.client.post(
302 reverse(
303 "api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk}
304 ),
305 data,
306 format="json",
307 )
308 self.assertEqual(201, response.status_code)
309 pk = response.data["pk"]
310 expected_response = {
311 "pk": pk,
312 "shift": self.shift.pk,
313 "created_at": "2021-01-01T01:00:00+01:00",
314 "order_items": [{"product": "beer", "amount": 4, "total": "2.00"}],
315 "order_description": "4x beer",
316 "age_restricted": True,
317 "subtotal": "2.00",
318 "discount": None,
319 "total_amount": "2.00",
320 "num_items": 4,
321 "payment": None,
322 "payer": None,
323 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
324 }
325 self.assertJSONEqual(response.content, expected_response)
327 with self.subTest("Add product item"):
328 data = {
329 "order_items": [
330 {"product": "beer", "amount": 5},
331 {"product": "soda", "amount": 2},
332 ]
333 }
334 response = self.client.put(
335 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
336 data,
337 format="json",
338 )
339 self.assertEqual(200, response.status_code)
340 expected_response = {
341 "pk": pk,
342 "shift": self.shift.pk,
343 "created_at": "2021-01-01T01:00:00+01:00",
344 "order_items": [
345 {"product": "beer", "amount": 5, "total": "2.50"},
346 {"product": "soda", "amount": 2, "total": "0.00"},
347 ],
348 "order_description": "5x beer, 2x soda",
349 "age_restricted": True,
350 "subtotal": "2.50",
351 "discount": None,
352 "total_amount": "2.50",
353 "num_items": 7,
354 "payment": None,
355 "payer": None,
356 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
357 }
358 self.assertJSONEqual(response.content, expected_response)
360 with self.subTest("Delete and add product item"):
361 data = {
362 "order_items": [
363 {"product": "wine", "amount": 1},
364 {"product": "soda", "amount": 2},
365 ]
366 }
367 response = self.client.put(
368 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
369 data,
370 format="json",
371 )
372 self.assertEqual(200, response.status_code)
373 expected_response = {
374 "pk": pk,
375 "shift": self.shift.pk,
376 "created_at": "2021-01-01T01:00:00+01:00",
377 "order_items": [
378 {"product": "wine", "amount": 1, "total": "0.50"},
379 {"product": "soda", "amount": 2, "total": "0.00"},
380 ],
381 "order_description": "1x wine, 2x soda",
382 "age_restricted": True,
383 "subtotal": "0.50",
384 "discount": None,
385 "total_amount": "0.50",
386 "num_items": 3,
387 "payment": None,
388 "payer": None,
389 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
390 }
391 self.assertJSONEqual(response.content, expected_response)
393 with self.subTest("Write discount"):
394 data = {"discount": 0.2}
395 response = self.client.patch(
396 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
397 data,
398 format="json",
399 )
400 self.assertEqual(200, response.status_code)
401 expected_response = {
402 "pk": pk,
403 "shift": self.shift.pk,
404 "created_at": "2021-01-01T01:00:00+01:00",
405 "order_items": [
406 {"product": "wine", "amount": 1, "total": "0.50"},
407 {"product": "soda", "amount": 2, "total": "0.00"},
408 ],
409 "order_description": "1x wine, 2x soda",
410 "age_restricted": True,
411 "subtotal": "0.50",
412 "discount": "0.20",
413 "total_amount": "0.30",
414 "num_items": 3,
415 "payment": None,
416 "payer": None,
417 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
418 }
419 self.assertJSONEqual(response.content, expected_response)
421 with self.subTest("Reset discount"):
422 data = {"discount": 0}
423 response = self.client.patch(
424 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
425 data,
426 format="json",
427 )
428 self.assertEqual(200, response.status_code)
429 expected_response = {
430 "pk": pk,
431 "shift": self.shift.pk,
432 "created_at": "2021-01-01T01:00:00+01:00",
433 "order_items": [
434 {"product": "wine", "amount": 1, "total": "0.50"},
435 {"product": "soda", "amount": 2, "total": "0.00"},
436 ],
437 "order_description": "1x wine, 2x soda",
438 "age_restricted": True,
439 "subtotal": "0.50",
440 "discount": "0.00",
441 "total_amount": "0.50",
442 "num_items": 3,
443 "payment": None,
444 "payer": None,
445 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
446 }
447 self.assertJSONEqual(response.content, expected_response)
449 with self.subTest("Override total field"):
450 data = {
451 "order_items": [
452 {"product": "wine", "amount": 1, "total": "1.30"},
453 {"product": "soda", "amount": 2, "total": "2.00"},
454 ]
455 }
456 response = self.client.patch(
457 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
458 data,
459 format="json",
460 )
461 self.assertEqual(200, response.status_code)
462 expected_response = {
463 "pk": pk,
464 "shift": self.shift.pk,
465 "created_at": "2021-01-01T01:00:00+01:00",
466 "order_items": [
467 {"product": "wine", "amount": 1, "total": "1.30"},
468 {"product": "soda", "amount": 2, "total": "2.00"},
469 ],
470 "order_description": "1x wine, 2x soda",
471 "age_restricted": True,
472 "subtotal": "3.30",
473 "discount": "0.00",
474 "total_amount": "3.30",
475 "num_items": 3,
476 "payment": None,
477 "payer": None,
478 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
479 }
480 self.assertJSONEqual(response.content, expected_response)
482 with self.subTest("Reset overridden total fields"):
483 data = {
484 "order_items": [
485 {"product": "wine", "amount": 1},
486 {"product": "soda", "amount": 2},
487 ]
488 }
489 response = self.client.patch(
490 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
491 data,
492 format="json",
493 )
494 self.assertEqual(200, response.status_code)
495 expected_response = {
496 "pk": pk,
497 "shift": self.shift.pk,
498 "created_at": "2021-01-01T01:00:00+01:00",
499 "order_items": [
500 {"product": "wine", "amount": 1, "total": "0.50"},
501 {"product": "soda", "amount": 2, "total": "0.00"},
502 ],
503 "order_description": "1x wine, 2x soda",
504 "age_restricted": True,
505 "subtotal": "0.50",
506 "discount": "0.00",
507 "total_amount": "0.50",
508 "num_items": 3,
509 "payment": None,
510 "payer": None,
511 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
512 }
513 self.assertJSONEqual(response.content, expected_response)
515 with self.subTest("Write discount without custom price permissions"):
516 self.member.is_superuser = False
517 self.member.save()
518 self.shift.managers.add(self.cie)
519 self.shift.save()
521 data = {"discount": 0.2}
522 response = self.client.patch(
523 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
524 data,
525 format="json",
526 )
527 self.assertEqual(200, response.status_code)
528 expected_response = {
529 "pk": pk,
530 "shift": self.shift.pk,
531 "created_at": "2021-01-01T01:00:00+01:00",
532 "order_items": [
533 {"product": "wine", "amount": 1, "total": "0.50"},
534 {"product": "soda", "amount": 2, "total": "0.00"},
535 ],
536 "order_description": "1x wine, 2x soda",
537 "age_restricted": True,
538 "subtotal": "0.50",
539 "discount": "0.00",
540 "total_amount": "0.50",
541 "num_items": 3,
542 "payment": None,
543 "payer": None,
544 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
545 }
546 self.assertJSONEqual(response.content, expected_response)
548 with self.subTest("Write total field without custom price permissions"):
549 data = {
550 "order_items": [
551 {"product": "wine", "amount": 1, "total": "1.30"},
552 {"product": "soda", "amount": 2, "total": "2.00"},
553 ]
554 }
555 response = self.client.patch(
556 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
557 data,
558 format="json",
559 )
560 self.assertEqual(200, response.status_code)
561 expected_response = {
562 "pk": pk,
563 "shift": self.shift.pk,
564 "created_at": "2021-01-01T01:00:00+01:00",
565 "order_items": [
566 {"product": "wine", "amount": 1, "total": "0.50"},
567 {"product": "soda", "amount": 2, "total": "0.00"},
568 ],
569 "order_description": "1x wine, 2x soda",
570 "age_restricted": True,
571 "subtotal": "0.50",
572 "discount": "0.00",
573 "total_amount": "0.50",
574 "num_items": 3,
575 "payment": None,
576 "payer": None,
577 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
578 }
579 self.assertJSONEqual(response.content, expected_response)
581 with self.subTest("Delete one product item"):
582 data = {
583 "order_items": [
584 {"product": "wine", "amount": 1},
585 ]
586 }
587 response = self.client.patch(
588 reverse("api:v2:admin:sales:order-detail", kwargs={"pk": pk}),
589 data,
590 format="json",
591 )
592 self.assertEqual(200, response.status_code)
593 expected_response = {
594 "pk": pk,
595 "shift": self.shift.pk,
596 "created_at": "2021-01-01T01:00:00+01:00",
597 "order_items": [
598 {"product": "wine", "amount": 1, "total": "0.50"},
599 ],
600 "order_description": "1x wine",
601 "age_restricted": True,
602 "subtotal": "0.50",
603 "discount": "0.00",
604 "total_amount": "0.50",
605 "num_items": 1,
606 "payment": None,
607 "payer": None,
608 "payment_url": f"http://localhost:8000/sales/order/{pk}/pay/",
609 }
610 self.assertJSONEqual(response.content, expected_response)
612 def test_invalid_product(self):
613 data = {"order_items": [{"product": "invalidproduct", "amount": 4}]}
614 response = self.client.post(
615 reverse("api:v2:admin:sales:shift-orders", kwargs={"pk": self.shift.pk}),
616 data,
617 format="json",
618 )
619 self.assertEqual(400, response.status_code)
621 def test_user_self_order(self):
622 data = {"order_items": [{"product": "beer", "amount": 4}]}
623 response = self.client.post(
624 reverse("api:v2:sales:user-order-list", kwargs={"pk": self.shift.pk}),
625 data,
626 format="json",
627 )
628 self.assertEqual(201, response.status_code)
629 order = Order.objects.get(pk=response.data["pk"])
630 self.assertEqual(order.payer, self.member)
632 def test_claim_order(self):
633 with self.subTest("Claim a normal order"):
634 response = self.client.patch(
635 reverse("api:v2:sales:order-claim", kwargs={"pk": self.o3.pk})
636 )
637 self.assertEqual(200, response.status_code)
638 self.assertEqual(
639 Order.objects.get(pk=response.data["pk"]).payer, self.member
640 )
642 self.o3.payer = None
643 self.o3.save()
645 with self.subTest("Claim an order that is already yours"):
646 self.o3.payer = self.member
647 self.o3.save()
649 response = self.client.patch(
650 reverse("api:v2:sales:order-claim", kwargs={"pk": self.o3.pk})
651 )
652 self.assertEqual(200, response.status_code)
653 self.assertEqual(
654 Order.objects.get(pk=response.data["pk"]).payer, self.member
655 )
657 self.o3.payer = None
658 self.o3.save()
660 with self.subTest("Claim an order that is not yours"):
661 member = Member.objects.create(
662 username="test1",
663 first_name="Test1",
664 last_name="Example",
665 email="test1@example.org",
666 is_staff=False,
667 is_superuser=False,
668 )
669 self.o3.payer = member
670 self.o3.save()
672 response = self.client.patch(
673 reverse("api:v2:sales:order-claim", kwargs={"pk": self.o3.pk})
674 )
675 self.assertEqual(403, response.status_code)
676 self.o3.refresh_from_db()
677 self.assertEqual(self.o3.payer, member)
679 self.o3.payer = None
680 self.o3.save()
682 with self.subTest("Claim a paid order"):
683 response = self.client.patch(
684 reverse("api:v2:sales:order-claim", kwargs={"pk": self.o4.pk})
685 )
686 self.assertEqual(403, response.status_code)
688 self.o3.payer = None
689 self.o3.save()
691 with self.subTest("Claim an age-restricted order as a minor"):
692 with mock.patch("sales.services.is_adult") as is_adult:
693 is_adult.return_value = False
694 response = self.client.patch(
695 reverse("api:v2:sales:order-claim", kwargs={"pk": self.o3.pk})
696 )
697 self.assertEqual(403, response.status_code)
698 self.o3.refresh_from_db()
699 self.assertEqual(self.o3.payer, self.member)
702class ShiftAPITest(TestCase):
703 fixtures = [
704 "members.json",
705 "bank_accounts.json",
706 "member_groups.json",
707 "products.json",
708 ]
710 @classmethod
711 def setUpTestData(cls):
712 """Create the following test data:
714 o0: an empty order
715 o1: an unpaid order of 2 beer
716 o2: an order of 2 soda that doesn't need a payment
717 o3: an unpaid order with 2 beer and 2 wine
718 o4: a paid order with 2 wine
719 o4: a paid order with 2 beer and 2 wine
720 """
721 cls.member = Member.objects.filter(last_name="Wiggers").first()
723 cls.beer = Product.objects.get(name="beer")
724 cls.wine = Product.objects.get(name="wine")
725 cls.soda = Product.objects.get(name="soda")
727 cls.normal = ProductList.objects.get(
728 name="normal",
729 )
730 cls.free = ProductList.objects.get(
731 name="free",
732 )
734 cls.shift = Shift.objects.create(
735 start=timezone.now(),
736 end=timezone.now() + timezone.timedelta(hours=1),
737 product_list=cls.normal,
738 )
740 cls.shift2 = Shift.objects.create(
741 start=timezone.now(),
742 end=timezone.now() + timezone.timedelta(hours=1),
743 product_list=cls.free,
744 )
746 cls.o0 = Order.objects.create(shift=cls.shift)
747 cls.o1 = Order.objects.create(shift=cls.shift)
748 OrderItem.objects.create(
749 order=cls.o1,
750 product=cls.shift.product_list.product_items.get(product=cls.beer),
751 amount=2,
752 )
753 cls.o2 = Order.objects.create(shift=cls.shift)
754 OrderItem.objects.create(
755 order=cls.o2,
756 product=cls.shift.product_list.product_items.get(product=cls.soda),
757 amount=2,
758 )
759 cls.o3 = Order.objects.create(shift=cls.shift)
760 OrderItem.objects.create(
761 order=cls.o3,
762 product=cls.shift.product_list.product_items.get(product=cls.beer),
763 amount=2,
764 )
765 OrderItem.objects.create(
766 order=cls.o3,
767 product=cls.shift.product_list.product_items.get(product=cls.wine),
768 amount=2,
769 )
770 cls.o4 = Order.objects.create(shift=cls.shift)
771 OrderItem.objects.create(
772 order=cls.o4,
773 product=cls.shift.product_list.product_items.get(product=cls.wine),
774 amount=2,
775 )
776 cls.o5 = Order.objects.create(shift=cls.shift)
777 OrderItem.objects.create(
778 order=cls.o5,
779 product=cls.shift.product_list.product_items.get(product=cls.beer),
780 amount=2,
781 )
782 OrderItem.objects.create(
783 order=cls.o5,
784 product=cls.shift.product_list.product_items.get(product=cls.wine),
785 amount=2,
786 )
787 cls.o4.payment = create_payment(
788 cls.o4, processed_by=cls.member, pay_type=Payment.CASH
789 )
790 cls.o4.save()
791 cls.o5.payment = create_payment(
792 cls.o5, processed_by=cls.member, pay_type=Payment.CASH
793 )
794 cls.o5.save()
796 cls.cie = Committee.objects.get(pk=1)
797 MemberGroupMembership.objects.create(group=cls.cie, member=cls.member)
798 content_type = ContentType.objects.get_for_model(Order)
799 permission1 = Permission.objects.get(
800 content_type=content_type, codename="add_order"
801 )
802 permission2 = Permission.objects.get(
803 content_type=content_type, codename="change_order"
804 )
805 permission3 = Permission.objects.get(
806 content_type=content_type, codename="delete_order"
807 )
808 permission4 = Permission.objects.get(
809 content_type=content_type, codename="view_order"
810 )
811 permission5 = Permission.objects.get(
812 content_type=ContentType.objects.get_for_model(Shift), codename="view_shift"
813 )
814 cls.cie.permissions.add(permission1)
815 cls.cie.permissions.add(permission2)
816 cls.cie.permissions.add(permission3)
817 cls.cie.permissions.add(permission4)
818 cls.cie.permissions.add(permission5)
820 def setUp(self):
821 self.client = APIClient()
822 self.client.force_login(self.member)
824 def test_detail_not_logged_in(self):
825 self.client.logout()
826 response = self.client.get(
827 reverse("api:v2:admin:sales:shift-detail", kwargs={"pk": self.shift.pk})
828 )
829 self.assertEqual(403, response.status_code)
831 def test_detail_not_authorized__get(self):
832 response = self.client.get(
833 reverse("api:v2:admin:sales:shift-detail", kwargs={"pk": self.shift.pk})
834 )
835 self.assertEqual(200, response.status_code)
837 self.member.is_superuser = False
838 self.member.save()
840 response = self.client.get(
841 reverse("api:v2:admin:sales:shift-detail", kwargs={"pk": self.shift.pk})
842 )
843 self.assertEqual(403, response.status_code)
845 self.shift.managers.add(self.cie)
846 self.shift.save()
848 response = self.client.get(
849 reverse("api:v2:admin:sales:shift-detail", kwargs={"pk": self.shift.pk})
850 )
851 self.assertEqual(200, response.status_code)
853 def test_list_not_logged_in(self):
854 self.client.logout()
855 response = self.client.get(reverse("api:v2:admin:sales:shift-list"))
856 self.assertEqual(403, response.status_code)
858 def test_list_not_authorized__get(self):
859 response = self.client.get(reverse("api:v2:admin:sales:shift-list"))
860 self.assertEqual(200, response.status_code)
861 self.assertEqual(2, response.data["count"])
863 self.member.is_superuser = False
864 self.member.save()
866 response = self.client.get(reverse("api:v2:admin:sales:shift-list"))
867 self.assertEqual(200, response.status_code)
868 self.assertEqual(0, response.data["count"])
870 self.shift.managers.add(self.cie)
871 self.shift.save()
873 response = self.client.get(reverse("api:v2:admin:sales:shift-list"))
874 self.assertEqual(200, response.status_code)
875 self.assertEqual(1, response.data["count"])