@adonis-agora/authkit-server 0.46.0 → 0.48.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/build/commands/clients_create.js +4 -4
- package/build/commands/configure.js +3 -2
- package/build/commands/doctor.js +8 -5
- package/build/commands/eject.js +1 -1
- package/build/commands/expire_scan.js +7 -5
- package/build/commands/import_users.js +1 -1
- package/build/commands/keys_rotate.js +7 -4
- package/build/host/views/account/apps.edge +5 -5
- package/build/host/views/account/login.edge +1 -1
- package/build/host/views/account/mfa.edge +7 -7
- package/build/host/views/account/orgs.edge +5 -5
- package/build/host/views/account/security.edge +10 -10
- package/build/host/views/account/tokens.edge +5 -5
- package/build/host/views/otp-unlock.edge +2 -2
- package/build/index.d.ts +7 -7
- package/build/index.js +5 -5
- package/build/providers/authkit_server_provider.d.ts +2 -2
- package/build/providers/authkit_server_provider.js +26 -10
- package/build/services/booted_app.d.ts +8 -0
- package/build/services/booted_app.js +27 -0
- package/build/services/main.d.ts +8 -1
- package/build/services/main.js +10 -2
- package/build/src/accounts/lucid_account_store.d.ts +3 -3
- package/build/src/accounts/lucid_account_store.js +6 -8
- package/build/src/accounts/lucid_store/core.js +1 -1
- package/build/src/accounts/lucid_store/mfa.js +1 -1
- package/build/src/accounts/lucid_store/organizations.js +2 -4
- package/build/src/accounts/lucid_store/password_hygiene.js +1 -4
- package/build/src/accounts/lucid_store/shared.d.ts +1 -1
- package/build/src/accounts/lucid_stores.d.ts +3 -3
- package/build/src/accounts/lucid_stores.js +2 -2
- package/build/src/adapters/database_adapter.js +3 -1
- package/build/src/adapters/factory.js +1 -1
- package/build/src/adapters/redis_adapter.js +2 -1
- package/build/src/commands/expire_scan_command.js +19 -5
- package/build/src/commands/settings_commands.js +22 -5
- package/build/src/define_config.d.ts +20 -20
- package/build/src/define_config.js +62 -67
- package/build/src/doctor/checks.js +45 -20
- package/build/src/events/dispatcher.d.ts +1 -1
- package/build/src/events/dispatcher.js +10 -10
- package/build/src/host/account_api/account_api_controller.js +95 -39
- package/build/src/host/account_deletion_ops.d.ts +4 -4
- package/build/src/host/account_deletion_ops.js +5 -5
- package/build/src/host/account_deletion_service.d.ts +2 -2
- package/build/src/host/account_deletion_service.js +2 -2
- package/build/src/host/account_export_service.d.ts +1 -1
- package/build/src/host/account_export_service.js +4 -6
- package/build/src/host/account_home.d.ts +0 -8
- package/build/src/host/account_home.js +6 -4
- package/build/src/host/account_login_url.d.ts +44 -0
- package/build/src/host/account_login_url.js +58 -0
- package/build/src/host/account_paths.d.ts +120 -0
- package/build/src/host/account_paths.js +161 -0
- package/build/src/host/admin_api/admin_orgs_service.d.ts +2 -2
- package/build/src/host/admin_api/admin_orgs_service.js +3 -2
- package/build/src/host/admin_api/admin_users_service.d.ts +12 -12
- package/build/src/host/admin_api/admin_users_service.js +20 -20
- package/build/src/host/admin_api/api_clients_controller.js +2 -2
- package/build/src/host/admin_api/api_misc_controller.js +2 -2
- package/build/src/host/admin_api/api_orgs_controller.js +3 -3
- package/build/src/host/admin_api/api_settings_controller.js +11 -5
- package/build/src/host/admin_api/api_users_controller.d.ts +2 -2
- package/build/src/host/admin_api/api_users_controller.js +37 -38
- package/build/src/host/admin_api/dto.d.ts +4 -4
- package/build/src/host/admin_clients_service.js +5 -4
- package/build/src/host/admin_console/admin_shell_controller.js +4 -2
- package/build/src/host/admin_console/console_audit_controller.js +1 -1
- package/build/src/host/admin_console/console_clients_controller.js +5 -3
- package/build/src/host/admin_console/console_impersonation_controller.js +1 -1
- package/build/src/host/admin_console/console_keys_controller.js +2 -4
- package/build/src/host/admin_console/console_orgs_controller.js +3 -3
- package/build/src/host/admin_console/console_roles_controller.js +30 -12
- package/build/src/host/admin_console/console_sessions_controller.js +3 -3
- package/build/src/host/admin_console/console_settings_controller.js +11 -5
- package/build/src/host/admin_console/console_users_controller.d.ts +2 -2
- package/build/src/host/admin_console/console_users_controller.js +46 -47
- package/build/src/host/admin_prefix.js +2 -2
- package/build/src/host/admin_sessions_service.d.ts +3 -1
- package/build/src/host/admin_sessions_service.js +36 -6
- package/build/src/host/adonis_auth_sync.d.ts +1 -1
- package/build/src/host/adonis_auth_user_provider.d.ts +1 -1
- package/build/src/host/app_key.js +1 -1
- package/build/src/host/avatar_storage.js +1 -3
- package/build/src/host/config_locks.js +1 -3
- package/build/src/host/console_session.d.ts +4 -0
- package/build/src/host/console_session.js +9 -2
- package/build/src/host/controllers/account_apps_controller.js +3 -2
- package/build/src/host/controllers/account_confirm_controller.js +2 -6
- package/build/src/host/controllers/account_mfa_controller.js +63 -12
- package/build/src/host/controllers/account_orgs_controller.js +53 -30
- package/build/src/host/controllers/account_security_controller.d.ts +2 -2
- package/build/src/host/controllers/account_security_controller.js +116 -116
- package/build/src/host/controllers/account_session_controller.js +7 -5
- package/build/src/host/controllers/account_tokens_controller.js +14 -2
- package/build/src/host/controllers/interaction_controller.js +59 -22
- package/build/src/host/controllers/pat_introspection_controller.js +10 -0
- package/build/src/host/controllers/registration_controller.js +28 -13
- package/build/src/host/default_mailer.js +11 -7
- package/build/src/host/durable/account_deletion_workflow.d.ts +2 -2
- package/build/src/host/durable/account_deletion_workflow.js +14 -14
- package/build/src/host/durable/account_export_workflow.d.ts +2 -2
- package/build/src/host/durable/account_export_workflow.js +12 -12
- package/build/src/host/durable/index.d.ts +5 -5
- package/build/src/host/durable/index.js +6 -6
- package/build/src/host/i18n.d.ts +1376 -1376
- package/build/src/host/i18n.js +1380 -1380
- package/build/src/host/impersonation.js +1 -7
- package/build/src/host/key_rotation_actions.d.ts +1 -1
- package/build/src/host/login_attempt.js +35 -6
- package/build/src/host/login_notify.js +1 -1
- package/build/src/host/middleware/account_auth.js +3 -1
- package/build/src/host/otp_lockout.js +1 -3
- package/build/src/host/rate_limit.js +1 -1
- package/build/src/host/register_auth_host.d.ts +96 -2
- package/build/src/host/register_auth_host.js +196 -91
- package/build/src/host/renderers/edge_renderer.js +19 -1
- package/build/src/host/renderers/inertia_renderer.d.ts +63 -0
- package/build/src/host/renderers/inertia_renderer.js +63 -0
- package/build/src/host/runtime_settings.js +1 -1
- package/build/src/host/runtime_toggles.d.ts +3 -3
- package/build/src/host/runtime_toggles.js +69 -24
- package/build/src/host/security_notice_service.d.ts +1 -1
- package/build/src/host/security_notice_service.js +1 -1
- package/build/src/host/session_context.js +1 -1
- package/build/src/host/sudo/index.d.ts +3 -3
- package/build/src/host/sudo/index.js +3 -3
- package/build/src/host/sudo/methods/magic_link.js +6 -5
- package/build/src/host/sudo/methods/passkey.js +7 -4
- package/build/src/host/sudo/methods/password.js +8 -3
- package/build/src/host/sudo/runtime.js +6 -13
- package/build/src/host/sudo_mode.js +3 -2
- package/build/src/host/ui-dist/assets/index-BQoTDiLV.js +137 -0
- package/build/src/host/ui-dist/index.html +1 -1
- package/build/src/keys/jwks_manager.js +1 -1
- package/build/src/keys/keystore.js +1 -1
- package/build/src/keys/keystore_manager.d.ts +2 -2
- package/build/src/keys/keystore_manager.js +2 -2
- package/build/src/keys/keystore_vault.js +8 -4
- package/build/src/mixins/with_audit_log.d.ts +1 -1
- package/build/src/mixins/with_auth_user.d.ts +1 -1
- package/build/src/mixins/with_auth_user.js +1 -1
- package/build/src/mixins/with_credentials.d.ts +1 -1
- package/build/src/mixins/with_mfa.d.ts +1 -1
- package/build/src/mixins/with_personal_access_token.d.ts +1 -1
- package/build/src/mixins/with_provider_identity.d.ts +1 -1
- package/build/src/mixins/with_webauthn_credential.d.ts +1 -1
- package/build/src/observability/diagnostics_bridge.js +2 -2
- package/build/src/observability/metrics_service.js +1 -1
- package/build/src/observability/telescope/data_providers.d.ts +1 -1
- package/build/src/observability/telescope/data_providers.js +29 -43
- package/build/src/observability/telescope/extension.d.ts +1 -1
- package/build/src/observability/telescope/extension.js +58 -58
- package/build/src/observability/telescope/index.d.ts +2 -2
- package/build/src/observability/telescope/index.js +2 -2
- package/build/src/observability/wire_provider_events.d.ts +1 -1
- package/build/src/observability/wire_provider_events.js +11 -11
- package/build/src/password/common_passwords.js +1 -1
- package/build/src/password/password_manager.d.ts +1 -1
- package/build/src/password/password_manager.js +4 -4
- package/build/src/pat/lucid_pat_store.js +2 -6
- package/build/src/pat/pat_tokens.js +1 -1
- package/build/src/provider/interaction_actions.js +1 -1
- package/build/src/provider/key_rotation_scheduler.js +3 -1
- package/build/src/provider/logout_sources.js +2 -8
- package/build/src/provider/oidc_service.d.ts +2 -2
- package/build/src/provider/oidc_service.js +22 -14
- package/build/src/provider/single_flight_lock.js +1 -3
- package/build/src/provider/token_exchange.d.ts +1 -1
- package/build/src/schema/ensure.js +3 -1
- package/build/stubs/ui/react/components/auth_shell.tsx +19 -19
- package/build/stubs/ui/react/pages/account/login.tsx +6 -7
- package/build/stubs/ui/react/pages/account/mfa.tsx +16 -15
- package/build/stubs/ui/react/pages/account/tokens.tsx +27 -17
- package/build/stubs/ui/react/pages/consent.tsx +12 -12
- package/build/stubs/ui/react/pages/forgot.tsx +7 -7
- package/build/stubs/ui/react/pages/login.tsx +22 -24
- package/build/stubs/ui/react/pages/mfa-challenge.tsx +9 -10
- package/build/stubs/ui/react/pages/reset.tsx +10 -10
- package/build/stubs/ui/react/pages/signup.tsx +30 -16
- package/build/stubs/ui/react/pages/verify-email.tsx +6 -6
- package/package.json +1 -1
- package/stubs/main.ts +2 -2
- package/stubs/ui/react/components/auth_shell.tsx +19 -19
- package/stubs/ui/react/pages/account/login.tsx +6 -7
- package/stubs/ui/react/pages/account/mfa.tsx +16 -15
- package/stubs/ui/react/pages/account/tokens.tsx +27 -17
- package/stubs/ui/react/pages/consent.tsx +12 -12
- package/stubs/ui/react/pages/forgot.tsx +7 -7
- package/stubs/ui/react/pages/login.tsx +22 -24
- package/stubs/ui/react/pages/mfa-challenge.tsx +9 -10
- package/stubs/ui/react/pages/reset.tsx +10 -10
- package/stubs/ui/react/pages/signup.tsx +30 -16
- package/stubs/ui/react/pages/verify-email.tsx +6 -6
- package/build/src/host/ui-dist/assets/index-BmI_J87g.js +0 -137
|
@@ -1,9 +1,11 @@
|
|
|
1
1
|
import '../augmentations.js';
|
|
2
2
|
import { supportsOrganizations } from '../../accounts/account_store.js';
|
|
3
|
+
import { getAccountLoginUrl } from '../account_login_url.js';
|
|
4
|
+
import { accountPath } from '../account_paths.js';
|
|
5
|
+
import { ACTIVE_ORG_COOKIE, ACTIVE_ORG_COOKIE_TTL, encodeActiveOrgCookie, } from '../active_org_cookie.js';
|
|
3
6
|
import { ACCOUNT_SESSION_KEY } from '../middleware/account_auth.js';
|
|
4
7
|
import { resolveRuntimeSettings } from '../runtime_settings.js';
|
|
5
8
|
import { isRoleInCatalog } from '../runtime_toggles.js';
|
|
6
|
-
import { ACTIVE_ORG_COOKIE, ACTIVE_ORG_COOKIE_TTL, encodeActiveOrgCookie, } from '../active_org_cookie.js';
|
|
7
9
|
/**
|
|
8
10
|
* Console de conta — Organizations. Server-rendered, padrão dos outros controllers
|
|
9
11
|
* de conta (account_tokens_controller, account_security_controller, etc.).
|
|
@@ -26,7 +28,7 @@ export default class AccountOrgsController {
|
|
|
26
28
|
const accountId = session.get(ACCOUNT_SESSION_KEY);
|
|
27
29
|
const account = await store.findById(accountId);
|
|
28
30
|
if (!account)
|
|
29
|
-
return response.redirect(
|
|
31
|
+
return response.redirect(getAccountLoginUrl());
|
|
30
32
|
const orgs = await store.listOrgsForAccount(accountId);
|
|
31
33
|
const pendingInvitations = await store.listPendingInvitationsForEmail(account.email);
|
|
32
34
|
// Enriquece convites com o nome da org
|
|
@@ -51,9 +53,7 @@ export default class AccountOrgsController {
|
|
|
51
53
|
availableRoles: cfg.organizations.roles,
|
|
52
54
|
messages,
|
|
53
55
|
};
|
|
54
|
-
return cfg.render
|
|
55
|
-
? cfg.render(ctx, 'account/orgs', props)
|
|
56
|
-
: response.notFound();
|
|
56
|
+
return cfg.render ? cfg.render(ctx, 'account/orgs', props) : response.notFound();
|
|
57
57
|
}
|
|
58
58
|
/** POST /account/orgs — criar nova org (requer allowSelfCreate). */
|
|
59
59
|
async store(ctx) {
|
|
@@ -68,7 +68,7 @@ export default class AccountOrgsController {
|
|
|
68
68
|
const name = request.input('name', '').trim();
|
|
69
69
|
const slug = request.input('slug', '').trim();
|
|
70
70
|
if (!name || !slug)
|
|
71
|
-
return response.redirect('
|
|
71
|
+
return response.redirect(accountPath('orgs'));
|
|
72
72
|
try {
|
|
73
73
|
await store.createOrg({ name, slug, ownerAccountId: accountId });
|
|
74
74
|
await cfg.audit?.record({ type: 'organization.created', accountId, metadata: { slug } });
|
|
@@ -76,7 +76,7 @@ export default class AccountOrgsController {
|
|
|
76
76
|
catch {
|
|
77
77
|
// slug duplicado ou outro erro — redireciona sem mensagem de erro específica
|
|
78
78
|
}
|
|
79
|
-
return response.redirect('
|
|
79
|
+
return response.redirect(accountPath('orgs'));
|
|
80
80
|
}
|
|
81
81
|
/** POST /account/orgs/:id/activate — define org ativa (valida membership). */
|
|
82
82
|
async activate(ctx) {
|
|
@@ -90,12 +90,16 @@ export default class AccountOrgsController {
|
|
|
90
90
|
const orgId = params.id;
|
|
91
91
|
const membership = await store.getOrgMembership(orgId, accountId);
|
|
92
92
|
if (!membership)
|
|
93
|
-
return response.redirect('
|
|
93
|
+
return response.redirect(accountPath('orgs'));
|
|
94
94
|
const org = await store.findOrgById(orgId);
|
|
95
95
|
if (!org)
|
|
96
|
-
return response.redirect('
|
|
96
|
+
return response.redirect(accountPath('orgs'));
|
|
97
97
|
// Grava cookie de org ativa
|
|
98
|
-
const cookieValue = encodeActiveOrgCookie({
|
|
98
|
+
const cookieValue = encodeActiveOrgCookie({
|
|
99
|
+
orgId,
|
|
100
|
+
orgSlug: org.slug,
|
|
101
|
+
orgRole: membership.role,
|
|
102
|
+
});
|
|
99
103
|
ctx.response.cookie(ACTIVE_ORG_COOKIE, cookieValue, {
|
|
100
104
|
httpOnly: true,
|
|
101
105
|
sameSite: 'lax',
|
|
@@ -103,8 +107,12 @@ export default class AccountOrgsController {
|
|
|
103
107
|
secure: ctx.request.secure(),
|
|
104
108
|
path: '/',
|
|
105
109
|
});
|
|
106
|
-
await cfg.audit?.record({
|
|
107
|
-
|
|
110
|
+
await cfg.audit?.record({
|
|
111
|
+
type: 'organization.switched',
|
|
112
|
+
accountId,
|
|
113
|
+
metadata: { orgId, orgSlug: org.slug },
|
|
114
|
+
});
|
|
115
|
+
return response.redirect(accountPath('orgs'));
|
|
108
116
|
}
|
|
109
117
|
/** POST /account/orgs/deactivate — remove org ativa. */
|
|
110
118
|
async deactivate(ctx) {
|
|
@@ -114,7 +122,7 @@ export default class AccountOrgsController {
|
|
|
114
122
|
const accountId = session.get(ACCOUNT_SESSION_KEY);
|
|
115
123
|
ctx.response.clearCookie(ACTIVE_ORG_COOKIE, { path: '/' });
|
|
116
124
|
await cfg.audit?.record({ type: 'organization.deactivated', accountId });
|
|
117
|
-
return response.redirect('
|
|
125
|
+
return response.redirect(accountPath('orgs'));
|
|
118
126
|
}
|
|
119
127
|
/** POST /account/orgs/:id/leave — sai da org (verifica last_owner). */
|
|
120
128
|
async leave(ctx) {
|
|
@@ -127,9 +135,13 @@ export default class AccountOrgsController {
|
|
|
127
135
|
return response.forbidden();
|
|
128
136
|
const result = await store.removeOrgMember(params.id, accountId);
|
|
129
137
|
if (result.ok) {
|
|
130
|
-
await cfg.audit?.record({
|
|
138
|
+
await cfg.audit?.record({
|
|
139
|
+
type: 'organization.member_removed',
|
|
140
|
+
accountId,
|
|
141
|
+
metadata: { orgId: params.id, self: true },
|
|
142
|
+
});
|
|
131
143
|
}
|
|
132
|
-
return response.redirect('
|
|
144
|
+
return response.redirect(accountPath('orgs'));
|
|
133
145
|
}
|
|
134
146
|
/** POST /account/orgs/:id/invite — convida membro por e-mail. */
|
|
135
147
|
async invite(ctx) {
|
|
@@ -148,7 +160,7 @@ export default class AccountOrgsController {
|
|
|
148
160
|
const email = request.input('email', '').trim();
|
|
149
161
|
const role = request.input('role', 'member').trim();
|
|
150
162
|
if (!email)
|
|
151
|
-
return response.redirect('
|
|
163
|
+
return response.redirect(accountPath('orgs'));
|
|
152
164
|
// H4: valida o role contra o catálogo efetivo de roles da org (runtime →
|
|
153
165
|
// config → defaults). Role fora do catálogo é rejeitada (não cria convite).
|
|
154
166
|
// Usa o helper PURO `isRoleInCatalog` (mesmo ponto de verdade do caminho admin).
|
|
@@ -159,7 +171,9 @@ export default class AccountOrgsController {
|
|
|
159
171
|
invitationTtlHours: cfg.organizations.invitationTtlHours,
|
|
160
172
|
}, params.id);
|
|
161
173
|
if (!roleValid) {
|
|
162
|
-
return response.unprocessableEntity({
|
|
174
|
+
return response.unprocessableEntity({
|
|
175
|
+
error: { code: 'invalid_role', message: 'Role inválida.' },
|
|
176
|
+
});
|
|
163
177
|
}
|
|
164
178
|
// H4: no fluxo member-facing, só um OWNER pode conceder a role `owner`.
|
|
165
179
|
// Um admin (não-owner) tentando convidar como `owner` é escalonamento.
|
|
@@ -176,7 +190,7 @@ export default class AccountOrgsController {
|
|
|
176
190
|
// Dispara e-mail via mail hook (best-effort)
|
|
177
191
|
if (cfg.mail?.onOrgInvitation) {
|
|
178
192
|
const org = await store.findOrgById(params.id);
|
|
179
|
-
const acceptUrl = `${ctx.request.protocol()}://${ctx.request.host()}
|
|
193
|
+
const acceptUrl = `${ctx.request.protocol()}://${ctx.request.host()}${accountPath('orgs')}/invitations/${token}/accept`;
|
|
180
194
|
try {
|
|
181
195
|
await cfg.mail.onOrgInvitation({
|
|
182
196
|
email,
|
|
@@ -197,7 +211,7 @@ export default class AccountOrgsController {
|
|
|
197
211
|
accountId,
|
|
198
212
|
metadata: { orgId: params.id, email, role },
|
|
199
213
|
});
|
|
200
|
-
return response.redirect('
|
|
214
|
+
return response.redirect(accountPath('orgs'));
|
|
201
215
|
}
|
|
202
216
|
/** GET /account/orgs/invitations/:token/accept — mostra tela de aceite. */
|
|
203
217
|
async showAcceptInvitation(ctx) {
|
|
@@ -210,9 +224,11 @@ export default class AccountOrgsController {
|
|
|
210
224
|
return response.notFound();
|
|
211
225
|
const accountId = session.get(ACCOUNT_SESSION_KEY);
|
|
212
226
|
if (!accountId) {
|
|
213
|
-
// Não logado: redireciona para login com return URL
|
|
214
|
-
const
|
|
215
|
-
|
|
227
|
+
// Não logado: redireciona para login (configurável) com return URL
|
|
228
|
+
const loginUrl = getAccountLoginUrl();
|
|
229
|
+
const returnTo = encodeURIComponent(`${accountPath('orgs')}/invitations/${params.token}/accept`);
|
|
230
|
+
const sep = loginUrl.includes('?') ? '&' : '?';
|
|
231
|
+
return response.redirect(`${loginUrl}${sep}returnTo=${returnTo}`);
|
|
216
232
|
}
|
|
217
233
|
const tokenHash = createHash('sha256').update(params.token).digest('hex');
|
|
218
234
|
const invitation = await store.findInvitationByTokenHash(tokenHash);
|
|
@@ -236,11 +252,11 @@ export default class AccountOrgsController {
|
|
|
236
252
|
return response.notFound();
|
|
237
253
|
const accountId = session.get(ACCOUNT_SESSION_KEY);
|
|
238
254
|
if (!accountId)
|
|
239
|
-
return response.redirect(
|
|
255
|
+
return response.redirect(getAccountLoginUrl());
|
|
240
256
|
const tokenHash = createHash('sha256').update(params.token).digest('hex');
|
|
241
257
|
const invitation = await store.findInvitationByTokenHash(tokenHash);
|
|
242
258
|
if (!invitation)
|
|
243
|
-
return response.redirect('
|
|
259
|
+
return response.redirect(accountPath('orgs'));
|
|
244
260
|
const result = await store.acceptInvitation(invitation.id, accountId);
|
|
245
261
|
if (result.ok) {
|
|
246
262
|
await cfg.audit?.record({
|
|
@@ -249,7 +265,7 @@ export default class AccountOrgsController {
|
|
|
249
265
|
metadata: { orgId: invitation.organizationId, invitationId: invitation.id },
|
|
250
266
|
});
|
|
251
267
|
}
|
|
252
|
-
return response.redirect('
|
|
268
|
+
return response.redirect(accountPath('orgs'));
|
|
253
269
|
}
|
|
254
270
|
/** POST /account/orgs/:id/members/:accountId/remove */
|
|
255
271
|
async removeMember(ctx) {
|
|
@@ -261,7 +277,8 @@ export default class AccountOrgsController {
|
|
|
261
277
|
if (!supportsOrganizations(store))
|
|
262
278
|
return response.forbidden();
|
|
263
279
|
const actorMembership = await store.getOrgMembership(params.id, actorId);
|
|
264
|
-
if (!actorMembership ||
|
|
280
|
+
if (!actorMembership ||
|
|
281
|
+
(actorMembership.role !== 'owner' && actorMembership.role !== 'admin')) {
|
|
265
282
|
return response.forbidden();
|
|
266
283
|
}
|
|
267
284
|
const result = await store.removeOrgMember(params.id, params.accountId);
|
|
@@ -272,7 +289,7 @@ export default class AccountOrgsController {
|
|
|
272
289
|
metadata: { orgId: params.id, targetAccountId: params.accountId },
|
|
273
290
|
});
|
|
274
291
|
}
|
|
275
|
-
return response.redirect('
|
|
292
|
+
return response.redirect(accountPath('orgs'));
|
|
276
293
|
}
|
|
277
294
|
/** POST /account/orgs/:id/invitations/:invId/revoke */
|
|
278
295
|
async revokeInvitation(ctx) {
|
|
@@ -284,7 +301,8 @@ export default class AccountOrgsController {
|
|
|
284
301
|
if (!supportsOrganizations(store))
|
|
285
302
|
return response.forbidden();
|
|
286
303
|
const actorMembership = await store.getOrgMembership(params.id, actorId);
|
|
287
|
-
if (!actorMembership ||
|
|
304
|
+
if (!actorMembership ||
|
|
305
|
+
(actorMembership.role !== 'owner' && actorMembership.role !== 'admin')) {
|
|
288
306
|
return response.forbidden();
|
|
289
307
|
}
|
|
290
308
|
// Escopado por org (params.id já validado acima): impede IDOR cross-org.
|
|
@@ -294,7 +312,7 @@ export default class AccountOrgsController {
|
|
|
294
312
|
actorId,
|
|
295
313
|
metadata: { orgId: params.id, invitationId: params.invId },
|
|
296
314
|
});
|
|
297
|
-
return response.redirect('
|
|
315
|
+
return response.redirect(accountPath('orgs'));
|
|
298
316
|
}
|
|
299
317
|
// ──────────────────────────────────────────────────────────────────────────
|
|
300
318
|
// JSON endpoints — consumed by @adonis-agora/authkit-react hooks.
|
|
@@ -353,7 +371,12 @@ export default class AccountOrgsController {
|
|
|
353
371
|
const members = canManage ? await store.listOrgMembers(params.id) : [];
|
|
354
372
|
const enrichedMembers = await Promise.all(members.map(async (m) => {
|
|
355
373
|
const account = await store.findById(m.accountId);
|
|
356
|
-
return {
|
|
374
|
+
return {
|
|
375
|
+
accountId: m.accountId,
|
|
376
|
+
email: account?.email ?? null,
|
|
377
|
+
role: m.role,
|
|
378
|
+
joinedAt: m.joinedAt,
|
|
379
|
+
};
|
|
357
380
|
}));
|
|
358
381
|
return {
|
|
359
382
|
id: org.id,
|
|
@@ -1,5 +1,5 @@
|
|
|
1
|
-
import
|
|
2
|
-
import type { HttpContext } from
|
|
1
|
+
import '../augmentations.js';
|
|
2
|
+
import type { HttpContext } from '@adonisjs/core/http';
|
|
3
3
|
/**
|
|
4
4
|
* Self-service de segurança da conta (console de conta): trocar a senha e o
|
|
5
5
|
* e-mail. A troca de senha exige a senha ATUAL (verifyCredentials). A troca de
|