Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-07-22 09:42:05

0001 from datetime import timedelta
0002 
0003 from django.contrib.auth.models import User
0004 from django.urls import reverse
0005 from django.utils import timezone
0006 from rest_framework import status
0007 from rest_framework.test import APITestCase
0008 
0009 from snapper_ai.models import CurrentComponent
0010 from monitor_app.workflow_models import WorkflowDefinition, WorkflowExecution
0011 
0012 
0013 class DatatakingPublicationTests(APITestCase):
0014     def setUp(self):
0015         self.user = User.objects.create_user(
0016             username="snapper-datataking-test",
0017             password="testpassword",
0018         )
0019         self.client.force_authenticate(user=self.user)
0020         self.initial_transition = timezone.now() - timedelta(minutes=1)
0021         self.workflow_definition = WorkflowDefinition.objects.create(
0022             workflow_name="state-history-test",
0023             version="1",
0024             workflow_type="test",
0025             definition="pass",
0026             parameter_values={},
0027             created_by=self.user.username,
0028         )
0029         self._create_execution("state-history-alice", "alice")
0030         self.run_data = {
0031             "run_number": 101,
0032             "phase": "initializing",
0033             "state": "imminent",
0034             "substate": "preparing",
0035             "target_worker_count": 2,
0036             "active_worker_count": 0,
0037             "stf_samples_received": 0,
0038             "slices_created": 0,
0039             "slices_queued": 0,
0040             "slices_processing": 0,
0041             "slices_completed": 0,
0042             "slices_failed": 0,
0043             "state_changed_at": self.initial_transition.isoformat(),
0044             "metadata": {"execution_id": "state-history-alice"},
0045         }
0046 
0047     def _create_execution(self, execution_id, namespace):
0048         return WorkflowExecution.objects.create(
0049             execution_id=execution_id,
0050             workflow_definition=self.workflow_definition,
0051             namespace=namespace,
0052             parameter_values={},
0053             status="running",
0054             start_time=self.initial_transition,
0055             executed_by=self.user.username,
0056         )
0057 
0058     def test_only_state_transitions_advance_datataking_revision(self):
0059         list_url = reverse("monitor_app:runstate-list")
0060         response = self.client.post(list_url, self.run_data, format="json")
0061         self.assertEqual(response.status_code, status.HTTP_201_CREATED)
0062 
0063         component = CurrentComponent.objects.get(
0064             scope="testbed",
0065             name="datataking",
0066         )
0067         self.assertEqual(component.component_schema_version, 2)
0068         self.assertEqual(component.revision, 1)
0069         self.assertEqual(
0070             component.data["namespaces"]["alice"],
0071             {
0072                 "run_number": 101,
0073                 "phase": "initializing",
0074                 "state": "imminent",
0075                 "substate": "preparing",
0076                 "last_transition_at": (
0077                     self.initial_transition.isoformat().replace("+00:00", "Z")
0078                 ),
0079             },
0080         )
0081 
0082         detail_url = reverse("monitor_app:runstate-detail", kwargs={"pk": 101})
0083         counter_time = self.initial_transition + timedelta(seconds=10)
0084         response = self.client.patch(
0085             detail_url,
0086             {
0087                 "slices_created": 4,
0088                 "state_changed_at": counter_time.isoformat(),
0089             },
0090             format="json",
0091         )
0092         self.assertEqual(response.status_code, status.HTTP_200_OK)
0093         component.refresh_from_db()
0094         self.assertEqual(component.revision, 1)
0095         self.assertEqual(
0096             component.data["namespaces"]["alice"]["last_transition_at"],
0097             self.initial_transition.isoformat().replace("+00:00", "Z"),
0098         )
0099 
0100         transition_time = counter_time + timedelta(seconds=10)
0101         response = self.client.patch(
0102             detail_url,
0103             {
0104                 "phase": "physics",
0105                 "state": "running",
0106                 "substate": "physics",
0107                 "state_changed_at": transition_time.isoformat(),
0108             },
0109             format="json",
0110         )
0111         self.assertEqual(response.status_code, status.HTTP_200_OK)
0112         component.refresh_from_db()
0113         self.assertEqual(component.revision, 2)
0114         alice = component.data["namespaces"]["alice"]
0115         self.assertEqual(alice["phase"], "physics")
0116         self.assertEqual(alice["state"], "running")
0117         self.assertEqual(alice["substate"], "physics")
0118         self.assertEqual(
0119             alice["last_transition_at"],
0120             transition_time.isoformat().replace("+00:00", "Z"),
0121         )
0122 
0123         self._create_execution("state-history-bob", "bob")
0124         bob_data = {
0125             **self.run_data,
0126             "run_number": 102,
0127             "metadata": {"execution_id": "state-history-bob"},
0128         }
0129         response = self.client.post(list_url, bob_data, format="json")
0130         self.assertEqual(response.status_code, status.HTTP_201_CREATED)
0131         component.refresh_from_db()
0132         self.assertEqual(component.revision, 3)
0133         self.assertEqual(set(component.data["namespaces"]), {"alice", "bob"})
0134         self.assertEqual(
0135             component.data["namespaces"]["alice"]["run_number"],
0136             101,
0137         )
0138         self.assertEqual(
0139             component.data["namespaces"]["bob"]["run_number"],
0140             102,
0141         )