Exemple #1
0
def transform_bbox(from_srs, to_srs, bbox):
    """
    Transform list of `features`. Modifies `features` in-place.
    """
    bbox_coverage = BBOXCoverage(bbox, SRS(from_srs))
    coverage_transformed = bbox_coverage.transform_to(SRS(to_srs))
    return coverage_transformed.bbox
Exemple #2
0
def transform_bbox(from_srs, to_srs, bbox):
    """
    Transform list of `features`. Modifies `features` in-place.
    """
    bbox_coverage = BBOXCoverage(bbox, SRS(from_srs))
    coverage_transformed = bbox_coverage.transform_to(SRS(to_srs))
    return coverage_transformed.bbox
Exemple #3
0
 def test_intersection(self):
     eq_(self.coverage.intersection((15, 15, 20, 20), SRS(4326)),
         BBOXCoverage((15, 15, 20, 20), SRS(4326)))
     eq_(self.coverage.intersection((15, 15, 80, 20), SRS(4326)),
         BBOXCoverage((15, 15, 80, 20), SRS(4326)))
     eq_(self.coverage.intersection((9, 10, 20, 20), SRS(4326)),
         BBOXCoverage((9, 10, 20, 20), SRS(4326)))
     eq_(self.coverage.intersection((-30, 10, -8, 70), SRS(4326)),
         BBOXCoverage((-10, 10, -8, 70), SRS(4326)))
     eq_(self.coverage.intersection((-30, 10, -11, 70), SRS(4326)), None)
     eq_(self.coverage.intersection((0, 0, 1000, 1000), SRS(900913)), None)
     assert bbox_equals(
         self.coverage.intersection((0, 0, 1500000, 1500000),
                                    SRS(900913)).bbox,
         (0.0, 10, 13.47472926179282, 13.352207626707813))
Exemple #4
0
    def seed_tasks(self):
        for grid_name in self.grids:
            for cache_name, cache in iteritems(self.caches):
                tile_manager = cache[grid_name]
                grid = self.seeding_conf.grids[grid_name]
                if self.coverage is False:
                    coverage = False
                elif self.coverage:
                    coverage = self.coverage.transform_to(grid.srs)
                else:
                    coverage = BBOXCoverage(grid.bbox, grid.srs)

                try:
                    if coverage is not False:
                        coverage.extent.llbbox
                except TransformationError:
                    raise SeedConfigurationError(
                        '%s: coverage transformation error' % self.name)

                if self.levels:
                    levels = self.levels.for_grid(grid)
                else:
                    levels = list(range(0, grid.levels))

                if not tile_manager.cache.supports_timestamp:
                    if self.refresh_timestamp:
                        # remove everything
                        self.refresh_timestamp = 0

                md = dict(name=self.name,
                          cache_name=cache_name,
                          grid_name=grid_name)
                yield SeedTask(md, tile_manager, levels,
                               self.refresh_timestamp, coverage)
Exemple #5
0
 def test_get_map_small_with_source_extent(self):
     self.source.extent = BBOXCoverage([0, 0, 90, 45], SRS(4326)).extent
     result = self.layer.get_map(MapQuery((-180, -90, 180, 90), (300, 150), SRS(4326), 'png'))
     eq_(self.file_cache.stored_tiles, set([(1, 0, 1)]))
     # source requests one tile (no meta-tiling configured) limited to source.extent
     eq_(self.client.requested, [((0, 0, 90, 45), (128, 64), (SRS(4326)))])
     eq_(result.size, (300, 150))
Exemple #6
0
 def test_get_map_small_with_source_extent(self, source, layer, mock_file_cache, mock_wms_client):
     source.extent = BBOXCoverage([0, 0, 90, 45], SRS(4326)).extent
     result = layer.get_map(MapQuery((-180, -90, 180, 90), (300, 150), SRS(4326), 'png'))
     assert mock_file_cache.stored_tiles == set([(1, 0, 1)])
     # source requests one tile (no meta-tiling configured) limited to source.extent
     assert mock_wms_client.requested == [((0, 0, 90, 45), (128, 64), (SRS(4326)))]
     assert result.size == (300, 150)
