github.com/apache/beam/sdks/v2@v2.48.2/python/apache_beam/io/gcp/dicomclient.py (about)

     1  #
     2  # Licensed to the Apache Software Foundation (ASF) under one or more
     3  # contributor license agreements.  See the NOTICE file distributed with
     4  # this work for additional information regarding copyright ownership.
     5  # The ASF licenses this file to You under the Apache License, Version 2.0
     6  # (the "License"); you may not use this file except in compliance with
     7  # the License.  You may obtain a copy of the License at
     8  #
     9  #    http://www.apache.org/licenses/LICENSE-2.0
    10  #
    11  # Unless required by applicable law or agreed to in writing, software
    12  # distributed under the License is distributed on an "AS IS" BASIS,
    13  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    14  # See the License for the specific language governing permissions and
    15  # limitations under the License.
    16  #
    17  
    18  # pytype: skip-file
    19  
    20  from google.auth import default
    21  from google.auth.transport import requests
    22  
    23  
    24  class DicomApiHttpClient:
    25    """DICOM api client that talk to api via http request"""
    26    healthcare_base_url = "https://healthcare.googleapis.com/v1"
    27    session = None
    28  
    29    def get_session(self, credential):
    30      if self.session:
    31        return self.session
    32  
    33      # if the credential is not provided, use the default credential.
    34      if not credential:
    35        credential, _ = default()
    36      new_seesion = requests.AuthorizedSession(credential)
    37      self.session = new_seesion
    38      return new_seesion
    39  
    40    def qido_search(
    41        self,
    42        project_id,
    43        region,
    44        dataset_id,
    45        dicom_store_id,
    46        search_type,
    47        params=None,
    48        credential=None):
    49      """function for searching a DICOM store"""
    50  
    51      # sending request to the REST healthcare api.
    52      api_endpoint = "{}/projects/{}/locations/{}".format(
    53          self.healthcare_base_url, project_id, region)
    54  
    55      # base of dicomweb path.
    56      dicomweb_path = "{}/datasets/{}/dicomStores/{}/dicomWeb/{}".format(
    57          api_endpoint, dataset_id, dicom_store_id, search_type)
    58  
    59      # Make an authenticated API request
    60      session = self.get_session(credential)
    61      headers = {"Content-Type": "application/dicom+json; charset=utf-8"}
    62      page_size = 500
    63  
    64      if params and 'limit' in params:
    65        page_size = params['limit']
    66      elif params:
    67        params['limit'] = page_size
    68      else:
    69        params = {'limit': page_size}
    70  
    71      offset = 0
    72      output = []
    73      # iterate to get all the results
    74      while True:
    75        params['offset'] = offset
    76        response = session.get(dicomweb_path, headers=headers, params=params)
    77        status = response.status_code
    78        if status != 200:
    79          if offset == 0:
    80            return [], status
    81          params['offset'] = offset - 1
    82          params['limit'] = 1
    83          response = session.get(dicomweb_path, headers=headers, params=params)
    84          check_status = response.status_code
    85          if check_status == 200:
    86            # if the number of results equals to page size
    87            return output, check_status
    88          else:
    89            # something wrong with the request or server
    90            return [], status
    91        results = response.json()
    92        output += results
    93        if len(results) < page_size:
    94          # got all the results, return
    95          break
    96        offset += len(results)
    97  
    98      return output, status
    99  
   100    def dicomweb_store_instance(
   101        self,
   102        project_id,
   103        region,
   104        dataset_id,
   105        dicom_store_id,
   106        dcm_file,
   107        credential=None):
   108      """function for storing an instance."""
   109  
   110      api_endpoint = "{}/projects/{}/locations/{}".format(
   111          self.healthcare_base_url, project_id, region)
   112  
   113      dicomweb_path = "{}/datasets/{}/dicomStores/{}/dicomWeb/studies".format(
   114          api_endpoint, dataset_id, dicom_store_id)
   115  
   116      # Make an authenticated API request
   117      session = self.get_session(credential)
   118      content_type = "application/dicom"
   119      headers = {"Content-Type": content_type}
   120  
   121      response = session.post(dicomweb_path, data=dcm_file, headers=headers)
   122  
   123      return None, response.status_code