simple-authz 1.0.4 → 1.0.5
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/README.md +197 -113
- package/package.json +1 -1
- package/simple-authz-1.0.5.tgz +0 -0
package/README.md
CHANGED
|
@@ -8,26 +8,36 @@ The goal of this project is to make authorization **simple, fast, readable, and
|
|
|
8
8
|
|
|
9
9
|
---
|
|
10
10
|
|
|
11
|
+
## ⚠️ Development Status
|
|
12
|
+
|
|
13
|
+
**simple-authz** is currently under active development.
|
|
14
|
+
|
|
15
|
+
Some features may change, and there may be inconsistencies between the documentation and the package behavior.
|
|
16
|
+
|
|
17
|
+
We recommend testing thoroughly before using it in production.
|
|
18
|
+
|
|
19
|
+
---
|
|
20
|
+
|
|
11
21
|
# Table of Contents
|
|
12
22
|
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
23
|
+
- Overview
|
|
24
|
+
- Why Simple Authz
|
|
25
|
+
- Key Features
|
|
26
|
+
- Installation
|
|
27
|
+
- Quick Start
|
|
28
|
+
- Core Concepts
|
|
29
|
+
- Policy Language (TOON)
|
|
30
|
+
- Policy Examples
|
|
31
|
+
- Using Conditions
|
|
32
|
+
- Working with Roles
|
|
33
|
+
- Authorization API
|
|
34
|
+
- Example Integrations
|
|
35
|
+
- Project Structure
|
|
36
|
+
- Performance
|
|
37
|
+
- Security Model
|
|
38
|
+
- Roadmap
|
|
39
|
+
- Contributing
|
|
40
|
+
- License
|
|
31
41
|
|
|
32
42
|
---
|
|
33
43
|
|
|
@@ -48,20 +58,30 @@ Over time this logic spreads across many files and becomes difficult to maintain
|
|
|
48
58
|
Example policy file:
|
|
49
59
|
|
|
50
60
|
```
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
61
|
+
rule
|
|
62
|
+
role admin
|
|
63
|
+
action *
|
|
64
|
+
resource *
|
|
65
|
+
end
|
|
54
66
|
|
|
55
|
-
|
|
67
|
+
rule
|
|
68
|
+
role broker
|
|
69
|
+
action publish
|
|
70
|
+
resource listing
|
|
71
|
+
end
|
|
56
72
|
|
|
57
|
-
|
|
58
|
-
|
|
73
|
+
rule
|
|
74
|
+
role user
|
|
75
|
+
action edit
|
|
76
|
+
resource listing
|
|
77
|
+
condition listing.owner_id == user.id
|
|
78
|
+
end
|
|
59
79
|
```
|
|
60
80
|
|
|
61
81
|
Your application then only needs to ask:
|
|
62
82
|
|
|
63
83
|
```javascript
|
|
64
|
-
authz.can(user, "edit", "listing", listing)
|
|
84
|
+
authz.can(user, "edit", "listing", listing);
|
|
65
85
|
```
|
|
66
86
|
|
|
67
87
|
---
|
|
@@ -70,24 +90,24 @@ authz.can(user, "edit", "listing", listing)
|
|
|
70
90
|
|
|
71
91
|
Benefits of centralized authorization:
|
|
72
92
|
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
93
|
+
- Clear separation between **business logic and security rules**
|
|
94
|
+
- Easy permission updates without touching application code
|
|
95
|
+
- Better maintainability for large projects
|
|
96
|
+
- Safer and more predictable access control
|
|
97
|
+
- Easier onboarding for new developers
|
|
78
98
|
|
|
79
99
|
---
|
|
80
100
|
|
|
81
101
|
# Key Features
|
|
82
102
|
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
103
|
+
- Simple and readable **policy language**
|
|
104
|
+
- Fast permission lookup
|
|
105
|
+
- Support for **multiple user roles**
|
|
106
|
+
- Logical **conditional rules**
|
|
107
|
+
- Policy **validation**
|
|
108
|
+
- Policy **AST compilation**
|
|
109
|
+
- Lightweight with minimal dependencies
|
|
110
|
+
- Works with any Node.js framework
|
|
91
111
|
|
|
92
112
|
---
|
|
93
113
|
|
|
@@ -106,9 +126,9 @@ npm install simple-authz
|
|
|
106
126
|
## 1. Import the library
|
|
107
127
|
|
|
108
128
|
```javascript
|
|
109
|
-
const Authz = require("simple-authz")
|
|
129
|
+
const Authz = require("simple-authz");
|
|
110
130
|
|
|
111
|
-
const authz = new Authz()
|
|
131
|
+
const authz = new Authz();
|
|
112
132
|
```
|
|
113
133
|
|
|
114
134
|
---
|
|
@@ -124,14 +144,24 @@ authz.toon
|
|
|
124
144
|
Example policy:
|
|
125
145
|
|
|
126
146
|
```
|
|
127
|
-
|
|
147
|
+
rule
|
|
148
|
+
role admin
|
|
149
|
+
action *
|
|
150
|
+
resource *
|
|
151
|
+
end
|
|
128
152
|
|
|
129
|
-
|
|
153
|
+
rule
|
|
154
|
+
role broker
|
|
155
|
+
action publish
|
|
156
|
+
resource listing
|
|
157
|
+
end
|
|
130
158
|
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
159
|
+
rule
|
|
160
|
+
role user
|
|
161
|
+
action edit
|
|
162
|
+
resource listing
|
|
163
|
+
condition listing.owner_id == user.id
|
|
164
|
+
end
|
|
135
165
|
```
|
|
136
166
|
|
|
137
167
|
---
|
|
@@ -139,7 +169,7 @@ condition listing.owner_id == user.id
|
|
|
139
169
|
## 3. Load the policy
|
|
140
170
|
|
|
141
171
|
```javascript
|
|
142
|
-
authz.load("./authz.toon")
|
|
172
|
+
authz.load("./authz.toon");
|
|
143
173
|
```
|
|
144
174
|
|
|
145
175
|
---
|
|
@@ -147,16 +177,16 @@ authz.load("./authz.toon")
|
|
|
147
177
|
## 4. Check permissions
|
|
148
178
|
|
|
149
179
|
```javascript
|
|
150
|
-
const allowed = authz.can(user, "edit", "listing", listing)
|
|
180
|
+
const allowed = authz.can(user, "edit", "listing", listing);
|
|
151
181
|
```
|
|
152
182
|
|
|
153
183
|
Example usage:
|
|
154
184
|
|
|
155
185
|
```javascript
|
|
156
|
-
if(authz.can(user,"edit", "listing", listing)){
|
|
157
|
-
|
|
158
|
-
}else{
|
|
159
|
-
|
|
186
|
+
if (authz.can(user, "edit", "listing", listing)) {
|
|
187
|
+
updateListing();
|
|
188
|
+
} else {
|
|
189
|
+
throw new Error("Access denied");
|
|
160
190
|
}
|
|
161
191
|
```
|
|
162
192
|
|
|
@@ -171,15 +201,15 @@ Unlike `authz.can()`, which returns only `true` or `false`, this method returns
|
|
|
171
201
|
### Usage
|
|
172
202
|
|
|
173
203
|
```javascript
|
|
174
|
-
authz.explain(user, "edit", "listing", listing)
|
|
204
|
+
authz.explain(user, "edit", "listing", listing);
|
|
175
205
|
```
|
|
176
206
|
|
|
177
207
|
### Example
|
|
178
208
|
|
|
179
209
|
```javascript
|
|
180
|
-
const result = authz.explain(user, "edit", "listing", listing)
|
|
210
|
+
const result = authz.explain(user, "edit", "listing", listing);
|
|
181
211
|
|
|
182
|
-
console.log(result)
|
|
212
|
+
console.log(result);
|
|
183
213
|
```
|
|
184
214
|
|
|
185
215
|
### Example Output
|
|
@@ -236,15 +266,34 @@ Policies are written in **TOON format**.
|
|
|
236
266
|
Basic rule syntax:
|
|
237
267
|
|
|
238
268
|
```
|
|
239
|
-
|
|
269
|
+
rule
|
|
270
|
+
role <Role>
|
|
271
|
+
action <Action>
|
|
272
|
+
resource <Resource>
|
|
273
|
+
end
|
|
240
274
|
```
|
|
241
275
|
|
|
242
276
|
Example:
|
|
243
277
|
|
|
244
278
|
```
|
|
245
|
-
|
|
246
|
-
|
|
247
|
-
|
|
279
|
+
rule
|
|
280
|
+
role admin
|
|
281
|
+
action *
|
|
282
|
+
resource *
|
|
283
|
+
end
|
|
284
|
+
|
|
285
|
+
rule
|
|
286
|
+
role broker
|
|
287
|
+
action publish
|
|
288
|
+
resource listing
|
|
289
|
+
end
|
|
290
|
+
|
|
291
|
+
rule
|
|
292
|
+
role user
|
|
293
|
+
action edit
|
|
294
|
+
resource listing
|
|
295
|
+
condition listing.owner_id == user.id
|
|
296
|
+
end
|
|
248
297
|
```
|
|
249
298
|
|
|
250
299
|
---
|
|
@@ -256,7 +305,11 @@ You can use `*` to allow everything.
|
|
|
256
305
|
Example:
|
|
257
306
|
|
|
258
307
|
```
|
|
259
|
-
|
|
308
|
+
rule
|
|
309
|
+
role admin
|
|
310
|
+
action *
|
|
311
|
+
resource *
|
|
312
|
+
end
|
|
260
313
|
```
|
|
261
314
|
|
|
262
315
|
This allows the admin role to perform **any action on any resource**.
|
|
@@ -270,15 +323,23 @@ Policies can include conditions.
|
|
|
270
323
|
Syntax:
|
|
271
324
|
|
|
272
325
|
```
|
|
273
|
-
|
|
274
|
-
|
|
326
|
+
rule
|
|
327
|
+
role <role>
|
|
328
|
+
action <action>
|
|
329
|
+
resource <resource>
|
|
330
|
+
condition <condition1> OR <condition2>
|
|
331
|
+
end
|
|
275
332
|
```
|
|
276
333
|
|
|
277
334
|
Example:
|
|
278
335
|
|
|
279
336
|
```
|
|
280
|
-
|
|
281
|
-
|
|
337
|
+
rule
|
|
338
|
+
role user
|
|
339
|
+
action view
|
|
340
|
+
resource listing
|
|
341
|
+
condition listing.status == "public" OR listing.owner_id == user.id
|
|
342
|
+
end
|
|
282
343
|
```
|
|
283
344
|
|
|
284
345
|
Meaning:
|
|
@@ -300,8 +361,12 @@ Conditions can reference:
|
|
|
300
361
|
Example:
|
|
301
362
|
|
|
302
363
|
```
|
|
303
|
-
|
|
304
|
-
|
|
364
|
+
rule
|
|
365
|
+
role user
|
|
366
|
+
action edit
|
|
367
|
+
resource profile
|
|
368
|
+
condition user.id == resource.id
|
|
369
|
+
end
|
|
305
370
|
```
|
|
306
371
|
|
|
307
372
|
---
|
|
@@ -311,11 +376,23 @@ condition user.id == resource.id
|
|
|
311
376
|
## Example 1 – Basic Roles
|
|
312
377
|
|
|
313
378
|
```
|
|
314
|
-
|
|
379
|
+
rule
|
|
380
|
+
role admin
|
|
381
|
+
action *
|
|
382
|
+
resource *
|
|
383
|
+
end
|
|
315
384
|
|
|
316
|
-
|
|
385
|
+
rule
|
|
386
|
+
role broker
|
|
387
|
+
action publish
|
|
388
|
+
resource listing
|
|
389
|
+
end
|
|
317
390
|
|
|
318
|
-
|
|
391
|
+
rule
|
|
392
|
+
role user
|
|
393
|
+
action edit
|
|
394
|
+
resource listing
|
|
395
|
+
end
|
|
319
396
|
```
|
|
320
397
|
|
|
321
398
|
---
|
|
@@ -323,8 +400,12 @@ allow broker publish listing
|
|
|
323
400
|
## Example 2 – Ownership Rules
|
|
324
401
|
|
|
325
402
|
```
|
|
326
|
-
|
|
327
|
-
|
|
403
|
+
rule
|
|
404
|
+
role broker
|
|
405
|
+
action edit
|
|
406
|
+
resource listing
|
|
407
|
+
condition listing.owner_id == user.id
|
|
408
|
+
end
|
|
328
409
|
```
|
|
329
410
|
|
|
330
411
|
---
|
|
@@ -332,14 +413,24 @@ condition listing.owner_id == user.id
|
|
|
332
413
|
## Example 3 – Multiple Rules
|
|
333
414
|
|
|
334
415
|
```
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
|
|
416
|
+
rule
|
|
417
|
+
role admin
|
|
418
|
+
action *
|
|
419
|
+
resource *
|
|
420
|
+
end
|
|
338
421
|
|
|
339
|
-
|
|
422
|
+
rule
|
|
423
|
+
role broker
|
|
424
|
+
action publish
|
|
425
|
+
resource listing
|
|
426
|
+
end
|
|
340
427
|
|
|
341
|
-
|
|
342
|
-
|
|
428
|
+
rule
|
|
429
|
+
role user
|
|
430
|
+
action edit
|
|
431
|
+
resource listing
|
|
432
|
+
condition listing.owner_id == user.id
|
|
433
|
+
end
|
|
343
434
|
```
|
|
344
435
|
|
|
345
436
|
---
|
|
@@ -352,18 +443,18 @@ Example user:
|
|
|
352
443
|
|
|
353
444
|
```javascript
|
|
354
445
|
const user = {
|
|
355
|
-
|
|
356
|
-
|
|
357
|
-
}
|
|
446
|
+
id: 10,
|
|
447
|
+
roles: ["broker"],
|
|
448
|
+
};
|
|
358
449
|
```
|
|
359
450
|
|
|
360
451
|
Multiple roles:
|
|
361
452
|
|
|
362
453
|
```javascript
|
|
363
454
|
const user = {
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
}
|
|
455
|
+
id: 5,
|
|
456
|
+
roles: ["user", "editor"],
|
|
457
|
+
};
|
|
367
458
|
```
|
|
368
459
|
|
|
369
460
|
The engine checks permissions against **all roles**.
|
|
@@ -375,7 +466,7 @@ The engine checks permissions against **all roles**.
|
|
|
375
466
|
## Load policy file
|
|
376
467
|
|
|
377
468
|
```javascript
|
|
378
|
-
authz.load("./authz.toon")
|
|
469
|
+
authz.load("./authz.toon");
|
|
379
470
|
```
|
|
380
471
|
|
|
381
472
|
---
|
|
@@ -383,13 +474,13 @@ authz.load("./authz.toon")
|
|
|
383
474
|
## Check permission
|
|
384
475
|
|
|
385
476
|
```javascript
|
|
386
|
-
authz.can(user, action, resource, object)
|
|
477
|
+
authz.can(user, action, resource, object);
|
|
387
478
|
```
|
|
388
479
|
|
|
389
480
|
Example:
|
|
390
481
|
|
|
391
482
|
```javascript
|
|
392
|
-
authz.can(user,"edit","listing",listing)
|
|
483
|
+
authz.can(user, "edit", "listing", listing);
|
|
393
484
|
```
|
|
394
485
|
|
|
395
486
|
Returns:
|
|
@@ -410,22 +501,22 @@ User:
|
|
|
410
501
|
```javascript
|
|
411
502
|
const user = {
|
|
412
503
|
id: 10,
|
|
413
|
-
roles: ["broker"]
|
|
414
|
-
}
|
|
504
|
+
roles: ["broker"],
|
|
505
|
+
};
|
|
415
506
|
```
|
|
416
507
|
|
|
417
508
|
Listing:
|
|
418
509
|
|
|
419
510
|
```javascript
|
|
420
511
|
const listing = {
|
|
421
|
-
owner_id: 10
|
|
422
|
-
}
|
|
512
|
+
owner_id: 10,
|
|
513
|
+
};
|
|
423
514
|
```
|
|
424
515
|
|
|
425
516
|
Permission check:
|
|
426
517
|
|
|
427
518
|
```javascript
|
|
428
|
-
authz.can(user,"edit","listing",listing)
|
|
519
|
+
authz.can(user, "edit", "listing", listing);
|
|
429
520
|
```
|
|
430
521
|
|
|
431
522
|
Result:
|
|
@@ -441,21 +532,15 @@ true
|
|
|
441
532
|
Example route protection:
|
|
442
533
|
|
|
443
534
|
```javascript
|
|
444
|
-
app.put("/listing/:id", async (req,res)=>{
|
|
535
|
+
app.put("/listing/:id", async (req, res) => {
|
|
536
|
+
const allowed = authz.can(req.user, "edit", "listing", req.listing);
|
|
445
537
|
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
"listing",
|
|
450
|
-
req.listing
|
|
451
|
-
)
|
|
538
|
+
if (!allowed) {
|
|
539
|
+
return res.status(403).send("Access denied");
|
|
540
|
+
}
|
|
452
541
|
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
}
|
|
456
|
-
|
|
457
|
-
updateListing()
|
|
458
|
-
})
|
|
542
|
+
updateListing();
|
|
543
|
+
});
|
|
459
544
|
```
|
|
460
545
|
|
|
461
546
|
---
|
|
@@ -510,13 +595,13 @@ This reduces the risk of unintended access.
|
|
|
510
595
|
|
|
511
596
|
Future versions may include:
|
|
512
597
|
|
|
513
|
-
|
|
514
|
-
|
|
515
|
-
|
|
516
|
-
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
598
|
+
- Policy hot reloading
|
|
599
|
+
- Role inheritance
|
|
600
|
+
- Policy debugger
|
|
601
|
+
- Middleware helpers
|
|
602
|
+
- Permission caching
|
|
603
|
+
- Modular policy files
|
|
604
|
+
- Distributed policy storage
|
|
520
605
|
|
|
521
606
|
---
|
|
522
607
|
|
|
@@ -543,5 +628,4 @@ This project is licensed under the [Apache 2.0 license](LICENSE).
|
|
|
543
628
|
|
|
544
629
|
Simple Authz was created to simplify authorization logic in modern Node.js applications.
|
|
545
630
|
|
|
546
|
-
|
|
547
|
-
# Keywords
|
|
631
|
+
# Keywords
|
package/package.json
CHANGED
|
Binary file
|