Exemple #7
0
    def seed_tasks(self):
        for grid_name in self.grids:
            for cache_name, cache in self.caches.iteritems():
                tile_manager = cache[grid_name]
                grid = self.seeding_conf.grids[grid_name]
                if self.coverage:
                    if isinstance(
                            self.coverage,
                            GeomCoverage) and self.coverage.geom.is_empty:
                        continue
                    coverage = self.coverage.transform_to(grid.srs)
                else:
                    coverage = BBOXCoverage(grid.bbox, grid.srs)
                if self.levels:
                    levels = self.levels.for_grid(grid)
                else:
                    levels = list(xrange(0, grid.levels))

                if not tile_manager.cache.supports_timestamp:
                    if self.refresh_timestamp:
                        # remove everything
                        self.refresh_timestamp = 0

                md = dict(name=self.name,
                          cache_name=cache_name,
                          grid_name=grid_name)
                yield SeedTask(md, tile_manager, levels,
                               self.refresh_timestamp, coverage)
Exemple #8
0
    def cleanup_tasks(self):
        for grid_name in self.grids:
            for cache_name, cache in self.caches.iteritems():
                tile_manager = cache[grid_name]
                grid = self.seeding_conf.grids[grid_name]
                if self.coverage:
                    coverage = self.coverage.transform_to(grid.srs)
                    complete_extent = False
                else:
                    coverage = BBOXCoverage(grid.bbox, grid.srs)
                    complete_extent = True
                if self.levels:
                    levels = self.levels.for_grid(grid)
                else:
                    levels = list(xrange(0, grid.levels))

                if not tile_manager.cache.supports_timestamp:
                    # for caches without timestamp support (like MBTiles)
                    if self.remove_timestamp is self.init_time:
                        # remove everything
                        self.remove_timestamp = 0
                    else:
                        raise SeedConfigurationError(
                            "cleanup does not support remove_before for '%s'"
                            " because cache '%s' does not support timestamps" %
                            (self.name, cache_name))
                md = dict(name=self.name,
                          cache_name=cache_name,
                          grid_name=grid_name)
                yield CleanupTask(md,
                                  tile_manager,
                                  levels,
                                  self.remove_timestamp,
                                  coverage=coverage,
                                  complete_extent=complete_extent)
Exemple #9
0
 def make_bbox_task(self, bbox, srs, levels):
     md = dict(name="", cache_name="", grid_name="")
     coverage = BBOXCoverage(bbox, srs)
     return SeedTask(md,
                     self.tile_mgr,
                     levels,
                     refresh_timestamp=None,
                     coverage=coverage)
Exemple #10
0
 def layer(self, mock_file_cache, source, tile_locker):
     grid = TileGrid(SRS(4326), bbox=[-180, -90, 180, 90])
     image_opts = ImageOptions(resampling='nearest', format='png')
     tile_mgr = TileManager(grid, mock_file_cache, [source], 'png',
         meta_size=[1, 1], meta_buffer=0, image_opts=image_opts,
         locker=tile_locker)
     layer = CacheMapLayer(tile_mgr, image_opts=default_image_opts)
     layer.extent = BBOXCoverage([0, 0, 90, 45], SRS(4326)).extent
     return layer
Exemple #11
0
def create_seed_task(tile_mgr, coverage, levels, update_tiles=None):
    if not coverage:
        coverage = BBOXCoverage(tile_mgr.grid.bbox, tile_mgr.grid.srs)

    if update_tiles:
        refresh_timestamp = time.time()
    else:
        refresh_timestamp = None
    return SeedTask(md={}, tile_manager=tile_mgr, levels=levels,
        refresh_timestamp=refresh_timestamp, coverage=coverage)
