Source code for fhirpack.load.base

import json
import importlib
from typing import Union
import os

import pandas as pd
import magic

from fhirpy.lib import SyncFHIRResource
from fhirpy.lib import SyncFHIRReference
import numpy as np
import fhirpack.utils as utils

# LOGGER = CONFIG.getLogger(__name__)


[docs]class BaseLoaderMixin: # TODO rename sendResourcesToJSON
[docs] def sendResourcesToFiles( self, # TODO if None save to os.getcwd paths: list[str] = None, input: Union[ list[str], list[SyncFHIRReference], list[SyncFHIRResource], ] = None, combine: bool = False, ): result = [] if not input and self.isFrame: input = self.data if not paths: paths = self.paths elif input and not self.isFrame: input = self.prepareOperationInput(input, SyncFHIRResource) elif input and self.isFrame: # TODO raise error references and isFrame not allowed raise NotImplementedError n = len(input) paths = [os.path.abspath(e) for e in paths] if len(paths) == 1 and combine: with open(paths[0], "w", encoding="utf-8") as f: sobj = json.dumps( input.apply(lambda x: x.serialize()).to_list(), indent=4, sort_keys=True, ) f.write(sobj) elif len(paths) == len(input): pass else: raise Exception("number of paths and number of data blobs must be equal") successes = np.full(n, True) if not combine: for i, res, path in zip(range(n), input, paths): try: with open(path, "a+", encoding="utf-8") as f: sobj = json.dumps(res.serialize(), indent=4, sort_keys=True) f.write(sobj) except Exception as e: # TODO raise or log? successes[i] = False return successes
[docs] def sendBytesToFile( self, input: list[bytearray] = None, paths: list[str] = None, guessExtension: bool = False, combine: bool = False, params: dict = None, ): if not params: params = {} if not input and self.isFrame: input = self.data.values paths = self.path.values elif input and not self.isFrame: pass elif input and self.isFrame: raise NotImplementedError n = len(input) if len(paths) == 1 and combine: paths = [paths[0]] * n elif len(paths) == len(input): pass else: raise Exception("number of paths and number of data blobs must be equal") successes = np.full(n, True) for i, data, path in zip(range(n), input, paths): try: extension = utils.guessBufferMIMEType(bytes(data[:50])) abspath = os.path.abspath(path) if guessExtension: abspath += "." + extension with open(abspath, "wb+") as f: f.write(data) except Exception as e: successes[i] = False # TODO raise or log? return successes
[docs] def sendToTable( self, input: Union[ list[str], list[SyncFHIRReference], list[SyncFHIRResource], ] = None, # combine: bool = False, params: dict = None, ignoreFrame: bool = False, fileType: str = "csv", # TODO enforce existence of paths in checks paths: list[str] = None, ): params = {} if params is None else params input = [] if input is None else input paths = [] if paths is None else paths result = [] if len(input): raise NotImplementedError # input = self.castOperand(input, SyncFHIRReference, "replace") # result = self.getResources(input, resourceType="replace", raw=True) try: if self.isFrame and not ignoreFrame: input = self n = len(input) if len(paths) > 1: raise NotImplementedError if fileType not in ["csv", "xls"]: raise ValueError(str(fileType) + " not supported. Use csv, xls.") path = f"{paths[0]}.{fileType}" if "/" in path: os.makedirs(os.path.dirname(path), exist_ok=True) else: path = f"./{path}" if fileType == "xls": raise ValueError("XLS not yet supported.") # TODO: disabled until the env has an xls engine # inFrame.to_excel(path, engine="xlsxwriter", sheet_name="cohort") elif fileType == "csv": input.to_csv(path_or_buf=path, index=False) else: raise NotImplementedError else: raise NotImplementedError result = [True] except Exception as e: raise e result = self.prepareOutput(result) return result
[docs] def sendDICOMToFiles( self, input: Union[ list[str], list[SyncFHIRReference], list[SyncFHIRResource], ] = None, combine: bool = False, params: dict = None, ignoreFrame: bool = False, ): params = {} if params is None else params input = [] if input is None else input result = [] if len(input): raise NotImplementedError # input = self.castOperand(input, SyncFHIRReference, "replace") # result = self.getResources(input, resourceType="replace", raw=True) elif self.isFrame and not ignoreFrame: input = self paths = self.path.values n = len(input) if len(paths) == 1 and combine: paths = [paths[0]] * n elif len(paths) == len(input): pass else: raise Exception( "number of paths and number of data blobs must be equal" ) if self.resourceTypeIs("ImagingStudy"): input.path.apply(lambda x: os.makedirs(x, exist_ok=True)) result = input.apply( lambda x: x.data.save_as(x.path + "/" + x.data.SOPInstanceUID), axis=1, ) else: raise NotImplementedError else: raise NotImplementedError result = self.prepareOutput(result) return result