@backstage/plugin-permission-node 0.5.0 → 0.5.1
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/CHANGELOG.md +12 -0
- package/dist/index.d.ts +301 -0
- package/package.json +7 -7
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,17 @@
|
|
|
1
1
|
# @backstage/plugin-permission-node
|
|
2
2
|
|
|
3
|
+
## 0.5.1
|
|
4
|
+
|
|
5
|
+
### Patch Changes
|
|
6
|
+
|
|
7
|
+
- Fix for the previous release with missing type declarations.
|
|
8
|
+
- Updated dependencies
|
|
9
|
+
- @backstage/backend-common@0.10.9
|
|
10
|
+
- @backstage/config@0.1.15
|
|
11
|
+
- @backstage/errors@0.2.2
|
|
12
|
+
- @backstage/plugin-auth-node@0.1.2
|
|
13
|
+
- @backstage/plugin-permission-common@0.5.1
|
|
14
|
+
|
|
3
15
|
## 0.5.0
|
|
4
16
|
|
|
5
17
|
### Minor Changes
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,301 @@
|
|
|
1
|
+
import { PermissionCriteria, AuthorizeQuery, AuthorizeResult, PermissionCondition, Identified, PermissionAuthorizer, AuthorizeRequestOptions, AuthorizeDecision } from '@backstage/plugin-permission-common';
|
|
2
|
+
import { BackstageIdentityResponse } from '@backstage/plugin-auth-node';
|
|
3
|
+
import express from 'express';
|
|
4
|
+
import { PluginEndpointDiscovery, TokenManager } from '@backstage/backend-common';
|
|
5
|
+
import { Config } from '@backstage/config';
|
|
6
|
+
|
|
7
|
+
/**
|
|
8
|
+
* A conditional rule that can be provided in an
|
|
9
|
+
* {@link @backstage/permission-common#AuthorizeDecision} response to an authorization request.
|
|
10
|
+
*
|
|
11
|
+
* @remarks
|
|
12
|
+
*
|
|
13
|
+
* Rules can either be evaluated against a resource loaded in memory, or used as filters when
|
|
14
|
+
* loading a collection of resources from a data source. The `apply` and `toQuery` methods implement
|
|
15
|
+
* these two concepts.
|
|
16
|
+
*
|
|
17
|
+
* The two operations should always have the same logical result. If they don’t, the effective
|
|
18
|
+
* outcome of an authorization operation will sometimes differ depending on how the authorization
|
|
19
|
+
* check was performed.
|
|
20
|
+
*
|
|
21
|
+
* @public
|
|
22
|
+
*/
|
|
23
|
+
declare type PermissionRule<TResource, TQuery, TParams extends unknown[] = unknown[]> = {
|
|
24
|
+
name: string;
|
|
25
|
+
description: string;
|
|
26
|
+
/**
|
|
27
|
+
* Apply this rule to a resource already loaded from a backing data source. The params are
|
|
28
|
+
* arguments supplied for the rule; for example, a rule could be `isOwner` with entityRefs as the
|
|
29
|
+
* params.
|
|
30
|
+
*/
|
|
31
|
+
apply(resource: TResource, ...params: TParams): boolean;
|
|
32
|
+
/**
|
|
33
|
+
* Translate this rule to criteria suitable for use in querying a backing data store. The criteria
|
|
34
|
+
* can be used for loading a collection of resources efficiently with conditional criteria already
|
|
35
|
+
* applied.
|
|
36
|
+
*/
|
|
37
|
+
toQuery(...params: TParams): PermissionCriteria<TQuery>;
|
|
38
|
+
};
|
|
39
|
+
|
|
40
|
+
/**
|
|
41
|
+
* Creates a condition factory function for a given authorization rule and parameter types.
|
|
42
|
+
*
|
|
43
|
+
* @remarks
|
|
44
|
+
*
|
|
45
|
+
* For example, an isEntityOwner rule for catalog entities might take an array of entityRef strings.
|
|
46
|
+
* The rule itself defines _how_ to check a given resource, whereas a condition also includes _what_
|
|
47
|
+
* to verify.
|
|
48
|
+
*
|
|
49
|
+
* Plugin authors should generally use the {@link createConditionExports} in order to efficiently
|
|
50
|
+
* create multiple condition factories. This helper should generally only be used to construct
|
|
51
|
+
* condition factories for third-party rules that aren't part of the backend plugin with which
|
|
52
|
+
* they're intended to integrate.
|
|
53
|
+
*
|
|
54
|
+
* @public
|
|
55
|
+
*/
|
|
56
|
+
declare const createConditionFactory: <TParams extends any[]>(rule: PermissionRule<unknown, unknown, TParams>) => (...params: TParams) => {
|
|
57
|
+
rule: string;
|
|
58
|
+
params: TParams;
|
|
59
|
+
};
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* An authorization request to be evaluated by the {@link PermissionPolicy}.
|
|
63
|
+
*
|
|
64
|
+
* @remarks
|
|
65
|
+
*
|
|
66
|
+
* This differs from {@link @backstage/permission-common#AuthorizeQuery} in that `resourceRef`
|
|
67
|
+
* should never be provided. This forces policies to be written in a way that's compatible with
|
|
68
|
+
* filtering collections of resources at data load time.
|
|
69
|
+
*
|
|
70
|
+
* @public
|
|
71
|
+
*/
|
|
72
|
+
declare type PolicyAuthorizeQuery = Omit<AuthorizeQuery, 'resourceRef'>;
|
|
73
|
+
/**
|
|
74
|
+
* A definitive result to an authorization request, returned by the {@link PermissionPolicy}.
|
|
75
|
+
*
|
|
76
|
+
* @remarks
|
|
77
|
+
*
|
|
78
|
+
* This indicates that the policy unconditionally allows (or denies) the request.
|
|
79
|
+
*
|
|
80
|
+
* @public
|
|
81
|
+
*/
|
|
82
|
+
declare type DefinitivePolicyDecision = {
|
|
83
|
+
result: AuthorizeResult.ALLOW | AuthorizeResult.DENY;
|
|
84
|
+
};
|
|
85
|
+
/**
|
|
86
|
+
* A conditional result to an authorization request, returned by the {@link PermissionPolicy}.
|
|
87
|
+
*
|
|
88
|
+
* @remarks
|
|
89
|
+
*
|
|
90
|
+
* This indicates that the policy allows authorization for the request, given that the returned
|
|
91
|
+
* conditions hold when evaluated. The conditions will be evaluated by the corresponding plugin
|
|
92
|
+
* which knows about the referenced permission rules.
|
|
93
|
+
*
|
|
94
|
+
* Similar to {@link @backstage/permission-common#AuthorizeDecision}, but with the plugin and resource
|
|
95
|
+
* identifiers needed to evaluate the returned conditions.
|
|
96
|
+
* @public
|
|
97
|
+
*/
|
|
98
|
+
declare type ConditionalPolicyDecision = {
|
|
99
|
+
result: AuthorizeResult.CONDITIONAL;
|
|
100
|
+
pluginId: string;
|
|
101
|
+
resourceType: string;
|
|
102
|
+
conditions: PermissionCriteria<PermissionCondition>;
|
|
103
|
+
};
|
|
104
|
+
/**
|
|
105
|
+
* The result of evaluating an authorization request with a {@link PermissionPolicy}.
|
|
106
|
+
*
|
|
107
|
+
* @public
|
|
108
|
+
*/
|
|
109
|
+
declare type PolicyDecision = DefinitivePolicyDecision | ConditionalPolicyDecision;
|
|
110
|
+
/**
|
|
111
|
+
* A policy to evaluate authorization requests for any permissioned action performed in Backstage.
|
|
112
|
+
*
|
|
113
|
+
* @remarks
|
|
114
|
+
*
|
|
115
|
+
* This takes as input a permission and an optional Backstage identity, and should return ALLOW if
|
|
116
|
+
* the user is permitted to execute that action; otherwise DENY. For permissions relating to
|
|
117
|
+
* resources, such a catalog entities, a conditional response can also be returned. This states
|
|
118
|
+
* that the action is allowed if the conditions provided hold true.
|
|
119
|
+
*
|
|
120
|
+
* Conditions are a rule, and parameters to evaluate against that rule. For example, the rule might
|
|
121
|
+
* be `isOwner` and the parameters a collection of entityRefs; if one of the entityRefs matches
|
|
122
|
+
* the `owner` field on a catalog entity, this would resolve to ALLOW.
|
|
123
|
+
*
|
|
124
|
+
* @public
|
|
125
|
+
*/
|
|
126
|
+
interface PermissionPolicy {
|
|
127
|
+
handle(request: PolicyAuthorizeQuery, user?: BackstageIdentityResponse): Promise<PolicyDecision>;
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
/**
|
|
131
|
+
* A utility type for mapping a single {@link PermissionRule} to its
|
|
132
|
+
* corresponding {@link @backstage/plugin-permission-common#PermissionCondition}.
|
|
133
|
+
*
|
|
134
|
+
* @public
|
|
135
|
+
*/
|
|
136
|
+
declare type Condition<TRule> = TRule extends PermissionRule<any, any, infer TParams> ? (...params: TParams) => PermissionCondition<TParams> : never;
|
|
137
|
+
/**
|
|
138
|
+
* A utility type for mapping {@link PermissionRule}s to their corresponding
|
|
139
|
+
* {@link @backstage/plugin-permission-common#PermissionCondition}s.
|
|
140
|
+
*
|
|
141
|
+
* @public
|
|
142
|
+
*/
|
|
143
|
+
declare type Conditions<TRules extends Record<string, PermissionRule<any, any>>> = {
|
|
144
|
+
[Name in keyof TRules]: Condition<TRules[Name]>;
|
|
145
|
+
};
|
|
146
|
+
/**
|
|
147
|
+
* Creates the recommended condition-related exports for a given plugin based on the built-in
|
|
148
|
+
* {@link PermissionRule}s it supports.
|
|
149
|
+
*
|
|
150
|
+
* @remarks
|
|
151
|
+
*
|
|
152
|
+
* The function returns a `conditions` object containing a
|
|
153
|
+
* {@link @backstage/plugin-permission-common#PermissionCondition} factory for each of the
|
|
154
|
+
* supplied {@link PermissionRule}s, along with a `createConditions` function which builds the
|
|
155
|
+
* wrapper object needed to enclose conditions when authoring {@link PermissionPolicy} implementations.
|
|
156
|
+
*
|
|
157
|
+
* Plugin authors should generally call this method with all the built-in {@link PermissionRule}s
|
|
158
|
+
* the plugin supports, and export the resulting `conditions` object and `createConditions`
|
|
159
|
+
* function so that they can be used by {@link PermissionPolicy} authors.
|
|
160
|
+
*
|
|
161
|
+
* @public
|
|
162
|
+
*/
|
|
163
|
+
declare const createConditionExports: <TResource, TRules extends Record<string, PermissionRule<TResource, any, unknown[]>>>(options: {
|
|
164
|
+
pluginId: string;
|
|
165
|
+
resourceType: string;
|
|
166
|
+
rules: TRules;
|
|
167
|
+
}) => {
|
|
168
|
+
conditions: Conditions<TRules>;
|
|
169
|
+
createPolicyDecision: (conditions: PermissionCriteria<PermissionCondition>) => ConditionalPolicyDecision;
|
|
170
|
+
};
|
|
171
|
+
|
|
172
|
+
/**
|
|
173
|
+
* A function which accepts {@link @backstage/plugin-permission-common#PermissionCondition}s
|
|
174
|
+
* logically grouped in a {@link @backstage/plugin-permission-common#PermissionCriteria}
|
|
175
|
+
* object, and transforms the {@link @backstage/plugin-permission-common#PermissionCondition}s
|
|
176
|
+
* into plugin specific query fragments while retaining the enclosing criteria shape.
|
|
177
|
+
*
|
|
178
|
+
* @public
|
|
179
|
+
*/
|
|
180
|
+
declare type ConditionTransformer<TQuery> = (conditions: PermissionCriteria<PermissionCondition>) => PermissionCriteria<TQuery>;
|
|
181
|
+
/**
|
|
182
|
+
* A higher-order helper function which accepts an array of
|
|
183
|
+
* {@link PermissionRule}s, and returns a {@link ConditionTransformer}
|
|
184
|
+
* which transforms input conditions into equivalent plugin-specific
|
|
185
|
+
* query fragments using the supplied rules.
|
|
186
|
+
*
|
|
187
|
+
* @public
|
|
188
|
+
*/
|
|
189
|
+
declare const createConditionTransformer: <TQuery, TRules extends PermissionRule<any, TQuery, unknown[]>[]>(permissionRules: [...TRules]) => ConditionTransformer<TQuery>;
|
|
190
|
+
|
|
191
|
+
/**
|
|
192
|
+
* A request to load the referenced resource and apply conditions in order to
|
|
193
|
+
* finalize a conditional authorization response.
|
|
194
|
+
*
|
|
195
|
+
* @public
|
|
196
|
+
*/
|
|
197
|
+
declare type ApplyConditionsRequestEntry = Identified<{
|
|
198
|
+
resourceRef: string;
|
|
199
|
+
resourceType: string;
|
|
200
|
+
conditions: PermissionCriteria<PermissionCondition>;
|
|
201
|
+
}>;
|
|
202
|
+
/**
|
|
203
|
+
* A batch of {@link ApplyConditionsRequestEntry} objects.
|
|
204
|
+
*
|
|
205
|
+
* @public
|
|
206
|
+
*/
|
|
207
|
+
declare type ApplyConditionsRequest = {
|
|
208
|
+
items: ApplyConditionsRequestEntry[];
|
|
209
|
+
};
|
|
210
|
+
/**
|
|
211
|
+
* The result of applying the conditions, expressed as a definitive authorize
|
|
212
|
+
* result of ALLOW or DENY.
|
|
213
|
+
*
|
|
214
|
+
* @public
|
|
215
|
+
*/
|
|
216
|
+
declare type ApplyConditionsResponseEntry = Identified<DefinitivePolicyDecision>;
|
|
217
|
+
/**
|
|
218
|
+
* A batch of {@link ApplyConditionsResponseEntry} objects.
|
|
219
|
+
*
|
|
220
|
+
* @public
|
|
221
|
+
*/
|
|
222
|
+
declare type ApplyConditionsResponse = {
|
|
223
|
+
items: ApplyConditionsResponseEntry[];
|
|
224
|
+
};
|
|
225
|
+
/**
|
|
226
|
+
* Create an express Router which provides an authorization route to allow
|
|
227
|
+
* integration between the permission backend and other Backstage backend
|
|
228
|
+
* plugins. Plugin owners that wish to support conditional authorization for
|
|
229
|
+
* their resources should add the router created by this function to their
|
|
230
|
+
* express app inside their `createRouter` implementation.
|
|
231
|
+
*
|
|
232
|
+
* @remarks
|
|
233
|
+
*
|
|
234
|
+
* To make this concrete, we can use the Backstage software catalog as an
|
|
235
|
+
* example. The catalog has conditional rules around access to specific
|
|
236
|
+
* _entities_ in the catalog. The _type_ of resource is captured here as
|
|
237
|
+
* `resourceType`, a string identifier (`catalog-entity` in this example) that
|
|
238
|
+
* can be provided with permission definitions. This is merely a _type_ to
|
|
239
|
+
* verify that conditions in an authorization policy are constructed correctly,
|
|
240
|
+
* not a reference to a specific resource.
|
|
241
|
+
*
|
|
242
|
+
* The `rules` parameter is an array of {@link PermissionRule}s that introduce
|
|
243
|
+
* conditional filtering logic for resources; for the catalog, these are things
|
|
244
|
+
* like `isEntityOwner` or `hasAnnotation`. Rules describe how to filter a list
|
|
245
|
+
* of resources, and the `conditions` returned allow these rules to be applied
|
|
246
|
+
* with specific parameters (such as 'group:default/team-a', or
|
|
247
|
+
* 'backstage.io/edit-url').
|
|
248
|
+
*
|
|
249
|
+
* The `getResources` argument should load resources based on a reference
|
|
250
|
+
* identifier. For the catalog, this is an
|
|
251
|
+
* {@link @backstage/catalog-model#EntityRef}. For other plugins, this can be
|
|
252
|
+
* any serialized format. This is used to construct the
|
|
253
|
+
* `createPermissionIntegrationRouter`, a function to add an authorization route
|
|
254
|
+
* to your backend plugin. This function will be called by the
|
|
255
|
+
* `permission-backend` when authorization conditions relating to this plugin
|
|
256
|
+
* need to be evaluated.
|
|
257
|
+
*
|
|
258
|
+
* @public
|
|
259
|
+
*/
|
|
260
|
+
declare const createPermissionIntegrationRouter: <TResource>(options: {
|
|
261
|
+
resourceType: string;
|
|
262
|
+
rules: PermissionRule<TResource, any, unknown[]>[];
|
|
263
|
+
getResources: (resourceRefs: string[]) => Promise<(TResource | undefined)[]>;
|
|
264
|
+
}) => express.Router;
|
|
265
|
+
|
|
266
|
+
/**
|
|
267
|
+
* Helper function to ensure that {@link PermissionRule} definitions are typed correctly.
|
|
268
|
+
*
|
|
269
|
+
* @public
|
|
270
|
+
*/
|
|
271
|
+
declare const createPermissionRule: <TResource, TQuery, TParams extends unknown[]>(rule: PermissionRule<TResource, TQuery, TParams>) => PermissionRule<TResource, TQuery, TParams>;
|
|
272
|
+
/**
|
|
273
|
+
* Helper for making plugin-specific createPermissionRule functions, that have
|
|
274
|
+
* the TResource and TQuery type parameters populated but infer the params from
|
|
275
|
+
* the supplied rule. This helps ensure that rules created for this plugin use
|
|
276
|
+
* consistent types for the resource and query.
|
|
277
|
+
*
|
|
278
|
+
* @public
|
|
279
|
+
*/
|
|
280
|
+
declare const makeCreatePermissionRule: <TResource, TQuery>() => <TParams extends unknown[]>(rule: PermissionRule<TResource, TQuery, TParams>) => PermissionRule<TResource, TQuery, TParams>;
|
|
281
|
+
|
|
282
|
+
/**
|
|
283
|
+
* A thin wrapper around
|
|
284
|
+
* {@link @backstage/plugin-permission-common#PermissionClient} that allows all
|
|
285
|
+
* backend-to-backend requests.
|
|
286
|
+
* @public
|
|
287
|
+
*/
|
|
288
|
+
declare class ServerPermissionClient implements PermissionAuthorizer {
|
|
289
|
+
private readonly permissionClient;
|
|
290
|
+
private readonly tokenManager;
|
|
291
|
+
private readonly permissionEnabled;
|
|
292
|
+
static fromConfig(config: Config, options: {
|
|
293
|
+
discovery: PluginEndpointDiscovery;
|
|
294
|
+
tokenManager: TokenManager;
|
|
295
|
+
}): ServerPermissionClient;
|
|
296
|
+
private constructor();
|
|
297
|
+
authorize(queries: AuthorizeQuery[], options?: AuthorizeRequestOptions): Promise<AuthorizeDecision[]>;
|
|
298
|
+
private isValidServerToken;
|
|
299
|
+
}
|
|
300
|
+
|
|
301
|
+
export { ApplyConditionsRequest, ApplyConditionsRequestEntry, ApplyConditionsResponse, ApplyConditionsResponseEntry, Condition, ConditionTransformer, ConditionalPolicyDecision, Conditions, DefinitivePolicyDecision, PermissionPolicy, PermissionRule, PolicyAuthorizeQuery, PolicyDecision, ServerPermissionClient, createConditionExports, createConditionFactory, createConditionTransformer, createPermissionIntegrationRouter, createPermissionRule, makeCreatePermissionRule };
|
package/package.json
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@backstage/plugin-permission-node",
|
|
3
3
|
"description": "Common permission and authorization utilities for backend plugins",
|
|
4
|
-
"version": "0.5.
|
|
4
|
+
"version": "0.5.1",
|
|
5
5
|
"main": "dist/index.cjs.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
7
7
|
"license": "Apache-2.0",
|
|
@@ -33,11 +33,11 @@
|
|
|
33
33
|
"start": "backstage-cli package start"
|
|
34
34
|
},
|
|
35
35
|
"dependencies": {
|
|
36
|
-
"@backstage/backend-common": "^0.10.
|
|
37
|
-
"@backstage/config": "^0.1.
|
|
38
|
-
"@backstage/errors": "^0.2.
|
|
39
|
-
"@backstage/plugin-auth-node": "^0.1.
|
|
40
|
-
"@backstage/plugin-permission-common": "^0.5.
|
|
36
|
+
"@backstage/backend-common": "^0.10.9",
|
|
37
|
+
"@backstage/config": "^0.1.15",
|
|
38
|
+
"@backstage/errors": "^0.2.2",
|
|
39
|
+
"@backstage/plugin-auth-node": "^0.1.2",
|
|
40
|
+
"@backstage/plugin-permission-common": "^0.5.1",
|
|
41
41
|
"@types/express": "^4.17.6",
|
|
42
42
|
"express": "^4.17.1",
|
|
43
43
|
"express-promise-router": "^4.1.0",
|
|
@@ -52,5 +52,5 @@
|
|
|
52
52
|
"files": [
|
|
53
53
|
"dist"
|
|
54
54
|
],
|
|
55
|
-
"gitHead": "
|
|
55
|
+
"gitHead": "e244b348c473700e7d5e5fbcef38bd9f9fd1d0ba"
|
|
56
56
|
}
|