Checking if ancillary files are already on the DB before starting upload. 0.8.0

Thu, 19 Dec 2019 18:02:57 +0200

author
Iannis <i.binietoglou@impworks.gr>
date
Thu, 19 Dec 2019 18:02:57 +0200
changeset 38
1b6786e9865d
parent 37
3d46ac5cba31
child 39
7f9605b75689

Checking if ancillary files are already on the DB before starting upload.

scc_access/__init__.py file | annotate | diff | comparison | revisions
scc_access/scc_access.py file | annotate | diff | comparison | revisions
--- a/scc_access/__init__.py	Thu Dec 05 18:27:28 2019 +0200
+++ b/scc_access/__init__.py	Thu Dec 19 18:02:57 2019 +0200
@@ -1,1 +1,1 @@
-__version__ = "0.7.1"
\ No newline at end of file
+__version__ = "0.8.0"
\ No newline at end of file
--- a/scc_access/scc_access.py	Thu Dec 05 18:27:28 2019 +0200
+++ b/scc_access/scc_access.py	Thu Dec 19 18:02:57 2019 +0200
@@ -66,6 +66,9 @@
         self.api_base_url = urlparse.urljoin(self.base_url, 'api/v1/')
         self.api_measurement_pattern = urlparse.urljoin(self.api_base_url, 'measurements/{0}/')
         self.api_measurements_url = urlparse.urljoin(self.api_base_url, 'measurements')
+        self.api_sounding_search_pattern = urlparse.urljoin(self.api_base_url, 'sounding_files/?filename={0}')
+        self.api_lidarratio_search_pattern = urlparse.urljoin(self.api_base_url, 'lidarratio_files/?filename={0}')
+        self.api_overlap_search_pattern = urlparse.urljoin(self.api_base_url, 'overlap_files/?filename={0}')
 
     def login(self, credentials):
         """ Login to SCC. """
@@ -104,16 +107,32 @@
         files = {'data': open(filename, 'rb')}
 
         if rs_filename is not None:
-            logger.debug('Adding sounding file %s' % rs_filename)
-            files['sounding_file'] = open(rs_filename, 'rb')
+            ancillary_file, _ = self.get_ancillary(rs_filename, 'sounding')
+
+            if ancillary_file.already_on_scc:
+                logger.warning("Sounding file {0.filename} already on the SCC with id {0.id}. Ignoring it.".format(ancillary_file))
+            else:
+                logger.debug('Adding sounding file %s' % rs_filename)
+                files['sounding_file'] = open(rs_filename, 'rb')
 
         if ov_filename is not None:
-            logger.debug('Adding overlap file %s' % ov_filename)
-            files['overlap_file'] = open(ov_filename, 'rb')
+            ancillary_file, _ = self.get_ancillary(ov_filename, 'overlap')
+
+            if ancillary_file.already_on_scc:
+                logger.warning("Overlap file {0.filename} already on the SCC with id {0.id}. Ignoring it.".format(ancillary_file))
+            else:
+                logger.debug('Adding overlap file %s' % ov_filename)
+                files['overlap_file'] = open(ov_filename, 'rb')
 
         if lr_filename is not None:
-            logger.debug('Adding lidar ratio file %s' % lr_filename)
-            files['lidar_ratio_file'] = open(lr_filename, 'rb')
+            ancillary_file, _ = self.get_ancillary(lr_filename, 'lidarratio')
+
+            if ancillary_file.already_on_scc:
+                logger.warning(
+                    "Lidar ratio file {0.filename} already on the SCC with id {0.id}. Ignoring it.".format(ancillary_file))
+            else:
+                logger.debug('Adding lidar ratio file %s' % lr_filename)
+                files['lidar_ratio_file'] = open(lr_filename, 'rb')
 
         logger.info("Uploading of file(s) %s started." % filename)
 
@@ -453,6 +472,50 @@
 
         return measurement_id
 
+    def get_ancillary(self, filename, file_type):
+        """
+        Try to get the ancillary file data from the SCC API.
+
+        The result will always be an API object. If the file does not exist, the .exists property is set to False.
+
+        Parameters
+        ----------
+        filename : str
+           Filename of the uploaded file.
+        file_type : str
+           Type of ancillary file. One of 'sounding', 'overlap', 'lidarratio'.
+
+        Returns
+        : AncillaryFile
+           The api object.
+        """
+        assert file_type in ['sounding', 'overlap', 'lidarratio']
+
+        if file_type == 'sounding':
+            file_url = self.api_sounding_search_pattern.format(filename)
+        elif file_type == 'overlap':
+            file_url = self.api_overlap_search_pattern.format(filename)
+        else:
+            file_url = self.api_lidarratio_search_pattern.format(filename)
+
+        response = self.session.get(file_url)
+
+        if not response.ok:
+            logger.error('Could not access API. Status code %s.' % response.status_code)
+            return None, response.status_code
+
+        response_dict = response.json()
+        object_list = response_dict['objects']
+
+        logger.debug("Ancillary file JSON: {0}".format(object_list))
+
+        if object_list:
+            ancillary_file = AncillaryFile(self.api_base_url, object_list[0])  # Assume only one file is returned
+        else:
+            ancillary_file = AncillaryFile(self.api_base_url, None)  # Create an empty object
+
+        return ancillary_file, response.status_code
+
     class PageNotAccessibleError(RuntimeError):
         pass
 
@@ -497,6 +560,22 @@
                                    self.processing)
 
 
+class AncillaryFile(ApiObject):
+    """ This class represents the ancilalry file object as returned in the SCC API.
+    """
+    @property
+    def already_on_scc(self):
+        if self.exists is False:
+            return False
+
+        return not self.status == 'missing'
+
+    def __str__(self):
+        return "%s: %s, %s" % (self.id,
+                               self.filename,
+                               self.status)
+
+
 def process_file(filename, system_id, settings, monitor=True, rs_filename=None, lr_filename=None, ov_filename=None):
     """ Shortcut function to process a file to the SCC. """
     logger.info("Processing file %s, using system %s" % (filename, system_id))

mercurial