@navirondynamics/accord 1.0.0 → 1.1.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/README.md CHANGED
@@ -1,49 +1,235 @@
1
- Accord
1
+ # Accord
2
2
 
3
- Accord is a policy-first identity and access engine designed to unify identity representation, context resolution, and authorization under a single, declarative policy model.
3
+ <p align="center">
4
+ <a href="https://www.npmjs.com/package/@navirondynamics/accord">
5
+ <img src="https://img.shields.io/npm/v/@navirondynamics/accord.svg" alt="npm version" />
6
+ </a>
7
+ <a href="https://www.npmjs.com/package/@navirondynamics/accord">
8
+ <img src="https://img.shields.io/npm/dm/@navirondynamics/accord.svg" alt="npm downloads" />
9
+ </a>
10
+ <a href="https://github.com/bsen-alt/Accord">
11
+ <img src="https://img.shields.io/github/license/bsen-alt/Accord" alt="license" />
12
+ </a>
13
+ </p>
4
14
 
5
- Installation
15
+ Accord is a **policy-first identity and access engine for Node.js**.
6
16
 
7
- `bashnpm install accord`
17
+ It treats access not as scattered application logic, but as a formal agreement between identities, systems, and resources - evaluated through declarative, versioned policies.
8
18
 
9
- Quick Start
19
+ **New in v1.1:** Observability, YAML configuration, hot reload, and native NestJS support.
10
20
 
11
- 1. Initialize Configuration
21
+ ---
12
22
 
13
- Create a config folder in your project root.
23
+ ## Table of Contents
14
24
 
