Forgejo (codeberg.org, self-served Swagger 2.0): spec vs live

Summary

Spec
https://codeberg.org/swagger.v1.json (Swagger 2.0, converted to OpenAPI 3 before checking)
Base URL
https://codeberg.org/api/v1
Run
, read-only GET requests, no credentials
Coverage
506 operations in the spec, 40 requests sent, 16 successful,38 operations observed
Hard violations
23 distinct schema locations
Reviewer note
Same drift as Gitea (Forgejo fork), plus repo.parent null on feeds.

Hard violations 23

A typed client generated from the spec would break on these.

Hide 23 findings
GET /orgs/{org}/activities/feeds > response 200 > application/json > /0/comment/user

response body at /0/comment/user: value is null but the schema does not allow null (and 14 more like it)

GET /orgs/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/comment/user.
  • If the implementation is the source of truth: Allow null at paths["/orgs/{org}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["comment"].properties["user"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /orgs/{org}/activities/feeds > response 200 > application/json > /0/repo/parent

response body at /0/repo/parent: value is null but the schema does not allow null (and 29 more like it)

GET /orgs/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/repo/parent.
  • If the implementation is the source of truth: Allow null at paths["/orgs/{org}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["repo"].properties["parent"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /orgs/{org}/activities/feeds > response 200 > application/json > /0/repo/repo_transfer

response body at /0/repo/repo_transfer: value is null but the schema does not allow null (and 29 more like it)

GET /orgs/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/repo/repo_transfer.
  • If the implementation is the source of truth: Allow null at paths["/orgs/{org}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["repo"].properties["repo_transfer"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /orgs/{org}/activities/feeds > response 200 > application/json > /5/comment

response body at /5/comment: value is null but the schema does not allow null (and 14 more like it)

GET /orgs/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /5/comment.
  • If the implementation is the source of truth: Allow null at paths["/orgs/{org}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["comment"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /orgs/{org}/repos > response 200 > application/json > /0/parent

response body at /0/parent: value is null but the schema does not allow null (and 19 more like it)

GET /orgs/forgejo/repos → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/parent.
  • If the implementation is the source of truth: Allow null at paths["/orgs/{org}/repos"].get.responses["200"].content["application/json"].schema.items.properties["parent"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /orgs/{org}/repos > response 200 > application/json > /0/repo_transfer

response body at /0/repo_transfer: value is null but the schema does not allow null (and 19 more like it)

GET /orgs/forgejo/repos → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/repo_transfer.
  • If the implementation is the source of truth: Allow null at paths["/orgs/{org}/repos"].get.responses["200"].content["application/json"].schema.items.properties["repo_transfer"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /packages/{owner} > response 200 > application/json > /0/repository/parent

response body at /0/repository/parent: value is null but the schema does not allow null (and 29 more like it)

GET /packages/forgejo → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/repository/parent.
  • If the implementation is the source of truth: Allow null at paths["/packages/{owner}"].get.responses["200"].content["application/json"].schema.items.properties["repository"].properties["parent"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /packages/{owner} > response 200 > application/json > /0/repository/repo_transfer

response body at /0/repository/repo_transfer: value is null but the schema does not allow null (and 29 more like it)

GET /packages/forgejo → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/repository/repo_transfer.
  • If the implementation is the source of truth: Allow null at paths["/packages/{owner}"].get.responses["200"].content["application/json"].schema.items.properties["repository"].properties["repo_transfer"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo} > response 200 > application/json > /parent

response body at /parent: value is null but the schema does not allow null

GET /repos/forgejo/forgejo → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /parent.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}"].get.responses["200"].content["application/json"].schema.properties["parent"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo} > response 200 > application/json > /repo_transfer

response body at /repo_transfer: value is null but the schema does not allow null

GET /repos/forgejo/forgejo → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /repo_transfer.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}"].get.responses["200"].content["application/json"].schema.properties["repo_transfer"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/activities/feeds > response 200 > application/json > /0/comment/user

response body at /0/comment/user: value is null but the schema does not allow null (and 24 more like it)

GET /repos/forgejo/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/comment/user.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["comment"].properties["user"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/activities/feeds > response 200 > application/json > /0/repo/parent

response body at /0/repo/parent: value is null but the schema does not allow null (and 29 more like it)

GET /repos/forgejo/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/repo/parent.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["repo"].properties["parent"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/activities/feeds > response 200 > application/json > /0/repo/repo_transfer

response body at /0/repo/repo_transfer: value is null but the schema does not allow null (and 29 more like it)

GET /repos/forgejo/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/repo/repo_transfer.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["repo"].properties["repo_transfer"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/activities/feeds > response 200 > application/json > /6/comment

response body at /6/comment: value is null but the schema does not allow null (and 4 more like it)

GET /repos/forgejo/forgejo/activities/feeds → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /6/comment.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["comment"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches > response 200 > application/json > /0/commit/added

response body at /0/commit/added: value is null but the schema does not allow null (and 29 more like it)

GET /repos/forgejo/forgejo/branches → 200 application/json;charset=utf-8
expected ["array"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/commit/added.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches"].get.responses["200"].content["application/json"].schema.items.properties["commit"].properties["added"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches > response 200 > application/json > /0/commit/modified

response body at /0/commit/modified: value is null but the schema does not allow null (and 29 more like it)

GET /repos/forgejo/forgejo/branches → 200 application/json;charset=utf-8
expected ["array"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/commit/modified.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches"].get.responses["200"].content["application/json"].schema.items.properties["commit"].properties["modified"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches > response 200 > application/json > /0/commit/removed

response body at /0/commit/removed: value is null but the schema does not allow null (and 29 more like it)

GET /repos/forgejo/forgejo/branches → 200 application/json;charset=utf-8
expected ["array"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/commit/removed.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches"].get.responses["200"].content["application/json"].schema.items.properties["commit"].properties["removed"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches > response 200 > application/json > /0/commit/verification/signer

response body at /0/commit/verification/signer: value is null but the schema does not allow null (and 17 more like it)

GET /repos/forgejo/forgejo/branches → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/commit/verification/signer.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches"].get.responses["200"].content["application/json"].schema.items.properties["commit"].properties["verification"].properties["signer"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches/{branch} > response 200 > application/json > /commit/added

response body at /commit/added: value is null but the schema does not allow null

GET /repos/forgejo/forgejo/branches/forgejo → 200 application/json;charset=utf-8
expected ["array"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /commit/added.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches/{branch}"].get.responses["200"].content["application/json"].schema.properties["commit"].properties["added"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches/{branch} > response 200 > application/json > /commit/modified

response body at /commit/modified: value is null but the schema does not allow null

GET /repos/forgejo/forgejo/branches/forgejo → 200 application/json;charset=utf-8
expected ["array"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /commit/modified.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches/{branch}"].get.responses["200"].content["application/json"].schema.properties["commit"].properties["modified"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches/{branch} > response 200 > application/json > /commit/removed

response body at /commit/removed: value is null but the schema does not allow null

GET /repos/forgejo/forgejo/branches/forgejo → 200 application/json;charset=utf-8
expected ["array"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /commit/removed.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches/{branch}"].get.responses["200"].content["application/json"].schema.properties["commit"].properties["removed"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/branches/{branch} > response 200 > application/json > /commit/verification/signer

response body at /commit/verification/signer: value is null but the schema does not allow null

GET /repos/forgejo/forgejo/branches/forgejo → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /commit/verification/signer.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/branches/{branch}"].get.responses["200"].content["application/json"].schema.properties["commit"].properties["verification"].properties["signer"] (add "null" to type, or nullable: true in OpenAPI 3.0).
GET /repos/{owner}/{repo}/commits > response 200 > application/json > /0/commit/verification/signer

response body at /0/commit/verification/signer: value is null but the schema does not allow null (and 26 more like it)

GET /repos/forgejo/forgejo/commits → 200 application/json;charset=utf-8
expected ["object"] actual null
  • If the spec is the source of truth: Return a non-null value in response body at /0/commit/verification/signer.
  • If the implementation is the source of truth: Allow null at paths["/repos/{owner}/{repo}/commits"].get.responses["200"].content["application/json"].schema.items.properties["commit"].properties["verification"].properties["signer"] (add "null" to type, or nullable: true in OpenAPI 3.0).

Other body findings 12

Undocumented fields and loose constraints on successful responses. Documentation gaps, not violations.

Hide 12 findings
GET /orgs/{org}/activities/feeds > response 200 > application/json > /0/act_user/username

response body at /0/act_user/username: property "username" is not documented (and 29 more like it)

GET /orgs/forgejo/activities/feeds → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /orgs/{org}/activities/feeds if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/orgs/{org}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["act_user"].properties.
GET /orgs/{org}/activities/feeds > response 200 > application/json > /0/repo/owner/username

response body at /0/repo/owner/username: property "username" is not documented (and 29 more like it)

GET /orgs/forgejo/activities/feeds → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /orgs/{org}/activities/feeds if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/orgs/{org}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["repo"].properties["owner"].properties.
GET /orgs/{org}/public_members > response 200 > application/json > /0/username

response body at /0/username: property "username" is not documented (and 29 more like it)

GET /orgs/forgejo/public_members → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /orgs/{org}/public_members if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/orgs/{org}/public_members"].get.responses["200"].content["application/json"].schema.items.properties.
GET /orgs/{org}/repos > response 200 > application/json > /0/owner/username

response body at /0/owner/username: property "username" is not documented (and 19 more like it)

GET /orgs/forgejo/repos → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /orgs/{org}/repos if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/orgs/{org}/repos"].get.responses["200"].content["application/json"].schema.items.properties["owner"].properties.
GET /packages/{owner} > response 200 > application/json > /0/creator/username

response body at /0/creator/username: property "username" is not documented (and 29 more like it)

GET /packages/forgejo → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /packages/{owner} if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/packages/{owner}"].get.responses["200"].content["application/json"].schema.items.properties["creator"].properties.
GET /packages/{owner} > response 200 > application/json > /0/owner/username

response body at /0/owner/username: property "username" is not documented (and 29 more like it)

GET /packages/forgejo → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /packages/{owner} if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/packages/{owner}"].get.responses["200"].content["application/json"].schema.items.properties["owner"].properties.
GET /packages/{owner} > response 200 > application/json > /0/repository/owner/username

response body at /0/repository/owner/username: property "username" is not documented (and 29 more like it)

GET /packages/forgejo → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /packages/{owner} if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/packages/{owner}"].get.responses["200"].content["application/json"].schema.items.properties["repository"].properties["owner"].properties.
GET /repos/{owner}/{repo} > response 200 > application/json > /owner/username

response body at /owner/username: property "username" is not documented

GET /repos/forgejo/forgejo → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /repos/{owner}/{repo} if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/repos/{owner}/{repo}"].get.responses["200"].content["application/json"].schema.properties["owner"].properties.
GET /repos/{owner}/{repo}/activities/feeds > response 200 > application/json > /0/act_user/username

response body at /0/act_user/username: property "username" is not documented (and 29 more like it)

GET /repos/forgejo/forgejo/activities/feeds → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /repos/{owner}/{repo}/activities/feeds if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/repos/{owner}/{repo}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["act_user"].properties.
GET /repos/{owner}/{repo}/activities/feeds > response 200 > application/json > /0/repo/owner/username

response body at /0/repo/owner/username: property "username" is not documented (and 29 more like it)

GET /repos/forgejo/forgejo/activities/feeds → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /repos/{owner}/{repo}/activities/feeds if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/repos/{owner}/{repo}/activities/feeds"].get.responses["200"].content["application/json"].schema.items.properties["repo"].properties["owner"].properties.
GET /repos/{owner}/{repo}/commits > response 200 > application/json > /0/author/username

response body at /0/author/username: property "username" is not documented (and 29 more like it)

GET /repos/forgejo/forgejo/commits → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /repos/{owner}/{repo}/commits if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/repos/{owner}/{repo}/commits"].get.responses["200"].content["application/json"].schema.items.properties["author"].properties.
GET /repos/{owner}/{repo}/commits > response 200 > application/json > /0/committer/username

response body at /0/committer/username: property "username" is not documented (and 29 more like it)

GET /repos/forgejo/forgejo/commits → 200 application/json;charset=utf-8
actual "username"
  • If the spec is the source of truth: Stop returning "username" from GET /repos/{owner}/{repo}/commits if it is not part of the contract.
  • If the implementation is the source of truth: Add "username" to paths["/repos/{owner}/{repo}/commits"].get.responses["200"].content["application/json"].schema.items.properties["committer"].properties.

Undocumented error responses 18

3xx and 4xx statuses the spec does not mention, usually auth or not-found cases.

Show 18 findings
errorsundocumented-statusbreaking
GET /actions/run > response 403

status 403 is not documented for "GET /actions/run"

GET /actions/run → 403 application/json;charset=utf-8
expected ["200"] actual 403
  • If the spec is the source of truth: Return one of the documented statuses (200) from GET /actions/run.
  • If the implementation is the source of truth: Add a "403" response under paths["/actions/run"].get.responses.
errorsundocumented-statusbreaking
GET /activitypub/actor > response 404

status 404 is not documented for "GET /activitypub/actor"

GET /activitypub/actor → 404 text/plain; charset=utf-8
expected ["200"] actual 404
  • If the spec is the source of truth: Return one of the documented statuses (200) from GET /activitypub/actor.
  • If the implementation is the source of truth: Add a "404" response under paths["/activitypub/actor"].get.responses.
errorsundocumented-statusbreaking
GET /nodeinfo > response 404

status 404 is not documented for "GET /nodeinfo"

GET /nodeinfo → 404 text/plain; charset=utf-8
expected ["200"] actual 404
  • If the spec is the source of truth: Return one of the documented statuses (200) from GET /nodeinfo.
  • If the implementation is the source of truth: Add a "404" response under paths["/nodeinfo"].get.responses.
errorsundocumented-statusbreaking
GET /orgs/{org}/labels/{id} > response 401

status 401 is not documented for "GET /orgs/{org}/labels/{id}"

GET /orgs/forgejo/labels/1 → 401 application/json;charset=utf-8
expected ["200","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 404) from GET /orgs/{org}/labels/{id}.
  • If the implementation is the source of truth: Add a "401" response under paths["/orgs/{org}/labels/{id}"].get.responses.
errorsundocumented-statusbreaking
GET /orgs/{org}/list_blocked > response 401

status 401 is not documented for "GET /orgs/{org}/list_blocked"

GET /orgs/forgejo/list_blocked → 401 application/json;charset=utf-8
expected ["200"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200) from GET /orgs/{org}/list_blocked.
  • If the implementation is the source of truth: Add a "401" response under paths["/orgs/{org}/list_blocked"].get.responses.
errorsundocumented-statusbreaking
GET /orgs/{org}/quota > response 401

status 401 is not documented for "GET /orgs/{org}/quota"

GET /orgs/forgejo/quota → 401 application/json;charset=utf-8
expected ["200","403","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 403, 404) from GET /orgs/{org}/quota.
  • If the implementation is the source of truth: Add a "401" response under paths["/orgs/{org}/quota"].get.responses.
errorsundocumented-statusbreaking
GET /orgs/{org}/quota/artifacts > response 401

status 401 is not documented for "GET /orgs/{org}/quota/artifacts"

GET /orgs/forgejo/quota/artifacts → 401 application/json;charset=utf-8
expected ["200","403","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 403, 404) from GET /orgs/{org}/quota/artifacts.
  • If the implementation is the source of truth: Add a "401" response under paths["/orgs/{org}/quota/artifacts"].get.responses.
errorsundocumented-statusbreaking
GET /orgs/{org}/quota/attachments > response 401

status 401 is not documented for "GET /orgs/{org}/quota/attachments"

GET /orgs/forgejo/quota/attachments → 401 application/json;charset=utf-8
expected ["200","403","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 403, 404) from GET /orgs/{org}/quota/attachments.
  • If the implementation is the source of truth: Add a "401" response under paths["/orgs/{org}/quota/attachments"].get.responses.
errorsundocumented-statusbreaking
GET /orgs/{org}/quota/packages > response 401

status 401 is not documented for "GET /orgs/{org}/quota/packages"

GET /orgs/forgejo/quota/packages → 401 application/json;charset=utf-8
expected ["200","403","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 403, 404) from GET /orgs/{org}/quota/packages.
  • If the implementation is the source of truth: Add a "401" response under paths["/orgs/{org}/quota/packages"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/actions/runners > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/actions/runners"

GET /repos/forgejo/forgejo/actions/runners → 401 application/json;charset=utf-8
expected ["200","400","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 400, 404) from GET /repos/{owner}/{repo}/actions/runners.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/actions/runners"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/actions/runners/jobs > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/actions/runners/jobs"

GET /repos/forgejo/forgejo/actions/runners/jobs → 401 application/json;charset=utf-8
expected ["200","403"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 403) from GET /repos/{owner}/{repo}/actions/runners/jobs.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/actions/runners/jobs"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/actions/runners/registration-token > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/actions/runners/registration-token"

GET /repos/forgejo/forgejo/actions/runners/registration-token → 401 application/json;charset=utf-8
expected ["200"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200) from GET /repos/{owner}/{repo}/actions/runners/registration-token.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/actions/runners/registration-token"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/actions/secrets > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/actions/secrets"

GET /repos/forgejo/forgejo/actions/secrets → 401 application/json;charset=utf-8
expected ["200","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 404) from GET /repos/{owner}/{repo}/actions/secrets.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/actions/secrets"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/actions/variables > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/actions/variables"

GET /repos/forgejo/forgejo/actions/variables → 401 application/json;charset=utf-8
expected ["200","400","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 400, 404) from GET /repos/{owner}/{repo}/actions/variables.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/actions/variables"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/assignees > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/assignees"

GET /repos/forgejo/forgejo/assignees → 401 application/json;charset=utf-8
expected ["200","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 404) from GET /repos/{owner}/{repo}/assignees.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/assignees"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/branch_protections > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/branch_protections"

GET /repos/forgejo/forgejo/branch_protections → 401 application/json;charset=utf-8
expected ["200"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200) from GET /repos/{owner}/{repo}/branch_protections.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/branch_protections"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/branch_protections/{name} > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/branch_protections/{name}"

GET /repos/forgejo/forgejo/branch_protections/forgejo → 401 application/json;charset=utf-8
expected ["200","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 404) from GET /repos/{owner}/{repo}/branch_protections/{name}.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/branch_protections/{name}"].get.responses.
errorsundocumented-statusbreaking
GET /repos/{owner}/{repo}/collaborators > response 401

status 401 is not documented for "GET /repos/{owner}/{repo}/collaborators"

GET /repos/forgejo/forgejo/collaborators → 401 application/json;charset=utf-8
expected ["200","404"] actual 401
  • If the spec is the source of truth: Return one of the documented statuses (200, 404) from GET /repos/{owner}/{repo}/collaborators.
  • If the implementation is the source of truth: Add a "401" response under paths["/repos/{owner}/{repo}/collaborators"].get.responses.

Our input 1

Our own request values were wrong. Not the API's fault; listed for honesty.

Show 1 finding
GET /repos/{owner}/{repo}/actions/runners/registration-token

"GET /repos/{owner}/{repo}/actions/runners/registration-token" is deprecated in the spec but still in use

GET /repos/forgejo/forgejo/actions/runners/registration-token → 401 application/json;charset=utf-8
  • If the spec is the source of truth: Migrate callers of GET /repos/{owner}/{repo}/actions/runners/registration-token to its replacement before removing it.
  • If the implementation is the source of truth: Remove deprecated: true from paths["/repos/{owner}/{repo}/actions/runners/registration-token"].get if the operation is still supported.

Reproduce

The first hard violation came from this request. Compare the response to the schema at the location named in the finding.

curl -s -H 'Accept: application/json' 'https://codeberg.org/api/v1/orgs/forgejo/activities/feeds'

Data

If a finding is wrong, open an issue; if it is right, a pull request on the spec is welcome.