Exemple #12
0
 def setup(self):
     self.file_cache = MockFileCache('/dev/null', 'png', lock_dir=tmp_lock_dir)
     self.grid = TileGrid(SRS(4326), bbox=[-180, -90, 180, 90])
     self.client = MockWMSClient()
     self.source = WMSSource(self.client)
     self.image_opts = ImageOptions(resampling='nearest', format='png')
     self.tile_mgr = TileManager(self.grid, self.file_cache, [self.source], 'png',
         meta_size=[1, 1], meta_buffer=0, image_opts=self.image_opts)
     self.layer = CacheMapLayer(self.tile_mgr, image_opts=default_image_opts)
     self.layer.extent = BBOXCoverage([0, 0, 90, 45], SRS(4326)).extent
Exemple #13
0
    def _init_tasks(self):
        for cache_name, options in iteritems(self.conf['seeds']):
            remove_before = None
            if 'remove_before' in options:
                remove_before = before_timestamp_from_options(
                    options['remove_before'])
            try:
                caches = self.mapproxy_conf.caches[cache_name].caches()
            except KeyError:
                print('error: cache %s not found. available caches: %s' %
                      (cache_name, ','.join(self.mapproxy_conf.caches.keys())),
                      file=sys.stderr)
                return
            caches = dict(
                (grid, tile_mgr) for grid, extent, tile_mgr in caches)
            for view in options['views']:
                view_conf = self.conf['views'][view]
                coverage = load_coverage(view_conf)

                cache_srs = view_conf.get('srs', None)
                if cache_srs is not None:
                    cache_srs = [SRS(s) for s in cache_srs]

                level = view_conf.get('level', None)
                assert len(level) == 2

                for grid, tile_mgr in iteritems(caches):
                    if cache_srs and grid.srs not in cache_srs: continue
                    md = dict(name=view,
                              cache_name=cache_name,
                              grid_name=self.grids[grid])
                    levels = list(range(level[0], level[1] + 1))
                    if coverage:
                        if isinstance(coverage,
                                      GeomCoverage) and coverage.geom.is_empty:
                            continue
                        seed_coverage = coverage.transform_to(grid.srs)
                    else:
                        seed_coverage = BBOXCoverage(grid.bbox, grid.srs)

                    self.seed_tasks.append(
                        SeedTask(md, tile_mgr, levels, remove_before,
                                 seed_coverage))

                    if remove_before:
                        levels = list(range(grid.levels))
                        complete_extent = bool(coverage)
                        self.cleanup_tasks.append(
                            CleanupTask(md,
                                        tile_mgr,
                                        levels,
                                        remove_before,
                                        seed_coverage,
                                        complete_extent=complete_extent))
Exemple #14
0
    levels = parse_levels(options.levels)
    if levels[-1] >= tile_grid.levels:
        print >>sys.stderr, 'ERROR: destination grid only has %d levels' % tile_grid.levels
        sys.exit(2)

    if options.srs:
        srs = SRS(options.srs)
    else:
        srs = tile_grid.srs

    if options.coverage:
        seed_coverage = load_coverage(
            {'datasource': options.coverage, 'srs': srs, 'where': options.where},
            base_path=os.getcwd())
    else:
        seed_coverage = BBOXCoverage(tile_grid.bbox, tile_grid.srs)

    if not supports_tiled_access(mgr):
        print >>sys.stderr, 'WARN: grids are incompatible. needs to scale/reproject tiles for export.'

    md = dict(name='export', cache_name='cache', grid_name=options.grid, dest=options.dest)
    task = SeedTask(md, mgr, levels, None, seed_coverage)

    print format_export_task(task, custom_grid=custom_grid)

    logger = ProgressLog(verbose=True, silent=False)
    try:
        seed_task(task, progress_logger=logger, dry_run=options.dry_run,
             concurrency=options.concurrency)
    except KeyboardInterrupt:
        print >>sys.stderr, 'stopping...'
