cd /news/developer-tools/model-your-business-once-for-humans-… · home topics developer-tools article
[ARTICLE · art-98016] src=klr-pattern.github.io ↗ pub= topic=developer-tools verified=true sentiment=↑ positive

Model your business once – for humans and AI alike

Nexusx, a new Python package, lets developers model business entities, relationships, and use cases once, then derives GraphQL, REST, MCP, CLI, and TypeScript SDK interfaces from that single typed model, aiming to reduce maintenance costs and make AI agents first-class consumers. The package uses SQLModel entities and typed DTOs, with MCP as a native protocol and GraphQL under the hood, and includes Voyager for live entity-relationship visualization. It is installable via `pip install nexusx`.

read4 min views1 publishedAug 15, 2026

Model your business entities, relationships, and use cases once — GraphQL, REST, MCP, CLI, and TS SDK all derive from it. Data is a graph; tools are just its projections.

pip install nexusx

The same typed business model serves AI agents and developers as first-class consumers.

MCP is a native protocol: strongly typed, GraphQL under the hood.

Write SQLModel entities and typed DTOs; that is the whole job.

LLMs generate code fast — but without structural constraints, the debt surfaces weeks later: duplicated logic, components bleeding into each other, debugging by guesswork. The industry calls it the cost of vibe coding.

nexusx narrows what AI writes to a declarative model — entities, relationships, and typed use-case methods. Structure is not something the AI has to get right; it is guaranteed by the model.

AI writes the model and use-case methods — not scattered glue code. Small diffs, reviewable by humans.

Change a business rule once; every protocol updates in sync. Maintenance cost does not multiply per delivery.

Typed contracts, plus Voyager: entities, relationships, use cases, and their dependencies rendered as one live ER view — grasp the whole project without reading code first, whether you are a new human or a fresh AI session. Voyager →

Semantic-level isomorphism — every protocol is generated from the same typed model, not wrapped around a copy of it.


@app.get("/sprints")
async def rest_list_sprints() -> list[SprintOut]:
    ...  # query + assembly, again

@strawberry.field
async def graphql_sprints(self) -> list[SprintType]:
    ...  # types + s, again

@mcp.tool()
async def sprints_for_agents() -> str:
    ...  # JSON dumping, again

class SprintService(UseCaseService):
    """Sprint planning operations."""

    @query
    async def list_sprints(cls) -> list[SprintSummary]:
        """List sprints with tasks, owners, and task count."""
        return await load_sprints()

Typed FastAPI route, visible in OpenAPI.

create_use_case_router(api)

Entities become by_id / by_filter roots for exploring connected data.

Sprint { by_filter(limit: 10) { ... } }

Use-case methods become typed fields via the compose schema.

compose_query(app, query, args)

Agents discover it progressively.

create_use_case_graphql_mcp_server([api])

Services become command groups.

list_sprints --select "name task_count"

Typed client generated from the compose schema.

sprintService.listSprints()

Two GraphQL surfaces for two different jobs — use either one, or both.

SQLModel entities and relationships become by_id / by_filter query roots. No relationship resolvers to write — Data batching keeps it N+1-proof as callers traverse.

GraphQLHandlerTyped business methods expose stable capabilities to web clients, integrations, and AI agents — served over REST, MCP, CLI, and SDK from one definition.

UseCaseServiceEntities are not API contracts. DefineSubset hides internal columns, auto-loads relationships, and computes derived fields.

async def get_sprints():
    sprints = await session.exec(select(Sprint))
    result = []
    for s in sprints:
        tasks = await session.exec(
            select(Task).where(Task.sprint_id == s.id))
        for t in tasks:
            t.owner = await session.get(User, t.owner_id)

python
from nexusx import DefineSubset, ErManager, build_dto_select

class UserDTO(DefineSubset):
    __subset__ = (User, ("id", "name"))

class TaskDTO(DefineSubset):
    __subset__ = (Task, ("id", "title", "owner_id"))
    owner: UserDTO | None = None   # auto-loaded

class SprintDTO(DefineSubset):
    __subset__ = (Sprint, ("id", "name"))
    tasks: list[TaskDTO] = []      # auto-loaded

er = ErManager(entities=[User, Sprint, Task], session_factory=async_session)
Resolver = er.create_resolver()

async def load_sprints() -> list[SprintDTO]:
    stmt = build_dto_select(SprintDTO)          # root columns only
    async with async_session() as session:
        rows = (await session.exec(stmt)).all()
    dtos = [SprintDTO(**dict(r._mapping)) for r in rows]
    return await Resolver().resolve(dtos)       # tree filled, batched

The same relationship model stretches into more advanced architectures.

Data batching, SQL column pruning, window-function pagination — and total_count computed only when the response asks for it.

post_* for aggregations, ExposeAs / SendTo for cross-layer data flow.

Ordinary Pydantic models as non-table graph roots — Redis, search, and SDK-backed data join the same graph.

Compose multiple nexusx data graphs without a central gateway — homogeneous federation of nexusx services.

ComposedErManager composes multiple engines in one process; DTO federation loads public DTO trees across services.

Independently packaged applications and databases, combined into a single MCP server.

The principles that shape every API decision.

One field selection shapes the GraphQL response, the SQL columns loaded, the DTO fields copied, the MCP output, CLI --select, and whether total_count is even computed.

Redis, search engines, other databases, external APIs — declare a Relationship with an async batch function and they join the same , DTO, GraphQL, and ER-diagram infrastructure.

Business methods depend on no protocol object — builders inspect the typed signature and attach REST / MCP / CLI / SDK adapters. FromContext injects trusted values (user, tenant) without exposing them as client arguments.

Install the 4-phase skill into your coding agent — Claude Code, Codex, Cursor, and more — then describe your app in plain words. The agent drives the workflow; you review the model.

npx skills add KLR-Pattern/nexusx -s nexusx-4phase -a claude-code

Confirm the domain model and persistence strategy with you before any code is written.

Entities and relationships, GraphQL helper surface, then UseCase REST / MCP / CLI deliveries.

Optionally emit a typed TypeScript SDK from the compose schema.

Works with your existing frameworks and tools.

Declare the model once — the data graph, response DTOs, and every delivery follow.

── more in #developer-tools 4 stories · sorted by recency
── more on @nexusx 3 stories trending now
sponsored brought to you by zahid.host 4,200+ EU-deployed projects
reading about agents? ship yours in a single git push.

Run your AI side-project on zahid.host

EU-based hosting, git-push deploys, automatic HTTPS, no cold starts. Free tier with a custom domain — perfect for shipping the agent you just read about.

$git push zahid main
Live at https://your-agent.zahid.host
Get free account → Pricing
from €0/mo · no card required
LIVE [news/model-your-business-…] indexed:0 read:4min 2026-08-15 ·