15
- config/policies.json`json[ { "id": "policy-admin", "version": "1.0", "effect": "allow", "subject": { "type": "user", "attributes": { "role": "admin" } }, "action": ["delete"], "resource": { "type": "booking" } }]`
25
+ - [Why Accord](#-why-accord)
26
+ - [Key Features](#key-features)
27
+ - [Installation](#-installation)
28
+ - [Quick Start](#-quick-start-v11)
29
+ - [Framework Integration](#-framework-integration)
30
+ - [CLI Tool](#-cli-tool)
31
+ - [Documentation](#-documentation)
32
+ - [Roadmap](#-roadmap)
33
+ - [Contributing](#-contributing)
34
+ - [License](#-license)
16
35
 
17
- config/identities.json`json[ { "id": "admin_01", "type": "user", "status": "active", "attributes": { "role": "admin" } }]`
36
+ ---
18
37
 
19
- 2. Use in Code
38
+ ## 🚀 Why Accord?
20
39
 
21
- ````typescriptimport
40
+ Modern authorization is fragmented:
22
41
 
23
- const accord = new Accord({ policyPath: './config/policies.json', identityPath: './config/identities.json'});
42
+ - Authentication in one service
43
+ - Roles in another
44
+ - Access logic scattered across microservices
24
45
 
25
- async function deleteBooking(bookingId: string, userId: string) { const decision = await accord.check(userId, 'delete', { type: 'booking', id: bookingId });
46
+ Accord centralizes authorization into a single **governance layer**, acting as the _System of Record_ for access control across your platform.
26
47
 
27
- if (decision.decision === 'allow') { console.log('Access Granted'); // Perform delete... } else { console.log('Access Denied:', decision.reason); }}```
48
+ Instead of embedding authorization logic throughout your codebase, Accord externalizes it into auditable, inspectable, and versioned policy definitions.
28
49
 
29
- Express Middleware
30
- Protect your routes easily:
50
+ ---
31
51
 
32
- ```typescriptimport express from 'express';import { Accord } from 'accord';import { protect } from 'accord/adapters/express'; // Note: Check actual path after build
52
+ ## Key Features
33
53
 
34
- const app = express();const accord = new Accord({ policyPath: './config/policies.json', ... });
54
+ - 🔍 **Observability** Built-in audit logging (console & file)
55
+ - 📝 **Policy as Code** – JSON and YAML configuration support
56
+ - 🛡️ **Reliability** – Zod-based schema validation to prevent invalid policies
57
+ - 🔄 **Zero-Downtime Updates** – Hot reload policies without restarting services
58
+ - 🧩 **Framework Adapters** – Express, NestJS, and Fastify integrations
59
+ - 📦 **CLI Tooling** – Validate and simulate access decisions locally
35
60
 
36
- // Protect this routeapp.delete('/bookings/:id', protect({ accordInstance: accord, action: 'delete', resourceType: 'booking' }), (req, res) => { // Only allowed users reach here res.send('Booking deleted'); });```
61
+ ---
37
62
 
38
- CLI Tool
39
- Validate policies locally:
63
+ ## 📦 Installation
40
64
 
41
- ```bashnpx accord-cli validate ./config/policies.json```
65
+ ```bash
66
+ npm install @navirondynamics/accord
67
+ ```
42
68
 
43
- Test access logic:
69
+ ---
44
70
 
45
- ```bashnpx accord-cli eval -i user_123 -a delete -r booking```
71
+ ## 🛠️ Quick Start (v1.1)
72
+
73
+ ### 1. Define Policies (YAML supported)
74
+
75
+ Create `config/policies.yaml`:
76
+
77
+ ```yaml
78
+ - id: 'admin-delete'
79
+ version: '1.1'
80
+ effect: 'allow'
81
+ subject:
82
+ type: 'user'
83
+ attributes:
84
+ role: 'admin'
85
+ action: ['delete']
86
+ resource:
87
+ type: 'booking'
88
+ ```
89
+
90
+ ---
91
+
92
+ ### 2. Initialize Accord
93
+
94
+ ```javascript
95
+ const { Accord, ConsoleAuditLogger } = require('@navirondynamics/accord');
96
+
97
+ const accord = new Accord({
98
+ policyPath: './config/policies.yaml',
99
+ identityPath: './config/identities.json',
100
+ logger: new ConsoleAuditLogger(),
101
+ });
102
+ ```
103
+
104
+ ---
105
+
106
+ ### 3. Check Access
107
+
108
+ ```javascript
109
+ async function deleteUser(userId) {
110
+ const decision = await accord.check(userId, 'delete', {
111
+ type: 'user',
112
+ id: userId,
113
+ });
114
+
115
+ if (decision.decision === 'allow') {
116
+ console.log('Permission Granted');
117
+ // Perform deletion...
118
+ } else {
119
+ console.log('Access Denied:', decision.reason);
120
+ }
121
+ }
122
+ ```
123
+
124
+ ---
125
+
126
+ ## 🛡️ Framework Integration
127
+
128
+ ### NestJS
129
+
130
+ ```typescript
131
+ import { AccordGuard } from '@navirondynamics/accord/adapters/nest';
132
+
133
+ @Controller('bookings')
134
+ export class BookingController {
135
+ @UseGuards(
136
+ new AccordGuard({
137
+ accordInstance: accord,
138
+ action: 'delete',
139
+ resourceType: 'booking',
140
+ })
141
+ )
142
+ @Delete(':id')
143
+ deleteBooking(@Param('id') id: string) {
144
+ // Only authorized users reach here
145
+ }
146
+ }
147
+ ```
148
+
149
+ ---
150
+
151
+ ### Express
152
+
153
+ ```javascript
154
+ const { protect } = require('@navirondynamics/accord/adapters/express');
155
+
156
+ app.delete(
157
+ '/bookings/:id',
158
+ protect({
159
+ accordInstance: accord,
160
+ action: 'delete',
161
+ resourceType: 'booking',
162
+ }),
163
+ (req, res) => {
164
+ res.send('Deleted');
165
+ }
166
+ );
167
+ ```
168
+
169
+ Fastify support and advanced usage are available in the adapters documentation.
170
+
171
+ ---
172
+
173
+ ## 🔧 CLI Tool
174
+
175
+ Validate policies or simulate access decisions directly from your terminal.
176
+
177
+ ```bash
178
+ # Validate policy syntax
179
+ npx @navirondynamics/accord validate ./config/policies.yaml
180
+
181
+ # Test access logic
182
+ npx @navirondynamics/accord eval -i user_123 -a delete -r booking
183
+ ```
184
+
185
+ ---
186
+
187
+ ## 📚 Documentation
188
+
189
+ - **Getting Started** – Installation and core concepts
190
+ - **Configuration Guide** – Identities, policies, JSON vs YAML
191
+ - **Observability & Auditing** – Production logging setup
192
+ - **Framework Adapters** – Express, NestJS, Fastify usage
193
+ - **CLI Reference** – Full command list
194
+
195
+ ---
196
+
197
+ ## 🗺️ Roadmap
198
+
199
+ Planned improvements:
200
+
201
+ - Policy versioning & rollback
202
+ - Database-backed policy storage
203
+ - Web-based policy editor
204
+ - Decision caching
205
+ - OpenTelemetry tracing
206
+ - Distributed policy synchronization
207
+
208
+ ---
209
+
210
+ ## 🤝 Contributing
211
+
212
+ Contributions are welcome.
213
+
214
+ 1. Fork the repository
215
+ 2. Create a feature branch
216
+
217
+ ```bash
218
+ git checkout -b feature/my-feature
219
+ ```
220
+
221
+ 3. Commit your changes
222
+ 4. Push to your fork
223
+ 5. Open a Pull Request
224
+
225
+ Please ensure tests pass and documentation is updated.
226
+
227
+ ---
228
+
229
+ ## 📜 License
46
230
 
47
- License
48
231
  ISC
49
- ````
232
+
233
+ ```
234
+
235
+ ```
package/dist/accord.d.ts CHANGED
@@ -1,16 +1,24 @@
1
1
  import { IdentityStore } from './store/identity';
2
+ import { AuditLogger } from './core/logger';
2
3
  import { Decision } from './core/types';
3
4
  export interface AccordConfig {
4
5
  policyPath: string;
5
6
  identityPath: string;
7
+ logger?: AuditLogger;
6
8
  }
7
9
  export declare class Accord {
8
10
  private policies;
9
11
  private identityStore;
10
12
  private resolver;
11
13
  private config;
14
+ private logger;
12
15
  constructor(config: AccordConfig);
13
16
  check(externalId: string, action: string, resource: any, context?: any): Promise<Decision>;
14
17
  getStore(): IdentityStore;
18
+ /**
19
+ * Reloads Policies and Identities from disk.
20
+ * SAFETY: If the new config is invalid, the old config remains active.
21
+ */
22
+ reload(): void;
15
23
  }
16
24
  //# sourceMappingURL=accord.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"accord.d.ts","sourceRoot":"","sources":["../src/accord.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAGjD,OAAO,EAAiB,QAAQ,EAAkB,MAAM,cAAc,CAAC;AAEvE,MAAM,WAAW,YAAY;IAC3B,UAAU,EAAE,MAAM,CAAC;IACnB,YAAY,EAAE,MAAM,CAAC;CACtB;AAED,qBAAa,MAAM;IACjB,OAAO,CAAC,QAAQ,CAAmB;IACnC,OAAO,CAAC,aAAa,CAAgB;IACrC,OAAO,CAAC,QAAQ,CAAmB;IACnC,OAAO,CAAC,MAAM,CAAe;gBAEjB,MAAM,EAAE,YAAY;IAc1B,KAAK,CACT,UAAU,EAAE,MAAM,EAClB,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,GAAG,EACb,OAAO,CAAC,EAAE,GAAG,GACZ,OAAO,CAAC,QAAQ,CAAC;IAyBpB,QAAQ,IAAI,aAAa;CAG1B"}
1
+ {"version":3,"file":"accord.d.ts","sourceRoot":"","sources":["../src/accord.ts"],"names":[],"mappings":"AAGA,OAAO,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAGjD,OAAO,EAAE,WAAW,EAAkC,MAAM,eAAe,CAAC;AAC5E,OAAO,EAAiB,QAAQ,EAAkB,MAAM,cAAc,CAAC;AAEvE,MAAM,WAAW,YAAY;IAC3B,UAAU,EAAE,MAAM,CAAC;IACnB,YAAY,EAAE,MAAM,CAAC;IACrB,MAAM,CAAC,EAAE,WAAW,CAAC;CACtB;AAED,qBAAa,MAAM;IACjB,OAAO,CAAC,QAAQ,CAAmB;IACnC,OAAO,CAAC,aAAa,CAAgB;IACrC,OAAO,CAAC,QAAQ,CAAmB;IACnC,OAAO,CAAC,MAAM,CAAe;IAC7B,OAAO,CAAC,MAAM,CAAc;gBAEhB,MAAM,EAAE,YAAY;IAiB1B,KAAK,CACT,UAAU,EAAE,MAAM,EAClB,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,GAAG,EACb,OAAO,CAAC,EAAE,GAAG,GACZ,OAAO,CAAC,QAAQ,CAAC;IAwCpB,QAAQ,IAAI,aAAa;IAIzB;;;OAGG;IACH,MAAM,IAAI,IAAI;CAmBf"}
package/dist/accord.js CHANGED
@@ -3,22 +3,26 @@ Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.Accord = void 0;
4
4
  // src/accord.ts
5
5
  const loader_1 = require("./core/loader");
6
- const compiler_1 = require("./core/compiler"); // NEW
6
+ const compiler_1 = require("./core/compiler");
7
7
  const identity_1 = require("./store/identity");
8
8
  const resolver_1 = require("./core/resolver");
9
9
  const evaluator_1 = require("./core/evaluator");
10
+ const logger_1 = require("./core/logger"); // NEW IMPORTS
10
11
  class Accord {
11
12
  constructor(config) {
12
13
  this.config = config;
13
- // 1. Initialize Store
14
+ // 1. Initialize Logger (Default to ConsoleAuditLogger)
15
+ this.logger = config.logger || new logger_1.ConsoleAuditLogger();
16
+ // 2. Initialize Store
14
17
  this.identityStore = new identity_1.IdentityStore(config.identityPath);
15
- // 2. Initialize Resolver
18
+ // 3. Initialize Resolver
16
19
  this.resolver = new resolver_1.IdentityResolver(this.identityStore);
17
- // 3. Load and COMPILE Policies
20
+ // 4. Load and COMPILE Policies
18
21
  const rawPolicies = (0, loader_1.loadPolicies)(config.policyPath);
19
22
  this.policies = (0, compiler_1.compilePolicies)(rawPolicies);
20
23
  }
21
24
  async check(externalId, action, resource, context) {
25
+ let decision;
22
26
  try {
23
27
  // 1. Resolve Identity
24
28
  const identity = this.resolver.resolve(externalId);
@@ -30,19 +34,51 @@ class Accord {
30
34
  context: context || {}
31
35
  };
32
36
  // 3. Evaluate
33
- const decision = await (0, evaluator_1.evaluate)(request, this.policies);
34
- return decision;
37
+ decision = await (0, evaluator_1.evaluate)(request, this.policies);
35
38
  }
36
39
  catch (error) {
37
- return {
40
+ decision = {
38
41
  decision: 'deny',
39
42
  reason: error.message
40
43
  };
41
44
  }
45
+ // 4. AUDIT LOG (New Step)
46
+ this.logger.log({
47
+ timestamp: new Date(),
48
+ decision: decision.decision,
49
+ policyId: decision.policy_id,
50
+ reason: decision.reason,
51
+ userId: externalId,
52
+ action: action,
53
+ resourceType: resource.type,
54
+ resourceId: resource.id
55
+ });
56
+ return decision;
42
57
  }
43
58
  getStore() {
44
59
  return this.identityStore;
45
60
  }
61
+ /**
62
+ * Reloads Policies and Identities from disk.
63
+ * SAFETY: If the new config is invalid, the old config remains active.
64
+ */
65
+ reload() {
66
+ try {
67
+ // 1. Reload Policies
68
+ const newRawPolicies = (0, loader_1.loadPolicies)(this.config.policyPath);
69
+ const newCompiledPolicies = (0, compiler_1.compilePolicies)(newRawPolicies);
70
+ // 2. Reload Identities
71
+ this.identityStore.reload();
72
+ // 3. Swap Logic (Atomic Update)
73
+ this.policies = newCompiledPolicies;
74
+ console.log('✓ Accord Reloaded Successfully');
75
+ }
76
+ catch (error) {
77
+ console.error('✗ Reload Failed. Old config is still active.');
78
+ console.error('Reason:', error.message);
79
+ // We do NOT throw here. We want the app to keep running on old config.
80
+ }
81
+ }
46
82
  }
47
83
  exports.Accord = Accord;
48
84
  //# sourceMappingURL=accord.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"accord.js","sourceRoot":"","sources":["../src/accord.ts"],"names":[],"mappings":";;;AAAA,gBAAgB;AAChB,0CAA6C;AAC7C,8CAAkD,CAAC,MAAM;AACzD,+CAAiD;AACjD,8CAAmD;AACnD,gDAA4C;AAQ5C,MAAa,MAAM;IAMjB,YAAY,MAAoB;QAC9B,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QAErB,sBAAsB;QACtB,IAAI,CAAC,aAAa,GAAG,IAAI,wBAAa,CAAC,MAAM,CAAC,YAAY,CAAC,CAAC;QAE5D,yBAAyB;QACzB,IAAI,CAAC,QAAQ,GAAG,IAAI,2BAAgB,CAAC,IAAI,CAAC,aAAa,CAAC,CAAC;QAEzD,+BAA+B;QAC/B,MAAM,WAAW,GAAG,IAAA,qBAAY,EAAC,MAAM,CAAC,UAAU,CAAC,CAAC;QACpD,IAAI,CAAC,QAAQ,GAAG,IAAA,0BAAe,EAAC,WAAW,CAAC,CAAC;IAC/C,CAAC;IAED,KAAK,CAAC,KAAK,CACT,UAAkB,EAClB,MAAc,EACd,QAAa,EACb,OAAa;QAEb,IAAI,CAAC;YACH,sBAAsB;YACtB,MAAM,QAAQ,GAAG,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC,UAAU,CAAC,CAAC;YAEnD,6BAA6B;YAC7B,MAAM,OAAO,GAAkB;gBAC7B,OAAO,EAAE,QAAQ;gBACjB,MAAM,EAAE,MAAM;gBACd,QAAQ,EAAE,QAAQ;gBAClB,OAAO,EAAE,OAAO,IAAI,EAAE;aACvB,CAAC;YAEF,cAAc;YACd,MAAM,QAAQ,GAAG,MAAM,IAAA,oBAAQ,EAAC,OAAO,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;YAExD,OAAO,QAAQ,CAAC;QAClB,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO;gBACL,QAAQ,EAAE,MAAM;gBAChB,MAAM,EAAG,KAAe,CAAC,OAAO;aACjC,CAAC;QACJ,CAAC;IACH,CAAC;IAED,QAAQ;QACN,OAAO,IAAI,CAAC,aAAa,CAAC;IAC5B,CAAC;CACF;AArDD,wBAqDC"}
1
+ {"version":3,"file":"accord.js","sourceRoot":"","sources":["../src/accord.ts"],"names":[],"mappings":";;;AAAA,gBAAgB;AAChB,0CAA6C;AAC7C,8CAAkD;AAClD,+CAAiD;AACjD,8CAAmD;AACnD,gDAA4C;AAC5C,0CAA4E,CAAC,cAAc;AAS3F,MAAa,MAAM;IAOjB,YAAY,MAAoB;QAC9B,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC;QAErB,uDAAuD;QACvD,IAAI,CAAC,MAAM,GAAG,MAAM,CAAC,MAAM,IAAI,IAAI,2BAAkB,EAAE,CAAC;QAExD,sBAAsB;QACtB,IAAI,CAAC,aAAa,GAAG,IAAI,wBAAa,CAAC,MAAM,CAAC,YAAY,CAAC,CAAC;QAE5D,yBAAyB;QACzB,IAAI,CAAC,QAAQ,GAAG,IAAI,2BAAgB,CAAC,IAAI,CAAC,aAAa,CAAC,CAAC;QAEzD,+BAA+B;QAC/B,MAAM,WAAW,GAAG,IAAA,qBAAY,EAAC,MAAM,CAAC,UAAU,CAAC,CAAC;QACpD,IAAI,CAAC,QAAQ,GAAG,IAAA,0BAAe,EAAC,WAAW,CAAC,CAAC;IAC/C,CAAC;IAED,KAAK,CAAC,KAAK,CACT,UAAkB,EAClB,MAAc,EACd,QAAa,EACb,OAAa;QAEb,IAAI,QAAkB,CAAC;QAEvB,IAAI,CAAC;YACH,sBAAsB;YACtB,MAAM,QAAQ,GAAG,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC,UAAU,CAAC,CAAC;YAEnD,6BAA6B;YAC7B,MAAM,OAAO,GAAkB;gBAC7B,OAAO,EAAE,QAAQ;gBACjB,MAAM,EAAE,MAAM;gBACd,QAAQ,EAAE,QAAQ;gBAClB,OAAO,EAAE,OAAO,IAAI,EAAE;aACvB,CAAC;YAEF,cAAc;YACd,QAAQ,GAAG,MAAM,IAAA,oBAAQ,EAAC,OAAO,EAAE,IAAI,CAAC,QAAQ,CAAC,CAAC;QAEpD,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,QAAQ,GAAG;gBACT,QAAQ,EAAE,MAAM;gBAChB,MAAM,EAAG,KAAe,CAAC,OAAO;aACjC,CAAC;QACJ,CAAC;QAED,0BAA0B;QAC1B,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC;YACd,SAAS,EAAE,IAAI,IAAI,EAAE;YACrB,QAAQ,EAAE,QAAQ,CAAC,QAAQ;YAC3B,QAAQ,EAAE,QAAQ,CAAC,SAAS;YAC5B,MAAM,EAAE,QAAQ,CAAC,MAAM;YACvB,MAAM,EAAE,UAAU;YAClB,MAAM,EAAE,MAAM;YACd,YAAY,EAAE,QAAQ,CAAC,IAAI;YAC3B,UAAU,EAAE,QAAQ,CAAC,EAAE;SACxB,CAAC,CAAC;QAEH,OAAO,QAAQ,CAAC;IAClB,CAAC;IAED,QAAQ;QACN,OAAO,IAAI,CAAC,aAAa,CAAC;IAC5B,CAAC;IAED;;;OAGG;IACH,MAAM;QACJ,IAAI,CAAC;YACH,qBAAqB;YACrB,MAAM,cAAc,GAAG,IAAA,qBAAY,EAAC,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC;YAC5D,MAAM,mBAAmB,GAAG,IAAA,0BAAe,EAAC,cAAc,CAAC,CAAC;YAE5D,uBAAuB;YACvB,IAAI,CAAC,aAAa,CAAC,MAAM,EAAE,CAAC;YAE5B,gCAAgC;YAChC,IAAI,CAAC,QAAQ,GAAG,mBAAmB,CAAC;YAEpC,OAAO,CAAC,GAAG,CAAC,gCAAgC,CAAC,CAAC;QAChD,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,8CAA8C,CAAC,CAAC;YAC9D,OAAO,CAAC,KAAK,CAAC,SAAS,EAAG,KAAe,CAAC,OAAO,CAAC,CAAC;YACnD,uEAAuE;QACzE,CAAC;IACH,CAAC;CACF;AAhGD,wBAgGC"}
@@ -0,0 +1,14 @@
1
+ import { FastifyRequest, FastifyReply } from 'fastify';
2
+ import { Accord } from '../accord';
3
+ export interface AccordHookOptions {
4
+ accordInstance: Accord;
5
+ action: string;
6
+ resourceType: string;
7
+ getId?: (req: FastifyRequest) => string;
8
+ }
9
+ /**
10
+ * Fastify Hook Factory
11
+ * Usage: fastify.addHook('onRequest', accordHook({ ... }))
12
+ */
13
+ export declare function accordHook(options: AccordHookOptions): (req: FastifyRequest, reply: FastifyReply) => Promise<undefined>;
14
+ //# sourceMappingURL=fastify.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fastify.d.ts","sourceRoot":"","sources":["../../src/adapters/fastify.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,cAAc,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AACvD,OAAO,EAAE,MAAM,EAAE,MAAM,WAAW,CAAC;AAGnC,MAAM,WAAW,iBAAiB;IAChC,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,EAAE,MAAM,CAAC;IACf,YAAY,EAAE,MAAM,CAAC;IAErB,KAAK,CAAC,EAAE,CAAC,GAAG,EAAE,cAAc,KAAK,MAAM,CAAC;CACzC;AAED;;;GAGG;AACH,wBAAgB,UAAU,CAAC,OAAO,EAAE,iBAAiB,IACrC,KAAK,cAAc,EAAE,OAAO,YAAY,wBAwCvD"}
@@ -0,0 +1,44 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.accordHook = accordHook;
4
+ /**
5
+ * Fastify Hook Factory
6
+ * Usage: fastify.addHook('onRequest', accordHook({ ... }))
7
+ */
8
+ function accordHook(options) {
9
+ return async (req, reply) => {
10
+ try {
11
+ // 1. Determine User ID
12
+ const userId = options.getId
13
+ ? options.getId(req)
14
+ : req.headers['x-user-id'];
15
+ if (!userId) {
16
+ return reply.status(401).send({ error: 'User ID missing' });
17
+ }
18
+ // 2. Construct Resource
19
+ const resource = {
20
+ type: options.resourceType,
21
+ id: req.params.id,
22
+ attributes: req.body || {}
23
+ };
24
+ // 3. Check Policy
25
+ const decision = await options.accordInstance.check(userId, options.action, resource);
26
+ // 4. Enforce
27
+ if (decision.decision === 'allow') {
28
+ req.authDecision = decision;
29
+ return; // Continue
30
+ }
31
+ else {
32
+ return reply.status(403).send({
33
+ error: 'Access Denied',
34
+ reason: decision.reason
35
+ });
36
+ }
37
+ }
38
+ catch (error) {
39
+ console.error('Fastify Accord Hook Error:', error);
40
+ return reply.status(500).send({ error: 'Internal Server Error' });
41
+ }
42
+ };
43
+ }
44
+ //# sourceMappingURL=fastify.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"fastify.js","sourceRoot":"","sources":["../../src/adapters/fastify.ts"],"names":[],"mappings":";;AAiBA,gCAyCC;AA7CD;;;GAGG;AACH,SAAgB,UAAU,CAAC,OAA0B;IACnD,OAAO,KAAK,EAAE,GAAmB,EAAE,KAAmB,EAAE,EAAE;QACxD,IAAI,CAAC;YACH,uBAAuB;YACvB,MAAM,MAAM,GAAG,OAAO,CAAC,KAAK;gBAC1B,CAAC,CAAC,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC;gBACpB,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,WAAW,CAAW,CAAC;YAEvC,IAAI,CAAC,MAAM,EAAE,CAAC;gBACZ,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,iBAAiB,EAAE,CAAC,CAAC;YAC9D,CAAC;YAED,wBAAwB;YACxB,MAAM,QAAQ,GAAG;gBACf,IAAI,EAAE,OAAO,CAAC,YAAY;gBAC1B,EAAE,EAAG,GAAG,CAAC,MAAc,CAAC,EAAE;gBAC1B,UAAU,EAAE,GAAG,CAAC,IAAI,IAAI,EAAE;aAC3B,CAAC;YAEF,kBAAkB;YAClB,MAAM,QAAQ,GAAa,MAAM,OAAO,CAAC,cAAc,CAAC,KAAK,CAC3D,MAAM,EACN,OAAO,CAAC,MAAM,EACd,QAAQ,CACT,CAAC;YAEF,aAAa;YACb,IAAI,QAAQ,CAAC,QAAQ,KAAK,OAAO,EAAE,CAAC;gBACjC,GAAW,CAAC,YAAY,GAAG,QAAQ,CAAC;gBACrC,OAAO,CAAC,WAAW;YACrB,CAAC;iBAAM,CAAC;gBACN,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC;oBAC5B,KAAK,EAAE,eAAe;oBACtB,MAAM,EAAE,QAAQ,CAAC,MAAM;iBACxB,CAAC,CAAC;YACL,CAAC;QACH,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,4BAA4B,EAAE,KAAK,CAAC,CAAC;YACnD,OAAO,KAAK,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,IAAI,CAAC,EAAE,KAAK,EAAE,uBAAuB,EAAE,CAAC,CAAC;QACpE,CAAC;IACH,CAAC,CAAC;AACJ,CAAC"}
@@ -0,0 +1,19 @@
1
+ import { CanActivate, ExecutionContext } from '@nestjs/common';
2
+ import { Accord } from '../accord';
3
+ /**
4
+ * Options for the NestJS Guard.
5
+ * For v1.1, we define Action/Resource statically on the guard.
6
+ * Future: Use Decorators to set metadata on routes.
7
+ */
8
+ export interface AccordGuardOptions {
9
+ accordInstance: Accord;
10
+ action: string;
11
+ resourceType: string;
12
+ getId?: (req: any) => string;
13
+ }
14
+ export declare class AccordGuard implements CanActivate {
15
+ private options;
16
+ constructor(options: AccordGuardOptions);
17
+ canActivate(context: ExecutionContext): Promise<boolean>;
18
+ }
19
+ //# sourceMappingURL=nest.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"nest.d.ts","sourceRoot":"","sources":["../../src/adapters/nest.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,WAAW,EAAE,gBAAgB,EAAc,MAAM,gBAAgB,CAAC;AAC3E,OAAO,EAAE,MAAM,EAAE,MAAM,WAAW,CAAC;AAGnC;;;;GAIG;AACH,MAAM,WAAW,kBAAkB;IACjC,cAAc,EAAE,MAAM,CAAC;IACvB,MAAM,EAAE,MAAM,CAAC;IACf,YAAY,EAAE,MAAM,CAAC;IAErB,KAAK,CAAC,EAAE,CAAC,GAAG,EAAE,GAAG,KAAK,MAAM,CAAC;CAC9B;AAED,qBACa,WAAY,YAAW,WAAW;IAC7C,OAAO,CAAC,OAAO,CAAqB;gBAExB,OAAO,EAAE,kBAAkB;IAIjC,WAAW,CAAC,OAAO,EAAE,gBAAgB,GAAG,OAAO,CAAC,OAAO,CAAC;CAuC/D"}
@@ -0,0 +1,95 @@
1
+ "use strict";
2
+ var __esDecorate = (this && this.__esDecorate) || function (ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {
3
+ function accept(f) { if (f !== void 0 && typeof f !== "function") throw new TypeError("Function expected"); return f; }
4
+ var kind = contextIn.kind, key = kind === "getter" ? "get" : kind === "setter" ? "set" : "value";
5
+ var target = !descriptorIn && ctor ? contextIn["static"] ? ctor : ctor.prototype : null;
6
+ var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});
7
+ var _, done = false;
8
+ for (var i = decorators.length - 1; i >= 0; i--) {
9
+ var context = {};
10
+ for (var p in contextIn) context[p] = p === "access" ? {} : contextIn[p];
11
+ for (var p in contextIn.access) context.access[p] = contextIn.access[p];
12
+ context.addInitializer = function (f) { if (done) throw new TypeError("Cannot add initializers after decoration has completed"); extraInitializers.push(accept(f || null)); };
13
+ var result = (0, decorators[i])(kind === "accessor" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);
14
+ if (kind === "accessor") {
15
+ if (result === void 0) continue;
16
+ if (result === null || typeof result !== "object") throw new TypeError("Object expected");
17
+ if (_ = accept(result.get)) descriptor.get = _;
18
+ if (_ = accept(result.set)) descriptor.set = _;
19
+ if (_ = accept(result.init)) initializers.unshift(_);
20
+ }
21
+ else if (_ = accept(result)) {
22
+ if (kind === "field") initializers.unshift(_);
23
+ else descriptor[key] = _;
24
+ }
25
+ }
26
+ if (target) Object.defineProperty(target, contextIn.name, descriptor);
27
+ done = true;
28
+ };
29
+ var __runInitializers = (this && this.__runInitializers) || function (thisArg, initializers, value) {
30
+ var useValue = arguments.length > 2;
31
+ for (var i = 0; i < initializers.length; i++) {
32
+ value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);
33
+ }
34
+ return useValue ? value : void 0;
35
+ };
36
+ var __setFunctionName = (this && this.__setFunctionName) || function (f, name, prefix) {
37
+ if (typeof name === "symbol") name = name.description ? "[".concat(name.description, "]") : "";
38
+ return Object.defineProperty(f, "name", { configurable: true, value: prefix ? "".concat(prefix, " ", name) : name });
39
+ };
40
+ Object.defineProperty(exports, "__esModule", { value: true });
41
+ exports.AccordGuard = void 0;
42
+ // src/adapters/nest.ts
43
+ const common_1 = require("@nestjs/common");
44
+ let AccordGuard = (() => {
45
+ let _classDecorators = [(0, common_1.Injectable)()];
46
+ let _classDescriptor;
47
+ let _classExtraInitializers = [];
48
+ let _classThis;
49
+ var AccordGuard = _classThis = class {
50
+ constructor(options) {
51
+ this.options = options;
52
+ }
53
+ async canActivate(context) {
54
+ const req = context.switchToHttp().getRequest();
55
+ const res = context.switchToHttp().getResponse();
56
+ try {
57
+ // 1. Determine User ID
58
+ const userId = this.options.getId
59
+ ? this.options.getId(req)
60
+ : req.headers['x-user-id'];
61
+ if (!userId) {
62
+ // Nest often handles exceptions via Exception Filters,
63
+ // but returning false is standard for guards.
64
+ return false;
65
+ }
66
+ // 2. Construct Resource
67
+ const resource = {
68
+ type: this.options.resourceType,
69
+ id: req.params.id,
70
+ attributes: req.body || {}
71
+ };
72
+ // 3. Check Policy
73
+ const decision = await this.options.accordInstance.check(userId, this.options.action, resource);
74
+ // 4. Attach decision to request (useful for downstream logic)
75
+ req.authDecision = decision;
76
+ return decision.decision === 'allow';
77
+ }
78
+ catch (error) {
79
+ console.error('NestJS Accord Guard Error:', error);
80
+ return false; // Fail safe: Deny
81
+ }
82
+ }
83
+ };
84
+ __setFunctionName(_classThis, "AccordGuard");
85
+ (() => {
86
+ const _metadata = typeof Symbol === "function" && Symbol.metadata ? Object.create(null) : void 0;
87
+ __esDecorate(null, _classDescriptor = { value: _classThis }, _classDecorators, { kind: "class", name: _classThis.name, metadata: _metadata }, null, _classExtraInitializers);
88
+ AccordGuard = _classThis = _classDescriptor.value;
89
+ if (_metadata) Object.defineProperty(_classThis, Symbol.metadata, { enumerable: true, configurable: true, writable: true, value: _metadata });
90
+ __runInitializers(_classThis, _classExtraInitializers);
91
+ })();
92
+ return AccordGuard = _classThis;
93
+ })();
94
+ exports.AccordGuard = AccordGuard;
95
+ //# sourceMappingURL=nest.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"nest.js","sourceRoot":"","sources":["../../src/adapters/nest.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,uBAAuB;AACvB,2CAA2E;IAkB9D,WAAW;4BADvB,IAAA,mBAAU,GAAE;;;;;QAIX,YAAY,OAA2B;YACrC,IAAI,CAAC,OAAO,GAAG,OAAO,CAAC;QACzB,CAAC;QAED,KAAK,CAAC,WAAW,CAAC,OAAyB;YACzC,MAAM,GAAG,GAAG,OAAO,CAAC,YAAY,EAAE,CAAC,UAAU,EAAE,CAAC;YAChD,MAAM,GAAG,GAAG,OAAO,CAAC,YAAY,EAAE,CAAC,WAAW,EAAE,CAAC;YAEjD,IAAI,CAAC;gBACH,uBAAuB;gBACvB,MAAM,MAAM,GAAG,IAAI,CAAC,OAAO,CAAC,KAAK;oBAC/B,CAAC,CAAC,IAAI,CAAC,OAAO,CAAC,KAAK,CAAC,GAAG,CAAC;oBACzB,CAAC,CAAC,GAAG,CAAC,OAAO,CAAC,WAAW,CAAW,CAAC;gBAEvC,IAAI,CAAC,MAAM,EAAE,CAAC;oBACZ,wDAAwD;oBACxD,8CAA8C;oBAC9C,OAAO,KAAK,CAAC;gBACf,CAAC;gBAED,wBAAwB;gBACxB,MAAM,QAAQ,GAAG;oBACf,IAAI,EAAE,IAAI,CAAC,OAAO,CAAC,YAAY;oBAC/B,EAAE,EAAE,GAAG,CAAC,MAAM,CAAC,EAAE;oBACjB,UAAU,EAAE,GAAG,CAAC,IAAI,IAAI,EAAE;iBAC3B,CAAC;gBAEF,kBAAkB;gBAClB,MAAM,QAAQ,GAAa,MAAM,IAAI,CAAC,OAAO,CAAC,cAAc,CAAC,KAAK,CAChE,MAAM,EACN,IAAI,CAAC,OAAO,CAAC,MAAM,EACnB,QAAQ,CACT,CAAC;gBAEF,8DAA8D;gBAC7D,GAAW,CAAC,YAAY,GAAG,QAAQ,CAAC;gBAErC,OAAO,QAAQ,CAAC,QAAQ,KAAK,OAAO,CAAC;YACvC,CAAC;YAAC,OAAO,KAAK,EAAE,CAAC;gBACf,OAAO,CAAC,KAAK,CAAC,4BAA4B,EAAE,KAAK,CAAC,CAAC;gBACnD,OAAO,KAAK,CAAC,CAAC,kBAAkB;YAClC,CAAC;QACH,CAAC;;;;;QA7CH,6KA8CC;;;QA9CY,uDAAW;;;;AAAX,kCAAW"}
@@ -1,6 +1,7 @@
1
1
  import { Policy } from './types';
2
2
  /**
3
- * Loads Policies from a JSON file.
3
+ * Loads Policies from a file (JSON or YAML).
4
+ * Validates structure using Zod.
4
5
  */
5
6
  export declare function loadPolicies(filePath: string): Policy[];
6
7
  //# sourceMappingURL=loader.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"loader.d.ts","sourceRoot":"","sources":["../../src/core/loader.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,MAAM,EAAY,MAAM,SAAS,CAAC;AAI3C;;GAEG;AACH,wBAAgB,YAAY,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,EAAE,CASvD"}
1
+ {"version":3,"file":"loader.d.ts","sourceRoot":"","sources":["../../src/core/loader.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,MAAM,EAAY,MAAM,SAAS,CAAC;AAM3C;;;GAGG;AACH,wBAAgB,YAAY,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,EAAE,CA+BvD"}
@@ -34,20 +34,42 @@ var __importStar = (this && this.__importStar) || (function () {
34
34
  })();
35
35
  Object.defineProperty(exports, "__esModule", { value: true });
36
36
  exports.loadPolicies = loadPolicies;
37
+ const validation_1 = require("./validation");
37
38
  const fs = __importStar(require("fs"));
38
39
  const path = __importStar(require("path"));
40
+ const yaml = __importStar(require("js-yaml"));
39
41
  /**
40
- * Loads Policies from a JSON file.
42
+ * Loads Policies from a file (JSON or YAML).
43
+ * Validates structure using Zod.
41
44
  */
42
45
  function loadPolicies(filePath) {
43
46
  try {
44
47
  const absolutePath = path.resolve(filePath);
45
48
  const fileContent = fs.readFileSync(absolutePath, 'utf-8');
46
- return JSON.parse(fileContent);
49
+ let rawData;
50
+ // Detect extension and parse
51
+ if (filePath.endsWith('.yaml') || filePath.endsWith('.yml')) {
52
+ rawData = yaml.load(fileContent);
53
+ // Normalize to Array if YAML returns a single object (single policy in a file) -> wrapped in an array automatically.
54
+ if (!Array.isArray(rawData)) {
55
+ rawData = [rawData];
56
+ }
57
+ }
58
+ else {
59
+ // Default to JSON
60
+ rawData = JSON.parse(fileContent);
61
+ }
62
+ // VALIDATION STEP
63
+ const result = validation_1.Schemas.Policy.array().safeParse(rawData);
64
+ if (!result.success) {
65
+ console.error('Invalid Policy Structure:', result.error.format());
66
+ throw new Error(`Policy validation failed for ${filePath}`);
67
+ }
68
+ return result.data; // Return validated, typed data
47
69
  }
48
70
  catch (error) {
49
71
  console.error(`Failed to load policies from ${filePath}:`, error);
50
- return []; // Return empty array on failure to be safe
72
+ throw error; // Let application fail hard if config is bad.
51
73
  }
52
74
  }
53
75
  //# sourceMappingURL=loader.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"loader.js","sourceRoot":"","sources":["../../src/core/loader.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAQA,oCASC;AAfD,uCAAyB;AACzB,2CAA6B;AAE7B;;GAEG;AACH,SAAgB,YAAY,CAAC,QAAgB;IAC3C,IAAI,CAAC;QACH,MAAM,YAAY,GAAG,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC5C,MAAM,WAAW,GAAG,EAAE,CAAC,YAAY,CAAC,YAAY,EAAE,OAAO,CAAC,CAAC;QAC3D,OAAO,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;IACjC,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,gCAAgC,QAAQ,GAAG,EAAE,KAAK,CAAC,CAAC;QAClE,OAAO,EAAE,CAAC,CAAC,2CAA2C;IACxD,CAAC;AACH,CAAC"}
1
+ {"version":3,"file":"loader.js","sourceRoot":"","sources":["../../src/core/loader.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAWA,oCA+BC;AAxCD,6CAAuC;AACvC,uCAAyB;AACzB,2CAA6B;AAC7B,8CAAgC;AAEhC;;;GAGG;AACH,SAAgB,YAAY,CAAC,QAAgB;IAC3C,IAAI,CAAC;QACH,MAAM,YAAY,GAAG,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC5C,MAAM,WAAW,GAAG,EAAE,CAAC,YAAY,CAAC,YAAY,EAAE,OAAO,CAAC,CAAC;QAC3D,IAAI,OAAY,CAAC;QAEjB,6BAA6B;QAC7B,IAAI,QAAQ,CAAC,QAAQ,CAAC,OAAO,CAAC,IAAI,QAAQ,CAAC,QAAQ,CAAC,MAAM,CAAC,EAAE,CAAC;YAC5D,OAAO,GAAG,IAAI,CAAC,IAAI,CAAC,WAAW,CAAC,CAAC;YACnC,qHAAqH;YACnH,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,OAAO,CAAC,EAAE,CAAC;gBAC5B,OAAO,GAAG,CAAC,OAAO,CAAC,CAAC;YACtB,CAAC;QACH,CAAC;aAAM,CAAC;YACN,kBAAkB;YAClB,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACpC,CAAC;QAED,kBAAkB;QAClB,MAAM,MAAM,GAAG,oBAAO,CAAC,MAAM,CAAC,KAAK,EAAE,CAAC,SAAS,CAAC,OAAO,CAAC,CAAC;QAEzD,IAAI,CAAC,MAAM,CAAC,OAAO,EAAE,CAAC;YACpB,OAAO,CAAC,KAAK,CAAC,2BAA2B,EAAE,MAAM,CAAC,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC;YAClE,MAAM,IAAI,KAAK,CAAC,gCAAgC,QAAQ,EAAE,CAAC,CAAC;QAC9D,CAAC;QAED,OAAO,MAAM,CAAC,IAAI,CAAC,CAAC,+BAA+B;IACrD,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,OAAO,CAAC,KAAK,CAAC,gCAAgC,QAAQ,GAAG,EAAE,KAAK,CAAC,CAAC;QAClE,MAAM,KAAK,CAAC,CAAC,8CAA8C;IAC7D,CAAC;AACH,CAAC"}
@@ -0,0 +1,37 @@
1
+ /**
2
+ * Data shape for a single Audit Event.
3
+ */
4
+ export interface AuditEvent {
5
+ timestamp: Date;
6
+ decision: 'allow' | 'deny';
7
+ policyId?: string;
8
+ reason?: string;
9
+ userId: string;
10
+ action: string;
11
+ resourceType: string;
12
+ resourceId?: string;
13
+ }
14
+ /**
15
+ * Interface for Audit Loggers.
16
+ * Allows users to implement custom loggers (e.g., send to Splunk).
17
+ */
18
+ export interface AuditLogger {
19
+ log(event: AuditEvent): void | Promise<void>;
20
+ }
21
+ /**
22
+ * Console Logger: For local development.
23
+ * Color codes output (Green = Allow, Red = Deny).
24
+ */
25
+ export declare class ConsoleAuditLogger implements AuditLogger {
26
+ log(event: AuditEvent): void;
27
+ }
28
+ /**
29
+ * File Logger: For production/audit trails.
30
+ * Appends JSON lines to a file (Splunk/ELK friendly).
31
+ */
32
+ export declare class FileAuditLogger implements AuditLogger {
33
+ private filePath;
34
+ constructor(filePath: string);
35
+ log(event: AuditEvent): void;
36
+ }
37
+ //# sourceMappingURL=logger.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.d.ts","sourceRoot":"","sources":["../../src/core/logger.ts"],"names":[],"mappings":"AAKA;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,SAAS,EAAE,IAAI,CAAC;IAChB,QAAQ,EAAE,OAAO,GAAG,MAAM,CAAC;IAC3B,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,YAAY,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED;;;GAGG;AACH,MAAM,WAAW,WAAW;IAC1B,GAAG,CAAC,KAAK,EAAE,UAAU,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;CAC9C;AAED;;;GAGG;AACH,qBAAa,kBAAmB,YAAW,WAAW;IACpD,GAAG,CAAC,KAAK,EAAE,UAAU,GAAG,IAAI;CAY7B;AAED;;;GAGG;AACH,qBAAa,eAAgB,YAAW,WAAW;IACjD,OAAO,CAAC,QAAQ,CAAS;gBAEb,QAAQ,EAAE,MAAM;IAI5B,GAAG,CAAC,KAAK,EAAE,UAAU,GAAG,IAAI;CAS7B"}
@@ -0,0 +1,77 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || (function () {
19
+ var ownKeys = function(o) {
20
+ ownKeys = Object.getOwnPropertyNames || function (o) {
21
+ var ar = [];
22
+ for (var k in o) if (Object.prototype.hasOwnProperty.call(o, k)) ar[ar.length] = k;
23
+ return ar;
24
+ };
25
+ return ownKeys(o);
26
+ };
27
+ return function (mod) {
28
+ if (mod && mod.__esModule) return mod;
29
+ var result = {};
30
+ if (mod != null) for (var k = ownKeys(mod), i = 0; i < k.length; i++) if (k[i] !== "default") __createBinding(result, mod, k[i]);
31
+ __setModuleDefault(result, mod);
32
+ return result;
33
+ };
34
+ })();
35
+ Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.FileAuditLogger = exports.ConsoleAuditLogger = void 0;
37
+ const fs = __importStar(require("fs"));
38
+ const path = __importStar(require("path"));
39
+ /**
40
+ * Console Logger: For local development.
41
+ * Color codes output (Green = Allow, Red = Deny).
42
+ */
43
+ class ConsoleAuditLogger {
44
+ log(event) {
45
+ const color = event.decision === 'allow' ? '\x1b[32m' : '\x1b[31m'; // Green or Red
46
+ const reset = '\x1b[0m';
47
+ const message = `${color}[${event.decision.toUpperCase()}]${reset} ${event.userId} -> ${event.action} on ${event.resourceType}${event.resourceId ? `/${event.resourceId}` : ''}`;
48
+ if (event.decision === 'deny') {
49
+ console.warn(message, `| Reason: ${event.reason}`);
50
+ }
51
+ else {
52
+ console.log(message, `| Policy: ${event.policyId}`);
53
+ }
54
+ }
55
+ }
56
+ exports.ConsoleAuditLogger = ConsoleAuditLogger;
57
+ /**
58
+ * File Logger: For production/audit trails.
59
+ * Appends JSON lines to a file (Splunk/ELK friendly).
60
+ */
61
+ class FileAuditLogger {
62
+ constructor(filePath) {
63
+ this.filePath = path.resolve(filePath);
64
+ }
65
+ log(event) {
66
+ try {
67
+ const logLine = JSON.stringify(event) + '\n';
68
+ fs.appendFileSync(this.filePath, logLine, 'utf-8');
69
+ }
70
+ catch (error) {
71
+ // Don't crash the app if logging fails, just warn
72
+ console.error('Failed to write audit log:', error);
73
+ }
74
+ }
75
+ }
76
+ exports.FileAuditLogger = FileAuditLogger;
77
+ //# sourceMappingURL=logger.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"logger.js","sourceRoot":"","sources":["../../src/core/logger.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAEA,uCAAyB;AACzB,2CAA6B;AAwB7B;;;GAGG;AACH,MAAa,kBAAkB;IAC7B,GAAG,CAAC,KAAiB;QACnB,MAAM,KAAK,GAAG,KAAK,CAAC,QAAQ,KAAK,OAAO,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,CAAC,UAAU,CAAC,CAAC,eAAe;QACnF,MAAM,KAAK,GAAG,SAAS,CAAC;QAExB,MAAM,OAAO,GAAG,GAAG,KAAK,IAAI,KAAK,CAAC,QAAQ,CAAC,WAAW,EAAE,IAAI,KAAK,IAAI,KAAK,CAAC,MAAM,OAAO,KAAK,CAAC,MAAM,OAAO,KAAK,CAAC,YAAY,GAAG,KAAK,CAAC,UAAU,CAAC,CAAC,CAAC,IAAI,KAAK,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC;QAEjL,IAAI,KAAK,CAAC,QAAQ,KAAK,MAAM,EAAE,CAAC;YAC9B,OAAO,CAAC,IAAI,CAAC,OAAO,EAAE,aAAa,KAAK,CAAC,MAAM,EAAE,CAAC,CAAC;QACrD,CAAC;aAAM,CAAC;YACN,OAAO,CAAC,GAAG,CAAC,OAAO,EAAE,aAAa,KAAK,CAAC,QAAQ,EAAE,CAAC,CAAC;QACtD,CAAC;IACH,CAAC;CACF;AAbD,gDAaC;AAED;;;GAGG;AACH,MAAa,eAAe;IAG1B,YAAY,QAAgB;QAC1B,IAAI,CAAC,QAAQ,GAAG,IAAI,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;IACzC,CAAC;IAED,GAAG,CAAC,KAAiB;QACnB,IAAI,CAAC;YACH,MAAM,OAAO,GAAG,IAAI,CAAC,SAAS,CAAC,KAAK,CAAC,GAAG,IAAI,CAAC;YAC7C,EAAE,CAAC,cAAc,CAAC,IAAI,CAAC,QAAQ,EAAE,OAAO,EAAE,OAAO,CAAC,CAAC;QACrD,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,kDAAkD;YAClD,OAAO,CAAC,KAAK,CAAC,4BAA4B,EAAE,KAAK,CAAC,CAAC;QACrD,CAAC;IACH,CAAC;CACF;AAhBD,0CAgBC"}
@@ -0,0 +1,39 @@
1
+ import { z } from 'zod';
2
+ export declare const Schemas: {
3
+ Policy: z.ZodObject<{
4
+ id: z.ZodString;
5
+ version: z.ZodString;
6
+ effect: z.ZodEnum<{
7
+ allow: "allow";
8
+ deny: "deny";
9
+ }>;
10
+ subject: z.ZodObject<{
11
+ type: z.ZodOptional<z.ZodString>;
12
+ id: z.ZodOptional<z.ZodString>;
13
+ attributes: z.ZodDefault<z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodAny>>>;
14
+ }, z.core.$strip>;
15
+ action: z.ZodArray<z.ZodString>;
16
+ resource: z.ZodObject<{
17
+ type: z.ZodOptional<z.ZodString>;
18
+ id: z.ZodOptional<z.ZodString>;
19
+ attributes: z.ZodDefault<z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodAny>>>;
20
+ }, z.core.$strip>;
21
+ condition: z.ZodOptional<z.ZodString>;
22
+ }, z.core.$strip>;
23
+ Identity: z.ZodObject<{
24
+ id: z.ZodString;
25
+ type: z.ZodEnum<{
26
+ user: "user";
27
+ service: "service";
28
+ system: "system";
29
+ agent: "agent";
30
+ }>;
31
+ status: z.ZodEnum<{
32
+ active: "active";
33
+ suspended: "suspended";
34
+ revoked: "revoked";
35
+ }>;
36
+ attributes: z.ZodDefault<z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodAny>>>;
37
+ }, z.core.$strip>;
38
+ };
39
+ //# sourceMappingURL=validation.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validation.d.ts","sourceRoot":"","sources":["../../src/core/validation.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AA2CxB,eAAO,MAAM,OAAO;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAGnB,CAAC"}
@@ -0,0 +1,45 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.Schemas = void 0;
4
+ // src/core/validation.ts
5
+ const zod_1 = require("zod");
6
+ /**
7
+ * Zod Schemas for Accord v1.1
8
+ * These ensure that config files are structurally correct before the engine runs.
9
+ */
10
+ // Enums
11
+ const EffectSchema = zod_1.z.enum(['allow', 'deny']);
12
+ const StatusSchema = zod_1.z.enum(['active', 'suspended', 'revoked']);
13
+ const IdentityTypeSchema = zod_1.z.enum(['user', 'service', 'system', 'agent']);
14
+ // Objects
15
+ const ResourceSchema = zod_1.z.object({
16
+ type: zod_1.z.string().optional(),
17
+ id: zod_1.z.string().optional(),
18
+ attributes: zod_1.z.record(zod_1.z.string(), zod_1.z.any()).optional().default({}),
19
+ });
20
+ const SubjectSchema = zod_1.z.object({
21
+ type: zod_1.z.string().optional(),
22
+ id: zod_1.z.string().optional(),
23
+ attributes: zod_1.z.record(zod_1.z.string(), zod_1.z.any()).optional().default({}),
24
+ });
25
+ const PolicySchema = zod_1.z.object({
26
+ id: zod_1.z.string(),
27
+ version: zod_1.z.string(),
28
+ effect: EffectSchema,
29
+ subject: SubjectSchema,
30
+ action: zod_1.z.array(zod_1.z.string()),
31
+ resource: ResourceSchema,
32
+ condition: zod_1.z.string().optional(),
33
+ });
34
+ const IdentitySchema = zod_1.z.object({
35
+ id: zod_1.z.string(),
36
+ type: IdentityTypeSchema,
37
+ status: StatusSchema,
38
+ attributes: zod_1.z.record(zod_1.z.string(), zod_1.z.any()).optional().default({}),
39
+ });
40
+ // Export for use in Loaders
41
+ exports.Schemas = {
42
+ Policy: PolicySchema,
43
+ Identity: IdentitySchema,
44
+ };
45
+ //# sourceMappingURL=validation.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validation.js","sourceRoot":"","sources":["../../src/core/validation.ts"],"names":[],"mappings":";;;AAAA,yBAAyB;AACzB,6BAAwB;AAExB;;;GAGG;AAEH,QAAQ;AACR,MAAM,YAAY,GAAG,OAAC,CAAC,IAAI,CAAC,CAAC,OAAO,EAAE,MAAM,CAAC,CAAC,CAAC;AAC/C,MAAM,YAAY,GAAG,OAAC,CAAC,IAAI,CAAC,CAAC,QAAQ,EAAE,WAAW,EAAE,SAAS,CAAC,CAAC,CAAC;AAChE,MAAM,kBAAkB,GAAG,OAAC,CAAC,IAAI,CAAC,CAAC,MAAM,EAAE,SAAS,EAAE,QAAQ,EAAE,OAAO,CAAC,CAAC,CAAC;AAE1E,UAAU;AACV,MAAM,cAAc,GAAG,OAAC,CAAC,MAAM,CAAC;IAC9B,IAAI,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IAC3B,EAAE,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IACzB,UAAU,EAAE,OAAC,CAAC,MAAM,CAAC,OAAC,CAAC,MAAM,EAAE,EAAE,OAAC,CAAC,GAAG,EAAE,CAAC,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,EAAE,CAAC;CACjE,CAAC,CAAC;AAEH,MAAM,aAAa,GAAG,OAAC,CAAC,MAAM,CAAC;IAC7B,IAAI,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IAC3B,EAAE,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IACzB,UAAU,EAAE,OAAC,CAAC,MAAM,CAAC,OAAC,CAAC,MAAM,EAAE,EAAE,OAAC,CAAC,GAAG,EAAE,CAAC,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,EAAE,CAAC;CACjE,CAAC,CAAC;AAEH,MAAM,YAAY,GAAG,OAAC,CAAC,MAAM,CAAC;IAC5B,EAAE,EAAE,OAAC,CAAC,MAAM,EAAE;IACd,OAAO,EAAE,OAAC,CAAC,MAAM,EAAE;IACnB,MAAM,EAAE,YAAY;IACpB,OAAO,EAAE,aAAa;IACtB,MAAM,EAAE,OAAC,CAAC,KAAK,CAAC,OAAC,CAAC,MAAM,EAAE,CAAC;IAC3B,QAAQ,EAAE,cAAc;IACxB,SAAS,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;CACjC,CAAC,CAAC;AAEH,MAAM,cAAc,GAAG,OAAC,CAAC,MAAM,CAAC;IAC9B,EAAE,EAAE,OAAC,CAAC,MAAM,EAAE;IACd,IAAI,EAAE,kBAAkB;IACxB,MAAM,EAAE,YAAY;IACpB,UAAU,EAAE,OAAC,CAAC,MAAM,CAAC,OAAC,CAAC,MAAM,EAAE,EAAE,OAAC,CAAC,GAAG,EAAE,CAAC,CAAC,QAAQ,EAAE,CAAC,OAAO,CAAC,EAAE,CAAC;CACjE,CAAC,CAAC;AAEH,4BAA4B;AACf,QAAA,OAAO,GAAG;IACrB,MAAM,EAAE,YAAY;IACpB,QAAQ,EAAE,cAAc;CACzB,CAAC"}
package/dist/index.d.ts CHANGED
@@ -1,3 +1,6 @@
1
1
  export { Accord, AccordConfig } from './accord';
2
2
  export * from './core/types';
3
+ export * from './adapters/express';
4
+ export { AccordGuard } from './adapters/nest';
5
+ export { accordHook } from './adapters/fastify';
3
6
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAEhD,cAAc,cAAc,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AAEhD,cAAc,cAAc,CAAC;AAC7B,cAAc,oBAAoB,CAAC;AACnC,OAAO,EAAE,WAAW,EAAE,MAAM,iBAAiB,CAAC;AAC9C,OAAO,EAAE,UAAU,EAAE,MAAM,oBAAoB,CAAC"}
package/dist/index.js CHANGED
@@ -14,10 +14,15 @@ var __exportStar = (this && this.__exportStar) || function(m, exports) {
14
14
  for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
15
15
  };
16
16
  Object.defineProperty(exports, "__esModule", { value: true });
17
- exports.Accord = void 0;
17
+ exports.accordHook = exports.AccordGuard = exports.Accord = void 0;
18
18
  // src/index.ts
19
19
  var accord_1 = require("./accord");
20
20
  Object.defineProperty(exports, "Accord", { enumerable: true, get: function () { return accord_1.Accord; } });
21
21
  // Re-export types for convenience if needed
22
22
  __exportStar(require("./core/types"), exports);
23
+ __exportStar(require("./adapters/express"), exports);
24
+ var nest_1 = require("./adapters/nest");
25
+ Object.defineProperty(exports, "AccordGuard", { enumerable: true, get: function () { return nest_1.AccordGuard; } });
26
+ var fastify_1 = require("./adapters/fastify");
27
+ Object.defineProperty(exports, "accordHook", { enumerable: true, get: function () { return fastify_1.accordHook; } });
23
28
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,eAAe;AACf,mCAAgD;AAAvC,gGAAA,MAAM,OAAA;AACf,4CAA4C;AAC5C,+CAA6B"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;AAAA,eAAe;AACf,mCAAgD;AAAvC,gGAAA,MAAM,OAAA;AACf,4CAA4C;AAC5C,+CAA6B;AAC7B,qDAAmC;AACnC,wCAA8C;AAArC,mGAAA,WAAW,OAAA;AACpB,8CAAgD;AAAvC,qGAAA,UAAU,OAAA"}
@@ -24,5 +24,10 @@ export declare class IdentityStore {
24
24
  * Helper to get all identities (useful for testing/debugging)
25
25
  */
26
26
  getAllIdentities(): Identity[];
27
+ /**
28
+ * Reloads identities from disk.
29
+ * Useful if the file was edited externally.
30
+ */
31
+ reload(): void;
27
32
  }
28
33
  //# sourceMappingURL=identity.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"identity.d.ts","sourceRoot":"","sources":["../../src/store/identity.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAIzC,qBAAa,aAAa;IACxB,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,UAAU,CAAkB;gBAExB,QAAQ,EAAE,MAAM;IAK5B;;OAEG;IACH,OAAO,CAAC,IAAI;IAeZ;;OAEG;IACH,OAAO,CAAC,IAAI;IASZ;;OAEG;IACH,WAAW,CAAC,EAAE,EAAE,MAAM,GAAG,QAAQ,GAAG,SAAS;IAI7C;;;OAGG;IACH,cAAc,CAAC,EAAE,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,CAAC,QAAQ,CAAC,GAAG,QAAQ;IAyBhE;;OAEG;IACH,gBAAgB,IAAI,QAAQ,EAAE;CAG/B"}
1
+ {"version":3,"file":"identity.d.ts","sourceRoot":"","sources":["../../src/store/identity.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AAKzC,qBAAa,aAAa;IACxB,OAAO,CAAC,QAAQ,CAAS;IACzB,OAAO,CAAC,UAAU,CAAkB;gBAExB,QAAQ,EAAE,MAAM;IAK5B;;OAEG;IACH,OAAO,CAAC,IAAI;IA2BZ;;OAEG;IACH,OAAO,CAAC,IAAI;IASZ;;OAEG;IACH,WAAW,CAAC,EAAE,EAAE,MAAM,GAAG,QAAQ,GAAG,SAAS;IAI7C;;;OAGG;IACH,cAAc,CAAC,EAAE,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,CAAC,QAAQ,CAAC,GAAG,QAAQ;IAyBhE;;OAEG;IACH,gBAAgB,IAAI,QAAQ,EAAE;IAI5B;;;KAGC;IACH,MAAM,IAAI,IAAI;CAGf"}
@@ -34,6 +34,7 @@ var __importStar = (this && this.__importStar) || (function () {
34
34
  })();
35
35
  Object.defineProperty(exports, "__esModule", { value: true });
36
36
  exports.IdentityStore = void 0;
37
+ const validation_1 = require("../core/validation");
37
38
  const fs = __importStar(require("fs"));
38
39
  const path = __importStar(require("path"));
39
40
  class IdentityStore {
@@ -49,7 +50,16 @@ class IdentityStore {
49
50
  try {
50
51
  if (fs.existsSync(this.filePath)) {
51
52
  const fileContent = fs.readFileSync(this.filePath, 'utf-8');
52
- this.identities = JSON.parse(fileContent);
53
+ const rawData = JSON.parse(fileContent);
54
+ // VALIDATION STEP
55
+ const result = validation_1.Schemas.Identity.array().safeParse(rawData);
56
+ if (!result.success) {
57
+ console.error('Invalid Identity Structure:', result.error.format());
58
+ // For v1, we start empty on fail to be safe, or throw.
59
+ // Let's throw to match enterprise behavior.
60
+ throw new Error(`Identity validation failed for ${this.filePath}`);
61
+ }
62
+ this.identities = result.data;
53
63
  }
54
64
  else {
55
65
  this.identities = [];
@@ -110,6 +120,13 @@ class IdentityStore {
110
120
  getAllIdentities() {
111
121
  return this.identities;
112
122
  }
123
+ /**
124
+ * Reloads identities from disk.
125
+ * Useful if the file was edited externally.
126
+ */
127
+ reload() {
128
+ this.load(); // Re-run the load logic
129
+ }
113
130
  }
114
131
  exports.IdentityStore = IdentityStore;
115
132
  //# sourceMappingURL=identity.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"identity.js","sourceRoot":"","sources":["../../src/store/identity.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"identity.js","sourceRoot":"","sources":["../../src/store/identity.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@navirondynamics/accord",
3
- "version": "1.0.0",
3
+ "version": "1.1.1",
4
4
  "description": "A policy-first identity and access engine for modular systems.",
5
5
  "main": "./dist/index.js",
6
6
  "types": "./dist/index.d.ts",
@@ -8,19 +8,38 @@
8
8
  "dist",
9
9
  "README.md"
10
10
  ],
11
+
12
+ "repository": {
13
+ "type": "git",
14
+ "url": "git+https://github.com/bsen-alt/Accord.git"
15
+ },
16
+ "bugs": {
17
+ "url": "https://github.com/bsen-alt/Accord/issues"
18
+ },
19
+ "homepage": "https://github.com/bsen-alt/Accord#readme",
20
+
21
+
11
22
  "scripts": {
12
23
  "test": "jest",
13
24
  "build": "tsc",
14
25
  "prepublishOnly": "npm run build",
15
26
  "cli": "ts-node src/cli/index.ts"
16
27
  },
17
- "keywords": ["authorization", "access-control", "rbac", "abac", "policy"],
28
+ "keywords": [
29
+ "authorization",
30
+ "access-control",
31
+ "rbac",
32
+ "abac",
33
+ "policy"
34
+ ],
18
35
  "author": "",
19
36
  "license": "ISC",
20
37
  "type": "commonjs",
21
38
  "devDependencies": {
39
+ "@nestjs/common": "^11.1.12",
22
40
  "@types/express": "^5.0.6",
23
41
  "@types/jest": "^30.0.0",
42
+ "@types/js-yaml": "^4.0.9",
24
43
  "@types/jsonata": "^1.3.1",
25
44
  "@types/node": "^25.0.10",
26
45
  "@typescript-eslint/eslint-plugin": "^8.53.1",
@@ -28,13 +47,19 @@
28
47
  "eslint": "^9.39.2",
29
48
  "jest": "^30.2.0",
30
49
  "prettier": "^3.8.1",
50
+ "reflect-metadata": "^0.2.2",
31
51
  "ts-jest": "^29.4.6",
32
52
  "ts-node": "^10.9.2",
53
+ "tslib": "^2.8.1",
33
54
  "typescript": "^5.9.3"
34
55
  },
35
56
  "dependencies": {
57
+ "@nestjs/common": "^11.1.12",
36
58
  "commander": "^14.0.2",
37
59
  "express": "^5.2.1",
38
- "jsonata": "^2.1.0"
60
+ "fastify": "^5.7.1",
61
+ "js-yaml": "^4.1.1",
62
+ "jsonata": "^2.1.0",
63
+ "zod": "^4.3.6"
39
64
  }
40
65
  }