mirror of
https://github.com/chanzuckerberg/cellxgene.git
synced 2026-10-08 02:58:12 +08:00
Add backend endpoint
This commit is contained in:
@@ -190,6 +190,11 @@ class SummarizeVarAPI(Resource):
|
||||
def post(self, data_adaptor):
|
||||
return common_rest.summarize_var_post(request, data_adaptor)
|
||||
|
||||
class SpatialImageAPI(Resource):
|
||||
@rest_get_data_adaptor
|
||||
def get(self, data_adaptor):
|
||||
return common_rest.spatial_image_get(request, data_adaptor)
|
||||
|
||||
|
||||
def get_api_base_resources(bp_base):
|
||||
"""Add resources that are accessed from the api url"""
|
||||
@@ -222,6 +227,8 @@ def get_api_dataroot_resources(bp_dataroot):
|
||||
# Computation routes
|
||||
add_resource(DiffExpObsAPI, "/diffexp/obs")
|
||||
add_resource(LayoutObsAPI, "/layout/obs")
|
||||
# Spatial routes
|
||||
add_resource(SpatialImageAPI, "/spatial/image")
|
||||
return api
|
||||
|
||||
|
||||
|
||||
+37
-1
@@ -5,7 +5,7 @@ from http import HTTPStatus
|
||||
import zlib
|
||||
import json
|
||||
|
||||
from flask import make_response, jsonify, current_app, abort
|
||||
from flask import make_response, jsonify, current_app, abort, send_file
|
||||
from werkzeug.urls import url_unquote
|
||||
|
||||
from server.common.config.client_config import get_client_config
|
||||
@@ -397,3 +397,39 @@ def summarize_var_post(request, data_adaptor):
|
||||
|
||||
key = request.args.get("key", default=None)
|
||||
return summarize_var_helper(request, data_adaptor, key, request.get_data())
|
||||
|
||||
def spatial_image_get(request, data_adaptor):
|
||||
import io
|
||||
import matplotlib.pyplot
|
||||
|
||||
resolution = "hires"
|
||||
spatial = data_adaptor.get_spatial()
|
||||
|
||||
if len(list(spatial)) == 0:
|
||||
return abort_and_log(HTTPStatus.BAD_REQUEST, "uns does not have spatial information")
|
||||
|
||||
library_id = list(spatial)[0]
|
||||
if len(spatial) > 1:
|
||||
current_app.logger.warning(f"More than one library found under uns.spatial, using library '{library_id}'")
|
||||
|
||||
if "images" not in spatial[library_id]:
|
||||
return abort_and_log(HTTPStatus.BAD_REQUEST, "spatial information does not contain images")
|
||||
|
||||
if resolution not in spatial[library_id]["images"]:
|
||||
return abort_and_log(HTTPStatus.BAD_REQUEST, f"spatial information does not contain requested resolution '{resolution}'")
|
||||
|
||||
response_image = io.BytesIO()
|
||||
matplotlib.pyplot.imsave(response_image, spatial[library_id]["images"][resolution])
|
||||
response_image.seek(0)
|
||||
|
||||
try:
|
||||
return send_file(response_image, attachment_filename=f"{library_id}-{resolution}.png", mimetype="image/png")
|
||||
except (KeyError, DatasetAccessError) as e:
|
||||
return abort_and_log(HTTPStatus.BAD_REQUEST, str(e), include_exc_info=True)
|
||||
except PrepareError:
|
||||
return abort_and_log(
|
||||
HTTPStatus.NOT_IMPLEMENTED,
|
||||
f"No spatial image available {request.path}",
|
||||
loglevel=logging.ERROR,
|
||||
include_exc_info=True,
|
||||
)
|
||||
|
||||
@@ -274,6 +274,9 @@ class AnndataAdaptor(DataAdaptor):
|
||||
df = df[fields]
|
||||
return encode_matrix_fbs(df, col_idx=df.columns)
|
||||
|
||||
def get_spatial(self):
|
||||
return self.data.uns["spatial"]
|
||||
|
||||
def get_embedding_names(self):
|
||||
"""
|
||||
Return pre-computed embeddings.
|
||||
|
||||
@@ -14,6 +14,7 @@ flatten-dict>=0.2.0
|
||||
fsspec>=0.4.4,<0.8.0
|
||||
gunicorn>=20.0.4
|
||||
h5py>=3.0.0
|
||||
matplotlib>=3.5.0
|
||||
numba>=0.51.2
|
||||
numpy>=1.17.5
|
||||
packaging>=20.0
|
||||
|
||||
Reference in New Issue
Block a user