feat: more role backend and admin/writer roles additions and adjustments

This commit is contained in:
Florian Sylvain committed 2026-10-26 18:15:26 +01:00
1 parent 8c6c6456da
commit de142f6c5f
131 files changed
+2663 -435

No files matched your search

+2 -3
View File
@@ -430,7 +430,7 @@ describe('Owner or admin purge routes', () => {
for (const endpoint of allEndpoints().filter((item) => item.access === 'Owner or admin')) {
expect(endpoint.errors).toContainEqual({
status: 403,
caption: 'Only owners and admins can do this.',
caption: 'missing_permission',
})
}
})
@@ -762,7 +762,7 @@ describe('Per-endpoint error captions use the real strings', () => {
['POST /v1/user/invite', 409, 'This address already has an account.'],
['POST /v1/user/invite', 409, "There's already a pending invite for this address."],
['POST /v1/user/invite/{id}/renew', 409, 'This invite has already been accepted.'],
['POST /v1/user/invite', 403, 'Only the owner can do this.'],
['POST /v1/user/invite', 403, 'missing_permission'],
]
it.each(captions)('%s lists %i "%s"', (route, status, caption) => {
@@ -852,7 +852,6 @@ describe('Errors table', () => {
[
SESSION_REQUIRED_MESSAGE,
OWNER_OR_ADMIN_MESSAGE,
OWNER_REQUIRED_MESSAGE,
'You must verify your account to access this resource.',
],
[],
+3 -8
View File
@@ -93,8 +93,8 @@ export interface EndpointExamples {
export const API_KEY_PLACEHOLDER = 'rcms_Kf3x9QwL0aBc…'
export const NO_CONTENT_RESPONSE = '204 No Content'
export const SESSION_REQUIRED_MESSAGE = 'This action needs a real session.'
export const OWNER_REQUIRED_MESSAGE = 'Only the owner can do this.'
export const OWNER_OR_ADMIN_MESSAGE = 'Only owners and admins can do this.'
export const OWNER_REQUIRED_MESSAGE = 'missing_permission'
export const OWNER_OR_ADMIN_MESSAGE = 'missing_permission'
export const IMAGES_AFTER_GROUP = 'sites'
export const FIELD_TYPES_ANCHOR = 'ct-fields'
export const LOGIN_FAMILY_CAPTION = 'Made for the browser. A key is ignored here, with no 403.'
@@ -1857,12 +1857,7 @@ export const ERROR_ROWS: ErrorRow[] = [
{
status: 403,
meaning: 'Forbidden',
messages: [
SESSION_REQUIRED_MESSAGE,
OWNER_OR_ADMIN_MESSAGE,
OWNER_REQUIRED_MESSAGE,
VERIFY_REQUIRED,
],
messages: [SESSION_REQUIRED_MESSAGE, OWNER_OR_ADMIN_MESSAGE, VERIFY_REQUIRED],
note: 'Site SEO defaults are owner only. Article SEO fields need only the right to edit the article.',
},
{
+2 -2
View File
@@ -961,8 +961,8 @@ export const messages = {
'Envoyez `Authorization: Bearer rcms_…`. Les requêtes agissent comme la personne qui a créé la clé, avec son rôle (propriétaire ou administrateur). Une clé n’a jamais plus de droits que son créateur.',
'Keys start with `rcms_` and are shown in full once, when you create them.':
'Les clés commencent par `rcms_` et ne sont affichées en entier qu’une fois, à leur création.',
'A key can\'t create, list or revoke API keys, verify or cancel a registration, or call anything under `/v1/system`. Those routes answer 403 "This action needs a real session." An invalid, unknown, expired or revoked key answers 401, even on public routes, and so does a key whose user was deleted or unverified. Owner and admin routes answer 403 to a key whose creator is neither.':
'Une clé ne peut pas créer, lister ni révoquer de clés d’API, vérifier ou annuler une inscription, ni appeler quoi que ce soit sous `/v1/system`. Ces routes répondent 403 « This action needs a real session. » Une clé invalide, inconnue, expirée ou révoquée reçoit 401, même sur les routes publiques, tout comme une clé dont l’utilisateur a été supprimé ou n’est pas vérifié. Les routes propriétaire et administrateur répondent 403 à une clé dont le créateur n’est ni l’un ni l’autre.',
'A key can\'t create, list or revoke API keys, verify or cancel a registration, or call anything under `/v1/system`. Those routes answer 403 "This action needs a real session." An invalid, unknown, expired or revoked key answers 401, even on public routes, and so does a key whose user was deleted or unverified. Routes that need a permission answer 403 "missing_permission" to a key when the role of its creator does not hold it.':
'Une clé ne peut pas créer, lister ni révoquer de clés d’API, vérifier ou annuler une inscription, ni appeler quoi que ce soit sous `/v1/system`. Ces routes répondent 403 « This action needs a real session. » Une clé invalide, inconnue, expirée ou révoquée reçoit 401, même sur les routes publiques, tout comme une clé dont l’utilisateur a été supprimé ou n’est pas vérifié. Les routes qui exigent une permission répondent 403 « missing_permission » à une clé dont le rôle du créateur ne la possède pas.',
'Each key can make 120 requests per minute. Beyond that the API answers 429 with a `Retry-After` header.':
'Chaque clé peut faire 120 requêtes par minute. Au-delà, l’API répond 429 avec un en-tête `Retry-After`.',
'Every error is a plain-text body with a single sentence. The status code is in the HTTP status line, and the Content-Type is text/plain.':
+1 -1
View File
@@ -74,7 +74,7 @@ const authItems = computed(() => {
const authNotes = computed(() => [
t(
'A key can\'t create, list or revoke API keys, verify or cancel a registration, or call anything under `/v1/system`. Those routes answer 403 "This action needs a real session." An invalid, unknown, expired or revoked key answers 401, even on public routes, and so does a key whose user was deleted or unverified. Owner and admin routes answer 403 to a key whose creator is neither.',
'A key can\'t create, list or revoke API keys, verify or cancel a registration, or call anything under `/v1/system`. Those routes answer 403 "This action needs a real session." An invalid, unknown, expired or revoked key answers 401, even on public routes, and so does a key whose user was deleted or unverified. Routes that need a permission answer 403 "missing_permission" to a key when the role of its creator does not hold it.',
),
t(
'Each key can make 120 requests per minute. Beyond that the API answers 429 with a `Retry-After` header.',
@@ -395,7 +395,7 @@ describe('Group scrolled, one card expanded', () => {
expect(upload.text()).toContain('the file must be a PNG, JPEG, WEBP, or SVG image')
const invite = await expand(wrapper, 'POST /v1/user/invite')
expect(invite.text()).toContain('Only the owner can do this.')
expect(invite.text()).toContain('missing_permission')
expect(invite.text()).toContain('This route is rate limited. Too many requests answer 429.')
expect(invite.text()).toContain("There's already a pending invite for this address.")
})