Commit 536c9f14 authored by jlaura's avatar jlaura Committed by GitHub
Browse files

Db Fixes #309 (#316)

* Adds automatic overlap computation to the NCG

* Updates to fix filelist parsing

* Updates doc strings

* Removes obsolete SQL queries
parent b391c289
Loading
Loading
Loading
Loading
+58 −3
Original line number Diff line number Diff line
@@ -37,6 +37,7 @@ from autocnet.io.db.model import (Images, Keypoints, Matches, Cameras,
from autocnet.io.db.connection import new_connection, Parent
from autocnet.vis.graph_view import plot_graph, cluster_plot
from autocnet.control import control
from autocnet.spatial.overlap import compute_overlaps_sql

#np.warnings.filterwarnings('ignore')

@@ -1297,11 +1298,14 @@ class NetworkCandidateGraph(CandidateGraph):
        for s, d, e in self.edges(data='data'):
            e.parent = self

        # Execute the computation to compute overlapping geometries
        self._execute_sql(compute_overlaps_sql)

        # Setup the redis queues
        redis = config.get('redis')
        if redis:
            self.processing_queue = redis['processing_queue']


    def _setup_queues(self):
        """
        Setup a 2 queue redis connection for pushing and pulling work/results
@@ -1320,6 +1324,23 @@ class NetworkCandidateGraph(CandidateGraph):
        """
        return self.redis_queue.flushall()

    def _execute_sql(self, sql):
        """
        Execute a raw SQL string in the database currently specified
        by the AutoCNet config file.

        Use this method with caution as you can easily do things like
        truncate a table.

        Parameters
        ----------
        sql : str
              The SQL string to be passed to the DB engine and executed.
        """
        conn = engine.connect()
        conn.execute(sql)
        conn.close()

    def apply(self, function, on='edge', args=(), walltime='01:00:00', **kwargs):
        """
        A mirror of the apply function from the standard CandidateGraph object. This implementation
@@ -1421,7 +1442,7 @@ class NetworkCandidateGraph(CandidateGraph):
        For the nodes in the graph, genreate a GDAL compliant vrt file.
        This is just a dispatcher to the knoten generate_vrt file.
        """
        for i, n in self.nodes(data='data'):
        for _, n in self.nodes(data='data'):
            n.generate_vrt(**kwargs)

    def to_isis(self, path, flistpath=None,sql = """
@@ -1459,6 +1480,40 @@ WHERE points.active = True AND measures.active=TRUE AND measures.jigreject=FALSE
        cnet.to_isis(path, df, self.serials())
        cnet.write_filelist(self.files, path=flistpath)

    @classmethod
    def from_filelist(cls, filelist):
        """
        Parse a filelist to add nodes to the database. Using the
        information in the database, then instantiate a complete,
        NCG.

        Parameters
        ----------
        filelist : list, str
                   If a list, this is a list of paths. If a str, this is
                   a path to a file containing a list of image paths
                   that is newline ("\\n") delimited.

        Returns
        -------
        ncg : object
              A network candidate graph object
        """
        if isinstance(filelist, list):
            pass
        elif os.path.exists(filelist):
            filelist = io_utils.file_to_list(filelist)
        else:
            warning.warn('Unable to parse the passed filelist')

        for f in filelist:
            # Create the nodes in the graph. Really, this is creating the
            # images in the DB
            image_name = os.path.basename(f)
            NetworkNode(image_path=f, image_name=image_name)
        
        return cls.from_database()
        
    @classmethod
    def from_database(cls, query_string='SELECT * FROM public.images'):
        """
@@ -1515,6 +1570,6 @@ AND i1.id < i2.id""".format(query_string)
                adjacency[spath].append(dpath)
        session.close()
        # Add nodes that do not overlap any images
        obj = cls.from_adjacency(adjacency, node_id_map=adjacency_lookup, config=config)
        obj = cls(adjacency, node_id_map=adjacency_lookup, config=config)

        return obj
+19 −0
Original line number Diff line number Diff line
@@ -103,3 +103,22 @@ def place_points_in_overlaps(cg, size_threshold=0.0007, reference=None, height=0
    session.add_all(points)
    session.commit()

compute_overlaps_sql = """
WITH intersectiongeom AS
(SELECT geom AS geom FROM ST_Dump((
   SELECT ST_Polygonize(the_geom) AS the_geom FROM (
     SELECT ST_Union(the_geom) AS the_geom FROM (
	   SELECT ST_ExteriorRing((ST_DUMP(footprint_latlon)).geom) AS the_geom
	     FROM images WHERE images.footprint_latlon IS NOT NULL) AS lines
	) AS noded_lines))),
iid AS (
 SELECT images.id, intersectiongeom.geom AS geom
		FROM images, intersectiongeom
		WHERE images.footprint_latlon is NOT NULL AND
		ST_INTERSECTS(intersectiongeom.geom, images.footprint_latlon) AND
		ST_AREA(ST_INTERSECTION(intersectiongeom.geom, images.footprint_latlon)) > 0.000001
)
INSERT INTO overlay(intersections, geom) SELECT row.intersections, row.geom FROM 
(SELECT iid.geom, array_agg(iid.id) AS intersections
  FROM iid GROUP BY iid.geom) AS row WHERE array_length(intersections, 1) > 1;
"""
 No newline at end of file
+0 −22
Original line number Diff line number Diff line
INSERT INTO overlay(geom)
(
	SELECT ST_AsEWKB(geom) AS geom FROM ST_Dump((
        SELECT ST_Polygonize(the_geom) AS the_geom FROM (
            SELECT ST_Union(the_geom) AS the_geom FROM (
                SELECT ST_ExteriorRing((ST_DUMP(footprint_latlon)).geom) AS the_geom
                FROM images WHERE images.footprint_latlon IS NOT NULL) AS lines
        ) AS noded_lines
    ))
);

UPDATE overlay
SET intersections = imgs.iid
FROM (
		SELECT overlay.id, array_agg(images.id) as iid
		FROM overlay, images
		WHERE images.footprint_latlon is NOT NULL AND
		ST_INTERSECTS(overlay.geom, images.footprint_latlon) AND
		ST_AREA(ST_INTERSECTION(overlay.geom, images.footprint_latlon)) > 0.000001
		GROUP BY overlay.id
	) AS imgs
WHERE imgs.id = overlay.id;