Exemplo n.º 1
0
def directory_contents(dir_path: Path) -> list[Path]:
    dir_path = Path(dir_path)
    if not dir_path.is_dir():
        raise exc.QgrRuntimeError(
            f'`dir_path` must be a directory. Got {dir_path}')

    return sorted(dir_path.glob('**/*'), )
Exemplo n.º 2
0
def make_map_layer(layer_node: LayerNode) -> qgc.QgsMapLayer:
    layer_path = _layer_path(layer_node=layer_node, )
    layer_type = vector_or_raster(layer_node)
    if layer_type == 'Vector':
        provider = 'ogr'
        qgs_layer_creator = qgc.QgsVectorLayer
    elif layer_type == 'Raster':
        provider = 'gdal'
        qgs_layer_creator = qgc.QgsRasterLayer

    # For online layers, the provider is specified in the config.
    layer_cfg = layer_node.layer_cfg
    if type(layer_cfg.input.asset) is OnlineAsset:
        provider = layer_cfg.input.asset.provider

    creator = functools.partial(
        qgs_layer_creator,
        str(layer_path),
        layer_cfg.title,
        provider,
    )
    map_layer = _create_layer_with_side_effects(
        creator,
        layer_node=layer_node,
    )

    if not map_layer.isValid():
        raise exc.QgrRuntimeError(
            f'Invalid QgsMapLayer created for layer {layer_cfg.id}', )

    add_layer_metadata(map_layer, layer_cfg)

    if style_filepath := layer_cfg.style_filepath:
        _load_qml_style(map_layer, style_filepath)
Exemplo n.º 3
0
def get_layer_fp(layer_dir: Path) -> Path:
    """Look for one and only one standard file type 'gpkg' or 'tif'."""
    # TODO: Extract standard file types into some structure
    rasters = list(layer_dir.glob('*.tif'))
    vectors = list(layer_dir.glob('*.gpkg'))
    files = rasters + vectors

    if len(files) != 1:
        raise exc.QgrRuntimeError(
            'Expected exactly 1 .tif or .gpkg in layer output directory'
            f' {layer_dir}. Found: {files}.', )

    return files[0]
Exemplo n.º 4
0
def fetch_and_write_file(  # noqa:C901
        url: str,
        *,
        output_dir: Path,
        session=None,
        verify=True,
):
    """Attempt to download and write file from url.

    Assumes filename from URL or content-disposition header.
    """
    if url.startswith('ftp://'):
        if not verify:
            raise exc.QgrRuntimeError(
                'Ignoring TLS certificate verification is not supported for FTP'
                ' sources.', )

        _ftp_fetch_and_write(url, output_dir)
    else:
        # TODO: Share the session across requests somehow?
        if not session:
            session = create_earthdata_authenticated_session(hosts=[url],
                                                             verify=verify)

        with session.get(
                url,
                timeout=REQUEST_TIMEOUT,
                stream=True,
                headers={'User-Agent': 'QGreenland'},
        ) as resp:

            # Try to extract the filename from the `content-disposition` header
            if ((disposition := resp.headers.get('content-disposition'))
                    and 'filename' in disposition):
                # Sometimes the filename is quoted, sometimes it's not.
                parsed = cgi.parse_header(disposition)
                # Handle case where disposition itself (usually "attachment")
                # isn't present (geothermal heat flux :bell:).
                matcher = re.compile('filename="?(.*)"?')
                if ('filename' in parsed[0]
                        and (match := matcher.match(parsed[0]))):
                    fn = match.groups()[0].strip('\'"')
                else:
Exemplo n.º 5
0
            # Try to extract the filename from the `content-disposition` header
            if ((disposition := resp.headers.get('content-disposition'))
                    and 'filename' in disposition):
                # Sometimes the filename is quoted, sometimes it's not.
                parsed = cgi.parse_header(disposition)
                # Handle case where disposition itself (usually "attachment")
                # isn't present (geothermal heat flux :bell:).
                matcher = re.compile('filename="?(.*)"?')
                if ('filename' in parsed[0]
                        and (match := matcher.match(parsed[0]))):
                    fn = match.groups()[0].strip('\'"')
                else:
                    fn = parsed[1]['filename']
            else:
                if not (fn := _filename_from_url(url)):
                    raise exc.QgrRuntimeError(
                        f'Failed to retrieve output filename from {url}', )

            if resp.status_code != 200:
                raise exc.QgrRuntimeError(
                    f"Received '{resp.status_code}' from {resp.request.url}."
                    f' Content: {resp.text}', )

            fp = output_dir / fn

            with open(fp, 'wb') as f:
                for chunk in resp.iter_content(chunk_size=CHUNK_SIZE):
                    f.write(chunk)

        return fp