Пример #1
0
    def query_segments(self, shape_id):
        self._current_shape_id = shape_id

        a = self.stop_class
        b = self.traffic_class
        rez = self.session.query(
            self.stop_class, self.traffic_class,
            func.ST_AsText(
                func.ST_ClosestPoint(func.ST_Points(a.geom),
                                     func.ST_StartPoint(b.geom))),
            func.ST_AsText(
                func.ST_ClosestPoint(func.ST_Points(a.geom),
                                     func.ST_EndPoint(b.geom))),
            func.ST_Distance(func.ST_StartPoint(b.geom), a.geom),
            func.ST_Distance(func.ST_EndPoint(b.geom), a.geom),
            func.ST_Distance(a.geom, b.geom)).filter(
                and_(a.shape_id == shape_id,
                     func.ST_DWithin(a.geom, b.geom, 0.001))).order_by(a.id)
        """
        , func.ST_ClosestPoint(func.ST_Points(a.geom), func.ST_StartPoint(b.geom))
        , func.ST_ClosestPoint(func.ST_Points(a.geom), func.ST_EndPoint(b.geom))
        , func.ST_ClosestPoint(func.ST_Points(b.geom), func.ST_StartPoint(a.geom))
        , func.ST_ClosestPoint(func.ST_Points(b.geom), func.ST_EndPoint(a.geom))
        , func.ST_Contains(func.ST_Buffer(a.geom, 0.00001), b.geom)
        , func.ST_Contains(func.ST_Buffer(a.geom, 0.0001), b.geom)
        , func.ST_Contains(func.ST_Buffer(a.geom, 0.001), b.geom)
        """

        qsegs = self.group_results(rez)
        return qsegs
Пример #2
0
    def prepare_merge(self):
        # Remove this when https://github.com/brazil-data-cube/stac.py/issues/10 is fixed.
        _ = stac_cli.catalog

        for tileid in self.mosaics:
            if len(self.mosaics) != 1:
                self.params['tileid'] = tileid
                continue

            bbox_result = db.session.query(
                Tile.id,
                func.ST_AsText(
                    func.ST_BoundingDiagonal(func.ST_Force2D(
                        Tile.geom_wgs84)))).filter(Tile.id == tileid).first()

            bbox = bbox_result[1][bbox_result[1].find('(') +
                                  1:bbox_result[0].find(')')]
            bbox = bbox.replace(' ', ',')

            for periodkey in self.mosaics[tileid]['periods']:
                start = self.mosaics[tileid]['periods'][periodkey]['start']
                end = self.mosaics[tileid]['periods'][periodkey]['end']

                # Search all images
                self.mosaics[tileid]['periods'][periodkey][
                    'scenes'] = self.search_images(bbox, start, end)
Пример #3
0
    def get_bbox(tile_id: str) -> str:
        """Retrieve the bounding box representation as string."""
        bbox_result = db.session.query(
            Tile.id,
            func.ST_AsText(
                func.ST_BoundingDiagonal(func.ST_Force2D(
                    Tile.geom_wgs84)))).filter(Tile.id == tile_id).first()

        bbox = bbox_result[1][bbox_result[1].find('(') +
                              1:bbox_result[0].find(')')]
        bbox = bbox.replace(' ', ',')

        return bbox
Пример #4
0
    def get_bbox(tile_id: str, grs: GridRefSys) -> str:
        """Retrieve the bounding box representation as string."""
        geom_table = grs.geom_table

        bbox_result = db.session.query(
            geom_table.c.tile,
            func.ST_AsText(func.ST_BoundingDiagonal(func.ST_Transform(geom_table.c.geom, 4326)))
        ).filter(
            geom_table.c.tile == tile_id
        ).first()

        bbox = bbox_result[1][bbox_result[1].find('(') + 1:bbox_result[0].find(')')]
        bbox = bbox.replace(' ', ',')

        return bbox
Пример #5
0
    def create_tiles(self, tiles: List[str], collection: Collection):
        """Create Collection tiles on database.

        Args:
            tiles - List of tiles in same GRS schema of collection
            collection - Collection object
        """
        tiles_by_grs = db.session() \
            .query(Tile, func.ST_AsText(func.ST_BoundingDiagonal(Tile.geom_wgs84))) \
            .filter(
                Tile.grs_schema_id == collection.grs_schema_id,
                Tile.id.in_(tiles)
            ).all()

        collection_tiles = []
        tiles = list(set(tiles))
        tiles_infos = {}

        datacube = "_".join(collection.id.split('_')[:-1])

        with db.session.begin_nested():
            for tile in tiles:
                # verify tile exists
                tile_info = list(
                    filter(lambda t: t[0].id == tile, tiles_by_grs))
                if not tile_info:
                    raise RuntimeError(
                        'Tile ({}) not found in GRS ({})'.format(
                            tile, collection.grs_schema_id))

                tiles_infos[tile] = tile_info[0]
                for function in ['WARPED', 'STK', 'MED']:
                    collection_tile = CollectionTile.query().filter(
                        CollectionTile.collection_id == '{}_{}'.format(
                            datacube, function), CollectionTile.grs_schema_id
                        == collection.grs_schema_id,
                        CollectionTile.tile_id == tile).first()
                    if not collection_tile:
                        CollectionTile(collection_id='{}_{}'.format(
                            datacube, function),
                                       grs_schema_id=collection.grs_schema_id,
                                       tile_id=tile).save(commit=False)

        db.session.commit()
