@@ -1997,16 +1997,27 @@ def insert_instances(
1997
1997
transfer_syntax_uid = transfer_syntax_uid
1998
1998
)
1999
1999
dcmwrite (b , ds , write_like_original = False )
2000
+ # The data set needs to be read back (at least partially)
2001
+ # to determine the offset of the Pixel Data element. This
2002
+ # is required to either read or build the Basic Offset Table
2003
+ # for image instances to allow for fast retrieval of frames.
2004
+ fp .seek (0 )
2005
+ # One needs to specify at least one tag to satisfy mypy.
2006
+ tag = tag_for_keyword ('PatientID' )
2007
+ dcmread (
2008
+ fp ,
2009
+ specific_tags = [tag ], # type: ignore
2010
+ stop_before_pixels = True
2011
+ )
2012
+ pixel_data_offset = fp .tell ()
2013
+
2000
2014
pixel_data_element : Union [DataElement , None ] = None
2001
2015
for pixel_data_tag in _PIXEL_DATA_TAGS :
2002
2016
try :
2003
2017
pixel_data_element = ds [pixel_data_tag ]
2004
2018
except KeyError :
2005
2019
continue
2006
2020
if pixel_data_element is not None :
2007
- pixel_data_offset = pixel_data_element .file_tell
2008
- if pixel_data_offset is None :
2009
- continue
2010
2021
fp .seek (pixel_data_offset , 0 )
2011
2022
first_frame_offset , bot = _get_frame_offsets (
2012
2023
fp ,
@@ -2017,7 +2028,8 @@ def insert_instances(
2017
2028
np .product ([
2018
2029
ds .Rows ,
2019
2030
ds .Columns ,
2020
- ds .SamplesPerPixel ])
2031
+ ds .SamplesPerPixel
2032
+ ])
2021
2033
),
2022
2034
transfer_syntax_uid = ds .file_meta .TransferSyntaxUID ,
2023
2035
bits_allocated = ds .BitsAllocated
@@ -2028,14 +2040,14 @@ def insert_instances(
2028
2040
2029
2041
fp .seek (0 )
2030
2042
file_content = fp .read ()
2043
+
2031
2044
instances [sop_instance_uid ] = (
2032
2045
* instance_metadata ,
2033
2046
str (ds .file_meta .TransferSyntaxUID ),
2034
2047
str (rel_file_path ),
2035
2048
first_frame_offset ,
2036
2049
bot ,
2037
2050
)
2038
-
2039
2051
file_path = self .base_dir .joinpath (rel_file_path )
2040
2052
successes .append ((ds , file_path , file_content ))
2041
2053
except Exception as error :
@@ -2899,6 +2911,7 @@ def retrieve_instance_rendered(
2899
2911
frame_index = frame_index ,
2900
2912
transfer_syntax_uid = transfer_syntax_uid
2901
2913
)
2914
+ image_file_pointer .close ()
2902
2915
2903
2916
# TODO: ICC Profile
2904
2917
codec_name , codec_kwargs = self ._get_image_codec_parameters (
@@ -3187,6 +3200,8 @@ def iter_instance_frames(
3187
3200
else :
3188
3201
yield frame
3189
3202
3203
+ image_file_pointer .close ()
3204
+
3190
3205
def retrieve_instance_frames (
3191
3206
self ,
3192
3207
study_instance_uid : str ,
@@ -3313,6 +3328,7 @@ def retrieve_instance_frames(
3313
3328
else :
3314
3329
retrieved_frames .append (frame )
3315
3330
3331
+ image_file_pointer .close ()
3316
3332
return retrieved_frames
3317
3333
3318
3334
def retrieve_instance_frames_rendered (
@@ -3383,6 +3399,7 @@ def retrieve_instance_frames_rendered(
3383
3399
frame_index = frame_index ,
3384
3400
transfer_syntax_uid = transfer_syntax_uid
3385
3401
)
3402
+ image_file_pointer .close ()
3386
3403
3387
3404
# TODO: ICC Profile
3388
3405
codec_name , codec_kwargs = self ._get_image_codec_parameters (
@@ -3573,6 +3590,9 @@ def store_instances(
3573
3590
response = Dataset ()
3574
3591
response .RetrieveURL = None
3575
3592
3593
+ if len (successes ) == 0 and len (failures ) == 0 :
3594
+ raise RuntimeError ('Failed to store instances.' )
3595
+
3576
3596
if len (successes ) > 0 :
3577
3597
response .ReferencedSOPSequence = []
3578
3598
for ds , file_path , file_content in successes :
0 commit comments