From b8671635cd891068afee81fde05bed880124ec85 Mon Sep 17 00:00:00 2001 From: Christophe Besson Date: Mon, 5 Oct 2026 10:36:18 +0200 Subject: docs: generate an HTTP API listing for the hub and the node control API MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit docs/MESHBAY_HTTP_API.md lists every route of the hub (by domain, with the authentication each requires) and of the node's loopback control API. It is written by docs/generate_http_api.py from the routes and their docstrings; test_http_api_doc.py fails when the file drifts from the code or when a route has no docstring, so a new route must say what it does. 79 routes had no docstring and get a one-line description; a few whose first line did not describe the route get a summary line. The login page's developer docs gain an API link next to Design and Protocol, in every language. README, MESHBAY_DESIGN.md (§0.1, §6.7, §7) and CLAUDE.md point to the listing; README also points to examples/. The examples scripts with a shebang become executable. Co-Authored-By: Claude Opus 5.5 --- packages/meshbay-hub/src/meshbay_hub/api/groups.py | 8 ++++++++ 1 file changed, 8 insertions(+) (limited to 'packages/meshbay-hub/src/meshbay_hub/api/groups.py') diff --git a/packages/meshbay-hub/src/meshbay_hub/api/groups.py b/packages/meshbay-hub/src/meshbay_hub/api/groups.py index fc117bf..d58e32c 100644 --- a/packages/meshbay-hub/src/meshbay_hub/api/groups.py +++ b/packages/meshbay-hub/src/meshbay_hub/api/groups.py @@ -120,6 +120,7 @@ async def accept_invitation( current_user: User = Depends(require_user_scope), db: AsyncSession = Depends(get_db), ): + """Accept an invitation: the account becomes a member of the group.""" inv = await db.get(GroupInvitation, (group_id, current_user.id)) group = await db.get(Group, group_id) if inv is None or group is None or group.status != "active": @@ -141,6 +142,7 @@ async def decline_invitation( current_user: User = Depends(require_user_scope), db: AsyncSession = Depends(get_db), ): + """Decline an invitation to a group.""" inv = await db.get(GroupInvitation, (group_id, current_user.id)) if inv is None: raise HTTPException(status_code=404, detail="No such invitation") @@ -281,6 +283,7 @@ async def group_members( current_user: User = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): + """A group's members, for its members only.""" group = await db.get(Group, group_id) if not group: raise HTTPException(status_code=404, detail="Group not found") @@ -319,6 +322,7 @@ async def join_group( current_user: User = Depends(require_user_scope), db: AsyncSession = Depends(get_db), ): + """Join an open group.""" group = await db.get(Group, group_id) if not group: raise HTTPException(status_code=404, detail="Group not found") @@ -421,6 +425,7 @@ async def create_group( current_user: User = Depends(require_user_scope), db: AsyncSession = Depends(get_db), ): + """Create a group, owned by the caller. No node hosts it yet.""" # Being listed and being open are one question, not two. # # A public group that admits nobody is a contradiction: it is in the @@ -643,6 +648,7 @@ async def add_group_member( current_user: User = Depends(get_current_user), db: AsyncSession = Depends(get_db), ): + """Add an account to a group the caller owns. Also called by the owner's node.""" # `get_current_user`, not `require_user_scope`: the node calls this after a # CLI `member invite` so the group becomes visible in the invitee's SPA # (commit 0443cf8). The node authenticates with a node-scoped token, and the @@ -713,6 +719,7 @@ async def delete_group( current_user: User = Depends(require_user_scope), db: AsyncSession = Depends(get_db), ): + """Delete a group. Its owner only.""" group = await db.get(Group, group_id) if not group: raise HTTPException(status_code=404, detail="Group not found") @@ -827,6 +834,7 @@ async def list_hosts( current_user: User = Depends(require_user_scope), db: AsyncSession = Depends(get_db), ): + """The nodes that host a group or asked to, for its owner.""" from meshbay_hub.api.revocation import is_node_connected await _owned(db, group_id, current_user) rows = (await db.execute( -- cgit v1.2.3