0
Fork 0
mirror of https://github.com/logto-io/logto.git synced 2025-03-10 22:22:45 -05:00

refactor: remove internal role policies (#5904)

* refactor: remove internal role policies

* refactor: remove unused tests
This commit is contained in:
Gao Sun 2024-05-21 21:44:24 +08:00 committed by GitHub
parent e762d64120
commit 38811e1099
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
8 changed files with 47 additions and 56 deletions

View file

@ -238,6 +238,7 @@ export default function applicationRoutes<T extends ManagementApiRouter>(
const { isAdmin, protectedAppMetadata, ...rest } = body;
// @deprecated
// User can enable the admin access of Machine-to-Machine apps by switching on a toggle on Admin Console.
// Since those apps sit in the user tenant, we provide an internal role to apply the necessary scopes.
// This role is NOT intended for user assignment.

View file

@ -111,7 +111,7 @@ async function handleSubmitRegister(
const { client_id } = ctx.interactionDetails.params;
const { isCloud } = EnvSet.values;
const { isCloud, isIntegrationTest } = EnvSet.values;
const [currentTenantId] = await getTenantId(ctx.URL);
const isInAdminTenant = currentTenantId === adminTenantId;
/**
@ -119,7 +119,7 @@ async function handleSubmitRegister(
* security issues.
*/
const isCreatingFirstAdminUser =
(!EnvSet.values.isCloud || EnvSet.values.isIntegrationTest) &&
(!isCloud || isIntegrationTest) &&
isInAdminTenant &&
String(client_id) === adminConsoleApplicationId &&
!(await hasActiveUsers());

View file

@ -124,14 +124,4 @@ describe('roles scopes', () => {
);
expect(response instanceof HTTPError && response.response.status).toBe(404);
});
it('should fail when try to assign a scope to an internal role', async () => {
const resource = await createResource();
const scope = await createScope(resource.id);
const response = await assignScopesToRole([scope.id], defaultManagementApi.role.id).catch(
(error: unknown) => error
);
expect(response instanceof HTTPError && response.response.status).toBe(403);
});
});

View file

@ -52,12 +52,6 @@ describe('roles', () => {
expect(response instanceof HTTPError && response.response.status).toBe(422);
});
it('should fail when try to create an internal role', async () => {
const response = await createRole({ name: '#internal:foo' }).catch((error: unknown) => error);
expect(response instanceof HTTPError && response.response.status).toBe(403);
});
it('should fail when try to create role with management API scope(s)', async () => {
const response = await createRole({ scopeIds: [defaultManagementApi.scopes[0]!.id] }).catch(
(error: unknown) => error
@ -113,16 +107,6 @@ describe('roles', () => {
expect(response instanceof HTTPError && response.response.status).toBe(404);
});
it('should fail when try to update an internal role', async () => {
const role = await createRole({});
const response = await updateRole(role.id, {
name: '#internal:foo',
}).catch((error: unknown) => error);
expect(response instanceof HTTPError && response.response.status).toBe(403);
});
it('should delete role successfully', async () => {
const role = await createRole({});

View file

@ -0,0 +1,37 @@
import { sql } from '@silverhand/slonik';
import type { AlterationScript } from '../lib/types/alteration.js';
const alteration: AlterationScript = {
up: async (pool) => {
await pool.query(sql`
drop policy if exists roles_select on roles;
drop policy if exists roles_modification on roles;
create policy roles_modification on roles using (true);
drop policy if exists roles_scopes_select on roles_scopes;
drop policy if exists roles_scopes_modification on roles_scopes;
create policy roles_scopes_modification on roles_scopes using (true);
`);
},
down: async (pool) => {
await pool.query(sql`
create policy roles_select on roles
for select using (true);
drop policy roles_modification on roles;
create policy roles_modification on roles
using (not starts_with(name, '#internal:'));
-- Restrict role - scope modification
create policy roles_scopes_select on roles_scopes
for select using (true);
drop policy roles_scopes_modification on roles_scopes;
create policy roles_scopes_modification on roles_scopes
using (not starts_with((select roles.name from roles where roles.id = role_id), '#internal:'));
`);
},
};
export default alteration;

View file

@ -49,7 +49,11 @@ export const userMfaVerificationResponseGuard = z
export type UserMfaVerificationResponse = z.infer<typeof userMfaVerificationResponseGuard>;
/** Internal read-only roles for user tenants. */
/**
* Internal read-only roles for user tenants.
*
* @deprecated We don't use internal roles anymore.
*/
export enum InternalRole {
/**
* Internal admin role for Machine-to-Machine apps in Logto user tenants.

View file

@ -1,3 +1,5 @@
/** @deprecated We don't restrict roles in the database anymore. */
export const internalRolePrefix = '#internal:';
/** @deprecated We don't restrict roles in the database anymore. */
export const isInternalRole = (roleName: string) => roleName.startsWith(internalRolePrefix);

View file

@ -32,30 +32,3 @@ revoke all privileges
revoke all privileges
on table service_logs
from logto_tenant_${database};
---- Create policies to make internal roles read-only ----
/**
* Note:
*
* Internal roles have scope preset and they are read-only, but we do not
* limit user or application assignment since it's business logic.
*/
-- Restrict direct role modification
create policy roles_select on roles
for select using (true);
drop policy roles_modification on roles;
create policy roles_modification on roles
using (not starts_with(name, '#internal:'));
-- Restrict role - scope modification
create policy roles_scopes_select on roles_scopes
for select using (true);
drop policy roles_scopes_modification on roles_scopes;
create policy roles_scopes_modification on roles_scopes
using (not starts_with((select roles.name from roles where roles.id = role_id), '#internal:'));
---- TODO: Make internal API Resources read-only ----