permission-docs: update tutorial with boolean operator support
Signed-off-by: MT Lewis <mtlewis@users.noreply.github.com>
This commit is contained in:
@@ -90,7 +90,7 @@ The source code is available here:
|
||||
apiRouter.use(notFoundHandler());
|
||||
```
|
||||
|
||||
Apply the following changes to `packages/app/src/App.ts`:
|
||||
Apply the following changes to `packages/app/src/App.tsx`:
|
||||
|
||||
```diff
|
||||
+ import { TodoListPage } from '@internal/plugin-todo-list';
|
||||
|
||||
@@ -15,7 +15,8 @@ We'll start by creating a new permission, and then we'll use the permission api
|
||||
Install the following module:
|
||||
|
||||
```
|
||||
$ yarn workspace @internal/plugin-todo-list-backend add @backstage/plugin-permission-common
|
||||
$ yarn workspace @internal/plugin-todo-list-backend \
|
||||
add @backstage/plugin-permission-common
|
||||
```
|
||||
|
||||
## Creating a new permission
|
||||
@@ -40,12 +41,15 @@ We recommend exporting all permissions from your plugin, so that Backstage integ
|
||||
Edit `plugins/todo-list-backend/src/service/router.ts`:
|
||||
|
||||
```diff
|
||||
...
|
||||
|
||||
- import { InputError } from '@backstage/errors';
|
||||
+ import { InputError, NotAllowedError } from '@backstage/errors';
|
||||
import { add, getAll, getTodo, Todo, TodoFilter, update } from './todos';
|
||||
+ import { PermissionAuthorizer, AuthorizeResult } from '@backstage/plugin-permission-common';
|
||||
+ import { todosListCreate } from './permissions';
|
||||
|
||||
...
|
||||
|
||||
export interface RouterOptions {
|
||||
logger: Logger;
|
||||
identity: IdentityClient;
|
||||
|
||||
@@ -63,12 +63,11 @@ To start with, let's edit `plugins/todo-list-backend/src/service/router.ts` in a
|
||||
+ )
|
||||
+ )[0];
|
||||
|
||||
- res.json(update(req.body));
|
||||
+ if (decision.result === AuthorizeResult.ALLOW) {
|
||||
+ res.json(update(req.body));
|
||||
+ return;
|
||||
+ if (decision.result !== AuthorizeResult.ALLOW) {
|
||||
+ throw new NotAllowedError('Unauthorized');
|
||||
+ }
|
||||
+ throw new NotAllowedError('Unauthorized');
|
||||
+
|
||||
res.json(update(req.body));
|
||||
});
|
||||
```
|
||||
|
||||
@@ -128,29 +127,30 @@ $ yarn workspace @internal/plugin-todo-list-backend add @backstage/plugin-permis
|
||||
|
||||
Create a new `plugins/todo-list-backend/src/service/rules.ts` file and append the following code:
|
||||
|
||||
<!-- TODO: serializable result from `toQuery` method -->
|
||||
```typescript
|
||||
import { makeCreatePermissionRule } from '@backstage/plugin-permission-node';
|
||||
import { Todo, TodoFilter } from './todos';
|
||||
|
||||
```diff
|
||||
+ import { makeCreatePermissionRule } from '@backstage/plugin-permission-node';
|
||||
+ import { Todo, TodoFilter } from './todos';
|
||||
const createTodoListPermissionRule = makeCreatePermissionRule<
|
||||
Todo,
|
||||
TodoFilter
|
||||
>();
|
||||
|
||||
+ const createTodoListPermissionRule = makeCreatePermissionRule<
|
||||
+ Todo,
|
||||
+ TodoFilter
|
||||
+ >();
|
||||
export const isOwner = createTodoListPermissionRule({
|
||||
name: 'IS_OWNER',
|
||||
description: 'Should allow only if the todo belongs to the user',
|
||||
apply: (resource: Todo, userId: string) => {
|
||||
return resource.author === userId;
|
||||
},
|
||||
toQuery: (userId: string) => {
|
||||
return {
|
||||
property: 'author',
|
||||
values: [userId],
|
||||
};
|
||||
},
|
||||
});
|
||||
|
||||
+ export const isOwner = createTodoListPermissionRule({
|
||||
+ name: 'IS_OWNER',
|
||||
+ description: 'Should allow only if the todo belongs to the user',
|
||||
+ apply: (resource, userId) => {
|
||||
+ return resource.author === userId;
|
||||
+ },
|
||||
+ toQuery: userId => {
|
||||
+ return resource => resource.author === userId;
|
||||
+ },
|
||||
+ });
|
||||
|
||||
+ export const rules = { isOwner };
|
||||
export const rules = { isOwner };
|
||||
```
|
||||
|
||||
`makeCreatePermissionRule` is a helper used to ensure that rules created for this plugin use consistent types for the resource and query.
|
||||
@@ -168,9 +168,11 @@ Now, let's create the new endpoint by editing `plugins/todo-list-backend/src/ser
|
||||
|
||||
```diff
|
||||
+ import { createPermissionIntegrationRouter } from '@backstage/plugin-permission-node';
|
||||
- import { add, getAll, update } from './todos';
|
||||
+ import { add, getAll, getTodo, update } from './todos';
|
||||
- import { todosListCreate, todosListUpdate } from './permissions';
|
||||
+ import { todosListCreate, todosListUpdate, TODO_LIST_RESOURCE_TYPE } from './permissions';
|
||||
+ import { rules } from './rules;
|
||||
+ import { rules } from './rules';
|
||||
|
||||
export async function createRouter(
|
||||
options: RouterOptions,
|
||||
|
||||
@@ -77,6 +77,8 @@ export const todosListUpdate: Permission = {
|
||||
+ createConditionTransformer,
|
||||
+ ConditionTransformer,
|
||||
+ } from '@backstage/plugin-permission-node';
|
||||
- import { add, getAll, getTodo, update } from './todos';
|
||||
+ import { add, getAll, getTodo, TodoFilter, update } from './todos';
|
||||
import {
|
||||
todosListCreate,
|
||||
todosListUpdate,
|
||||
@@ -105,10 +107,11 @@ export const todosListUpdate: Permission = {
|
||||
+ createConditionTransformer(Object.values(rules));
|
||||
+ const filter = conditionTransformer(decision.conditions) as TodoFilter;
|
||||
+ res.json(getAll(filter));
|
||||
+ return;
|
||||
+ } else {
|
||||
+ res.json(getAll());
|
||||
+ }
|
||||
|
||||
res.json(getAll());
|
||||
+ }
|
||||
- res.json(getAll());
|
||||
});
|
||||
```
|
||||
|
||||
@@ -144,6 +147,4 @@ Let's update our permission policy's handler to return a conditional result when
|
||||
|
||||
Once the changes to the permission policy are saved, the UI should should show only the items you have created.
|
||||
|
||||
// TODO(vinzscam): add support for boolean operators
|
||||
|
||||
// TODO(vinzscam): add frontend documentation
|
||||
|
||||
Reference in New Issue
Block a user