Ejemplo n.º 1
0
def get_voi(atlas_id: str, space_id: str,
            boundingbox: Tuple[Tuple[float, float, float], Tuple[float, float,
                                                                 float]]):
    atlas = validate_and_return_atlas(atlas_id)
    space = validate_and_return_space(space_id, atlas)
    bbox = BoundingBox(boundingbox[0], boundingbox[1], space)

    def serialize_point(point):
        return [p for p in point]

    def serialize_voi(voi: VolumeOfInterest):
        return {
            "@id": voi.id,
            "name": voi.name,
            "description": voi.description,
            "url": voi.urls,
            "location": {
                "space": {
                    "@id": voi.location.space.id
                },
                "center": serialize_point(voi.location.center),
                "minpoint": serialize_point(voi.location.minpoint),
                "maxpoint": serialize_point(voi.location.maxpoint),
            },
            "volumes": [vol_src_sans_space(vol) for vol in voi.volumes]
        }

    return [
        serialize_voi(feat) for feat in all_voi_features
        if feat.location.space is space and bbox.intersection(feat.location)
    ]
Ejemplo n.º 2
0
def get_template_by_space_id(atlas_id: str, space_id: str):
    """
    Returns a template for a given space id.
    """
    atlas = validate_and_return_atlas(atlas_id)
    space = validate_and_return_space(space_id)
    template = atlas.get_template(space).fetch()

    # create file-object in memory
    # file_object = io.BytesIO()
    filename = get_file_from_nibabel(template, 'template', space)

    return FileResponse(filename, filename=filename)
Ejemplo n.º 3
0
def get_region_by_name(base_url: str,
                       atlas_id: str,
                       parcellation_id: str,
                       region_id: str,
                       space_id: str = None):
    """
    Returns a specific region for a given id.
    """
    atlas = siibra.atlases[atlas_id]
    parcellation = atlas.get_parcellation(parcellation_id)
    try:
        region = validate_and_return_region(region_id, parcellation)
    except ValueError:
        raise HTTPException(404, 'Region spec {region_id} cannot be decoded')

    if space_id:
        space = validate_and_return_space(space_id)
        region_json = region_encoder(region, space=space)
        region_json['props'] = get_region_props(space_id, atlas, region)
        region_json['hasRegionalMap'] = region.has_regional_map(
            space, siibra.commons.MapType.CONTINUOUS)
        region_json['_dataset_specs'] = [
            spec for spec in region_json['_dataset_specs']
            if spec.get('@type') != 'minds/core/dataset/v1.0.0'
        ]
        for ds in [
                ds for ds in region.datasets
                if type(ds) == siibra.core.datasets.EbrainsDataset
        ]:
            region_json['_dataset_specs'].append(
                jsonable_encoder(ds,
                                 custom_encoder=siibra_custom_json_encoder))
    else:
        region_json = region_encoder(region)

    single_region_root_url = '{}atlases/{}/parcellations/{}/regions/{}'.format(
        base_url, quote(atlas_id), quote(parcellation_id), quote(region_id))

    region_json['links'] = {
        'features':
        f'{single_region_root_url}/features',
        'regional_map_info':
        f'{single_region_root_url}/regional_map/info?space_id={space_id}'
        if region_json.get('hasRegionalMap') else None,
        'regional_map':
        f'{single_region_root_url}/regional_map/map?space_id={space_id}'
        if region_json.get('hasRegionalMap') else None,
    }

    return region_json
Ejemplo n.º 4
0
def get_all_regions_for_parcellation_id(atlas_id: str,
                                        parcellation_id: str,
                                        space_id: Optional[str] = None):
    """
    Returns all regions for a given parcellation id.
    """
    parcellation = validate_and_return_parcellation(parcellation_id)
    if not space_id is None:
        space = validate_and_return_space(space_id)
    else:
        space = None

    return [
        region_encoder(region, space=space)
        for region in parcellation.regiontree.children
    ]
Ejemplo n.º 5
0
def get_parcellation_map_for_space(atlas_id: str, space_id: str):
    """
    Returns all parcellation maps for a given space id.
    """
    validate_and_return_atlas(atlas_id)
    space = validate_and_return_space(space_id)
    valid_parcs = [p for p in siibra.parcellations if p.supports_space(space)]

    if len(valid_parcs) == 1:
        maps = [valid_parcs[0].get_map(space)]
        filename = get_file_from_nibabel(maps[0], 'maps', space)
        return FileResponse(filename, filename=filename)
    else:
        raise HTTPException(
            status_code=501,
            detail=
            f'space with id {space_id} has multiple parc, not yet implemented')
        maps = [p.get_map(space) for p in valid_parcs]
        files = []
        mem_zip = io.BytesIO()

        label_index = 0
        for map in maps:
            files.append(
                get_file_from_nibabel(map, 'map-{}'.format(label_index),
                                      space))
            label_index = label_index + 1

        with zipfile.ZipFile(mem_zip,
                             mode="w",
                             compression=zipfile.ZIP_DEFLATED) as zf:
            for f in files:
                zf.write(f)
                print(zf.namelist())

        mem_zip.seek(0)
        response = StreamingResponse(iter([mem_zip.getvalue()]),
                                     media_type="application/x-zip-compressed")
        response.headers[
            "Content-Disposition"] = 'attachment; filename=maps-{}.zip'.format(
                space.name.replace(' ', '_'))
        return response
    raise HTTPException(
        status_code=404,
        detail='Maps for space with id: {} not found'.format(space_id))
