1- import os
2-
3- from utils . audit_logging_setup import LoggingService
1+ from enums . lambda_error import LambdaError
2+ from enums . snomed_codes import SnomedCode
3+ from models . document_reference import DocumentReference
44from models .fhir .R4 .fhir_document_reference import (
55 DocumentReference as FhirDocumentReference ,
66)
7- from models . document_reference import DocumentReference
8- from services .fhir_document_reference_service_base import FhirDocumentReferenceServiceBase
9- from enums . snomed_codes import SnomedCode
10- from enums . lambda_error import LambdaError
11- from utils .lambda_exceptions import UpdateFhirDocumentReferenceException
7+ from pydantic import ValidationError
8+ from services .fhir_document_reference_service_base import (
9+ FhirDocumentReferenceServiceBase ,
10+ )
11+ from utils .audit_logging_setup import LoggingService
1212from utils .dynamo_utils import DocTypeTableRouter
13+ from utils .exceptions import FhirDocumentReferenceException , InvalidNhsNumberException
1314from utils .lambda_exceptions import (
1415 InvalidDocTypeException ,
15- )
16- from pydantic import ValidationError
17- from utils .exceptions import (
18- InvalidNhsNumberException ,
19- FhirDocumentReferenceException ,
16+ UpdateFhirDocumentReferenceException ,
2017)
2118
2219logger = LoggingService (__name__ )
2320
21+
2422class PutFhirDocumentReferenceService (FhirDocumentReferenceServiceBase ):
2523 def __init__ (self ):
2624 super ().__init__ ()
2725 self .doc_router = DocTypeTableRouter ()
2826
2927 def process_fhir_document_reference (self , fhir_document : str ) -> str :
3028 try :
31- validated_fhir_doc = FhirDocumentReference .model_validate_json (fhir_document )
29+ validated_fhir_doc = FhirDocumentReference .model_validate_json (
30+ fhir_document
31+ )
3232 except ValidationError as e :
3333 logger .error (f"FHIR document validation error: { str (e )} " )
3434 raise UpdateFhirDocumentReferenceException (400 , LambdaError .DocRefNoParse )
@@ -38,38 +38,41 @@ def process_fhir_document_reference(self, fhir_document: str) -> str:
3838 doc_type = self ._determine_document_type (validated_fhir_doc )
3939 except FhirDocumentReferenceException :
4040 logger .error ("Could not determine document type" )
41- raise UpdateFhirDocumentReferenceException (400 , LambdaError .DocRefInvalidType )
41+ raise UpdateFhirDocumentReferenceException (
42+ 400 , LambdaError .DocRefInvalidType
43+ )
4244
4345 # Determine which DynamoDB table to use based on the document type
4446 dynamo_table = self ._get_dynamo_table_for_doc_type (doc_type )
4547
4648 # Get the current document from the database
4749 current_doc = self ._get_current_doc (validated_fhir_doc , dynamo_table )
48-
50+
4951 # Check that the NHS number in the request matches the one in the stored document
5052 request_nhs_number = self ._validate_nhs_number (validated_fhir_doc , current_doc )
51-
53+
5254 # Check that the version number matches the stored document
5355 self ._validate_version_number (validated_fhir_doc , current_doc )
54-
56+
5557 # Create a new document reference with the new version number
5658 new_doc_reference = self ._create_new_document_reference (
57- validated_fhir_doc ,
58- current_doc ,
59- request_nhs_number ,
60- doc_type
59+ validated_fhir_doc , current_doc , request_nhs_number , doc_type
6160 )
6261
6362 # Handle binary content if present, otherwise create a pre-signed URL
64- presigned_url = self ._handle_document_save (new_doc_reference , validated_fhir_doc , dynamo_table )
65-
63+ presigned_url = self ._handle_document_save (
64+ new_doc_reference , validated_fhir_doc , dynamo_table
65+ )
66+
6667 try :
6768 return self ._create_fhir_response (new_doc_reference , presigned_url )
6869 except (ValidationError , InvalidNhsNumberException ) as e :
6970 logger .error (f"FHIR document validation error: { str (e )} " )
7071 raise UpdateFhirDocumentReferenceException (400 , LambdaError .DocRefNoParse )
71-
72- def _get_current_doc (self , fhir_doc : FhirDocumentReference , dynamo_table : str ) -> DocumentReference :
72+
73+ def _get_current_doc (
74+ self , fhir_doc : FhirDocumentReference , dynamo_table : str
75+ ) -> DocumentReference :
7376 try :
7477 current_doc = self ._get_document_reference (fhir_doc .id , dynamo_table )
7578 except FhirDocumentReferenceException :
@@ -83,10 +86,12 @@ def _get_current_doc(self, fhir_doc: FhirDocumentReference, dynamo_table: str) -
8386 raise UpdateFhirDocumentReferenceException (
8487 400 , LambdaError .UpdateDocNotLatestVersion
8588 )
86-
89+
8790 return current_doc
88-
89- def _validate_nhs_number (self , fhir_doc : FhirDocumentReference , current_doc : DocumentReference ):
91+
92+ def _validate_nhs_number (
93+ self , fhir_doc : FhirDocumentReference , current_doc : DocumentReference
94+ ):
9095 try :
9196 request_nhs_number = fhir_doc .extract_nhs_number_from_fhir ()
9297 except FhirDocumentReferenceException :
@@ -98,30 +103,38 @@ def _validate_nhs_number(self, fhir_doc: FhirDocumentReference, current_doc: Doc
98103 raise UpdateFhirDocumentReferenceException (
99104 400 , LambdaError .UpdateDocNHSNumberMismatch
100105 )
101-
106+
102107 return request_nhs_number
103-
104- def _validate_version_number (self , fhir_doc : FhirDocumentReference , current_doc : DocumentReference ):
108+
109+ def _validate_version_number (
110+ self , fhir_doc : FhirDocumentReference , current_doc : DocumentReference
111+ ):
105112 if fhir_doc .meta is None :
106113 logger .error ("Missing version number" )
107- raise UpdateFhirDocumentReferenceException (400 , LambdaError .DocumentReferenceMissingParameters )
108-
114+ raise UpdateFhirDocumentReferenceException (
115+ 400 , LambdaError .DocumentReferenceMissingParameters
116+ )
117+
109118 if current_doc .version != fhir_doc .meta .versionId :
110119 logger .error ("Version does not match current version." )
111- raise UpdateFhirDocumentReferenceException (400 , LambdaError .UpdateDocVersionMismatch )
112-
120+ raise UpdateFhirDocumentReferenceException (
121+ 400 , LambdaError .UpdateDocVersionMismatch
122+ )
123+
113124 def _create_new_document_reference (
114- self ,
115- fhir_doc : FhirDocumentReference ,
116- current_doc : DocumentReference ,
117- nhs_number : str ,
118- doc_type : SnomedCode ,
119- ) -> DocumentReference :
125+ self ,
126+ fhir_doc : FhirDocumentReference ,
127+ current_doc : DocumentReference ,
128+ nhs_number : str ,
129+ doc_type : SnomedCode ,
130+ ) -> DocumentReference :
120131 try :
121132 patient_details = self ._check_nhs_number_with_pds (nhs_number )
122133 except FhirDocumentReferenceException :
123- raise UpdateFhirDocumentReferenceException (400 , LambdaError .DocRefPatientSearchInvalid )
124-
134+ raise UpdateFhirDocumentReferenceException (
135+ 400 , LambdaError .DocRefPatientSearchInvalid
136+ )
137+
125138 new_doc_version = int (current_doc .version ) + 1
126139
127140 # Create a document reference model
@@ -135,13 +148,13 @@ def _create_new_document_reference(
135148 )
136149
137150 return document_reference
138-
151+
139152 def _handle_document_save (
140- self ,
141- document_reference : DocumentReference ,
142- fhir_doc : FhirDocumentReference ,
143- dynamo_table : str ,
144- ) -> str :
153+ self ,
154+ document_reference : DocumentReference ,
155+ fhir_doc : FhirDocumentReference ,
156+ dynamo_table : str ,
157+ ) -> str :
145158 binary_content = fhir_doc .content [0 ].attachment .data
146159
147160 presigned_url = None
@@ -150,21 +163,27 @@ def _handle_document_save(
150163 try :
151164 self ._store_binary_in_s3 (document_reference , binary_content )
152165 except FhirDocumentReferenceException :
153- raise UpdateFhirDocumentReferenceException (500 , LambdaError .DocRefNoParse )
166+ raise UpdateFhirDocumentReferenceException (
167+ 500 , LambdaError .DocRefNoParse
168+ )
154169 else :
155170 # Create a pre-signed URL for uploading
156171 try :
157172 presigned_url = self ._create_s3_presigned_url (document_reference )
158173 except FhirDocumentReferenceException :
159- raise UpdateFhirDocumentReferenceException (500 , LambdaError .InternalServerError )
174+ raise UpdateFhirDocumentReferenceException (
175+ 500 , LambdaError .InternalServerError
176+ )
160177 try :
161178 # Save document reference to DynamoDB
162179 self ._save_document_reference_to_dynamo (dynamo_table , document_reference )
163180 except FhirDocumentReferenceException :
164- raise UpdateFhirDocumentReferenceException (500 , LambdaError .DocRefUploadInternalError )
165-
181+ raise UpdateFhirDocumentReferenceException (
182+ 500 , LambdaError .DocRefUploadInternalError
183+ )
184+
166185 return presigned_url
167-
186+
168187 def _get_dynamo_table_for_doc_type (self , doc_type : SnomedCode ) -> str :
169188 try :
170189 return self .doc_router .resolve (doc_type )
0 commit comments