diff --git a/docs/docs/how-tos/persistence_postgres.ipynb b/docs/docs/how-tos/persistence_postgres.ipynb index cb0057d20..a5ce05a2a 100644 --- a/docs/docs/how-tos/persistence_postgres.ipynb +++ b/docs/docs/how-tos/persistence_postgres.ipynb @@ -156,6 +156,29 @@ "Async connections allow non-blocking database operations. This means other parts of your application can continue running while waiting for database operations to complete. It's particularly useful in high-concurrency scenarios or when dealing with I/O-bound operations." ] }, + { + "cell_type": "code", + "execution_count": null, + "id": "2d8d6c9a", + "metadata": {}, + "outputs": [], + "source": [ + "DB_URI = \"postgresql://postgres:postgres@localhost:5442/postgres?sslmode=disable\"" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "id": "351b4251", + "metadata": {}, + "outputs": [], + "source": [ + "connection_kwargs = {\n", + " \"autocommit\": True,\n", + " \"prepare_threshold\": 0,\n", + "}" + ] + }, { "cell_type": "markdown", "id": "8e1dd27d", @@ -244,11 +267,14 @@ "import contextlib\n", "\n", "from starlette.applications import Starlette\n", + "from starlette.requests import Request\n", + "from starlette.responses import Response\n", + "from starlette.routing import Route\n", + "from psycopg_pool import AsyncConnectionPool\n", + "from langgraph.checkpoint.postgres.aio import AsyncPostgresSaver\n", "\n", - "checkpointer = None\n", "@contextlib.asynccontextmanager\n", "async def lifespan(app):\n", - " global checkpointer\n", " async with AsyncConnectionPool(\n", " # Example configuration\n", " conninfo=DB_URI,\n", @@ -259,34 +285,25 @@ "\n", " # NOTE: you need to call .setup() the first time you're using your checkpointer\n", " await checkpointer.setup()\n", - " yield\n", + " yield {\"checkpointer\": checkpointer}\n", "\n", "\n", "graph = create_react_agent(model, tools=tools, checkpointer=checkpointer)\n", "\n", - "async def my_route(request):\n", + "async def my_route(request: Request):\n", + " checkpointer = request.state.checkpointer\n", " agent = graph.copy({\"checkpointer\": checkpointer})\n", " await agent.ainvoke(request)\n", " return Response(...)\n", "\n", "routes = [\n", - " ...\n", + " Route(\"/\", my_route),\n", "]\n", "\n", "app = Starlette(routes=routes, lifespan=lifespan)\n", "```" ] }, - { - "cell_type": "code", - "execution_count": null, - "id": "876c5e02", - "metadata": {}, - "outputs": [], - "source": [ - "https://www.starlette.io/lifespan/" - ] - }, { "cell_type": "markdown", "id": "6e53287e", @@ -394,29 +411,6 @@ "Synchronous connections execute operations in a blocking manner, meaning each operation waits for completion before moving to the next one. The `DB_URI` is the database connection URI, with the protocol used for connecting to a PostgreSQL database, authentication, and host where database is running. The connection_kwargs dictionary defines additional parameters for the database connection." ] }, - { - "cell_type": "code", - "execution_count": 2, - "id": "2b9d13b1-9d72-48a0-b63a-adc062c06c29", - "metadata": {}, - "outputs": [], - "source": [ - "DB_URI = \"postgresql://postgres:postgres@localhost:5442/postgres?sslmode=disable\"" - ] - }, - { - "cell_type": "code", - "execution_count": 3, - "id": "3fe36f67-073a-4fd7-a8f8-da196dd46a0d", - "metadata": {}, - "outputs": [], - "source": [ - "connection_kwargs = {\n", - " \"autocommit\": True,\n", - " \"prepare_threshold\": 0,\n", - "}" - ] - }, { "cell_type": "markdown", "id": "e39fc712-9e1c-4831-9077-dd07b0c13594",