Exemple #15
0
    if coverage.geom:
        coverage_area = coverage.geom.area
    else:
        coverage_area = _area_from_bbox(coverage.bbox)

    return coverage_area / grid_area

def estimate_tiles(grid, levels, coverage=None):
    if coverage:
        ratio = grid_coverage_ratio(grid.bbox, grid.srs, coverage)
    else:
        ratio = 1

    tiles = 0
    for level in levels:
        grid_size = grid.grid_sizes[level]
        level_tiles = grid_size[0] * grid_size[1]
        level_tiles = int(math.ceil(level_tiles * ratio))

        tiles += level_tiles

    return tiles


if __name__ == '__main__':
    from mapproxy.srs import SRS
    from mapproxy.grid import tile_grid
    from mapproxy.util.coverage import BBOXCoverage

    print estimate_tiles(tile_grid(3857), levels=range(12), coverage=BBOXCoverage([5, 50, 10, 60], SRS(4326)))
Exemple #16
0
def coverage(geom, srs):
    if isinstance(geom, (list, tuple)):
        return BBOXCoverage(geom, srs)
    else:
        return GeomCoverage(geom, srs)
Exemple #17
0
def export_command(args=None):
    parser = optparse.OptionParser("%prog grids [options] mapproxy_conf")
    parser.add_option("-f",
                      "--mapproxy-conf",
                      dest="mapproxy_conf",
                      help="MapProxy configuration")

    parser.add_option(
        "-q",
        "--quiet",
        action="count",
        dest="quiet",
        default=0,
        help=
        "reduce number of messages to stdout, repeat to disable progress output"
    )

    parser.add_option("--source",
                      dest="source",
                      help="source to export (source or cache)")

    parser.add_option(
        "--grid",
        help="grid for export. either the name of an existing grid or "
        "the grid definition as a string")

    parser.add_option("--dest",
                      help="destination of the export (directory or filename)")

    parser.add_option("--type", help="type of the export format")

    parser.add_option("--levels", help="levels to export: e.g 1,2,3 or 1..10")

    parser.add_option(
        "--fetch-missing-tiles",
        dest="fetch_missing_tiles",
        action='store_true',
        default=False,
        help="if missing tiles should be fetched from the sources")

    parser.add_option(
        "--force",
        action='store_true',
        default=False,
        help="overwrite/append to existing --dest files/directories")

    parser.add_option("-n",
                      "--dry-run",
                      action="store_true",
                      default=False,
                      help="do not export, just print output")

    parser.add_option("-c",
                      "--concurrency",
                      type="int",
                      dest="concurrency",
                      default=1,
                      help="number of parallel export processes")

    parser.add_option(
        "--coverage",
        help="the coverage for the export as a BBOX string, WKT file "
        "or OGR datasource")
    parser.add_option("--srs", help="the SRS of the coverage")
    parser.add_option("--where", help="filter for OGR coverages")

    from mapproxy.script.util import setup_logging
    import logging
    setup_logging(logging.WARN)

    if args:
        args = args[1:]  # remove script name

    (options, args) = parser.parse_args(args)

    if not options.mapproxy_conf:
        if len(args) != 1:
            parser.print_help()
            sys.exit(1)
        else:
            options.mapproxy_conf = args[0]

    required_options = ['mapproxy_conf', 'grid', 'source', 'dest', 'levels']
    for required in required_options:
        if not getattr(options, required):
            print('ERROR: missing required option --%s' %
                  required.replace('_', '-'),
                  file=sys.stderr)
            parser.print_help()
            sys.exit(1)

    try:
        conf = load_configuration(options.mapproxy_conf)
    except IOError as e:
        print('ERROR: ',
              "%s: '%s'" % (e.strerror, e.filename),
              file=sys.stderr)
        sys.exit(2)
    except ConfigurationError as e:
        print(e, file=sys.stderr)
        print('ERROR: invalid configuration (see above)', file=sys.stderr)
        sys.exit(2)

    if '=' in options.grid:
        try:
            grid_conf = parse_grid_definition(options.grid)
        except ValidationError as ex:
            print('ERROR: invalid grid configuration', file=sys.stderr)
            for error in ex.errors:
                print(' ', error, file=sys.stderr)
            sys.exit(2)
        except ValueError:
            print('ERROR: invalid grid configuration', file=sys.stderr)
            sys.exit(2)
        options.grid = 'tmp_mapproxy_export_grid'
        grid_conf['name'] = options.grid
        custom_grid = True
        conf.grids[options.grid] = GridConfiguration(grid_conf, conf)
    else:
        custom_grid = False

    if os.path.exists(options.dest) and not options.force:
        print('ERROR: destination exists, remove first or use --force',
              file=sys.stderr)
        sys.exit(2)

    cache_conf = {
        'name': 'export',
        'grids': [options.grid],
        'sources': [options.source],
    }
    if options.type == 'mbtile':
        cache_conf['cache'] = {
            'type': 'mbtiles',
            'filename': options.dest,
        }
    elif options.type == 'sqlite':
        cache_conf['cache'] = {
            'type': 'sqlite',
            'directory': options.dest,
        }
    elif options.type == 'geopackage':
        cache_conf['cache'] = {
            'type': 'geopackage',
            'filename': options.dest,
        }
    elif options.type == 'compact-v1':
        cache_conf['cache'] = {
            'type': 'compact',
            'version': 1,
            'directory': options.dest,
        }
    elif options.type == 'compact-v2':
        cache_conf['cache'] = {
            'type': 'compact',
            'version': 2,
            'directory': options.dest,
        }
    elif options.type in ('tc', 'mapproxy'):
        cache_conf['cache'] = {
            'type': 'file',
            'directory': options.dest,
        }
    elif options.type == 'arcgis':
        cache_conf['cache'] = {
            'type': 'file',
            'directory_layout': 'arcgis',
            'directory': options.dest,
        }
    elif options.type in ('tms', None):  # default
        cache_conf['cache'] = {
            'type': 'file',
            'directory_layout': 'tms',
            'directory': options.dest,
        }
    else:
        print('ERROR: unsupported --type %s' % (options.type, ),
              file=sys.stderr)
        sys.exit(2)

    if not options.fetch_missing_tiles:
        for source in conf.sources.values():
            source.conf['seed_only'] = True

    tile_grid, extent, mgr = CacheConfiguration(cache_conf, conf).caches()[0]

    levels = parse_levels(options.levels)
    if levels[-1] >= tile_grid.levels:
        print('ERROR: destination grid only has %d levels' % tile_grid.levels,
              file=sys.stderr)
        sys.exit(2)

    if options.srs:
        srs = SRS(options.srs)
    else:
        srs = tile_grid.srs

    if options.coverage:
        seed_coverage = load_coverage(
            {
                'datasource': options.coverage,
                'srs': srs,
                'where': options.where
            },
            base_path=os.getcwd())
    else:
        seed_coverage = BBOXCoverage(tile_grid.bbox, tile_grid.srs)

    if not supports_tiled_access(mgr):
        print(
            'WARN: grids are incompatible. needs to scale/reproject tiles for export.',
            file=sys.stderr)

    md = dict(name='export',
              cache_name='cache',
              grid_name=options.grid,
              dest=options.dest)
    task = SeedTask(md, mgr, levels, 1, seed_coverage)

    print(format_export_task(task, custom_grid=custom_grid))

    logger = ProgressLog(verbose=options.quiet == 0, silent=options.quiet >= 2)
    try:
        seed_task(task,
                  progress_logger=logger,
                  dry_run=options.dry_run,
                  concurrency=options.concurrency)
    except KeyboardInterrupt:
        print('stopping...', file=sys.stderr)
        sys.exit(2)