{
  "openapi": "3.1.0",
  "info": {
    "title": "Habitat API",
    "summary": "OpenAPI spec generated from Habitat's AT Protocol lexicons.",
    "description": "Welcome to the Habitat API reference! We are currently under development and our API may make breaking changes without notice. Stay tuned [@habitat.network](https://bsky.app/profile/habitat.network) on Bluesky and [habitat.leaflet.pub](https://habitat.leaflet.pub) for future formal releases.",
    "version": "0.0.0",
    "license": {
      "name": "MIT License",
      "identifier": "MIT"
    }
  },
  "servers": [
    {
      "url": "https://pear.habitat.network/xrpc/",
      "description": "Habitat XRPC server"
    }
  ],
  "paths": {
    "/community.opensocial.assignRoles": {
      "post": {
        "tags": [
          "community.opensocial.assignRoles"
        ],
        "summary": "community.opensocial.assignRoles",
        "description": "Set a member's full role set, replacing whatever roles they previously held. Requires service-auth. Requires the `role.assign` action, bounded by the roles the caller may assign: every role being added or removed must be one the caller's own roles are permitted to assign, per the community's permissions record.",
        "operationId": "community.opensocial.assignRoles",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "member",
                  "roles"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community.",
                    "format": "did"
                  },
                  "member": {
                    "type": "string",
                    "description": "DID of the member whose roles to set.",
                    "format": "did"
                  },
                  "roles": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "RoleNotAssignable"
                        },
                        {
                          "const": "MemberNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.createInvite": {
      "post": {
        "tags": [
          "community.opensocial.createInvite"
        ],
        "summary": "community.opensocial.createInvite",
        "description": "Invite a user to join the community. Tracks the invite in the org's invite table; no repo records are written until the invitee accepts via requestJoin. Requires service-auth. Requires the `invite` action.",
        "operationId": "community.opensocial.createInvite",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "invitee"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community to invite into.",
                    "format": "did"
                  },
                  "invitee": {
                    "type": "string",
                    "description": "DID of the user to invite.",
                    "format": "did"
                  },
                  "roles": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "invite"
                  ],
                  "properties": {
                    "invite": {
                      "$ref": "#/components/schemas/community.opensocial.defs.inviteView"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "AlreadyMember"
                        },
                        {
                          "const": "InviteAlreadyExists"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.createSpace": {
      "post": {
        "tags": [
          "community.opensocial.createSpace"
        ],
        "summary": "community.opensocial.createSpace",
        "description": "Create a modality-specific space under the community DID and index it with a community.opensocial.space record. Requires service-auth. Requires the `space.create` action.",
        "operationId": "community.opensocial.createSpace",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "type"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community to create the space under.",
                    "format": "did"
                  },
                  "type": {
                    "type": "string",
                    "description": "The NSID of the space's type, describing its modality.",
                    "format": "nsid"
                  },
                  "skey": {
                    "type": "string",
                    "description": "The space key. If not provided, one will be auto-generated (TID).",
                    "maxLength": 512
                  },
                  "roles": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the created space.",
                      "format": "at-uri"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceAlreadyExists"
                        },
                        {
                          "const": "InvalidType"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.deleteRole": {
      "post": {
        "tags": [
          "community.opensocial.deleteRole"
        ],
        "summary": "community.opensocial.deleteRole",
        "description": "Remove a role. Members holding it keep their other roles; the role is left off any access or permissions bindings that named it. Requires service-auth. Requires the `community.configure` action.",
        "operationId": "community.opensocial.deleteRole",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "role"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community the role belongs to.",
                    "format": "did"
                  },
                  "role": {
                    "type": "string",
                    "description": "Record key of the role to remove."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "RoleNotFound"
                        },
                        {
                          "const": "CannotDeleteBuiltinRole"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.ejectMember": {
      "post": {
        "tags": [
          "community.opensocial.ejectMember"
        ],
        "summary": "community.opensocial.ejectMember",
        "description": "Remove a member from the community, revoking their roles and access. Requires service-auth. Requires the `eject` action, bounded by the roles the caller may assign.",
        "operationId": "community.opensocial.ejectMember",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "member"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community to remove the member from.",
                    "format": "did"
                  },
                  "member": {
                    "type": "string",
                    "description": "DID of the member to remove.",
                    "format": "did"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "MemberNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.listInvites": {
      "get": {
        "tags": [
          "community.opensocial.listInvites"
        ],
        "summary": "community.opensocial.listInvites",
        "description": "List the calling user's pending invites across every community on this instance.",
        "operationId": "community.opensocial.listInvites",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 50
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "invites"
                  ],
                  "properties": {
                    "cursor": {
                      "type": "string"
                    },
                    "invites": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/community.opensocial.defs.inviteView"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.listPendingInvites": {
      "get": {
        "tags": [
          "community.opensocial.listPendingInvites"
        ],
        "summary": "community.opensocial.listPendingInvites",
        "description": "List all pending invites for the org, across all invitees. Requires service-auth. Requires the `invite` action.",
        "operationId": "community.opensocial.listPendingInvites",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "org",
            "in": "query",
            "description": "DID of the community to list pending invites for.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "DID of the community to list pending invites for.",
              "format": "did"
            }
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 50
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "invites"
                  ],
                  "properties": {
                    "cursor": {
                      "type": "string"
                    },
                    "invites": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/community.opensocial.defs.inviteView"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.putRole": {
      "post": {
        "tags": [
          "community.opensocial.putRole"
        ],
        "summary": "community.opensocial.putRole",
        "description": "Create or update a role. Requires service-auth. Requires the `community.configure` action.",
        "operationId": "community.opensocial.putRole",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "role",
                  "name"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community the role belongs to.",
                    "format": "did"
                  },
                  "role": {
                    "type": "string",
                    "description": "Record key for the role, e.g. \"moderator\"."
                  },
                  "name": {
                    "type": "string",
                    "maxLength": 256
                  },
                  "description": {
                    "type": "string",
                    "maxLength": 2048
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.requestJoin": {
      "post": {
        "tags": [
          "community.opensocial.requestJoin"
        ],
        "summary": "community.opensocial.requestJoin",
        "description": "Accept the calling user's pending invite to this community. Removes the invite from the org's invite table and writes a community.opensocial.membership record (in the org repo) and a community.opensocial.acceptance record (in the user's repo, members space). Requires service-auth.",
        "operationId": "community.opensocial.requestJoin",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community whose invite to accept.",
                    "format": "did"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "roles"
                  ],
                  "properties": {
                    "roles": {
                      "type": "array",
                      "items": {
                        "type": "string"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "InviteNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.revokeInvite": {
      "post": {
        "tags": [
          "community.opensocial.revokeInvite"
        ],
        "summary": "community.opensocial.revokeInvite",
        "description": "Retract a pending invite before it is accepted. Requires service-auth. Requires the `invite` action.",
        "operationId": "community.opensocial.revokeInvite",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "id"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community the invite belongs to.",
                    "format": "did"
                  },
                  "id": {
                    "type": "string",
                    "description": "Id of the invite to revoke, from community.opensocial.defs#inviteView."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "InviteNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.updatePermissions": {
      "post": {
        "tags": [
          "community.opensocial.updatePermissions"
        ],
        "summary": "community.opensocial.updatePermissions",
        "description": "Replace the community's authz configuration: which roles authorize which actions, and which roles each role may assign/eject. Requires service-auth. Requires the `community.configure` action.",
        "operationId": "community.opensocial.updatePermissions",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "bindings",
                  "assignable"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community whose permissions to update.",
                    "format": "did"
                  },
                  "bindings": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/community.opensocial.permissions.actionBinding"
                    }
                  },
                  "assignable": {
                    "type": "array",
                    "items": {
                      "$ref": "#/components/schemas/community.opensocial.permissions.assignableBinding"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.updateProfile": {
      "post": {
        "tags": [
          "community.opensocial.updateProfile"
        ],
        "summary": "community.opensocial.updateProfile",
        "description": "Replace the community's profile: name, description, and join policy. Avatar is set separately via uploadImage. Requires service-auth. Requires the `community.configure` action.",
        "operationId": "community.opensocial.updateProfile",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "org",
                  "name"
                ],
                "properties": {
                  "org": {
                    "type": "string",
                    "description": "DID of the community whose profile to update.",
                    "format": "did"
                  },
                  "name": {
                    "type": "string",
                    "maxLength": 256
                  },
                  "description": {
                    "type": "string",
                    "maxLength": 2048
                  },
                  "joinPolicy": {
                    "type": "string",
                    "enum": [
                      "community.opensocial.profile#open",
                      "community.opensocial.profile#invite",
                      "community.opensocial.profile#request"
                    ]
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.updateSpace": {
      "post": {
        "tags": [
          "community.opensocial.updateSpace"
        ],
        "summary": "community.opensocial.updateSpace",
        "description": "Replace the roles that may read a space, written into its community.opensocial.access record. Requires service-auth. Requires the `space.configure` action.",
        "operationId": "community.opensocial.updateSpace",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space",
                  "roles"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "URI of the space to update.",
                    "format": "at-uri"
                  },
                  "roles": {
                    "type": "array",
                    "items": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "InvalidSpace"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/community.opensocial.uploadImage": {
      "post": {
        "tags": [
          "community.opensocial.uploadImage"
        ],
        "summary": "community.opensocial.uploadImage",
        "description": "Upload an image and set it as the community's profile avatar. Requires service-auth. Requires the `community.configure` action.",
        "operationId": "community.opensocial.uploadImage",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "*/*": {}
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "blob"
                  ],
                  "properties": {
                    "blob": {
                      "type": "string",
                      "format": "binary"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.admin.getSettings": {
      "get": {
        "tags": [
          "network.habitat.admin"
        ],
        "summary": "network.habitat.admin.getSettings",
        "description": "Get this instance's admin-configurable settings. Requires an authenticated instance admin session.",
        "operationId": "network.habitat.admin.getSettings",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "instanceName",
                    "orgCreationPolicy"
                  ],
                  "properties": {
                    "instanceName": {
                      "type": "string",
                      "description": "This instance's display name."
                    },
                    "orgCreationPolicy": {
                      "type": "string",
                      "description": "'open' or 'invite_only'."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.admin.issueInvite": {
      "post": {
        "tags": [
          "network.habitat.admin"
        ],
        "summary": "network.habitat.admin.issueInvite",
        "description": "Issue a single-use invite token for creating an org on this instance. Requires an authenticated instance admin session.",
        "operationId": "network.habitat.admin.issueInvite",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "token"
                  ],
                  "properties": {
                    "token": {
                      "type": "string",
                      "description": "Signed, single-use invite token to embed in an org-creation link."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.admin.updateSettings": {
      "post": {
        "tags": [
          "network.habitat.admin"
        ],
        "summary": "network.habitat.admin.updateSettings",
        "description": "Update this instance's admin-configurable settings. Requires an authenticated instance admin session.",
        "operationId": "network.habitat.admin.updateSettings",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "instanceName": {
                    "type": "string",
                    "description": "This instance's display name. Omit to leave unchanged."
                  },
                  "orgCreationPolicy": {
                    "type": "string",
                    "description": "'open' or 'invite_only'. Omit to leave unchanged."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "instanceName",
                    "orgCreationPolicy"
                  ],
                  "properties": {
                    "instanceName": {
                      "type": "string"
                    },
                    "orgCreationPolicy": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.docs.createDoc": {
      "post": {
        "tags": [
          "network.habitat.docs"
        ],
        "summary": "network.habitat.docs.createDoc",
        "description": "Create a new collaborative document. Implemented by the docs server, which writes the canonical record into the org's docs space using the org credential.",
        "operationId": "network.habitat.docs.createDoc",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {}
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri",
                    "docId"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the created document record."
                    },
                    "docId": {
                      "type": "string",
                      "description": "The record key identifying the document, used in subsequent updateDoc calls."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.docs.listDocs": {
      "get": {
        "tags": [
          "network.habitat.docs"
        ],
        "summary": "network.habitat.docs.listDocs",
        "description": "List all documents in the org, with titles. Implemented by the docs server, which lists the doc spaces from pear using the org credential and reads each space's markdown 'self' record for the title.",
        "operationId": "network.habitat.docs.listDocs",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "docs"
                  ],
                  "properties": {
                    "docs": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.docs.listDocs.docView"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.docs.updateDoc": {
      "post": {
        "tags": [
          "network.habitat.docs"
        ],
        "summary": "network.habitat.docs.updateDoc",
        "description": "Apply a CRDT update to a collaborative document. Implemented by the docs server, which merges the update into the canonical document and writes it back using the org credential.",
        "operationId": "network.habitat.docs.updateDoc",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "docId",
                  "update"
                ],
                "properties": {
                  "docId": {
                    "type": "string",
                    "description": "The record key identifying the document to update."
                  },
                  "update": {
                    "type": "string",
                    "description": "Base64-encoded Yjs update to merge into the document."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the updated document record."
                    },
                    "cid": {
                      "type": "string",
                      "description": "CID of the updated record.",
                      "format": "cid"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.groups.addMember": {
      "post": {
        "tags": [
          "network.habitat.groups"
        ],
        "summary": "network.habitat.groups.addMember",
        "description": "Add a member to a group. The member is either an individual user (subjectDid) or another group whose members are inherited (subjectGroup). The home server writes the backing relationship tuple using the org credential. Caller must be able to manage the group.",
        "operationId": "network.habitat.groups.addMember",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "group"
                ],
                "properties": {
                  "group": {
                    "type": "string",
                    "description": "URI of the group-space to add the member to.",
                    "format": "uri"
                  },
                  "subjectDid": {
                    "type": "string",
                    "description": "DID of the user to add as a member. Mutually exclusive with subjectGroup.",
                    "format": "did"
                  },
                  "subjectGroup": {
                    "type": "string",
                    "description": "URI of another group-space whose members this group should inherit. Mutually exclusive with subjectDid.",
                    "format": "uri"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the written relationship tuple."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "GroupNotFound"
                        },
                        {
                          "const": "Forbidden"
                        },
                        {
                          "const": "InvalidSubject"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.groups.createGroup": {
      "post": {
        "tags": [
          "network.habitat.groups"
        ],
        "summary": "network.habitat.groups.createGroup",
        "description": "Create a new group. The home server creates a network.habitat.group space using the org credential, writes a network.habitat.group.profile self record, and grants the calling user the manager role so they are both a member and able to manage the group.",
        "operationId": "network.habitat.groups.createGroup",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "name"
                ],
                "properties": {
                  "name": {
                    "type": "string",
                    "maxLength": 256
                  },
                  "description": {
                    "type": "string",
                    "maxLength": 2048
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the created group-space.",
                      "format": "uri"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.groups.deleteMember": {
      "post": {
        "tags": [
          "network.habitat.groups"
        ],
        "summary": "network.habitat.groups.deleteMember",
        "description": "Remove a member from a group. The member is either an individual user (subjectDid) or an inherited group (subjectGroup). The home server deletes the backing relationship tuple using the org credential. Caller must be able to manage the group.",
        "operationId": "network.habitat.groups.deleteMember",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "group"
                ],
                "properties": {
                  "group": {
                    "type": "string",
                    "description": "URI of the group-space to remove the member from.",
                    "format": "uri"
                  },
                  "subjectDid": {
                    "type": "string",
                    "description": "DID of the user to remove. Mutually exclusive with subjectGroup.",
                    "format": "did"
                  },
                  "subjectGroup": {
                    "type": "string",
                    "description": "URI of an inherited group-space to stop inheriting. Mutually exclusive with subjectDid.",
                    "format": "uri"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "GroupNotFound"
                        },
                        {
                          "const": "Forbidden"
                        },
                        {
                          "const": "InvalidSubject"
                        },
                        {
                          "const": "MemberNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.groups.getGroup": {
      "get": {
        "tags": [
          "network.habitat.groups"
        ],
        "summary": "network.habitat.groups.getGroup",
        "description": "Fetch a single group with its full membership expanded, including which other groups it inherits members from. Implemented by the home server and reached via pear service proxying.",
        "operationId": "network.habitat.groups.getGroup",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "group",
            "in": "query",
            "description": "URI of the group-space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "URI of the group-space.",
              "format": "uri"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "$ref": "#/components/schemas/network.habitat.groups.defs.groupView"
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "GroupNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.groups.listGroups": {
      "get": {
        "tags": [
          "network.habitat.groups"
        ],
        "summary": "network.habitat.groups.listGroups",
        "description": "List the groups visible to the calling user: groups they are a member of (directly or through inherited groups) and groups they can manage. Implemented by the home server and reached via pear service proxying.",
        "operationId": "network.habitat.groups.listGroups",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "groups"
                  ],
                  "properties": {
                    "groups": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.groups.defs.groupView"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.groups.updateGroup": {
      "post": {
        "tags": [
          "network.habitat.groups"
        ],
        "summary": "network.habitat.groups.updateGroup",
        "description": "Update a group's profile (name and/or description). Caller must be able to manage the group.",
        "operationId": "network.habitat.groups.updateGroup",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "group"
                ],
                "properties": {
                  "group": {
                    "type": "string",
                    "description": "URI of the group-space.",
                    "format": "uri"
                  },
                  "name": {
                    "type": "string",
                    "maxLength": 256
                  },
                  "description": {
                    "type": "string",
                    "maxLength": 2048
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "format": "uri"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "GroupNotFound"
                        },
                        {
                          "const": "Forbidden"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.instance.describeInstance": {
      "get": {
        "tags": [
          "network.habitat.instance"
        ],
        "summary": "network.habitat.instance.describeInstance",
        "description": "Get public info about this instance. Modeled on com.atproto.server.describeServer. No authentication required.",
        "operationId": "network.habitat.instance.describeInstance",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "name",
                    "inviteRequired"
                  ],
                  "properties": {
                    "name": {
                      "type": "string",
                      "description": "This instance's manager-configured display name."
                    },
                    "inviteRequired": {
                      "type": "boolean",
                      "description": "Whether creating an org on this instance requires an invite token."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.internal.notifyOfUpdate": {
      "post": {
        "tags": [
          "network.habitat.internal"
        ],
        "summary": "network.habitat.internal.notifyOfUpdate",
        "description": "Notify another DID that there is an update for them on the fiven record.",
        "operationId": "network.habitat.internal.notifyOfUpdate",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "collection",
                  "rkey",
                  "recipient"
                ],
                "properties": {
                  "recipient": {
                    "type": "string",
                    "description": "The DID to grant permission to (URL parameter).",
                    "format": "did"
                  },
                  "collection": {
                    "type": "string",
                    "description": "The NSID of the record collection that the update is for.",
                    "format": "nsid"
                  },
                  "rkey": {
                    "type": "string",
                    "description": "The record key which was updated."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.listConnectedApps": {
      "get": {
        "tags": [
          "network.habitat.listConnectedApps"
        ],
        "summary": "network.habitat.listConnectedApps",
        "description": "List apps connected to habitat for a given user. Returns connected apps for the authenticated user.",
        "operationId": "network.habitat.listConnectedApps",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "apps"
                  ],
                  "properties": {
                    "apps": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.listConnectedApps.app"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.opensocial.createOrg": {
      "post": {
        "tags": [
          "network.habitat.opensocial"
        ],
        "summary": "network.habitat.opensocial.createOrg",
        "description": "Create a new opensocial-backed org: mints the org DID, bootstraps its about/members spaces (profile, admin and member roles), and grants the calling user the admin role. Requires service-auth.",
        "operationId": "network.habitat.opensocial.createOrg",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "handle"
                ],
                "properties": {
                  "handle": {
                    "type": "string",
                    "description": "Subdomain handle for the org (alphanumeric, 1-50 chars)."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "org"
                  ],
                  "properties": {
                    "org": {
                      "type": "string",
                      "description": "DID of the created org.",
                      "format": "did"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.addAdmin": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.addAdmin",
        "description": "Add an admin to the org. Only callable by existing admins.",
        "operationId": "network.habitat.org.addAdmin",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "admin"
                ],
                "properties": {
                  "admin": {
                    "type": "string",
                    "description": "The DID of the user to add as an admin.",
                    "format": "did"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.addMembers": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.addMembers",
        "description": "Add member(s) to the org. Only callable by admins.",
        "operationId": "network.habitat.org.addMembers",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "members"
                ],
                "properties": {
                  "members": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "format": "did"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.create": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.create",
        "description": "Create a new org with a bootstrap admin member.",
        "operationId": "network.habitat.org.create",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "admin_handle",
                  "contact_email"
                ],
                "properties": {
                  "admin_handle": {
                    "type": "string",
                    "description": "Internal handle for the bootstrap admin (alphanumeric, 1-50 chars)."
                  },
                  "contact_email": {
                    "type": "string",
                    "description": "Email address for contacting the org about its account (not used for login)."
                  },
                  "admin_password": {
                    "type": "string",
                    "description": "Password for the bootstrap admin account (required for password login method)."
                  },
                  "handle_subdomain": {
                    "type": "string",
                    "description": "Subdomain for all org member handles (e.g. 'acmecorp')."
                  },
                  "name": {
                    "type": "string",
                    "description": "A display name for this org."
                  },
                  "login_method": {
                    "type": "string",
                    "description": "Login method for the org: 'password', 'atproto', or 'google'.",
                    "default": "password"
                  },
                  "login_id": {
                    "type": "string",
                    "description": "Provider-specific identifier (public ATProto DID for 'atproto', email for 'google'). Ignored for 'password'."
                  },
                  "invite_token": {
                    "type": "string",
                    "description": "Single-use invite token from an instance admin, required when the instance's org creation policy is invite_only."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "org_id",
                    "admin_did",
                    "admin_handle",
                    "name"
                  ],
                  "properties": {
                    "org_id": {
                      "type": "string",
                      "description": "The ID of the created org."
                    },
                    "admin_did": {
                      "type": "string",
                      "description": "The DID of the bootstrap admin."
                    },
                    "admin_handle": {
                      "type": "string",
                      "description": "The full handle of the bootstrap admin."
                    },
                    "name": {
                      "type": "string",
                      "description": "The display name of the created org."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.downgradeAdmin": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.downgradeAdmin",
        "description": "Downgrade an admin to a regular member. Only callable by existing admins. The last admin cannot be downgraded.",
        "operationId": "network.habitat.org.downgradeAdmin",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "admin"
                ],
                "properties": {
                  "admin": {
                    "type": "string",
                    "description": "The DID of the admin to downgrade to member.",
                    "format": "did"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.getAdmins": {
      "get": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.getAdmins",
        "description": "Get the list of admins in the org. Callable by any org member.",
        "operationId": "network.habitat.org.getAdmins",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "admins"
                  ],
                  "properties": {
                    "admins": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.org.getAdmins.member"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.getMembers": {
      "get": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.getMembers",
        "description": "Get the list of members in the org. Callable by any org member.",
        "operationId": "network.habitat.org.getMembers",
        "security": [
          {
            "Bearer": []
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "members"
                  ],
                  "properties": {
                    "members": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.org.getMembers.member"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.getMetadata": {
      "get": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.getMetadata",
        "description": "Get general info about this organization.",
        "operationId": "network.habitat.org.getMetadata",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "orgId",
            "in": "query",
            "description": "The orge ID of the organization to look up. If not specified, defaults to the authenticated caller's org.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "The orge ID of the organization to look up. If not specified, defaults to the authenticated caller's org."
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "loginMethod",
                    "handleSubdomain",
                    "orgId"
                  ],
                  "properties": {
                    "name": {
                      "type": "string",
                      "description": "The name of this organization."
                    },
                    "description": {
                      "type": "string",
                      "description": "A description for this organization."
                    },
                    "loginMethod": {
                      "type": "string",
                      "description": "Login method for the org: 'password', 'atproto', or 'google'."
                    },
                    "handleSubdomain": {
                      "type": "string",
                      "description": "The subdomain used for all org member handles."
                    },
                    "orgId": {
                      "type": "string",
                      "description": "The unique ID of this organization."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.issueInviteToken": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.issueInviteToken",
        "description": "Generate an invite token that can be sent to a member to join this organization.",
        "operationId": "network.habitat.org.issueInviteToken",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "properties": {
                  "expiresAt": {
                    "type": "string",
                    "description": "When this token expires; defaults to 1 week.",
                    "format": "date-time"
                  },
                  "reusable": {
                    "type": "boolean",
                    "description": "Whether this token is reusable to invite more than one member; defaults to false."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "token"
                  ],
                  "properties": {
                    "token": {
                      "type": "string",
                      "description": "The generated invite token."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.loginMember": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.loginMember",
        "description": "Authenticate a habitat org member with their handle and password, returning a short-lived token for use in the OAuth callback flow.",
        "operationId": "network.habitat.org.loginMember",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "handle",
                  "password"
                ],
                "properties": {
                  "handle": {
                    "type": "string",
                    "description": "The full handle of the member (e.g. alice.example.com)."
                  },
                  "password": {
                    "type": "string",
                    "description": "The member's password."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "callbackURL"
                  ],
                  "properties": {
                    "callbackURL": {
                      "type": "string",
                      "description": "The URL to redirect the browser to in order to complete the OAuth flow."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.mintMemberIdentity": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.mintMemberIdentity",
        "description": "Mint a new organization member identity with the given handle and token.",
        "operationId": "network.habitat.org.mintMemberIdentity",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "token",
                  "handle"
                ],
                "properties": {
                  "orgId": {
                    "type": "string",
                    "description": "The ID of the org this member is joining."
                  },
                  "handle": {
                    "type": "string",
                    "description": "The internal handle (all letters + numbers, no special characters, does not include org domain) that will be used by the member."
                  },
                  "token": {
                    "type": "string",
                    "description": "The token that was issued by an org admin to allow members to join the organization."
                  },
                  "password": {
                    "type": "string",
                    "description": "The password for the new member's account (required for 'password' login method)."
                  },
                  "loginID": {
                    "type": "string",
                    "description": "Provider-specific identifier (AT Protocol handle for 'atproto', email for 'google'). Required for non-password login methods."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "handle",
                    "did"
                  ],
                  "properties": {
                    "handle": {
                      "type": "string",
                      "description": "The full handle of the newly minted member identity."
                    },
                    "did": {
                      "type": "string",
                      "description": "The DID of the newly minted member identity."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.removeAdmin": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.removeAdmin",
        "description": "Remove an admin from the org. Only callable by existing admins. The last admin cannot be removed.",
        "operationId": "network.habitat.org.removeAdmin",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "admin"
                ],
                "properties": {
                  "admin": {
                    "type": "string",
                    "description": "The DID of the admin to remove.",
                    "format": "did"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.org.removeMembers": {
      "post": {
        "tags": [
          "network.habitat.org"
        ],
        "summary": "network.habitat.org.removeMembers",
        "description": "Remove member(s) from the org. Only callable by admins.",
        "operationId": "network.habitat.org.removeMembers",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "members"
                ],
                "properties": {
                  "members": {
                    "type": "array",
                    "items": {
                      "type": "string",
                      "format": "did"
                    }
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.checkSpaceRelation": {
      "get": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.checkSpaceRelation",
        "description": "Check whether a space-role userset (all subjects holding subjectRole on another space) holds a role on space, resolving built-in role implications. Enables checking cross-space inheritance, e.g. whether spaceA's writers hold reader role on spaceB. Caller must have the reader role on space.",
        "operationId": "network.habitat.relationship.checkSpaceRelation",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "subject",
            "in": "query",
            "description": "URI of the subject space (or group-space) whose role-holders form the userset to check.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "URI of the subject space (or group-space) whose role-holders form the userset to check.",
              "format": "uri"
            }
          },
          {
            "name": "subjectRole",
            "in": "query",
            "description": "The role held on the subject space, forming the userset.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The role held on the subject space, forming the userset."
            }
          },
          {
            "name": "relation",
            "in": "query",
            "description": "The role to check for on the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The role to check for on the space."
            }
          },
          {
            "name": "space",
            "in": "query",
            "description": "URI of the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "URI of the space.",
              "format": "uri"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "allowed"
                  ],
                  "properties": {
                    "allowed": {
                      "type": "boolean",
                      "description": "Whether the subject userset holds the role on the space."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.checkUserRelation": {
      "get": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.checkUserRelation",
        "description": "Check whether a user holds a role on a space, resolving through space-role usersets (groups, including org member/admin groups, are spaces, so group membership and nested groups resolve as space-role usersets) and built-in role implications (owner implies manager implies writer implies reader). Caller must have the reader role on the space.",
        "operationId": "network.habitat.relationship.checkUserRelation",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "subject",
            "in": "query",
            "description": "DID of the user to check.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "DID of the user to check.",
              "format": "did"
            }
          },
          {
            "name": "relation",
            "in": "query",
            "description": "The role to check for on the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The role to check for on the space."
            }
          },
          {
            "name": "space",
            "in": "query",
            "description": "URI of the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "URI of the space.",
              "format": "uri"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "allowed"
                  ],
                  "properties": {
                    "allowed": {
                      "type": "boolean",
                      "description": "Whether the subject holds the role on the space."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.deleteRelation": {
      "post": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.deleteRelation",
        "description": "Delete a relationship record (user or space relation) by its record URI. Caller must have the manager role on the relation's governing space.",
        "operationId": "network.habitat.relationship.deleteRelation",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "uri"
                ],
                "properties": {
                  "uri": {
                    "type": "string",
                    "description": "URI of the relation record to delete."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "RelationNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.listRelatedSpaces": {
      "get": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.listRelatedSpaces",
        "description": "List the spaces on which a user holds a role, expanding space-role usersets (groups, including org member/admin groups, are spaces, so group membership and nested groups resolve as space-role usersets) and built-in role implications. Returns only spaces the caller has the reader role on.",
        "operationId": "network.habitat.relationship.listRelatedSpaces",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "did",
            "in": "query",
            "description": "DID of the user.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "DID of the user.",
              "format": "did"
            }
          },
          {
            "name": "relation",
            "in": "query",
            "description": "The role to query for.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The role to query for."
            }
          },
          {
            "name": "type",
            "in": "query",
            "description": "Filter to spaces of this type.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "Filter to spaces of this type.",
              "format": "nsid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "spaces"
                  ],
                  "properties": {
                    "spaces": {
                      "type": "array",
                      "items": {
                        "type": "string",
                        "format": "uri"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.listRelations": {
      "get": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.listRelations",
        "description": "List relationship records governing a space, optionally filtered by object, subject, subject type, or relation. Caller must have the reader role on the space. This is the interoperable read surface other apps use to understand the permission structure.",
        "operationId": "network.habitat.relationship.listRelations",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "URI of the governing space whose relations to list.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "URI of the governing space whose relations to list.",
              "format": "uri"
            }
          },
          {
            "name": "subjectDid",
            "in": "query",
            "description": "Optional. Restrict to relations whose subject is this user DID.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "Optional. Restrict to relations whose subject is this user DID.",
              "format": "did"
            }
          },
          {
            "name": "subjectType",
            "in": "query",
            "description": "Optional. Restrict to relations whose subject is a user (userRelation) or a space userset (spaceRelation).",
            "required": false,
            "schema": {
              "type": "string",
              "description": "Optional. Restrict to relations whose subject is a user (userRelation) or a space userset (spaceRelation)."
            }
          },
          {
            "name": "relation",
            "in": "query",
            "description": "Optional. Restrict to relations with this role.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "Optional. Restrict to relations with this role."
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "relations"
                  ],
                  "properties": {
                    "relations": {
                      "type": "array",
                      "items": {
                        "oneOf": [
                          {
                            "$ref": "#/components/schemas/network.habitat.relationship.listRelations.userRelationView"
                          },
                          {
                            "$ref": "#/components/schemas/network.habitat.relationship.listRelations.spaceRelationView"
                          }
                        ]
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.resolveRelations": {
      "get": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.resolveRelations",
        "description": "List the user DIDs that hold a role on a space, expanding space-role usersets (groups, including org member/admin groups, are spaces, so group membership and nested groups resolve as space-role usersets) and built-in role implications. Caller must have the reader role on the space.",
        "operationId": "network.habitat.relationship.resolveRelations",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "URI of the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "URI of the space.",
              "format": "uri"
            }
          },
          {
            "name": "relation",
            "in": "query",
            "description": "The role to expand.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The role to expand."
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "dids"
                  ],
                  "properties": {
                    "dids": {
                      "type": "array",
                      "items": {
                        "type": "string",
                        "format": "did"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.setSpaceRelation": {
      "post": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.setSpaceRelation",
        "description": "Write a space relation, creating it if it does not already exist. The relation record is owned by the org repo within its governing space. Caller must have the manager role on the space.",
        "operationId": "network.habitat.relationship.setSpaceRelation",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "subject",
                  "subjectRole",
                  "relation",
                  "space"
                ],
                "properties": {
                  "subject": {
                    "type": "string",
                    "description": "URI of the subject space (or group-space) whose role-holders form the userset to grant the role to.",
                    "format": "uri"
                  },
                  "subjectRole": {
                    "type": "string",
                    "description": "The role held on the subject space, forming the userset."
                  },
                  "relation": {
                    "type": "string",
                    "description": "Role granted on the space (owner|manager|writer|reader).",
                    "enum": [
                      "owner",
                      "manager",
                      "writer",
                      "reader"
                    ]
                  },
                  "space": {
                    "type": "string",
                    "description": "URI of the space to grant the role on.",
                    "format": "uri"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the written relation record."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "InvalidRelation"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.relationship.setUserRelation": {
      "post": {
        "tags": [
          "network.habitat.relationship"
        ],
        "summary": "network.habitat.relationship.setUserRelation",
        "description": "Write a user relation, creating it if it does not already exist. The relation record is owned by the org repo within its governing space. Caller must have the manager role on the space.",
        "operationId": "network.habitat.relationship.setUserRelation",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "subject",
                  "relation",
                  "space"
                ],
                "properties": {
                  "subject": {
                    "type": "string",
                    "description": "DID of the user to grant the role to.",
                    "format": "did"
                  },
                  "relation": {
                    "type": "string",
                    "description": "Role granted on the space (owner|manager|writer|reader).",
                    "enum": [
                      "owner",
                      "manager",
                      "writer",
                      "reader"
                    ]
                  },
                  "space": {
                    "type": "string",
                    "description": "URI of the space to grant the role on.",
                    "format": "uri"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the written relation record."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "InvalidRelation"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.repo.getBlob": {
      "get": {
        "tags": [
          "network.habitat.repo"
        ],
        "summary": "network.habitat.repo.getBlob",
        "description": "Get a blob associated with a given account. Returns the full blob as originally uploaded. Does not require auth; implemented by PDS.",
        "operationId": "network.habitat.repo.getBlob",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "did",
            "in": "query",
            "description": "The DID of the account.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The DID of the account.",
              "format": "did"
            }
          },
          {
            "name": "cid",
            "in": "query",
            "description": "The CID of the blob to fetch",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The CID of the blob to fetch",
              "format": "cid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "*/*": {}
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "BlobNotFound"
                        },
                        {
                          "const": "RepoNotFound"
                        },
                        {
                          "const": "RepoTakendown"
                        },
                        {
                          "const": "RepoSuspended"
                        },
                        {
                          "const": "RepoDeactivated"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.repo.uploadBlob": {
      "post": {
        "tags": [
          "network.habitat.repo"
        ],
        "summary": "network.habitat.repo.uploadBlob",
        "description": "Upload a new blob, to be referenced from a repository record. The blob will be deleted if it is not referenced within a time window (eg, minutes). Blob restrictions (mimetype, size, etc) are enforced when the reference is created. Requires auth, implemented by PDS.",
        "operationId": "network.habitat.repo.uploadBlob",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "*/*": {}
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "blob"
                  ],
                  "properties": {
                    "blob": {
                      "type": "string",
                      "format": "binary"
                    },
                    "cid": {
                      "type": "string",
                      "format": "cid"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.search.query": {
      "get": {
        "tags": [
          "network.habitat.search"
        ],
        "summary": "network.habitat.search.query",
        "description": "Full-text search over records the caller's org has indexed.",
        "operationId": "network.habitat.search.query",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "q",
            "in": "query",
            "description": "The search query text.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The search query text."
            }
          },
          {
            "name": "limit",
            "in": "query",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 25
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "results"
                  ],
                  "properties": {
                    "results": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.search.query.resultView"
                      }
                    },
                    "cursor": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.simplespace.addMember": {
      "post": {
        "tags": [
          "network.habitat.simplespace"
        ],
        "summary": "network.habitat.simplespace.addMember",
        "description": "Add a member to a space's member list. The member list is host-internal state consulted at credential-mint time when the space's policy is 'member-list'. It is not a synced protocol structure and is not enumerated to the network. Requires auth as the space owner.",
        "operationId": "network.habitat.simplespace.addMember",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space",
                  "did"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space.",
                    "format": "at-uri"
                  },
                  "did": {
                    "type": "string",
                    "description": "The DID of the member to add.",
                    "format": "did"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "NotSpaceOwner"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.simplespace.createSpace": {
      "post": {
        "tags": [
          "network.habitat.simplespace"
        ],
        "summary": "network.habitat.simplespace.createSpace",
        "description": "Create a new space managed by the simplespace implementation. The authenticated user becomes the space owner. Requires auth, implemented by PDS.",
        "operationId": "network.habitat.simplespace.createSpace",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "did",
                  "type"
                ],
                "properties": {
                  "did": {
                    "type": "string",
                    "description": "The DID of the space.",
                    "format": "did"
                  },
                  "type": {
                    "type": "string",
                    "description": "The NSID of the space type, describing the modality of the space (e.g. app.bsky.group, app.bsky.personal).",
                    "format": "nsid"
                  },
                  "skey": {
                    "type": "string",
                    "description": "The space key. Used to differentiate multiple spaces of the same type under the same owner. If not provided, one will be auto-generated (TID).",
                    "maxLength": 512
                  },
                  "config": {
                    "$ref": "#/components/schemas/network.habitat.simplespace.defs.spaceConfig"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the created space.",
                      "format": "at-uri"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceAlreadyExists"
                        },
                        {
                          "const": "InvalidType"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.simplespace.deleteSpace": {
      "post": {
        "tags": [
          "network.habitat.simplespace"
        ],
        "summary": "network.habitat.simplespace.deleteSpace",
        "description": "Delete a space. The authenticated user must be the space owner. The authority's own repo in the space is deleted along with it, since the space host and the repo host are the same service here; other members' repos are flagged as belonging to a deleted space rather than erased. After deletion, all reads and writes against the space fail with SpaceNotFound, and getSpaceCredential answers SpaceDeleted so a syncer that missed the notification still learns to drop its copy. Idempotent. Requires auth, implemented by PDS.",
        "operationId": "network.habitat.simplespace.deleteSpace",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space to delete.",
                    "format": "uri"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "NotSpaceOwner"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.simplespace.listMembers": {
      "get": {
        "tags": [
          "network.habitat.simplespace"
        ],
        "summary": "network.habitat.simplespace.listMembers",
        "description": "List the members in a space's host-internal member list. Must be called on the space owner's PDS, by the space owner. This reflects the simplespace member list, not a protocol-level reader set.",
        "operationId": "network.habitat.simplespace.listMembers",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          },
          {
            "name": "limit",
            "in": "query",
            "description": "Maximum number of members to return.",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 1000,
              "default": 100
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "members"
                  ],
                  "properties": {
                    "cursor": {
                      "type": "string"
                    },
                    "members": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.simplespace.listMembers.member"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "NotSpaceOwner"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.simplespace.removeMember": {
      "post": {
        "tags": [
          "network.habitat.simplespace"
        ],
        "summary": "network.habitat.simplespace.removeMember",
        "description": "Remove a member from a space's member list. The member list is host-internal state consulted at credential-mint time when the space's policy is 'member-list'. Requires auth as the space owner.",
        "operationId": "network.habitat.simplespace.removeMember",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space",
                  "did"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space.",
                    "format": "at-uri"
                  },
                  "did": {
                    "type": "string",
                    "description": "The DID of the member to remove.",
                    "format": "did"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "NotSpaceOwner"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.deleteRecord": {
      "post": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.deleteRecord",
        "description": "Delete a record in a permissioned space, or ensure it doesn't exist. Requires auth, implemented by PDS.",
        "operationId": "network.habitat.space.deleteRecord",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space",
                  "repo",
                  "collection",
                  "rkey"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space.",
                    "format": "at-uri"
                  },
                  "repo": {
                    "type": "string",
                    "description": "The DID of the repo to delete from (the authenticated member).",
                    "format": "did"
                  },
                  "collection": {
                    "type": "string",
                    "description": "The NSID of the record collection.",
                    "format": "nsid"
                  },
                  "rkey": {
                    "type": "string",
                    "description": "The Record Key.",
                    "format": "record-key"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {}
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.getBlob": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.getBlob",
        "description": "Get a blob stored within a permissioned space, addressed by its CID. Requires read access to the space.",
        "operationId": "network.habitat.space.getBlob",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space the blob belongs to.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space the blob belongs to.",
              "format": "at-uri"
            }
          },
          {
            "name": "cid",
            "in": "query",
            "description": "The CID of the blob to fetch.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The CID of the blob to fetch.",
              "format": "cid"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "*/*": {}
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "BlobNotFound"
                        },
                        {
                          "const": "SpaceNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.getDelegationToken": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.getDelegationToken",
        "description": "Mint a delegation token for a space, proving the requesting app is acting on the user's behalf. Exchanged with the space authority for a space credential. Served by the requesting user's PDS. Requires OAuth auth.",
        "operationId": "network.habitat.space.getDelegationToken",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "token"
                  ],
                  "properties": {
                    "token": {
                      "type": "string",
                      "description": "A signed JWT delegation token."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.getLatestCommit": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.getLatestCommit",
        "description": "Get the current signed commit for an account's permissioned repo within a space. Served by a repo host. Callable with either OAuth (for the authenticated user's own data) or a space credential (for syncing services).",
        "operationId": "network.habitat.space.getLatestCommit",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          },
          {
            "name": "repo",
            "in": "query",
            "description": "The DID of the account whose latest commit to retrieve.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The DID of the account whose latest commit to retrieve.",
              "format": "did"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "properties": {
                    "commit": {
                      "$ref": "#/components/schemas/network.habitat.space.defs.signedCommit"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "RepoTakendown"
                        },
                        {
                          "const": "RepoSuspended"
                        },
                        {
                          "const": "RepoDeactivated"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.getRecord": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.getRecord",
        "description": "Get a single record from a permissioned space. Callable with either OAuth (for the authenticated user's own data) or a space credential (for syncing services).",
        "operationId": "network.habitat.space.getRecord",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          },
          {
            "name": "repo",
            "in": "query",
            "description": "The DID of the account whose repo to read from.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The DID of the account whose repo to read from.",
              "format": "did"
            }
          },
          {
            "name": "collection",
            "in": "query",
            "description": "The NSID of the record collection.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The NSID of the record collection.",
              "format": "nsid"
            }
          },
          {
            "name": "rkey",
            "in": "query",
            "description": "The Record Key.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The Record Key.",
              "format": "record-key"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri",
                    "cid",
                    "value"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "format": "at-uri"
                    },
                    "cid": {
                      "type": "string",
                      "format": "cid"
                    },
                    "value": {}
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "RecordNotFound"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "RepoTakendown"
                        },
                        {
                          "const": "RepoSuspended"
                        },
                        {
                          "const": "RepoDeactivated"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.getRepo": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.getRepo",
        "description": "Download an account's permissioned repo within a space as a CAR file, for full-state recovery. The CAR declares two roots in order: the signed commit, then a DRISL (DAG-CBOR) index mapping '{collection}/{rkey}' to record CID. Record blocks follow in lexicographic order. Blobs are not included and are fetched separately via getBlob. Served by a repo host. Callable with either OAuth (for the authenticated user's own data) or a space credential (for syncing services).",
        "operationId": "network.habitat.space.getRepo",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          },
          {
            "name": "repo",
            "in": "query",
            "description": "The DID of the account whose repo to download.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The DID of the account whose repo to download.",
              "format": "did"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/vnd.ipld.car": {}
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "RepoNotFound"
                        },
                        {
                          "const": "RepoTakendown"
                        },
                        {
                          "const": "RepoSuspended"
                        },
                        {
                          "const": "RepoDeactivated"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.getSpaceCredential": {
      "post": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.getSpaceCredential",
        "description": "Exchange a delegation token for a space credential. Called on the space authority, with the delegation token as the request's authorization token. The resulting space credential reads repos across the space. Requires a delegation token, plus a client attestation when the space gates on app identity.",
        "operationId": "network.habitat.space.getSpaceCredential",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space.",
                    "format": "at-uri"
                  },
                  "clientAttestation": {
                    "type": "string",
                    "description": "Optional client attestation JWT establishing the app's identity. Required only when the space gates on app identity."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "credential"
                  ],
                  "properties": {
                    "credential": {
                      "type": "string",
                      "description": "A signed JWT space credential."
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "SpaceDeleted"
                        },
                        {
                          "const": "UserNotAuthorized"
                        },
                        {
                          "const": "AppNotAuthorized"
                        },
                        {
                          "const": "NotAuthorized"
                        },
                        {
                          "const": "InvalidDelegationToken"
                        },
                        {
                          "const": "InvalidClientAttestation"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.listRecords": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.listRecords",
        "description": "List the records in an account's repo within a permissioned space, optionally filtered by collection. By default each record's value is inlined; set excludeValues for a metadata-only listing (collection, rkey, cid). Used for full-state recovery. Callable with either OAuth (for the authenticated user's own data) or a space credential (for syncing services).",
        "operationId": "network.habitat.space.listRecords",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          },
          {
            "name": "repo",
            "in": "query",
            "description": "The DID of the account whose repo to list.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The DID of the account whose repo to list.",
              "format": "did"
            }
          },
          {
            "name": "collection",
            "in": "query",
            "description": "The NSID of the record collection. If omitted, lists records across all collections.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "The NSID of the record collection. If omitted, lists records across all collections.",
              "format": "nsid"
            }
          },
          {
            "name": "limit",
            "in": "query",
            "description": "The number of records to return.",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 50
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            }
          },
          {
            "name": "reverse",
            "in": "query",
            "description": "Flag to reverse the order of the returned records.",
            "required": false,
            "schema": {
              "type": "boolean",
              "description": "Flag to reverse the order of the returned records."
            }
          },
          {
            "name": "excludeValues",
            "in": "query",
            "description": "If true, omit inlined record values and return only metadata (collection, rkey, cid).",
            "required": false,
            "schema": {
              "type": "boolean",
              "description": "If true, omit inlined record values and return only metadata (collection, rkey, cid)."
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "records"
                  ],
                  "properties": {
                    "cursor": {
                      "type": "string"
                    },
                    "records": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.space.listRecords.record"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "RepoTakendown"
                        },
                        {
                          "const": "RepoSuspended"
                        },
                        {
                          "const": "RepoDeactivated"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.listRepoOps": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.listRepoOps",
        "description": "List the operation log for an account's permissioned repo within a space, returning operations after a given revision. Primary incremental sync mechanism. By default each created or updated operation inlines the record's current value; set excludeValues for metadata-only entries. Callable with either OAuth (for the authenticated user's own data) or a space credential (for syncing services).",
        "operationId": "network.habitat.space.listRepoOps",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          },
          {
            "name": "repo",
            "in": "query",
            "description": "The DID of the account whose oplog to retrieve.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "The DID of the account whose oplog to retrieve.",
              "format": "did"
            }
          },
          {
            "name": "since",
            "in": "query",
            "description": "Return operations after this revision.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "Return operations after this revision."
            }
          },
          {
            "name": "limit",
            "in": "query",
            "description": "Maximum number of operations to return.",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 1000,
              "default": 100
            }
          },
          {
            "name": "excludeValues",
            "in": "query",
            "description": "If true, omit inlined record values and return only operation metadata.",
            "required": false,
            "schema": {
              "type": "boolean",
              "description": "If true, omit inlined record values and return only operation metadata."
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "ops"
                  ],
                  "properties": {
                    "ops": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.space.listRepoOps.opEntry"
                      }
                    },
                    "commit": {
                      "$ref": "#/components/schemas/network.habitat.space.defs.signedCommit"
                    },
                    "cursor": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        },
                        {
                          "const": "RepoTakendown"
                        },
                        {
                          "const": "RepoSuspended"
                        },
                        {
                          "const": "RepoDeactivated"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.listRepos": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.listRepos",
        "description": "List the known repos that hold data in a space (the writer set), with each repo's current rev and commit hash. Served by the space host. This is the sync boundary, not an access-control list: it enumerates only writers, never readers. The set is what the authority claims from write notifications and is not itself authoritative; a repo's host is the source of truth.",
        "operationId": "network.habitat.space.listRepos",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "space",
            "in": "query",
            "description": "Reference to the space.",
            "required": true,
            "schema": {
              "type": "string",
              "description": "Reference to the space.",
              "format": "at-uri"
            }
          },
          {
            "name": "limit",
            "in": "query",
            "description": "Maximum number of repos to return.",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 1000,
              "default": 100
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "repos"
                  ],
                  "properties": {
                    "cursor": {
                      "type": "string"
                    },
                    "repos": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.space.listRepos.repo"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.listSpaces": {
      "get": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.listSpaces",
        "description": "List the spaces the authenticated user holds a repo in (i.e. spaces the user has written data to), optionally filtered by type and/or owner DID. Note this is not 'spaces I'm a member of' — a member's PDS only tracks spaces its user has written to. Requires auth, implemented by PDS.",
        "operationId": "network.habitat.space.listSpaces",
        "security": [
          {
            "Bearer": []
          }
        ],
        "parameters": [
          {
            "name": "type",
            "in": "query",
            "description": "Filter to spaces of this type. Required if the caller's OAuth scope is narrower than `space:*`.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "Filter to spaces of this type. Required if the caller's OAuth scope is narrower than `space:*`.",
              "format": "nsid"
            }
          },
          {
            "name": "did",
            "in": "query",
            "description": "Filter to spaces owned by this DID. Required if the caller's OAuth scope is narrower than `?did=*`.",
            "required": false,
            "schema": {
              "type": "string",
              "description": "Filter to spaces owned by this DID. Required if the caller's OAuth scope is narrower than `?did=*`.",
              "format": "did"
            }
          },
          {
            "name": "limit",
            "in": "query",
            "description": "The number of spaces to return.",
            "required": false,
            "schema": {
              "type": "integer",
              "minimum": 1,
              "maximum": 100,
              "default": 50
            }
          },
          {
            "name": "cursor",
            "in": "query",
            "required": false,
            "schema": {
              "type": "string"
            }
          }
        ],
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "spaces"
                  ],
                  "properties": {
                    "cursor": {
                      "type": "string"
                    },
                    "spaces": {
                      "type": "array",
                      "items": {
                        "$ref": "#/components/schemas/network.habitat.space.listSpaces.spaceView"
                      }
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.notifySpaceDeleted": {
      "post": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.notifySpaceDeleted",
        "description": "Notify a repo host or syncing service that a space has been deleted. Sent by the space authority, best-effort. Authenticated with service auth.",
        "operationId": "network.habitat.space.notifySpaceDeleted",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the deleted space.",
                    "format": "at-uri"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.notifyWrite": {
      "post": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.notifyWrite",
        "description": "Notify that a repo in a space has advanced to a new revision. Sent by a repo host to the space host, and forwarded to registered syncers. Best-effort. Authenticated with service auth.",
        "operationId": "network.habitat.space.notifyWrite",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space",
                  "repo",
                  "rev",
                  "hash"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space.",
                    "format": "at-uri"
                  },
                  "repo": {
                    "type": "string",
                    "description": "The DID of the account whose repo advanced.",
                    "format": "did"
                  },
                  "rev": {
                    "type": "string",
                    "description": "The revision of the write."
                  },
                  "hash": {
                    "type": "string",
                    "format": "byte",
                    "description": "The repo's current commit hash (sha256 of the LtHash state) after the write. Lets the space host maintain each repo's hash for listRepos."
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK"
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.putRecord": {
      "post": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.putRecord",
        "description": "Write a record in a permissioned space, creating or updating it as needed. Requires auth, implemented by PDS.",
        "operationId": "network.habitat.space.putRecord",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space",
                  "repo",
                  "collection",
                  "record"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space.",
                    "format": "at-uri"
                  },
                  "repo": {
                    "type": "string",
                    "description": "The DID of the repo to write to (the authenticated member).",
                    "format": "did"
                  },
                  "collection": {
                    "type": "string",
                    "description": "The NSID of the record collection.",
                    "format": "nsid"
                  },
                  "rkey": {
                    "type": "string",
                    "description": "The Record Key.",
                    "format": "record-key",
                    "maxLength": 512
                  },
                  "validate": {
                    "type": "boolean",
                    "description": "Can be set to 'false' to skip Lexicon schema validation of record data, 'true' to require it, or leave unset to validate only for known Lexicons."
                  },
                  "record": {}
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "uri",
                    "cid"
                  ],
                  "properties": {
                    "uri": {
                      "type": "string",
                      "description": "URI of the written record.",
                      "format": "at-uri"
                    },
                    "cid": {
                      "type": "string",
                      "format": "cid"
                    },
                    "validationStatus": {
                      "type": "string",
                      "enum": [
                        "valid",
                        "unknown"
                      ]
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    },
    "/network.habitat.space.registerNotify": {
      "post": {
        "tags": [
          "network.habitat.space"
        ],
        "summary": "network.habitat.space.registerNotify",
        "description": "Register an endpoint to be notified of writes. On a space host, subscribes to all repos in the space; on a repo host with a `repo`, subscribes to that repo only. Authenticated with a space credential.",
        "operationId": "network.habitat.space.registerNotify",
        "security": [
          {
            "Bearer": []
          }
        ],
        "requestBody": {
          "required": true,
          "content": {
            "application/json": {
              "schema": {
                "type": "object",
                "required": [
                  "space",
                  "endpoint"
                ],
                "properties": {
                  "space": {
                    "type": "string",
                    "description": "Reference to the space.",
                    "format": "at-uri"
                  },
                  "repo": {
                    "type": "string",
                    "description": "The DID of a specific repo to subscribe to (repo host). Omit to subscribe to the whole space (space host).",
                    "format": "did"
                  },
                  "endpoint": {
                    "type": "string",
                    "description": "The endpoint to which notifyWrite events should be delivered.",
                    "format": "uri"
                  }
                }
              }
            }
          }
        },
        "responses": {
          "200": {
            "description": "OK",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "expiresAt"
                  ],
                  "properties": {
                    "expiresAt": {
                      "type": "string",
                      "description": "When the registration expires.",
                      "format": "date-time"
                    }
                  }
                }
              }
            }
          },
          "400": {
            "description": "Bad Request",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "type": "string",
                      "oneOf": [
                        {
                          "const": "InvalidRequest"
                        },
                        {
                          "const": "ExpiredToken"
                        },
                        {
                          "const": "InvalidToken"
                        },
                        {
                          "const": "SpaceNotFound"
                        }
                      ]
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          },
          "401": {
            "description": "Unauthorized",
            "content": {
              "application/json": {
                "schema": {
                  "type": "object",
                  "required": [
                    "error",
                    "message"
                  ],
                  "properties": {
                    "error": {
                      "const": "AuthMissing"
                    },
                    "message": {
                      "type": "string"
                    }
                  }
                }
              }
            }
          }
        }
      }
    }
  },
  "components": {
    "schemas": {
      "community.opensocial.acceptance": {
        "type": "object",
        "required": [
          "updatedAt"
        ],
        "properties": {
          "updatedAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "community.opensocial.access": {
        "type": "object",
        "required": [
          "roles"
        ],
        "properties": {
          "roles": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "updatedAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "community.opensocial.defs.inviteView": {
        "type": "object",
        "description": "A pending invite to join the community, tracked in the org's invite table (not yet a repo record).",
        "required": [
          "id",
          "org",
          "invitee",
          "roles",
          "createdAt"
        ],
        "properties": {
          "id": {
            "type": "string",
            "description": "Opaque id of the invite, used to revoke it."
          },
          "org": {
            "type": "string",
            "description": "DID of the community the invite is for.",
            "format": "did"
          },
          "invitee": {
            "type": "string",
            "description": "DID of the invited user.",
            "format": "did"
          },
          "roles": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "createdAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "community.opensocial.membership": {
        "type": "object",
        "required": [
          "roles",
          "updatedAt"
        ],
        "properties": {
          "roles": {
            "type": "array",
            "items": {
              "type": "string"
            }
          },
          "updatedAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "community.opensocial.permissions": {
        "type": "object",
        "required": [
          "bindings",
          "assignable"
        ],
        "properties": {
          "bindings": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/community.opensocial.permissions.actionBinding"
            }
          },
          "assignable": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/community.opensocial.permissions.assignableBinding"
            }
          },
          "updatedAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "community.opensocial.permissions.actionBinding": {
        "type": "object",
        "required": [
          "action",
          "roles"
        ],
        "properties": {
          "action": {
            "type": "string",
            "description": "The action this binding authorizes.",
            "enum": [
              "invite",
              "eject",
              "role.assign",
              "space.create",
              "space.configure",
              "space.delete",
              "community.configure"
            ]
          },
          "roles": {
            "type": "array",
            "items": {
              "type": "string"
            }
          }
        }
      },
      "community.opensocial.permissions.assignableBinding": {
        "type": "object",
        "required": [
          "role",
          "roles"
        ],
        "properties": {
          "role": {
            "type": "string",
            "description": "Record key of the role this binding applies to."
          },
          "roles": {
            "type": "array",
            "items": {
              "type": "string"
            }
          }
        }
      },
      "community.opensocial.profile": {
        "type": "object",
        "required": [
          "name"
        ],
        "properties": {
          "name": {
            "type": "string",
            "description": "The community's display name.",
            "maxLength": 256
          },
          "description": {
            "type": "string",
            "description": "A short description of the community.",
            "maxLength": 2048
          },
          "avatar": {
            "type": "string",
            "format": "binary",
            "maxLength": 1000000
          },
          "updatedAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "community.opensocial.role": {
        "type": "object",
        "required": [
          "name"
        ],
        "properties": {
          "name": {
            "type": "string",
            "description": "Display name for the role, e.g. \"Admin\" or \"Moderator\".",
            "maxLength": 256
          },
          "description": {
            "type": "string",
            "maxLength": 2048
          },
          "updatedAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "community.opensocial.space": {
        "type": "object",
        "required": [
          "uri"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "description": "URI of the indexed space.",
            "format": "at-uri"
          },
          "updatedAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "network.habitat.docs.comment": {
        "type": "object",
        "required": [
          "body",
          "anchorStart",
          "anchorEnd",
          "createdAt"
        ],
        "properties": {
          "body": {
            "type": "string",
            "description": "The comment text.",
            "maxLength": 10000
          },
          "anchorStart": {
            "type": "string",
            "format": "byte",
            "description": "Yjs relative position (Y.encodeRelativePosition, applied to the doc's 'default' XML fragment) marking the start of the commented range. Together with anchorEnd and the document's current CRDT state, this is sufficient to resolve the exact range being commented on — an editor placing this comment needs no other context, and the position survives concurrent edits made anywhere else in the document the way a plain character offset would not.",
            "maxLength": 512
          },
          "anchorEnd": {
            "type": "string",
            "format": "byte",
            "description": "Yjs relative position marking the end of the commented range. See anchorStart.",
            "maxLength": 512
          },
          "quotedText": {
            "type": "string",
            "description": "A snapshot of the document text the anchor pointed to when the comment was created, shown as a fallback if the anchor no longer resolves to a valid range (e.g. the text was later deleted entirely).",
            "maxLength": 2000
          },
          "createdAt": {
            "type": "string",
            "description": "When the comment was written.",
            "format": "date-time"
          }
        }
      },
      "network.habitat.docs.commentReply": {
        "type": "object",
        "required": [
          "comment",
          "body",
          "createdAt"
        ],
        "properties": {
          "comment": {
            "$ref": "#/components/schemas/network.habitat.docs.commentReply.commentRef"
          },
          "body": {
            "type": "string",
            "description": "The reply text.",
            "maxLength": 10000
          },
          "createdAt": {
            "type": "string",
            "description": "When the reply was written.",
            "format": "date-time"
          }
        }
      },
      "network.habitat.docs.commentReply.commentRef": {
        "type": "object",
        "description": "A URI with a content-hash fingerprint — the same shape as com.atproto.repo.strongRef, defined locally for now because lexgen doesn't generate Go bindings for com.atproto.* refs.",
        "required": [
          "uri",
          "cid"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "format": "at-uri"
          },
          "cid": {
            "type": "string",
            "format": "cid"
          }
        }
      },
      "network.habitat.docs.crdt": {
        "type": "object",
        "required": [
          "blob"
        ],
        "properties": {
          "blob": {
            "type": "string",
            "description": "Base64-encoded Yjs state update representing the document content."
          }
        }
      },
      "network.habitat.docs.listDocs.docView": {
        "type": "object",
        "required": [
          "docId",
          "uri",
          "title"
        ],
        "properties": {
          "docId": {
            "type": "string",
            "description": "The doc's space key, used as the document identifier in updateDoc and routing."
          },
          "uri": {
            "type": "string",
            "description": "URI of the doc's space."
          },
          "title": {
            "type": "string",
            "description": "The document title, from its markdown 'self' record."
          }
        }
      },
      "network.habitat.docs.markdown": {
        "type": "object",
        "required": [
          "title",
          "content"
        ],
        "properties": {
          "title": {
            "type": "string",
            "description": "The document title, derived from the first heading or line."
          },
          "content": {
            "type": "string",
            "description": "The rendered markdown content of the document."
          }
        }
      },
      "network.habitat.group.profile": {
        "type": "object",
        "required": [
          "name"
        ],
        "properties": {
          "name": {
            "type": "string",
            "maxLength": 256
          },
          "description": {
            "type": "string",
            "maxLength": 2048
          },
          "createdAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "network.habitat.groups.defs.groupView": {
        "type": "object",
        "description": "A group, backed by a network.habitat.group space, with its membership resolved. Membership is the set of users holding at least the writer role on the group-space, expanded through inherited groups.",
        "required": [
          "uri",
          "name",
          "isMember",
          "canManage"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "description": "URI of the group-space.",
            "format": "uri"
          },
          "name": {
            "type": "string"
          },
          "description": {
            "type": "string"
          },
          "createdAt": {
            "type": "string",
            "format": "date-time"
          },
          "memberCount": {
            "type": "integer"
          },
          "isMember": {
            "type": "boolean",
            "description": "Whether the calling user is a member of this group."
          },
          "canManage": {
            "type": "boolean",
            "description": "Whether the calling user can manage this group (add members, edit it)."
          },
          "members": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/network.habitat.groups.defs.memberView"
            }
          },
          "inheritedGroups": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/network.habitat.groups.defs.groupRef"
            }
          }
        }
      },
      "network.habitat.groups.defs.memberView": {
        "type": "object",
        "required": [
          "did",
          "direct"
        ],
        "properties": {
          "did": {
            "type": "string",
            "format": "did"
          },
          "role": {
            "type": "string",
            "description": "Role held on the group-space (owner|manager|writer|reader)."
          },
          "direct": {
            "type": "boolean",
            "description": "True if the member is granted a role directly on this group, false if the membership is inherited from another group."
          },
          "viaGroup": {
            "type": "string",
            "description": "If inherited, the URI of the group-space the membership came from.",
            "format": "uri"
          }
        }
      },
      "network.habitat.groups.defs.groupRef": {
        "type": "object",
        "required": [
          "uri",
          "name"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "format": "uri"
          },
          "name": {
            "type": "string"
          }
        }
      },
      "network.habitat.listConnectedApps.app": {
        "type": "object",
        "required": [
          "name",
          "clientID",
          "clientUri",
          "lastUsed"
        ],
        "properties": {
          "name": {
            "type": "string",
            "description": "The name of this app."
          },
          "clientID": {
            "type": "string",
            "description": "The ID of this app."
          },
          "clientUri": {
            "type": "string",
            "description": "The uri of this app."
          },
          "lastUsed": {
            "type": "string",
            "description": "The last time habitat detected a session with this app.",
            "format": "date-time"
          },
          "logoUri": {
            "type": "string",
            "description": "The logo URI of this app."
          }
        }
      },
      "network.habitat.org.getAdmins.member": {
        "type": "object",
        "required": [
          "did",
          "handle"
        ],
        "properties": {
          "did": {
            "type": "string",
            "format": "did"
          },
          "handle": {
            "type": "string"
          }
        }
      },
      "network.habitat.org.getMembers.member": {
        "type": "object",
        "required": [
          "did",
          "handle"
        ],
        "properties": {
          "did": {
            "type": "string",
            "format": "did"
          },
          "handle": {
            "type": "string"
          }
        }
      },
      "network.habitat.photo": {
        "type": "object",
        "required": [
          "ref"
        ],
        "properties": {
          "ref": {
            "type": "string",
            "format": "binary"
          },
          "createdAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "network.habitat.relationship.listRelations.userRelationView": {
        "type": "object",
        "description": "A user relation record together with its URI.",
        "required": [
          "uri",
          "subject",
          "relation",
          "object"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "description": "URI of the relation record."
          },
          "subject": {
            "type": "string",
            "description": "DID of the user the role is granted to.",
            "format": "did"
          },
          "relation": {
            "type": "string"
          },
          "object": {
            "type": "string",
            "description": "URI of the space the role is granted on.",
            "format": "uri"
          }
        }
      },
      "network.habitat.relationship.listRelations.spaceRelationView": {
        "type": "object",
        "description": "A space relation record together with its URI.",
        "required": [
          "uri",
          "subject",
          "subjectRole",
          "relation",
          "object"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "description": "URI of the relation record."
          },
          "subject": {
            "type": "string",
            "description": "URI of the subject space (or group-space) whose role-holders form the userset.",
            "format": "uri"
          },
          "subjectRole": {
            "type": "string",
            "description": "The role held on the subject space, forming the userset."
          },
          "relation": {
            "type": "string"
          },
          "object": {
            "type": "string",
            "description": "URI of the space the role is granted on.",
            "format": "uri"
          }
        }
      },
      "network.habitat.relationship.spaceRelation": {
        "type": "object",
        "required": [
          "subject",
          "subjectRole",
          "relation"
        ],
        "properties": {
          "subject": {
            "type": "string",
            "description": "URI of the subject space (or group-space) whose role-holders form the userset.",
            "format": "uri"
          },
          "subjectRole": {
            "type": "string",
            "description": "The role held on the subject space, forming the userset."
          },
          "relation": {
            "type": "string",
            "description": "Role granted on the object space (owner|manager|writer|reader).",
            "enum": [
              "owner",
              "manager",
              "writer",
              "reader"
            ]
          },
          "createdAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "network.habitat.relationship.userRelation": {
        "type": "object",
        "required": [
          "subject",
          "relation"
        ],
        "properties": {
          "subject": {
            "type": "string",
            "description": "DID of the user the role is granted to.",
            "format": "did"
          },
          "relation": {
            "type": "string",
            "description": "Role granted on the object space (owner|manager|writer|reader).",
            "enum": [
              "owner",
              "manager",
              "writer",
              "reader"
            ]
          },
          "createdAt": {
            "type": "string",
            "format": "date-time"
          }
        }
      },
      "network.habitat.render.schema": {
        "type": "object",
        "required": [
          "targetLexicon",
          "title",
          "fields"
        ],
        "properties": {
          "targetLexicon": {
            "type": "string",
            "description": "The NSID of the lexicon this render schema applies to."
          },
          "title": {
            "type": "string",
            "description": "Human-readable name for this record type."
          },
          "description": {
            "type": "string",
            "description": "A brief description of what this record type represents."
          },
          "fields": {
            "type": "array",
            "items": {
              "$ref": "#/components/schemas/network.habitat.render.schema.fieldSchema"
            }
          }
        }
      },
      "network.habitat.render.schema.fieldSchema": {
        "type": "object",
        "description": "Describes how to display a single field of a record.",
        "required": [
          "path",
          "label",
          "displayType",
          "priority"
        ],
        "properties": {
          "path": {
            "type": "string",
            "description": "Dot-notation path into the record value (e.g. 'name', 'startsAt')."
          },
          "label": {
            "type": "string",
            "description": "Human-readable label for this field."
          },
          "displayType": {
            "type": "string",
            "description": "How to render the value.",
            "enum": [
              "network.habitat.render.schema#text",
              "network.habitat.render.schema#datetime",
              "network.habitat.render.schema#url",
              "network.habitat.render.schema#badge",
              "network.habitat.render.schema#list"
            ]
          },
          "priority": {
            "type": "string",
            "description": "Layout prominence of this field.",
            "enum": [
              "network.habitat.render.schema#primary",
              "network.habitat.render.schema#secondary",
              "network.habitat.render.schema#metadata"
            ]
          },
          "optional": {
            "type": "boolean",
            "description": "If true, omit this field from display when its value is missing or empty."
          }
        }
      },
      "network.habitat.render.schema.text": {
        "type": "string",
        "format": "token",
        "description": "Render as plain text."
      },
      "network.habitat.render.schema.datetime": {
        "type": "string",
        "format": "token",
        "description": "Render as a formatted date/time string."
      },
      "network.habitat.render.schema.url": {
        "type": "string",
        "format": "token",
        "description": "Render as a hyperlink."
      },
      "network.habitat.render.schema.badge": {
        "type": "string",
        "format": "token",
        "description": "Render as a pill badge, extracting the token name from an NSID#token value."
      },
      "network.habitat.render.schema.list": {
        "type": "string",
        "format": "token",
        "description": "Render as a list of items."
      },
      "network.habitat.render.schema.primary": {
        "type": "string",
        "format": "token",
        "description": "Most prominent display — used for the record's main identifier (e.g. title)."
      },
      "network.habitat.render.schema.secondary": {
        "type": "string",
        "format": "token",
        "description": "Standard field-value display."
      },
      "network.habitat.render.schema.metadata": {
        "type": "string",
        "format": "token",
        "description": "De-emphasized display, shown at the bottom or collapsed."
      },
      "network.habitat.search.query.resultView": {
        "type": "object",
        "required": [
          "uri",
          "spaceUri",
          "recordType"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "description": "URI of the matched record."
          },
          "spaceUri": {
            "type": "string",
            "description": "URI of the space the record belongs to."
          },
          "recordType": {
            "type": "string",
            "description": "The NSID of the record type.",
            "format": "nsid"
          },
          "snippet": {
            "type": "string",
            "description": "A highlighted excerpt of the matching content."
          },
          "rank": {
            "type": "integer"
          }
        }
      },
      "network.habitat.simplespace.defs.spaceConfig": {
        "type": "object",
        "description": "Configuration for a space managed by the simplespace implementation. A credential is minted only when the user is authorized by `policy` and their app by `appAccess`.",
        "required": [
          "policy",
          "appAccess"
        ],
        "properties": {
          "policy": {
            "type": "string",
            "description": "How the authority decides whether to authorize a requesting user. 'member-list' (default) consults the member list, 'public' authorizes anyone, 'managing-app' asks the managingApp via checkUserAccess.",
            "enum": [
              "public",
              "member-list",
              "managing-app"
            ]
          },
          "appAccess": {
            "oneOf": [
              {
                "$ref": "#/components/schemas/network.habitat.simplespace.defs.open"
              },
              {
                "$ref": "#/components/schemas/network.habitat.simplespace.defs.allowList"
              }
            ]
          },
          "managingApp": {
            "type": "string",
            "description": "Service identifier (e.g. did:web:example.com#forum) of the app that manages this space. Routes application-level requests and is the checkUserAccess target when policy is 'managing-app'."
          }
        }
      },
      "network.habitat.simplespace.defs.open": {
        "type": "object",
        "description": "App access policy: any app may access the space. No client attestation required.",
        "properties": {}
      },
      "network.habitat.simplespace.defs.allowList": {
        "type": "object",
        "description": "App access policy: only the named clients may access the space, evaluated against the attested client_id.",
        "required": [
          "allowed"
        ],
        "properties": {
          "allowed": {
            "type": "array",
            "items": {
              "type": "string",
              "description": "An OAuth client ID."
            }
          }
        }
      },
      "network.habitat.simplespace.listMembers.member": {
        "type": "object",
        "required": [
          "did"
        ],
        "properties": {
          "did": {
            "type": "string",
            "format": "did"
          }
        }
      },
      "network.habitat.space.appAccess": {
        "type": "object",
        "properties": {
          "note": {
            "type": "string",
            "description": "Optional human-readable label for this grant, for admin display. Not used for enforcement.",
            "maxLength": 640
          },
          "createdAt": {
            "type": "string",
            "format": "date-time"
          },
          "scopes": {
            "type": "array",
            "items": {
              "type": "string"
            }
          }
        }
      },
      "network.habitat.space.defs.signedCommit": {
        "type": "object",
        "description": "A signed commit over the current state of a permissioned repo.",
        "required": [
          "ver",
          "hash",
          "mac",
          "ikm",
          "sig",
          "rev"
        ],
        "properties": {
          "ver": {
            "type": "integer"
          },
          "habitatSigned": {
            "type": "boolean",
            "description": "True if sig was produced by the space host's key rather than the author's own key."
          },
          "hash": {
            "type": "string",
            "format": "byte",
            "description": "sha256 digest of the LtHash state (32 bytes)."
          },
          "ikm": {
            "type": "string",
            "format": "byte",
            "description": "Per-signature input keying material (32 random bytes)"
          },
          "sig": {
            "type": "string",
            "format": "byte",
            "description": "Signature over ctx (space, author DID, rev, ikm) by the user's atproto signing key. Does not cover the repo hash."
          },
          "mac": {
            "type": "string",
            "format": "byte",
            "description": "HMAC-SHA256 over hash, keyed by HKDF-SHA256(ikm, info=ctx). Binds the repo hash to this commit's context."
          },
          "rev": {
            "type": "string",
            "description": "Commit revision (TID), also bound into ctx."
          }
        }
      },
      "network.habitat.space.listRecords.record": {
        "type": "object",
        "required": [
          "collection",
          "rkey",
          "cid"
        ],
        "properties": {
          "collection": {
            "type": "string",
            "format": "nsid"
          },
          "rkey": {
            "type": "string",
            "format": "record-key"
          },
          "cid": {
            "type": "string",
            "format": "cid"
          },
          "value": {}
        }
      },
      "network.habitat.space.listRepoOps.opEntry": {
        "type": "object",
        "description": "A single operation in a permissioned repo's oplog. cid is null for deletes; prev is null for creates. Operations sharing the same rev belong to the same batch. value carries the record's current value for creates and updates, unless excludeValues was set or the value is stale (superseded by a later operation).",
        "required": [
          "rev",
          "collection",
          "rkey",
          "cid",
          "prev"
        ],
        "properties": {
          "rev": {
            "type": "string"
          },
          "collection": {
            "type": "string",
            "format": "nsid"
          },
          "rkey": {
            "type": "string",
            "format": "record-key"
          },
          "cid": {
            "type": "string",
            "format": "cid"
          },
          "prev": {
            "type": "string",
            "format": "cid"
          },
          "value": {}
        }
      },
      "network.habitat.space.listRepos.repo": {
        "type": "object",
        "required": [
          "did"
        ],
        "properties": {
          "did": {
            "type": "string",
            "description": "The DID of a repo that holds data in the space.",
            "format": "did"
          },
          "rev": {
            "type": "string",
            "description": "The repo's current revision (TID), as last reported to the authority. May lag the repo host, which is the source of truth."
          },
          "hash": {
            "type": "string",
            "format": "byte",
            "description": "The repo's current commit hash (sha256 of the LtHash state), as last reported to the authority."
          }
        }
      },
      "network.habitat.space.listSpaces.spaceView": {
        "type": "object",
        "required": [
          "uri",
          "isOwner"
        ],
        "properties": {
          "uri": {
            "type": "string",
            "description": "URI of the space.",
            "format": "at-uri"
          },
          "isOwner": {
            "type": "boolean",
            "description": "Whether the authenticated user is the owner of the space."
          }
        }
      }
    },
    "securitySchemes": {
      "Bearer": {
        "type": "http",
        "scheme": "bearer"
      }
    }
  },
  "tags": [
    {
      "name": "community.opensocial.acceptance"
    },
    {
      "name": "community.opensocial.access"
    },
    {
      "name": "community.opensocial.assignRoles"
    },
    {
      "name": "community.opensocial.createInvite"
    },
    {
      "name": "community.opensocial.createSpace"
    },
    {
      "name": "community.opensocial.defs"
    },
    {
      "name": "community.opensocial.deleteRole"
    },
    {
      "name": "community.opensocial.ejectMember"
    },
    {
      "name": "community.opensocial.listInvites"
    },
    {
      "name": "community.opensocial.listPendingInvites"
    },
    {
      "name": "community.opensocial.membership"
    },
    {
      "name": "community.opensocial.permissions"
    },
    {
      "name": "community.opensocial.profile"
    },
    {
      "name": "community.opensocial.putRole"
    },
    {
      "name": "community.opensocial.requestJoin"
    },
    {
      "name": "community.opensocial.revokeInvite"
    },
    {
      "name": "community.opensocial.role"
    },
    {
      "name": "community.opensocial.space"
    },
    {
      "name": "community.opensocial.updatePermissions"
    },
    {
      "name": "community.opensocial.updateProfile"
    },
    {
      "name": "community.opensocial.updateSpace"
    },
    {
      "name": "community.opensocial.uploadImage"
    },
    {
      "name": "network.habitat.admin"
    },
    {
      "name": "network.habitat.docs"
    },
    {
      "name": "network.habitat.group"
    },
    {
      "name": "network.habitat.groups"
    },
    {
      "name": "network.habitat.instance"
    },
    {
      "name": "network.habitat.internal"
    },
    {
      "name": "network.habitat.listConnectedApps"
    },
    {
      "name": "network.habitat.opensocial"
    },
    {
      "name": "network.habitat.org"
    },
    {
      "name": "network.habitat.photo"
    },
    {
      "name": "network.habitat.relationship"
    },
    {
      "name": "network.habitat.render"
    },
    {
      "name": "network.habitat.repo"
    },
    {
      "name": "network.habitat.search"
    },
    {
      "name": "network.habitat.simplespace"
    },
    {
      "name": "network.habitat.space"
    }
  ]
}