Пример #6
0
    def index(self):
        if request.args.get('bounds') is None:
            return Response(json.dumps([]), mimetype='application/json')
        bounds_parts = request.args.get("bounds").split(',')
        zoom = int(request.args.get("zoom") or 1)

        powerlines = []

        if int(zoom) < 12:
            if int(zoom) < 8:
                # min_lenth is a multiplicator to reduce the number of shown powerlines based on their length and
                # zoom level
                min_length = 15000
            else:
                min_length = 10000

            powerlines = Powerline.query.filter(
                func.ST_Intersects(
                    func.ST_MakeEnvelope(bounds_parts[1], bounds_parts[0],
                                         bounds_parts[3], bounds_parts[2]),
                    Powerline.geom)).filter(
                        func.ST_Length(
                            func.ST_GeographyFromText(
                                func.ST_AsText(Powerline.geom))) > min_length *
                        (10 - zoom)).all()

        else:
            powerlines = Powerline.query.filter(
                func.ST_Intersects(
                    func.ST_MakeEnvelope(bounds_parts[1], bounds_parts[0],
                                         bounds_parts[3], bounds_parts[2]),
                    Powerline.geom)).all()

        powerlines = list(
            map(lambda powerline: powerline.serialize(), powerlines))

        return Response(json.dumps(powerlines), mimetype='application/json')
Пример #7
0
def orchestrate(datacube, cube_infos, tiles, start_date, end_date):
    # create collection_tiles
    tiles_by_grs = db.session() \
        .query(Tile, func.ST_AsText(func.ST_BoundingDiagonal(Tile.geom_wgs84))) \
        .filter(
            Tile.grs_schema_id == cube_infos.grs_schema_id,
            Tile.id.in_(tiles)
        ).all()

    collection_tiles = []
    tiles = list(set(tiles))
    tiles_infos = {}
    for tile in tiles:
        # verify tile exists
        tile_info = list(filter(lambda t: t[0].id == tile, tiles_by_grs))
        if not tile_info:
            return 'tile ({}) not found in GRS ({})'.format(tile, cube_infos.grs_schema_id), 404

        tiles_infos[tile] = tile_info[0]
        for function in ['IDENTITY', 'STK', 'MED']:
            cube_id = get_cube_id(datacube, function)
            collection_tile = CollectionTile.query().filter(
                CollectionTile.collection_id == cube_id,
                CollectionTile.grs_schema_id == cube_infos.grs_schema_id,
                CollectionTile.tile_id == tile
            ).first()
            if not collection_tile:
                collection_tiles.append(CollectionTile(
                    collection_id=cube_id,
                    grs_schema_id=cube_infos.grs_schema_id,
                    tile_id=tile
                ))
    BaseModel.save_all(collection_tiles)

    # get cube start_date if exists
    collections_items = CollectionItem.query().filter(
        CollectionItem.collection_id == cube_infos.id,
        CollectionItem.grs_schema_id == cube_infos.grs_schema_id
    ).order_by(CollectionItem.composite_start).all()
    cube_start_date = start_date
    if list(filter(lambda c_i: c_i.tile_id == tile, collections_items)):
        cube_start_date = collections_items[0].composite_start 

    # get/mount timeline
    temporal_schema = cube_infos.temporal_composition_schema.temporal_schema
    step = cube_infos.temporal_composition_schema.temporal_composite_t
    timeline = decode_periods(temporal_schema.upper(), cube_start_date, end_date, int(step))

    # create collection items (old model => mosaic)
    items_id = []
    items = {}
    for datekey in sorted(timeline):
        requestedperiod = timeline[datekey]
        for periodkey in requestedperiod:
            (p_basedate, p_startdate, p_enddate) = periodkey.split('_')

            if start_date is not None and p_startdate < start_date : continue
            if end_date is not None and p_enddate > end_date : continue

            for tile in tiles:
                bbox = tiles_infos[tile][1].replace('LINESTRING(', '') \
                    .replace('LINESTRING Z (', '') \
                    .replace(')', '') \
                    .replace(' ', ',') \
                    .split(',')
                if len(bbox) != 4:
                    del bbox[2]
                    del bbox[-1]

                items[tile] = items.get(tile, {})
                items[tile]['bbox'] = ','.join(bbox)
                items[tile]['xmin'] = tiles_infos[tile][0].min_x
                items[tile]['ymax'] = tiles_infos[tile][0].max_y
                items[tile]['periods'] = items[tile].get('periods', {})

                item_id = '{}_{}_{}'.format(cube_infos.id, tile, p_basedate)
                if item_id not in items_id:
                    items_id.append(item_id)
                    if not list(filter(lambda c_i: c_i.id == item_id, collections_items)):
                        items[tile]['periods'][periodkey] = {
                            'collection': cube_infos.id,
                            'grs_schema_id': cube_infos.grs_schema_id,
                            'tile_id': tile,
                            'item_date': p_basedate,
                            'id': item_id,
                            'composite_start': p_startdate,
                            'composite_end': p_enddate,
                            'dirname': '{}/{}/'.format(get_cube_id(datacube), tile)
                        }
    return items