Renamed Resource to View, and allow custom root links

This commit is contained in:
Joel Collins 2020-01-14 11:41:56 +00:00
parent 234ebc1cbb
commit a329b9197b
18 changed files with 90 additions and 67 deletions

View file

@ -79,16 +79,20 @@ for extension in find_extensions(USER_EXTENSIONS_PATH):
# Attach captures resources # Attach captures resources
labthing.add_view(views.CaptureList, f"/captures") labthing.add_view(views.CaptureList, f"/captures")
labthing.add_view(views.CaptureResource, f"/captures/<id>") labthing.add_root_link(views.CaptureList, "captures")
labthing.add_view(views.CaptureView, f"/captures/<id>")
labthing.add_view(views.CaptureDownload, f"/captures/<id>/download/<filename>") labthing.add_view(views.CaptureDownload, f"/captures/<id>/download/<filename>")
labthing.add_view(views.CaptureTags, f"/captures/<id>/tags") labthing.add_view(views.CaptureTags, f"/captures/<id>/tags")
labthing.add_view(views.CaptureMetadata, f"/captures/<id>/metadata") labthing.add_view(views.CaptureMetadata, f"/captures/<id>/metadata")
# Attach settings and status resources # Attach settings and status resources
labthing.add_view(views.SettingsProperty, f"/settings") labthing.add_view(views.SettingsProperty, f"/settings")
labthing.add_root_link(views.SettingsProperty, "settings")
labthing.add_view(views.NestedSettingsProperty, "/settings/<path:route>") labthing.add_view(views.NestedSettingsProperty, "/settings/<path:route>")
labthing.add_view(views.StatusProperty, "/status") labthing.add_view(views.StatusProperty, "/status")
labthing.add_view(views.NestedStatusProperty, "/status/<path:route>") labthing.add_view(views.NestedStatusProperty, "/status/<path:route>")
labthing.add_root_link(views.StatusProperty, "status")
# Attach streams resources # Attach streams resources
labthing.add_view(views.MjpegStream, f"/streams/mjpeg") labthing.add_view(views.MjpegStream, f"/streams/mjpeg")

View file

