From 685cda89ff5d2448857d195d3f79a258bbe48c14 Mon Sep 17 00:00:00 2001 From: psychedelicious <4822129+psychedelicious@users.noreply.github.com> Date: Tue, 17 Oct 2023 14:28:39 +1100 Subject: [PATCH] feat(api): restore get_session route --- invokeai/app/api/routers/sessions.py | 456 +++++++++++++-------------- invokeai/app/api_app.py | 4 +- 2 files changed, 226 insertions(+), 234 deletions(-) diff --git a/invokeai/app/api/routers/sessions.py b/invokeai/app/api/routers/sessions.py index cd93a267ad..fb850d0b2b 100644 --- a/invokeai/app/api/routers/sessions.py +++ b/invokeai/app/api/routers/sessions.py @@ -1,57 +1,50 @@ # Copyright (c) 2022 Kyle Schouviller (https://github.com/kyle0654) -from typing import Annotated, Optional, Union -from fastapi import Body, HTTPException, Path, Query, Response +from fastapi import HTTPException, Path from fastapi.routing import APIRouter -from pydantic.fields import Field -from invokeai.app.services.shared.pagination import PaginatedResults - -# Importing * is bad karma but needed here for node detection -from ...invocations import * # noqa: F401 F403 -from ...invocations.baseinvocation import BaseInvocation -from ...services.shared.graph import Edge, EdgeConnection, Graph, GraphExecutionState, NodeAlreadyExecutedError +from ...services.shared.graph import GraphExecutionState from ..dependencies import ApiDependencies session_router = APIRouter(prefix="/v1/sessions", tags=["sessions"]) -@session_router.post( - "/", - operation_id="create_session", - responses={ - 200: {"model": GraphExecutionState}, - 400: {"description": "Invalid json"}, - }, - deprecated=True, -) -async def create_session( - queue_id: str = Query(default="", description="The id of the queue to associate the session with"), - graph: Optional[Graph] = Body(default=None, description="The graph to initialize the session with"), -) -> GraphExecutionState: - """Creates a new session, optionally initializing it with an invocation graph""" - session = ApiDependencies.invoker.create_execution_state(queue_id=queue_id, graph=graph) - return session +# @session_router.post( +# "/", +# operation_id="create_session", +# responses={ +# 200: {"model": GraphExecutionState}, +# 400: {"description": "Invalid json"}, +# }, +# deprecated=True, +# ) +# async def create_session( +# queue_id: str = Query(default="", description="The id of the queue to associate the session with"), +# graph: Optional[Graph] = Body(default=None, description="The graph to initialize the session with"), +# ) -> GraphExecutionState: +# """Creates a new session, optionally initializing it with an invocation graph""" +# session = ApiDependencies.invoker.create_execution_state(queue_id=queue_id, graph=graph) +# return session -@session_router.get( - "/", - operation_id="list_sessions", - responses={200: {"model": PaginatedResults[GraphExecutionState]}}, - deprecated=True, -) -async def list_sessions( - page: int = Query(default=0, description="The page of results to get"), - per_page: int = Query(default=10, description="The number of results per page"), - query: str = Query(default="", description="The query string to search for"), -) -> PaginatedResults[GraphExecutionState]: - """Gets a list of sessions, optionally searching""" - if query == "": - result = ApiDependencies.invoker.services.graph_execution_manager.list(page, per_page) - else: - result = ApiDependencies.invoker.services.graph_execution_manager.search(query, page, per_page) - return result +# @session_router.get( +# "/", +# operation_id="list_sessions", +# responses={200: {"model": PaginatedResults[GraphExecutionState]}}, +# deprecated=True, +# ) +# async def list_sessions( +# page: int = Query(default=0, description="The page of results to get"), +# per_page: int = Query(default=10, description="The number of results per page"), +# query: str = Query(default="", description="The query string to search for"), +# ) -> PaginatedResults[GraphExecutionState]: +# """Gets a list of sessions, optionally searching""" +# if query == "": +# result = ApiDependencies.invoker.services.graph_execution_manager.list(page, per_page) +# else: +# result = ApiDependencies.invoker.services.graph_execution_manager.search(query, page, per_page) +# return result @session_router.get( @@ -61,7 +54,6 @@ async def list_sessions( 200: {"model": GraphExecutionState}, 404: {"description": "Session not found"}, }, - deprecated=True, ) async def get_session( session_id: str = Path(description="The id of the session to get"), @@ -74,211 +66,211 @@ async def get_session( return session -@session_router.post( - "/{session_id}/nodes", - operation_id="add_node", - responses={ - 200: {"model": str}, - 400: {"description": "Invalid node or link"}, - 404: {"description": "Session not found"}, - }, - deprecated=True, -) -async def add_node( - session_id: str = Path(description="The id of the session"), - node: Annotated[Union[BaseInvocation.get_invocations()], Field(discriminator="type")] = Body( # type: ignore - description="The node to add" - ), -) -> str: - """Adds a node to the graph""" - session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) - if session is None: - raise HTTPException(status_code=404) +# @session_router.post( +# "/{session_id}/nodes", +# operation_id="add_node", +# responses={ +# 200: {"model": str}, +# 400: {"description": "Invalid node or link"}, +# 404: {"description": "Session not found"}, +# }, +# deprecated=True, +# ) +# async def add_node( +# session_id: str = Path(description="The id of the session"), +# node: Annotated[Union[BaseInvocation.get_invocations()], Field(discriminator="type")] = Body( # type: ignore +# description="The node to add" +# ), +# ) -> str: +# """Adds a node to the graph""" +# session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) +# if session is None: +# raise HTTPException(status_code=404) - try: - session.add_node(node) - ApiDependencies.invoker.services.graph_execution_manager.set( - session - ) # TODO: can this be done automatically, or add node through an API? - return session.id - except NodeAlreadyExecutedError: - raise HTTPException(status_code=400) - except IndexError: - raise HTTPException(status_code=400) +# try: +# session.add_node(node) +# ApiDependencies.invoker.services.graph_execution_manager.set( +# session +# ) # TODO: can this be done automatically, or add node through an API? +# return session.id +# except NodeAlreadyExecutedError: +# raise HTTPException(status_code=400) +# except IndexError: +# raise HTTPException(status_code=400) -@session_router.put( - "/{session_id}/nodes/{node_path}", - operation_id="update_node", - responses={ - 200: {"model": GraphExecutionState}, - 400: {"description": "Invalid node or link"}, - 404: {"description": "Session not found"}, - }, - deprecated=True, -) -async def update_node( - session_id: str = Path(description="The id of the session"), - node_path: str = Path(description="The path to the node in the graph"), - node: Annotated[Union[BaseInvocation.get_invocations()], Field(discriminator="type")] = Body( # type: ignore - description="The new node" - ), -) -> GraphExecutionState: - """Updates a node in the graph and removes all linked edges""" - session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) - if session is None: - raise HTTPException(status_code=404) +# @session_router.put( +# "/{session_id}/nodes/{node_path}", +# operation_id="update_node", +# responses={ +# 200: {"model": GraphExecutionState}, +# 400: {"description": "Invalid node or link"}, +# 404: {"description": "Session not found"}, +# }, +# deprecated=True, +# ) +# async def update_node( +# session_id: str = Path(description="The id of the session"), +# node_path: str = Path(description="The path to the node in the graph"), +# node: Annotated[Union[BaseInvocation.get_invocations()], Field(discriminator="type")] = Body( # type: ignore +# description="The new node" +# ), +# ) -> GraphExecutionState: +# """Updates a node in the graph and removes all linked edges""" +# session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) +# if session is None: +# raise HTTPException(status_code=404) - try: - session.update_node(node_path, node) - ApiDependencies.invoker.services.graph_execution_manager.set( - session - ) # TODO: can this be done automatically, or add node through an API? - return session - except NodeAlreadyExecutedError: - raise HTTPException(status_code=400) - except IndexError: - raise HTTPException(status_code=400) +# try: +# session.update_node(node_path, node) +# ApiDependencies.invoker.services.graph_execution_manager.set( +# session +# ) # TODO: can this be done automatically, or add node through an API? +# return session +# except NodeAlreadyExecutedError: +# raise HTTPException(status_code=400) +# except IndexError: +# raise HTTPException(status_code=400) -@session_router.delete( - "/{session_id}/nodes/{node_path}", - operation_id="delete_node", - responses={ - 200: {"model": GraphExecutionState}, - 400: {"description": "Invalid node or link"}, - 404: {"description": "Session not found"}, - }, - deprecated=True, -) -async def delete_node( - session_id: str = Path(description="The id of the session"), - node_path: str = Path(description="The path to the node to delete"), -) -> GraphExecutionState: - """Deletes a node in the graph and removes all linked edges""" - session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) - if session is None: - raise HTTPException(status_code=404) +# @session_router.delete( +# "/{session_id}/nodes/{node_path}", +# operation_id="delete_node", +# responses={ +# 200: {"model": GraphExecutionState}, +# 400: {"description": "Invalid node or link"}, +# 404: {"description": "Session not found"}, +# }, +# deprecated=True, +# ) +# async def delete_node( +# session_id: str = Path(description="The id of the session"), +# node_path: str = Path(description="The path to the node to delete"), +# ) -> GraphExecutionState: +# """Deletes a node in the graph and removes all linked edges""" +# session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) +# if session is None: +# raise HTTPException(status_code=404) - try: - session.delete_node(node_path) - ApiDependencies.invoker.services.graph_execution_manager.set( - session - ) # TODO: can this be done automatically, or add node through an API? - return session - except NodeAlreadyExecutedError: - raise HTTPException(status_code=400) - except IndexError: - raise HTTPException(status_code=400) +# try: +# session.delete_node(node_path) +# ApiDependencies.invoker.services.graph_execution_manager.set( +# session +# ) # TODO: can this be done automatically, or add node through an API? +# return session +# except NodeAlreadyExecutedError: +# raise HTTPException(status_code=400) +# except IndexError: +# raise HTTPException(status_code=400) -@session_router.post( - "/{session_id}/edges", - operation_id="add_edge", - responses={ - 200: {"model": GraphExecutionState}, - 400: {"description": "Invalid node or link"}, - 404: {"description": "Session not found"}, - }, - deprecated=True, -) -async def add_edge( - session_id: str = Path(description="The id of the session"), - edge: Edge = Body(description="The edge to add"), -) -> GraphExecutionState: - """Adds an edge to the graph""" - session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) - if session is None: - raise HTTPException(status_code=404) +# @session_router.post( +# "/{session_id}/edges", +# operation_id="add_edge", +# responses={ +# 200: {"model": GraphExecutionState}, +# 400: {"description": "Invalid node or link"}, +# 404: {"description": "Session not found"}, +# }, +# deprecated=True, +# ) +# async def add_edge( +# session_id: str = Path(description="The id of the session"), +# edge: Edge = Body(description="The edge to add"), +# ) -> GraphExecutionState: +# """Adds an edge to the graph""" +# session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) +# if session is None: +# raise HTTPException(status_code=404) - try: - session.add_edge(edge) - ApiDependencies.invoker.services.graph_execution_manager.set( - session - ) # TODO: can this be done automatically, or add node through an API? - return session - except NodeAlreadyExecutedError: - raise HTTPException(status_code=400) - except IndexError: - raise HTTPException(status_code=400) +# try: +# session.add_edge(edge) +# ApiDependencies.invoker.services.graph_execution_manager.set( +# session +# ) # TODO: can this be done automatically, or add node through an API? +# return session +# except NodeAlreadyExecutedError: +# raise HTTPException(status_code=400) +# except IndexError: +# raise HTTPException(status_code=400) -# TODO: the edge being in the path here is really ugly, find a better solution -@session_router.delete( - "/{session_id}/edges/{from_node_id}/{from_field}/{to_node_id}/{to_field}", - operation_id="delete_edge", - responses={ - 200: {"model": GraphExecutionState}, - 400: {"description": "Invalid node or link"}, - 404: {"description": "Session not found"}, - }, - deprecated=True, -) -async def delete_edge( - session_id: str = Path(description="The id of the session"), - from_node_id: str = Path(description="The id of the node the edge is coming from"), - from_field: str = Path(description="The field of the node the edge is coming from"), - to_node_id: str = Path(description="The id of the node the edge is going to"), - to_field: str = Path(description="The field of the node the edge is going to"), -) -> GraphExecutionState: - """Deletes an edge from the graph""" - session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) - if session is None: - raise HTTPException(status_code=404) +# # TODO: the edge being in the path here is really ugly, find a better solution +# @session_router.delete( +# "/{session_id}/edges/{from_node_id}/{from_field}/{to_node_id}/{to_field}", +# operation_id="delete_edge", +# responses={ +# 200: {"model": GraphExecutionState}, +# 400: {"description": "Invalid node or link"}, +# 404: {"description": "Session not found"}, +# }, +# deprecated=True, +# ) +# async def delete_edge( +# session_id: str = Path(description="The id of the session"), +# from_node_id: str = Path(description="The id of the node the edge is coming from"), +# from_field: str = Path(description="The field of the node the edge is coming from"), +# to_node_id: str = Path(description="The id of the node the edge is going to"), +# to_field: str = Path(description="The field of the node the edge is going to"), +# ) -> GraphExecutionState: +# """Deletes an edge from the graph""" +# session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) +# if session is None: +# raise HTTPException(status_code=404) - try: - edge = Edge( - source=EdgeConnection(node_id=from_node_id, field=from_field), - destination=EdgeConnection(node_id=to_node_id, field=to_field), - ) - session.delete_edge(edge) - ApiDependencies.invoker.services.graph_execution_manager.set( - session - ) # TODO: can this be done automatically, or add node through an API? - return session - except NodeAlreadyExecutedError: - raise HTTPException(status_code=400) - except IndexError: - raise HTTPException(status_code=400) +# try: +# edge = Edge( +# source=EdgeConnection(node_id=from_node_id, field=from_field), +# destination=EdgeConnection(node_id=to_node_id, field=to_field), +# ) +# session.delete_edge(edge) +# ApiDependencies.invoker.services.graph_execution_manager.set( +# session +# ) # TODO: can this be done automatically, or add node through an API? +# return session +# except NodeAlreadyExecutedError: +# raise HTTPException(status_code=400) +# except IndexError: +# raise HTTPException(status_code=400) -@session_router.put( - "/{session_id}/invoke", - operation_id="invoke_session", - responses={ - 200: {"model": None}, - 202: {"description": "The invocation is queued"}, - 400: {"description": "The session has no invocations ready to invoke"}, - 404: {"description": "Session not found"}, - }, - deprecated=True, -) -async def invoke_session( - queue_id: str = Query(description="The id of the queue to associate the session with"), - session_id: str = Path(description="The id of the session to invoke"), - all: bool = Query(default=False, description="Whether or not to invoke all remaining invocations"), -) -> Response: - """Invokes a session""" - session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) - if session is None: - raise HTTPException(status_code=404) +# @session_router.put( +# "/{session_id}/invoke", +# operation_id="invoke_session", +# responses={ +# 200: {"model": None}, +# 202: {"description": "The invocation is queued"}, +# 400: {"description": "The session has no invocations ready to invoke"}, +# 404: {"description": "Session not found"}, +# }, +# deprecated=True, +# ) +# async def invoke_session( +# queue_id: str = Query(description="The id of the queue to associate the session with"), +# session_id: str = Path(description="The id of the session to invoke"), +# all: bool = Query(default=False, description="Whether or not to invoke all remaining invocations"), +# ) -> Response: +# """Invokes a session""" +# session = ApiDependencies.invoker.services.graph_execution_manager.get(session_id) +# if session is None: +# raise HTTPException(status_code=404) - if session.is_complete(): - raise HTTPException(status_code=400) +# if session.is_complete(): +# raise HTTPException(status_code=400) - ApiDependencies.invoker.invoke(queue_id, session, invoke_all=all) - return Response(status_code=202) +# ApiDependencies.invoker.invoke(queue_id, session, invoke_all=all) +# return Response(status_code=202) -@session_router.delete( - "/{session_id}/invoke", - operation_id="cancel_session_invoke", - responses={202: {"description": "The invocation is canceled"}}, - deprecated=True, -) -async def cancel_session_invoke( - session_id: str = Path(description="The id of the session to cancel"), -) -> Response: - """Invokes a session""" - ApiDependencies.invoker.cancel(session_id) - return Response(status_code=202) +# @session_router.delete( +# "/{session_id}/invoke", +# operation_id="cancel_session_invoke", +# responses={202: {"description": "The invocation is canceled"}}, +# deprecated=True, +# ) +# async def cancel_session_invoke( +# session_id: str = Path(description="The id of the session to cancel"), +# ) -> Response: +# """Invokes a session""" +# ApiDependencies.invoker.cancel(session_id) +# return Response(status_code=202) diff --git a/invokeai/app/api_app.py b/invokeai/app/api_app.py index 5bbd8150c1..fa68d1b3e7 100644 --- a/invokeai/app/api_app.py +++ b/invokeai/app/api_app.py @@ -31,7 +31,7 @@ if True: # hack to make flake8 happy with imports coming after setting up the c from ..backend.util.logging import InvokeAILogger from .api.dependencies import ApiDependencies - from .api.routers import app_info, board_images, boards, images, models, session_queue, utilities + from .api.routers import app_info, board_images, boards, images, models, sessions, session_queue, utilities from .api.sockets import SocketIO from .invocations.baseinvocation import BaseInvocation, UIConfigBase, _InputField, _OutputField @@ -85,7 +85,7 @@ async def shutdown_event(): # Include all routers -# app.include_router(sessions.session_router, prefix="/api") +app.include_router(sessions.session_router, prefix="/api") app.include_router(utilities.utilities_router, prefix="/api")