Ejemplo n.º 6
0
def parse_region_selection(atlas_id: str, parcellation_id: str, region_id: str,
                           space_id: str):
    if space_id is None:
        raise HTTPException(
            status_code=400,
            detail='space_id is required for this functionality')

    space_of_interest = validate_and_return_space(space_id)
    validate_and_return_atlas(atlas_id)
    parcellation = validate_and_return_parcellation(parcellation_id)
    region = validate_and_return_region(region_id, parcellation)
    if region is None:
        raise HTTPException(status_code=404,
                            detail=f'cannot find region with spec {region_id}')
    # if len(region) > 1:
    #     raise HTTPException(
    #         status_code=400,
    #         detail=f'found multiple region withs pec {region_id}')
    return region, space_of_interest
Ejemplo n.º 7
0
def get_spatial_feature_names(atlas_id: str, space_id: str, request: Request):
    """
    Return all possible feature names and links to get more details
    """
    validate_and_return_atlas(atlas_id)
    space = validate_and_return_space(space_id)
    # TODO: Getting all features with result takes to much time at the moment
    # features = siibra.get_features(space, 'all')

    return {
        'features': [{
            feature.modality(): '{}atlases/{}/spaces/{}/features/{}'.format(
                get_base_url_from_request(request),
                atlas_id.replace('/', '%2F'), space_id.replace('/', '%2F'),
                quote(feature.modality()))
            for feature in siibra.features.modalities if issubclass(
                feature._FEATURETYPE, siibra.features.feature.SpatialFeature)
        }]
    }
Ejemplo n.º 8
0
def get_one_space_by_id(atlas_id: str, space_id: str, request: Request):
    """
    Returns one space for given id, with links to further resources
    """
    validate_and_return_atlas(atlas_id)
    space = validate_and_return_space(space_id)
    if space:
        json_result = jsonable_encoder(
            space, custom_encoder=siibra_custom_json_encoder)
        # TODO: Error on first call
        json_result['availableParcellations'] = get_parcellations_for_space(
            space)
        json_result['links'] = {
            'templates': {
                'href':
                '{}atlases/{}/spaces/{}/templates'.format(
                    get_base_url_from_request(request),
                    atlas_id.replace('/', '%2F'), space.id.replace('/', '%2F'))
            },
            'parcellation_maps': {
                'href':
                '{}atlases/{}/spaces/{}/parcellation_maps'.format(
                    get_base_url_from_request(request),
                    atlas_id.replace('/', '%2F'), space.id.replace('/', '%2F'))
            },
            'features': {
                'href':
                '{}atlases/{}/spaces/{}/features'.format(
                    get_base_url_from_request(request),
                    atlas_id.replace('/', '%2F'), space.id.replace('/', '%2F'))
            }
        }
        if hasattr(space, 'origin_datainfos'):
            json_result['originDatainfos'] = [
                origin_data_decoder(datainfo)
                for datainfo in space.origin_datainfos
            ]
        return json_result
    else:
        raise HTTPException(
            status_code=404,
            detail='space with id: {} not found'.format(space_id))
Ejemplo n.º 9
0
def get_spatial_features(atlas_id,
                         space_id,
                         modality_id,
                         feature_id=None,
                         detail=False,
                         parc_id=None,
                         region_id=None):

    if modality_id not in siibra.features.modalities:
        raise HTTPException(status_code=400,
                            detail=f'{modality_id} is not a valid modality')

    # TODO: Why only spatial features
    if not issubclass(
            # feature_classes[modality_id],
            # feature_export.SpatialFeature):
            siibra.features.modalities[modality_id]._FEATURETYPE,
            siibra.features.feature.SpatialFeature):
        # modality_id is not a global feature, return empty array
        return []

    atlas = validate_and_return_atlas(atlas_id)
    space_of_interest = validate_and_return_space(space_id, atlas)

    # TODO not working at the moment. Space_of_interest is never in atlas.spaces
    # if space_of_interest not in atlas.spaces:
    #     raise HTTPException(404, detail=f'space {space_id} not in atlas {atlas}')

    # TODO: No Selection of parcellation and region is needed - TODO: How to provide parcellation/region
    if parc_id is None:
        raise HTTPException(status_code=400, detail='Parc id is needed')

    parc = validate_and_return_parcellation(parc_id, atlas)
    roi = validate_and_return_region(region_id, parc)

    logger.debug(
        f'get_spatial_features: {str(atlas)}, {str(space_of_interest)}, {str(parc)}, {str(roi)}'
    )

    try:
        # spatial_features=atlas.get_features(modality_id)
        spatial_features = siibra.get_features(roi,
                                               modality_id,
                                               space=space_of_interest)
    except Exception as e:
        logger.warn(e, str(space_of_interest), space_id)
        raise HTTPException(404, detail=f'Could not get spatial features.')

    shaped_features = None
    if siibra.features.modalities[
            modality_id] == siibra.features.ieeg.IEEG_SessionQuery:
        shaped_features = [{
            'summary': {
                '@id': hashlib.md5(str(feat).encode("utf-8")).hexdigest(),
                'name': f'{feat.dataset.name} sub:{feat.sub_id}',
                'description': str(feat.dataset.description),
                'origin_datainfos': [{
                    'urls': feat.dataset.urls
                }]
            },
            'get_detail':
            lambda ft: get_ieeg_session_detail(ft,
                                               region=roi,
                                               parcellation=parc,
                                               space=space_of_interest,
                                               atlas=atlas),
            'instance':
            feat
        } for feat in spatial_features]

    if shaped_features is None:
        raise HTTPException(501, detail=f'{modality_id} not yet implemented')

    if feature_id is not None:
        shaped_features = [
            f for f in shaped_features if f['summary']['@id'] == feature_id
        ]

    return [{
        **f['summary'],
        **(f['get_detail'](f['instance']) if detail else {}),
    } for f in shaped_features]