A Reference Stack for Typed GraphQL from SQLAlchemy to React Hooks
Demo project to demonstrate how an asyncio Python project with SQLAlchemy and Strawberry can have a great typed DX on the frontend via codegen and TypeScript React hooks.
At a glance
- What is it?
- This demo project ties asyncio SQLAlchemy, Strawberry GraphQL, and codegen-generated urql hooks into one typed pipeline. It is a reference, not a library, and its value depends on how closely your stack matches its choices.
- Who is it for?
- Adopt this stack if you run an asyncio Python backend with SQLAlchemy, want GraphQL as the API layer, and are willing to commit to a TypeScript React frontend that uses urql. Do not adopt it if you need sync SQLAlchemy, prefer REST, or cannot tolerate the codegen watch process in your dev loop.
- Can I use it commercially?
- Not without permission. GitHub finds no licence file in the repository, and without a licence all rights are reserved by default: you may read the code but not reuse it. Check the README, or ask the authors, before using it.
- Is it still maintained?
- Probably not. The repository last received commits 59 months ago, on December 4, 2021.
- What is it written in?
- Mainly TypeScript, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on October 22, 2026, and from our analysis. They are not legal advice.
Star history
- jokull/python-ts-graphql-demo100 ★ · +0
| Repository | 2026-08-18 | 2026-10-22 |
|---|---|---|
| jokull/python-ts-graphql-demo | 100 | 100 |
0 Stars in the last 65 days, measured from the daily GitHub snapshot. Compare with other projects
Editorial analysis
What This Demo Actually Solves
The README positions this as a template for a modern Python web stack, but the concrete problem it addresses is data consistency across a language boundary. When your backend is Python with SQLAlchemy and your frontend is TypeScript with React, the type systems drift. The backend knows a User has an id and an email. The frontend has to guess, or write its own interfaces, or rely on runtime errors. This project demonstrates a chain: asyncio SQLAlchemy models, Strawberry GraphQL schemas, GraphQL codegen, and urql TypeScript hooks. The goal is that a change in a SQLAlchemy model propagates through to the React component props with type errors appearing in VS Code before you hit save. It is a reference for engineers who want that pipeline, not a drop-in package. The README says it is a mini version of the Inch tech stack, so it carries real production experience, but it is still a demo with a narrow scope.
The Mechanism: From SQLAlchemy Model to Typed Hook
The data flow starts with SQLAlchemy models defined with type hints. Strawberry, a GraphQL library built on Python dataclasses, uses those type hints to build the schema. The schema is then monitored by GraphQL Code Generator, which runs in watch mode. That codegen produces urql hooks in TypeScript. urql is a React GraphQL client, and the generated hooks give you typed query and mutation functions. The README emphasizes the mypy connection: Pylance does not handle declarative type hinted SQLAlchemy models well, so the project disables Pylance's type checking and enables mypy with a plugin. The chain is not automatic. Each step requires configuration: the SQLAlchemy models must be written in a way Strawberry can read, the codegen config must know where the schema lives, and the frontend must import the generated hooks. The README shows the commands but not the config files, so the actual wiring is left to the reader to inspect in the repository.
Getting It Running: The Exact Commands
The README gives a five-step setup. First, install dependencies with poetry install and npm i. Second, drop and recreate all database tables by running poetry run python models.py. Third, start the Python GraphQL backend with poetry run uvicorn app:app --reload --host '::', which listens on port 8000. Fourth, run npm run codegen --watch to generate the TypeScript hooks, and the watch flag means it regenerates when the schema changes. Fifth, run npm run dev to start the Next.js frontend, which reverse proxies /graphql to the backend. The order matters: the backend must be running before codegen can fetch the schema, and codegen must be running before the frontend can use the hooks. The README also points to .vscode/settings.json for the editor setup, where you can see how mypy is enabled and Pylance's type checking is switched off. These commands are concrete, but they assume you have poetry, Node, and a database configured. The README does not mention which database or how to configure the connection, so that is a gap you must fill yourself.
A Real Limitation: Pylance Is Turned Off
The most honest limitation in the README is the VS Code setup. It says Pylance does not deal well with declarative type hinted SQLAlchemy models, so they switch off python.analysis.typeCheckingMode and enable mypy instead. That is a trade-off. You lose Pylance's fast, built-in type checking for all your Python code, not just the models. Mypy is slower, and it requires a plugin and type stubs to work. If you prefer Pylance's IntelliSense or if your team is not comfortable with mypy configuration, this stack will fight you. Another limitation is the reliance on codegen watch mode. If you forget to run it, or it crashes, your frontend types go stale and you get errors that are not real. The demo does not address error handling for that process. Also, the README does not mention authentication, authorization, or real-world concerns like pagination or file uploads. This is a demo of the typed pipeline, not a production guide.
The Alternative: Manual Types or a Different Client
The obvious alternative is to skip codegen and write your GraphQL types by hand. You can define TypeScript interfaces for every query and mutation, and use urql or Apollo directly. That approach gives you full control but loses the consistency guarantee. When the backend schema changes, you must remember to update the interfaces. Another alternative is to use a different codegen tool or a different GraphQL client. The README specifically uses GraphQL Code Generator and urql, but Apollo has its own codegen, and there are other clients like Relay. The difference in approach is the degree of automation. This project pushes the automation to the extreme: the schema is the single source of truth, and the generated hooks are meant to be used without manual edits. A hand-typed approach treats the schema as documentation, not as a contract that is enforced. If you have a small schema, hand-typing might be simpler. If you have a large schema that changes often, this automated pipeline saves time but adds a build step.
Maintenance and Upgrade Cost
The README does not mention versions for any dependency, so the maintenance cost is not documented. But you can infer it from the architecture. You have three moving parts: SQLAlchemy, Strawberry, and GraphQL Code Generator. Each releases new versions, and the integration points are where breakage happens. SQLAlchemy's asyncio extension is relatively new, and Strawberry is new-ish, as the README says. That means the APIs may change. The codegen tool also changes its configuration format over time. The project has no license listed, which is a concern if you plan to copy it into a commercial product. You cannot assume you have the right to use the code without permission. The README is a template, so you are expected to adapt it, but without a license, the legal status is unclear. You should check the repository for a license file or contact the author before reusing the code. The upgrade cost is not zero: every dependency update could break the mypy plugin, the codegen config, or the Strawberry schema generation.
Who Should Use This Reference
This project is for a specific audience: a team already committed to asyncio SQLAlchemy, GraphQL, and React with TypeScript. If you are evaluating whether that stack works together, this demo gives you a working starting point. The README says the goal is a great typed developer experience, and the commands show how to achieve it. If you are not using asyncio, or you use a different ORM, or you prefer REST, this project has little to offer. The value is in the integration, not in any single component. The demo is small, so you can read the entire codebase in an afternoon. That is its strength. You can see how the models are defined, how the schema is built, and how the hooks are used. But you must verify that the patterns scale to your project. The README does not show a real application, only the plumbing. So use it as a proof of concept, not as a blueprint for a large system. The concrete next step is to clone the repo, run the commands, and see if the type errors appear as promised. If they do, you have a template. If they do not, you know the integration is more fragile than the README suggests.
Editorial conclusion
Adopt this stack if you run an asyncio Python backend with SQLAlchemy, want GraphQL as the API layer, and are willing to commit to a TypeScript React frontend that uses urql. Do not adopt it if you need sync SQLAlchemy, prefer REST, or cannot tolerate the codegen watch process in your dev loop. Before committing, verify that Strawberry supports your SQLAlchemy model patterns, that the mypy plugin catches the errors you care about, and that the generated hooks match your state management needs. The project is a demo, so treat its commands and settings as a starting point, not a production recipe.
Frequently asked questions
What is GraphQL used for in python-ts-graphql-demo?
It is the contract between the Python backend and the TypeScript frontend. Strawberry exposes a schema built from Python dataclasses, codegen watches schema.graphql and creates urql TypeScript hooks from it, and the stated goal is strong data consistency between the two sides.
Is GraphQL still relevant in 2026?
This project answers that question from 2021. The last push to main is dated 2021-12-04, and the pinned versions are Next 12, React 17.0.2, TypeScript 4.4.4, SQLAlchemy 1.4.26, Strawberry 0.85.1, and Python 3.9, so it demonstrates an approach rather than current practice.
How do I run the python-ts-graphql-demo project?
Run poetry install and npm i, then poetry run python models.py to drop and recreate all database tables, poetry run uvicorn app:app --reload --host '::' to serve the backend on port 8000, npm run codegen --watch to generate hooks, and npm run dev to start the frontend.
Which React hooks does codegen generate for python-ts-graphql-demo?
urql TypeScript hooks, produced by the typescript-urql plugin alongside the typescript and typescript-operations plugins, with the generated output written to graphql.ts. @shopify/react-form is also in the dependency list.
Why is python.analysis.typeCheckingMode switched off in python-ts-graphql-demo?
Pylance does not yet deal well with declarative type hinted SQLAlchemy models, so the settings file switches its type checking off and enables mypy instead, backed by SQLAlchemy type stubs and the sqlalchemy.ext.mypy.plugin.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/jokull-python-ts-graphql-demo)Star history chart for your README
[](https://hysenlabs.com/projects/jokull-python-ts-graphql-demo)