@ -1,6 +1,6 @@
from openflexure_microscope.common.flask_labthings.find import find_component from openflexure_microscope.common.flask_labthings.find import find_component
from openflexure_microscope.common.flask_labthings.extensions import BaseExtension from openflexure_microscope.common.flask_labthings.extensions import BaseExtension
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.decorators import ( from openflexure_microscope.common.flask_labthings.decorators import (
ThingAction, ThingAction,
ThingProperty, ThingProperty,
@ -292,7 +292,7 @@ def fast_up_down_up_autofocus(
return m.data_dict() return m.data_dict()
class MeasureSharpnessAPI(Resource): class MeasureSharpnessAPI(View):
def post(self): def post(self):
microscope = find_component("org.openflexure.microscope") microscope = find_component("org.openflexure.microscope")
@ -303,7 +303,7 @@ class MeasureSharpnessAPI(Resource):
@ThingAction @ThingAction
class AutofocusAPI(Resource): class AutofocusAPI(View):
""" """
Run a standard autofocus Run a standard autofocus
""" """
@ -330,7 +330,7 @@ class AutofocusAPI(Resource):
@ThingAction @ThingAction
class FastAutofocusAPI(Resource): class FastAutofocusAPI(View):
""" """
Run a fast autofocus Run a fast autofocus
""" """

View file

@ -19,7 +19,7 @@ from openflexure_microscope.common.flask_labthings import fields
from openflexure_microscope.devel import taskify, abort, update_task_progress from openflexure_microscope.devel import taskify, abort, update_task_progress
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
import time import time
@ -341,7 +341,7 @@ def stack(
@ThingAction @ThingAction
class TileScanAPI(Resource): class TileScanAPI(View):
@use_args( @use_args(
{ {
"filename": fields.String(), "filename": fields.String(),

View file

@ -15,7 +15,7 @@ import tempfile
import logging import logging
from openflexure_microscope.common.flask_labthings.find import find_component from openflexure_microscope.common.flask_labthings.find import find_component
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.extensions import BaseExtension from openflexure_microscope.common.flask_labthings.extensions import BaseExtension
from openflexure_microscope.common.flask_labthings.decorators import ( from openflexure_microscope.common.flask_labthings.decorators import (
ThingAction, ThingAction,
@ -96,7 +96,7 @@ default_zip_manager = ZipManager()
@ThingAction @ThingAction
class ZipBuilderAPIView(Resource): class ZipBuilderAPIView(View):
def post(self): def post(self):
ids = list(JsonResponse(request).json) ids = list(JsonResponse(request).json)
@ -109,12 +109,12 @@ class ZipBuilderAPIView(Resource):
@ThingProperty @ThingProperty
class ZipListAPIView(Resource): class ZipListAPIView(View):
def get(self): def get(self):
return jsonify(default_zip_manager.session_zips) return jsonify(default_zip_manager.session_zips)
class ZipGetterAPIView(Resource): class ZipGetterAPIView(View):
def get(self, session_id): def get(self, session_id):
if not session_id in default_zip_manager.session_zips: if not session_id in default_zip_manager.session_zips:
return abort(404) # 404 Not Found return abort(404) # 404 Not Found

View file

@ -1,4 +1,4 @@
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.extensions import BaseExtension from openflexure_microscope.common.flask_labthings.extensions import BaseExtension
from openflexure_microscope.common.flask_labthings.decorators import ( from openflexure_microscope.common.flask_labthings.decorators import (
ThingAction, ThingAction,
@ -77,7 +77,7 @@ static_form = {
@ThingProperty @ThingProperty
class TestAPIView(Resource): class TestAPIView(View):
def get(self): def get(self):
global val_int global val_int
val_int += 1 val_int += 1
@ -85,7 +85,7 @@ class TestAPIView(Resource):
@ThingAction @ThingAction
class TestDoAPIView(Resource): class TestDoAPIView(View):
def post(self): def post(self):
global val_int global val_int
val_int += 1 val_int += 1

View file

@ -1,5 +1,5 @@
from openflexure_microscope.api.utilities import get_bool, JsonResponse from openflexure_microscope.api.utilities import get_bool, JsonResponse
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.find import find_component from openflexure_microscope.common.flask_labthings.find import find_component
from openflexure_microscope.common.flask_labthings.decorators import ( from openflexure_microscope.common.flask_labthings.decorators import (
use_args, use_args,
@ -20,7 +20,7 @@ from flask import jsonify, request, abort, url_for, redirect, send_file
@ThingAction @ThingAction
class CaptureAPI(Resource): class CaptureAPI(View):
""" """
Create a new image capture. Create a new image capture.
""" """
@ -86,7 +86,7 @@ class CaptureAPI(Resource):
@ThingAction @ThingAction
class GPUPreviewStartAPI(Resource): class GPUPreviewStartAPI(View):
""" """
Start the onboard GPU preview. Start the onboard GPU preview.
Optional "window" parameter can be passed to control the position and size of the preview window, Optional "window" parameter can be passed to control the position and size of the preview window,
@ -119,7 +119,7 @@ class GPUPreviewStartAPI(Resource):
@ThingAction @ThingAction
class GPUPreviewStopAPI(Resource): class GPUPreviewStopAPI(View):
def post(self): def post(self):
""" """
Stop the onboard GPU preview. Stop the onboard GPU preview.

View file

@ -1,5 +1,5 @@
from openflexure_microscope.api.utilities import JsonResponse from openflexure_microscope.api.utilities import JsonResponse
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.find import find_component from openflexure_microscope.common.flask_labthings.find import find_component
from openflexure_microscope.common.flask_labthings.decorators import ( from openflexure_microscope.common.flask_labthings.decorators import (
use_args, use_args,
@ -17,7 +17,7 @@ import logging
@ThingAction @ThingAction
class MoveStageAPI(Resource): class MoveStageAPI(View):
@use_args( @use_args(
{ {
"absolute": fields.Boolean( "absolute": fields.Boolean(
@ -62,7 +62,7 @@ class MoveStageAPI(Resource):
@ThingAction @ThingAction
class ZeroStageAPI(Resource): class ZeroStageAPI(View):
def post(self): def post(self):
""" """
Zero the stage coordinates. Zero the stage coordinates.

View file

@ -1,4 +1,4 @@
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
import subprocess import subprocess
import os import os
from sys import platform from sys import platform
@ -18,7 +18,7 @@ def is_raspberrypi(raise_on_errors=False):
@ThingAction @ThingAction
class ShutdownAPI(Resource): class ShutdownAPI(View):
""" """
Attempt to shutdown the device Attempt to shutdown the device
""" """
@ -34,7 +34,7 @@ class ShutdownAPI(Resource):
@ThingAction @ThingAction
class RebootAPI(Resource): class RebootAPI(View):
""" """
Attempt to reboot the device Attempt to reboot the device
""" """

View file

@ -5,7 +5,7 @@ from openflexure_microscope.api.utilities import get_bool, JsonResponse
from openflexure_microscope.common.flask_labthings.schema import Schema from openflexure_microscope.common.flask_labthings.schema import Schema
from openflexure_microscope.common.flask_labthings import fields from openflexure_microscope.common.flask_labthings import fields
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.utilities import ( from openflexure_microscope.common.flask_labthings.utilities import (
description_from_view, description_from_view,
) )
@ -32,9 +32,9 @@ class CaptureSchema(Schema):
def generate_links(self, data, **kwargs): def generate_links(self, data, **kwargs):
data.links = { data.links = {
"self": { "self": {
"href": url_for(CaptureResource.endpoint, id=data.id, _external=True), "href": url_for(CaptureView.endpoint, id=data.id, _external=True),
"mimetype": "application/json", "mimetype": "application/json",
**description_from_view(CaptureResource), **description_from_view(CaptureView),
}, },
"tags": { "tags": {
"href": url_for(CaptureTags.endpoint, id=data.id, _external=True), "href": url_for(CaptureTags.endpoint, id=data.id, _external=True),
@ -66,7 +66,7 @@ capture_list_schema = CaptureSchema(many=True)
@ThingProperty @ThingProperty
@Tag("captures") @Tag("captures")
class CaptureList(Resource): class CaptureList(View):
@marshal_with(CaptureSchema(many=True)) @marshal_with(CaptureSchema(many=True))
def get(self): def get(self):
""" """
@ -78,7 +78,7 @@ class CaptureList(Resource):
@Tag("captures") @Tag("captures")
class CaptureResource(Resource): class CaptureView(View):
@marshal_with(CaptureSchema()) @marshal_with(CaptureSchema())
def get(self, id): def get(self, id):
""" """
@ -108,7 +108,7 @@ class CaptureResource(Resource):
@Tag("captures") @Tag("captures")
class CaptureDownload(Resource): class CaptureDownload(View):
@doc_response(200, mimetype="image/jpeg") @doc_response(200, mimetype="image/jpeg")
def get(self, id, filename): def get(self, id, filename):
""" """
@ -144,7 +144,7 @@ class CaptureDownload(Resource):
@Tag("captures") @Tag("captures")
class CaptureTags(Resource): class CaptureTags(View):
def get(self, id): def get(self, id):
""" """
Get tags associated with a single image capture Get tags associated with a single image capture
@ -199,7 +199,7 @@ class CaptureTags(Resource):
@Tag("captures") @Tag("captures")
class CaptureMetadata(Resource): class CaptureMetadata(View):
def get(self, id): def get(self, id):
""" """
Get metadata associated with a single image capture Get metadata associated with a single image capture

View file

@ -7,7 +7,7 @@ from openflexure_microscope.common.labthings_core.utilities import (
) )
from openflexure_microscope.common.flask_labthings.find import find_component from openflexure_microscope.common.flask_labthings.find import find_component
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.decorators import ThingProperty, Tag, doc_response from openflexure_microscope.common.flask_labthings.decorators import ThingProperty, Tag, doc_response
@ -16,7 +16,7 @@ import logging
@ThingProperty @ThingProperty
class SettingsProperty(Resource): class SettingsProperty(View):
def get(self): def get(self):
""" """
Current microscope settings, including camera and stage Current microscope settings, including camera and stage
@ -41,7 +41,7 @@ class SettingsProperty(Resource):
@Tag("properties") @Tag("properties")
class NestedSettingsProperty(Resource): class NestedSettingsProperty(View):
@doc_response(404, description="Settings key cannot be found") @doc_response(404, description="Settings key cannot be found")
def get(self, route): def get(self, route):
""" """
@ -76,7 +76,7 @@ class NestedSettingsProperty(Resource):
@ThingProperty @ThingProperty
class StatusProperty(Resource): class StatusProperty(View):
def get(self): def get(self):
""" """
Show current read-only state of the microscope Show current read-only state of the microscope
@ -86,7 +86,7 @@ class StatusProperty(Resource):
@Tag("properties") @Tag("properties")
class NestedStatusProperty(Resource): class NestedStatusProperty(View):
@doc_response(404, description="Status key cannot be found") @doc_response(404, description="Status key cannot be found")
def get(self, route): def get(self, route):
""" """

View file

@ -7,14 +7,14 @@ from openflexure_microscope.common.labthings_core.utilities import (
) )
from openflexure_microscope.common.flask_labthings.find import find_component from openflexure_microscope.common.flask_labthings.find import find_component
from openflexure_microscope.common.flask_labthings.resource import Resource from openflexure_microscope.common.flask_labthings.view import View
from openflexure_microscope.common.flask_labthings.decorators import doc_response, ThingProperty from openflexure_microscope.common.flask_labthings.decorators import doc_response, ThingProperty
from flask import Response from flask import Response
@ThingProperty @ThingProperty
class MjpegStream(Resource): class MjpegStream(View):
""" """
Real-time MJPEG stream from the microscope camera Real-time MJPEG stream from the microscope camera
""" """
@ -34,7 +34,7 @@ class MjpegStream(Resource):
@ThingProperty @ThingProperty
class SnapshotStream(Resource): class SnapshotStream(View):
""" """
Single JPEG snapshot from the camera stream Single JPEG snapshot from the camera stream
""" """

View file

@ -10,8 +10,8 @@ from .spec import rule2path, get_spec
from .decorators import tag from .decorators import tag
from .views.extensions import ExtensionList from .views.extensions import ExtensionList
from .views.tasks import TaskList, TaskResource from .views.tasks import TaskList, TaskView
from .views.docs import docs_blueprint, SwaggerUIResource, W3CThingDescriptionResource from .views.docs import docs_blueprint, SwaggerUIView, W3CThingDescriptionView
from openflexure_microscope.common.labthings_core.utilities import get_docstring from openflexure_microscope.common.labthings_core.utilities import get_docstring
@ -37,6 +37,8 @@ class LabThing(object):
self.properties = {} self.properties = {}
self.actions = {} self.actions = {}
self.custom_root_links = {}
self.endpoints = set() self.endpoints = set()
self.url_prefix = prefix self.url_prefix = prefix
@ -114,7 +116,7 @@ class LabThing(object):
self.add_view(ExtensionList, "/extensions", endpoint=EXTENSION_LIST_ENDPOINT) self.add_view(ExtensionList, "/extensions", endpoint=EXTENSION_LIST_ENDPOINT)
# Add task routes # Add task routes
self.add_view(TaskList, "/tasks", endpoint=TASK_LIST_ENDPOINT) self.add_view(TaskList, "/tasks", endpoint=TASK_LIST_ENDPOINT)
self.add_view(TaskResource, "/tasks/<id>", endpoint=TASK_ENDPOINT) self.add_view(TaskView, "/tasks/<id>", endpoint=TASK_ENDPOINT)
### Device stuff ### Device stuff
@ -234,15 +236,18 @@ class LabThing(object):
### Utilities ### Utilities
def url_for(self, resource, **values): def url_for(self, view, **values):
"""Generates a URL to the given resource. """Generates a URL to the given resource.
Works like :func:`flask.url_for`.""" Works like :func:`flask.url_for`."""
endpoint = resource.endpoint endpoint = view.endpoint
return url_for(endpoint, **values) return url_for(endpoint, **values)
def owns_endpoint(self, endpoint): def owns_endpoint(self, endpoint):
return endpoint in self.endpoints return endpoint in self.endpoints
def add_root_link(self, view, title, kwargs={}):
self.custom_root_links[title] = (view, kwargs)
### Description ### Description
def rootrep(self): def rootrep(self):
""" """
@ -257,11 +262,11 @@ class LabThing(object):
"links": { "links": {
"thingDescription": { "thingDescription": {
"href": url_for("labthings_docs.w3c_td", _external=True), "href": url_for("labthings_docs.w3c_td", _external=True),
"description": get_docstring(W3CThingDescriptionResource), "description": get_docstring(W3CThingDescriptionView),
}, },
"swaggerUI": { "swaggerUI": {
"href": url_for("labthings_docs.swagger_ui", _external=True), "href": url_for("labthings_docs.swagger_ui", _external=True),
**description_from_view(SwaggerUIResource), **description_from_view(SwaggerUIView),
}, },
"extensions": { "extensions": {
"href": self.url_for(ExtensionList, _external=True), "href": self.url_for(ExtensionList, _external=True),
@ -274,4 +279,10 @@ class LabThing(object):
}, },
} }
for title, (view, kwargs) in self.custom_root_links.items():
rr["links"][title] = {
"href": self.url_for(view, **kwargs, _external=True),
**description_from_view(view),
}
return jsonify(rr) return jsonify(rr)

View file

@ -1,4 +1,4 @@
from ..resource import Resource from ..view import View
from apispec import APISpec from apispec import APISpec
from apispec.ext.marshmallow import MarshmallowPlugin from apispec.ext.marshmallow import MarshmallowPlugin
@ -29,7 +29,7 @@ def get_spec(obj):
return obj.__apispec__ return obj.__apispec__
def rule2path(rule: Rule, view: Resource, spec: APISpec): def rule2path(rule: Rule, view: View, spec: APISpec):
params = { params = {
"path": rule_to_path(rule), "path": rule_to_path(rule),
"operations": view2operations(view, spec), "operations": view2operations(view, spec),
@ -52,7 +52,7 @@ def rule2path(rule: Rule, view: Resource, spec: APISpec):
return params return params
def view2operations(view: Resource, spec: APISpec): def view2operations(view: View, spec: APISpec):
# Operations inherit tags from parent # Operations inherit tags from parent
inherited_tags = [] inherited_tags = []
if hasattr(view, "__apispec__"): if hasattr(view, "__apispec__"):
@ -60,7 +60,7 @@ def view2operations(view: Resource, spec: APISpec):
# Build dictionary of operations (HTTP methods) # Build dictionary of operations (HTTP methods)
ops = {} ops = {}
for method in Resource.methods: for method in View.methods:
if hasattr(view, method): if hasattr(view, method):
ops[method] = {} ops[method] = {}

View file

@ -2,15 +2,23 @@ from openflexure_microscope.common.labthings_core.utilities import (
get_docstring, get_docstring,
get_summary, get_summary,
) )
from .view import View
from flask import current_app from flask import current_app
def description_from_view(view_class): def description_from_view(view_class):
summary = get_summary(view_class)
methods = [] methods = []
for method_key in ["get", "post", "put", "delete"]: for method_key in View.methods:
if hasattr(view_class, method_key): if hasattr(view_class, method_key):
methods.append(method_key.upper()) methods.append(method_key.upper())
summary = get_summary(view_class)
# If no class summary was given, try using summaries from method functions
if not summary:
summary = get_summary(getattr(view_class, method_key))
d = {"methods": methods, "description": summary} d = {"methods": methods, "description": summary}

View file

@ -1,7 +1,7 @@
from flask.views import MethodView from flask.views import MethodView
class Resource(MethodView): class View(MethodView):
""" """
A LabThing Resource class should make use of functions get(), put(), post(), and delete() A LabThing Resource class should make use of functions get(), put(), post(), and delete()
corresponding to HTTP methods. corresponding to HTTP methods.
@ -20,7 +20,7 @@ class Resource(MethodView):
if hasattr(self, "__apispec__"): if hasattr(self, "__apispec__"):
docs.update(self.__apispec__) docs.update(self.__apispec__)
for meth in BaseResource.methods: for meth in View.methods:
if hasattr(self, meth) and hasattr(getattr(self, meth), "__apispec__"): if hasattr(self, meth) and hasattr(getattr(self, meth), "__apispec__"):
docs["operations"][meth] = {} docs["operations"][meth] = {}
docs["operations"][meth] = getattr(self, meth).__apispec__ docs["operations"][meth] = getattr(self, meth).__apispec__

View file

@ -2,14 +2,14 @@ from flask import abort, url_for, jsonify, render_template, Blueprint, current_a
from openflexure_microscope.common.labthings_core.utilities import get_docstring from openflexure_microscope.common.labthings_core.utilities import get_docstring
from ...resource import Resource from ...view import View
from ...find import current_labthing from ...find import current_labthing
from ...spec import rule_to_path, rule_to_params from ...spec import rule_to_path, rule_to_params
import os import os
class APISpecResource(Resource): class APISpecView(View):
""" """
OpenAPI v3 documentation OpenAPI v3 documentation
""" """
@ -21,7 +21,7 @@ class APISpecResource(Resource):
return jsonify(current_labthing().spec.to_dict()) return jsonify(current_labthing().spec.to_dict())
class SwaggerUIResource(Resource): class SwaggerUIView(View):
""" """
Swagger UI documentation Swagger UI documentation
""" """
@ -30,7 +30,7 @@ class SwaggerUIResource(Resource):
return render_template("swagger-ui.html") return render_template("swagger-ui.html")
class W3CThingDescriptionResource(Resource): class W3CThingDescriptionView(View):
""" """
W3C-style Thing Description W3C-style Thing Description
""" """
@ -103,11 +103,11 @@ docs_blueprint = Blueprint(
) )
docs_blueprint.add_url_rule( docs_blueprint.add_url_rule(
"/swagger", view_func=APISpecResource.as_view("swagger_json") "/swagger", view_func=APISpecView.as_view("swagger_json")
) )
docs_blueprint.add_url_rule( docs_blueprint.add_url_rule(
"/swagger-ui", view_func=SwaggerUIResource.as_view("swagger_ui") "/swagger-ui", view_func=SwaggerUIView.as_view("swagger_ui")
) )
docs_blueprint.add_url_rule( docs_blueprint.add_url_rule(
"/td", view_func=W3CThingDescriptionResource.as_view("w3c_td") "/td", view_func=W3CThingDescriptionView.as_view("w3c_td")
) )

View file

@ -1,14 +1,14 @@
""" """
Top-level representation of attached and enabled Extensions Top-level representation of attached and enabled Extensions
""" """
from ..resource import Resource from ..view import View
from ..find import registered_extensions from ..find import registered_extensions
from ..schema import ExtensionSchema from ..schema import ExtensionSchema
from ..decorators import marshal_with, ThingProperty from ..decorators import marshal_with, ThingProperty
@ThingProperty @ThingProperty
class ExtensionList(Resource): class ExtensionList(View):
""" """
List and basic documentation for all enabled Extensions List and basic documentation for all enabled Extensions
""" """

View file

@ -1,7 +1,7 @@
from flask import abort, url_for from flask import abort, url_for
from ..decorators import marshal_with, ThingProperty, Tag from ..decorators import marshal_with, ThingProperty, Tag
from ..resource import Resource from ..view import View
from ..schema import TaskSchema from ..schema import TaskSchema
from openflexure_microscope.common.labthings_core import tasks from openflexure_microscope.common.labthings_core import tasks
@ -9,7 +9,7 @@ from openflexure_microscope.common.labthings_core import tasks
@ThingProperty @ThingProperty
@Tag("tasks") @Tag("tasks")
class TaskList(Resource): class TaskList(View):
@marshal_with(TaskSchema(many=True)) @marshal_with(TaskSchema(many=True))
def get(self): def get(self):
""" """
@ -19,7 +19,7 @@ class TaskList(Resource):
@Tag(["properties", "tasks"]) @Tag(["properties", "tasks"])
class TaskResource(Resource): class TaskView(View):
@marshal_with(TaskSchema()) @marshal_with(TaskSchema())
def get(self, id): def get(self, id):
""" """