@optimizely-opal/opal-tool-ocp-sdk 0.0.0-beta.7 โ 0.0.0-beta.9
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 +9 -43
- package/dist/auth/TokenVerifier.d.ts +31 -0
- package/dist/auth/TokenVerifier.d.ts.map +1 -0
- package/dist/auth/TokenVerifier.js +127 -0
- package/dist/auth/TokenVerifier.js.map +1 -0
- package/dist/auth/TokenVerifier.test.d.ts +2 -0
- package/dist/auth/TokenVerifier.test.d.ts.map +1 -0
- package/dist/auth/TokenVerifier.test.js +114 -0
- package/dist/auth/TokenVerifier.test.js.map +1 -0
- package/dist/function/ToolFunction.d.ts +4 -7
- package/dist/function/ToolFunction.d.ts.map +1 -1
- package/dist/function/ToolFunction.js +38 -10
- package/dist/function/ToolFunction.js.map +1 -1
- package/dist/function/ToolFunction.test.js +177 -196
- package/dist/function/ToolFunction.test.js.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/service/Service.d.ts +7 -7
- package/dist/service/Service.d.ts.map +1 -1
- package/dist/service/Service.js +22 -16
- package/dist/service/Service.js.map +1 -1
- package/dist/service/Service.test.js +8 -3
- package/dist/service/Service.test.js.map +1 -1
- package/dist/types/Models.d.ts +5 -5
- package/dist/types/Models.d.ts.map +1 -1
- package/dist/types/Models.js +9 -9
- package/dist/types/Models.js.map +1 -1
- package/package.json +5 -3
- package/src/auth/TokenVerifier.test.ts +152 -0
- package/src/auth/TokenVerifier.ts +145 -0
- package/src/function/ToolFunction.test.ts +194 -214
- package/src/function/ToolFunction.ts +45 -11
- package/src/index.ts +1 -0
- package/src/service/Service.test.ts +8 -3
- package/src/service/Service.ts +22 -17
- package/src/types/Models.ts +4 -4
package/README.md
CHANGED
|
@@ -10,7 +10,7 @@ A TypeScript SDK for building Opal tools in Optimizely Connect Platform. This SD
|
|
|
10
10
|
- ๐ง **Type-safe Development** - Full TypeScript support with comprehensive type definitions
|
|
11
11
|
- ๐๏ธ **Abstract Base Classes** - Extend `ToolFunction` for standardized request processing
|
|
12
12
|
- ๐ **Authentication Support** - OptiID authentication
|
|
13
|
-
- ๐ก๏ธ **Authorization Support** -
|
|
13
|
+
- ๐ก๏ธ **Authorization Support** - OptiID token tool authorization
|
|
14
14
|
- ๐ **Parameter Validation** - Define and validate tool parameters with types
|
|
15
15
|
- ๐งช **Comprehensive Testing** - Fully tested with Jest
|
|
16
16
|
|
|
@@ -115,7 +115,7 @@ export class MyToolFunction extends ToolFunction {
|
|
|
115
115
|
Your function class inherits a `perform()` method from `ToolFunction` that serves as the main entry point for handling all incoming requests. When called, the SDK automatically:
|
|
116
116
|
|
|
117
117
|
- **Routes requests** to your registered tools and interactions based on endpoints
|
|
118
|
-
- **Handles authentication** and
|
|
118
|
+
- **Handles authentication** and OptiID token validation before calling your methods
|
|
119
119
|
- **Provides discovery** at `/discovery` endpoint for OCP platform integration
|
|
120
120
|
- **Returns proper HTTP responses** with correct status codes and JSON formatting
|
|
121
121
|
|
|
@@ -169,29 +169,18 @@ interface AuthRequirementConfig {
|
|
|
169
169
|
}
|
|
170
170
|
```
|
|
171
171
|
|
|
172
|
-
####
|
|
172
|
+
#### OptiID Token Authorization
|
|
173
173
|
|
|
174
|
-
The SDK automatically
|
|
174
|
+
The SDK automatically handles OptiID token validation for tool authorization. OptiID tokens provide both user authentication and authorization for tools, ensuring that only authenticated users with proper permissions can access your tools.
|
|
175
175
|
|
|
176
176
|
**Token Validation:**
|
|
177
|
-
-
|
|
178
|
-
-
|
|
179
|
-
-
|
|
180
|
-
-
|
|
181
|
-
- If validation fails, returns HTTP 403 Forbidden before reaching your handler methods
|
|
177
|
+
- The SDK extracts and validates OptiID tokens from the request body
|
|
178
|
+
- Validation includes verifying that requests come from the same organization
|
|
179
|
+
- If validation fails, returns HTTP 403 Unauthorized before reaching your handler methods
|
|
180
|
+
- No additional configuration needed - validation is handled automatically
|
|
182
181
|
|
|
183
182
|
```typescript
|
|
184
183
|
export class MyToolFunction extends ToolFunction {
|
|
185
|
-
// Optional: Override this method to implement custom bearer token validation
|
|
186
|
-
protected override validateBearerToken(token: string): boolean {
|
|
187
|
-
// If you don't need bearer token validation, don't override this method
|
|
188
|
-
// The default implementation returns true
|
|
189
|
-
|
|
190
|
-
// For custom validation, compare against expected token
|
|
191
|
-
const expectedToken = process.env.OPAL_TOOL_TOKEN;
|
|
192
|
-
return token === expectedToken;
|
|
193
|
-
}
|
|
194
|
-
|
|
195
184
|
@tool({
|
|
196
185
|
name: 'secure_tool',
|
|
197
186
|
description: 'Tool that validates requests from Opal',
|
|
@@ -215,15 +204,6 @@ export class MyToolFunction extends ToolFunction {
|
|
|
215
204
|
}
|
|
216
205
|
```
|
|
217
206
|
|
|
218
|
-
**Bearer Token Usage:**
|
|
219
|
-
- Set by users when registering tools in Opal
|
|
220
|
-
- Used to authorize tool requests from Opal instances
|
|
221
|
-
- Validates that requests are coming from trusted Opal sources
|
|
222
|
-
- **Optionally override** the `validateBearerToken(token: string): boolean` method for custom authorization
|
|
223
|
-
- Default implementation accepts all tokens - override for security
|
|
224
|
-
- If validation fails, returns HTTP 403 Forbidden before reaching your handler methods
|
|
225
|
-
|
|
226
|
-
|
|
227
207
|
## API Reference
|
|
228
208
|
|
|
229
209
|
### Handler Function Signatures
|
|
@@ -240,8 +220,6 @@ async handlerMethod(
|
|
|
240
220
|
- **params**: The input parameters for tools, or interaction data for webhooks
|
|
241
221
|
- **authData**: Available when OptiID user authentication is configured and successful
|
|
242
222
|
|
|
243
|
-
**Note**: Bearer token validation is handled automatically by the base class. If a bearer token is present and fails validation, the request is rejected before reaching your handler methods.
|
|
244
|
-
|
|
245
223
|
### Decorators
|
|
246
224
|
|
|
247
225
|
#### `@tool(config: ToolConfig)`
|
|
@@ -279,11 +257,10 @@ Abstract base class for OCP functions:
|
|
|
279
257
|
export abstract class ToolFunction extends Function {
|
|
280
258
|
protected ready(): Promise<boolean>;
|
|
281
259
|
public async perform(): Promise<Response>;
|
|
282
|
-
protected validateBearerToken(token: string): boolean;
|
|
283
260
|
}
|
|
284
261
|
```
|
|
285
262
|
|
|
286
|
-
Extend this class and implement your OCP function. The `perform` method automatically routes requests to registered tools
|
|
263
|
+
Extend this class and implement your OCP function. The `perform` method automatically routes requests to registered tools.
|
|
287
264
|
|
|
288
265
|
### Models
|
|
289
266
|
|
|
@@ -407,11 +384,6 @@ yarn lint
|
|
|
407
384
|
import { ToolFunction, tool, interaction, ParameterType, OptiIdAuthData, InteractionResult } from '@optimizely-opal/opal-ocp-sdk';
|
|
408
385
|
|
|
409
386
|
export class AuthenticatedFunction extends ToolFunction {
|
|
410
|
-
// Optional: Override this method for custom bearer token validation
|
|
411
|
-
protected override validateBearerToken(token: string): boolean {
|
|
412
|
-
const expectedToken = process.env.OPAL_TOOL_TOKEN;
|
|
413
|
-
return token === expectedToken;
|
|
414
|
-
}
|
|
415
387
|
|
|
416
388
|
// OptiID authentication example
|
|
417
389
|
@tool({
|
|
@@ -573,12 +545,6 @@ import { ToolFunction } from '@optimizely-opal/opal-ocp-sdk';
|
|
|
573
545
|
import * from './tools';
|
|
574
546
|
|
|
575
547
|
export class MyToolFunction extends ToolFunction {
|
|
576
|
-
|
|
577
|
-
// Optional: Override this method for custom bearer token validation
|
|
578
|
-
protected override validateBearerToken(token: string): boolean {
|
|
579
|
-
const expectedToken = process.env.OPAL_TOOL_TOKEN;
|
|
580
|
-
return token === expectedToken;
|
|
581
|
-
}
|
|
582
548
|
}
|
|
583
549
|
```
|
|
584
550
|
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
export declare class TokenVerifier {
|
|
2
|
+
private static instance;
|
|
3
|
+
private jwksUri?;
|
|
4
|
+
private issuer?;
|
|
5
|
+
private jwks?;
|
|
6
|
+
private initialized;
|
|
7
|
+
/**
|
|
8
|
+
* Verify the provided Optimizely JWT token string
|
|
9
|
+
* @param token JWT token string to verify
|
|
10
|
+
* @returns boolean true if verification successful, false otherwise
|
|
11
|
+
* @throws Error if token is null, empty, or verifier is not properly configured
|
|
12
|
+
*/
|
|
13
|
+
verify(token: string | undefined): Promise<boolean>;
|
|
14
|
+
private static getInstance;
|
|
15
|
+
/**
|
|
16
|
+
* Get singleton instance of TokenVerifier and ensure it's initialized
|
|
17
|
+
* @returns Promise<TokenVerifier> - initialized singleton instance
|
|
18
|
+
*/
|
|
19
|
+
static getInitializedInstance(): Promise<TokenVerifier>;
|
|
20
|
+
/**
|
|
21
|
+
* Initialize the TokenVerifier with discovery document from well-known endpoint
|
|
22
|
+
*/
|
|
23
|
+
private initialize;
|
|
24
|
+
/**
|
|
25
|
+
* Fetch discovery document from well-known endpoint
|
|
26
|
+
*/
|
|
27
|
+
private fetchDiscoveryDocument;
|
|
28
|
+
private verifyToken;
|
|
29
|
+
}
|
|
30
|
+
export declare const getTokenVerifier: () => Promise<TokenVerifier>;
|
|
31
|
+
//# sourceMappingURL=TokenVerifier.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TokenVerifier.d.ts","sourceRoot":"","sources":["../../src/auth/TokenVerifier.ts"],"names":[],"mappings":"AAkCA,qBAAa,aAAa;IACxB,OAAO,CAAC,MAAM,CAAC,QAAQ,CAA8B;IACrD,OAAO,CAAC,OAAO,CAAC,CAAS;IACzB,OAAO,CAAC,MAAM,CAAC,CAAS;IACxB,OAAO,CAAC,IAAI,CAAC,CAAwC;IACrD,OAAO,CAAC,WAAW,CAAkB;IAErC;;;;;OAKG;IACU,MAAM,CAAC,KAAK,EAAE,MAAM,GAAG,SAAS,GAAG,OAAO,CAAC,OAAO,CAAC;IAQhE,OAAO,CAAC,MAAM,CAAC,WAAW;IAO1B;;;OAGG;WACiB,sBAAsB,IAAI,OAAO,CAAC,aAAa,CAAC;IAQpE;;OAEG;YACW,UAAU;IAyBxB;;OAEG;YACW,sBAAsB;YAetB,WAAW;CAsB1B;AAED,eAAO,MAAM,gBAAgB,QAAa,OAAO,CAAC,aAAa,CAA2C,CAAC"}
|
|
@@ -0,0 +1,127 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getTokenVerifier = exports.TokenVerifier = void 0;
|
|
4
|
+
const jose_1 = require("jose");
|
|
5
|
+
const app_sdk_1 = require("@zaiusinc/app-sdk");
|
|
6
|
+
/**
|
|
7
|
+
* Default JWKS cache expiration time in milliseconds (1 hour)
|
|
8
|
+
*/
|
|
9
|
+
const DEFAULT_JWKS_EXPIRES_IN = 60 * 60 * 1000;
|
|
10
|
+
/**
|
|
11
|
+
* Default clock skew tolerance in seconds
|
|
12
|
+
*/
|
|
13
|
+
const DEFAULT_LEEWAY = 30;
|
|
14
|
+
/**
|
|
15
|
+
* Expected JWT audience for token validation
|
|
16
|
+
*/
|
|
17
|
+
const AUDIENCE = 'api://default';
|
|
18
|
+
/**
|
|
19
|
+
* Prep Base URL for Optimizely OAuth2 endpoints
|
|
20
|
+
*/
|
|
21
|
+
const PREP_BASE_URL = 'https://prep.login.optimizely.com/oauth2/default';
|
|
22
|
+
/**
|
|
23
|
+
* Prod Base URL for Optimizely OAuth2 endpoints
|
|
24
|
+
*/
|
|
25
|
+
const PROD_BASE_URL = 'https://login.optimizely.com/oauth2/default';
|
|
26
|
+
class TokenVerifier {
|
|
27
|
+
static instance = null;
|
|
28
|
+
jwksUri;
|
|
29
|
+
issuer;
|
|
30
|
+
jwks;
|
|
31
|
+
initialized = false;
|
|
32
|
+
/**
|
|
33
|
+
* Verify the provided Optimizely JWT token string
|
|
34
|
+
* @param token JWT token string to verify
|
|
35
|
+
* @returns boolean true if verification successful, false otherwise
|
|
36
|
+
* @throws Error if token is null, empty, or verifier is not properly configured
|
|
37
|
+
*/
|
|
38
|
+
async verify(token) {
|
|
39
|
+
if (!token || token.trim().length === 0) {
|
|
40
|
+
throw new Error('Token cannot be null or empty');
|
|
41
|
+
}
|
|
42
|
+
return this.verifyToken(token);
|
|
43
|
+
}
|
|
44
|
+
static getInstance() {
|
|
45
|
+
if (!TokenVerifier.instance) {
|
|
46
|
+
TokenVerifier.instance = new TokenVerifier();
|
|
47
|
+
}
|
|
48
|
+
return TokenVerifier.instance;
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Get singleton instance of TokenVerifier and ensure it's initialized
|
|
52
|
+
* @returns Promise<TokenVerifier> - initialized singleton instance
|
|
53
|
+
*/
|
|
54
|
+
static async getInitializedInstance() {
|
|
55
|
+
const instance = TokenVerifier.getInstance();
|
|
56
|
+
if (!instance.initialized) {
|
|
57
|
+
await instance.initialize();
|
|
58
|
+
}
|
|
59
|
+
return instance;
|
|
60
|
+
}
|
|
61
|
+
/**
|
|
62
|
+
* Initialize the TokenVerifier with discovery document from well-known endpoint
|
|
63
|
+
*/
|
|
64
|
+
async initialize() {
|
|
65
|
+
if (this.initialized) {
|
|
66
|
+
return;
|
|
67
|
+
}
|
|
68
|
+
try {
|
|
69
|
+
// Use prep URL when environment variable is set to 'staging', otherwise use prod
|
|
70
|
+
const environment = process.env.environment || 'production';
|
|
71
|
+
const baseUrl = environment === 'staging' ? PREP_BASE_URL : PROD_BASE_URL;
|
|
72
|
+
const discoveryDocument = await this.fetchDiscoveryDocument(baseUrl);
|
|
73
|
+
this.issuer = discoveryDocument.issuer;
|
|
74
|
+
this.jwksUri = discoveryDocument.jwks_uri;
|
|
75
|
+
this.jwks = (0, jose_1.createRemoteJWKSet)(new URL(this.jwksUri), {
|
|
76
|
+
cacheMaxAge: DEFAULT_JWKS_EXPIRES_IN,
|
|
77
|
+
cooldownDuration: DEFAULT_JWKS_EXPIRES_IN
|
|
78
|
+
});
|
|
79
|
+
this.initialized = true;
|
|
80
|
+
app_sdk_1.logger.info(`TokenVerifier initialized with issuer: ${this.issuer} (environment: ${environment})`);
|
|
81
|
+
}
|
|
82
|
+
catch (error) {
|
|
83
|
+
app_sdk_1.logger.error('Failed to initialize TokenVerifier', error);
|
|
84
|
+
// Re-throw the original error to preserve specific error messages for tests
|
|
85
|
+
throw error;
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* Fetch discovery document from well-known endpoint
|
|
90
|
+
*/
|
|
91
|
+
async fetchDiscoveryDocument(baseUrl) {
|
|
92
|
+
const wellKnownUrl = `${baseUrl}/.well-known/oauth-authorization-server`;
|
|
93
|
+
const response = await fetch(wellKnownUrl);
|
|
94
|
+
if (!response.ok) {
|
|
95
|
+
throw new Error(`Failed to fetch discovery document: ${response.status} ${response.statusText}`);
|
|
96
|
+
}
|
|
97
|
+
const discoveryDocument = await response.json();
|
|
98
|
+
if (!discoveryDocument.issuer || !discoveryDocument.jwks_uri) {
|
|
99
|
+
throw new Error('Invalid discovery document: missing issuer or jwks_uri');
|
|
100
|
+
}
|
|
101
|
+
return discoveryDocument;
|
|
102
|
+
}
|
|
103
|
+
async verifyToken(token) {
|
|
104
|
+
if (!this.initialized) {
|
|
105
|
+
throw new Error('TokenVerifier not initialized. Call initialize() first.');
|
|
106
|
+
}
|
|
107
|
+
if (!this.jwks || !this.issuer) {
|
|
108
|
+
throw new Error('TokenVerifier not properly configured.');
|
|
109
|
+
}
|
|
110
|
+
try {
|
|
111
|
+
await (0, jose_1.jwtVerify)(token, this.jwks, {
|
|
112
|
+
issuer: this.issuer,
|
|
113
|
+
audience: AUDIENCE,
|
|
114
|
+
clockTolerance: DEFAULT_LEEWAY,
|
|
115
|
+
});
|
|
116
|
+
return true;
|
|
117
|
+
}
|
|
118
|
+
catch (error) {
|
|
119
|
+
app_sdk_1.logger.error('Token verification failed:', error);
|
|
120
|
+
return false;
|
|
121
|
+
}
|
|
122
|
+
}
|
|
123
|
+
}
|
|
124
|
+
exports.TokenVerifier = TokenVerifier;
|
|
125
|
+
const getTokenVerifier = async () => TokenVerifier.getInitializedInstance();
|
|
126
|
+
exports.getTokenVerifier = getTokenVerifier;
|
|
127
|
+
//# sourceMappingURL=TokenVerifier.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TokenVerifier.js","sourceRoot":"","sources":["../../src/auth/TokenVerifier.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TokenVerifier.test.d.ts","sourceRoot":"","sources":["../../src/auth/TokenVerifier.test.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,114 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
const TokenVerifier_1 = require("./TokenVerifier");
|
|
4
|
+
// Test constants
|
|
5
|
+
const TEST_ISSUER = 'https://prep.login.optimizely.com/oauth2/default';
|
|
6
|
+
const TEST_JWKS_URI = 'https://prep.login.optimizely.com/oauth2/v1/keys';
|
|
7
|
+
// Mock fetch globally
|
|
8
|
+
global.fetch = jest.fn();
|
|
9
|
+
describe('TokenVerifier', () => {
|
|
10
|
+
beforeEach(() => {
|
|
11
|
+
// Reset fetch mock
|
|
12
|
+
global.fetch.mockReset();
|
|
13
|
+
// Reset singleton instance for each test
|
|
14
|
+
TokenVerifier_1.TokenVerifier.instance = null;
|
|
15
|
+
});
|
|
16
|
+
describe('getInitializedInstance', () => {
|
|
17
|
+
it('should initialize successfully', async () => {
|
|
18
|
+
// Mock fetch for OAuth2 authorization server discovery
|
|
19
|
+
global.fetch.mockResolvedValue({
|
|
20
|
+
ok: true,
|
|
21
|
+
json: jest.fn().mockResolvedValue({
|
|
22
|
+
issuer: TEST_ISSUER,
|
|
23
|
+
jwks_uri: TEST_JWKS_URI
|
|
24
|
+
})
|
|
25
|
+
});
|
|
26
|
+
const tokenVerifier = await TokenVerifier_1.TokenVerifier.getInitializedInstance();
|
|
27
|
+
expect(tokenVerifier).toBeInstanceOf(TokenVerifier_1.TokenVerifier);
|
|
28
|
+
});
|
|
29
|
+
it('should throw error when discovery document is invalid', async () => {
|
|
30
|
+
global.fetch.mockResolvedValue({
|
|
31
|
+
ok: true,
|
|
32
|
+
json: jest.fn().mockResolvedValue({
|
|
33
|
+
// Missing issuer and jwks_uri
|
|
34
|
+
})
|
|
35
|
+
});
|
|
36
|
+
await expect(TokenVerifier_1.TokenVerifier.getInitializedInstance()).rejects.toThrow('Invalid discovery document: missing issuer or jwks_uri');
|
|
37
|
+
});
|
|
38
|
+
it('should throw error when discovery endpoint is unreachable', async () => {
|
|
39
|
+
global.fetch.mockResolvedValue({
|
|
40
|
+
ok: false,
|
|
41
|
+
status: 404,
|
|
42
|
+
statusText: 'Not Found'
|
|
43
|
+
});
|
|
44
|
+
await expect(TokenVerifier_1.TokenVerifier.getInitializedInstance()).rejects.toThrow('Failed to fetch discovery document: 404 Not Found');
|
|
45
|
+
});
|
|
46
|
+
});
|
|
47
|
+
describe('token verification', () => {
|
|
48
|
+
let tokenVerifier;
|
|
49
|
+
beforeEach(async () => {
|
|
50
|
+
// Mock successful initialization
|
|
51
|
+
global.fetch.mockResolvedValue({
|
|
52
|
+
ok: true,
|
|
53
|
+
json: jest.fn().mockResolvedValue({
|
|
54
|
+
issuer: TEST_ISSUER,
|
|
55
|
+
jwks_uri: TEST_JWKS_URI
|
|
56
|
+
})
|
|
57
|
+
});
|
|
58
|
+
tokenVerifier = await TokenVerifier_1.TokenVerifier.getInitializedInstance();
|
|
59
|
+
});
|
|
60
|
+
it('should throw error for empty token', async () => {
|
|
61
|
+
await expect(tokenVerifier.verify('')).rejects.toThrow('Token cannot be null or empty');
|
|
62
|
+
});
|
|
63
|
+
it('should throw error for undefined token', async () => {
|
|
64
|
+
await expect(tokenVerifier.verify(undefined)).rejects.toThrow('Token cannot be null or empty');
|
|
65
|
+
});
|
|
66
|
+
it('should throw error for whitespace-only token', async () => {
|
|
67
|
+
await expect(tokenVerifier.verify(' ')).rejects.toThrow('Token cannot be null or empty');
|
|
68
|
+
});
|
|
69
|
+
it('should return false for invalid token format', async () => {
|
|
70
|
+
const result = await tokenVerifier.verify('invalid.jwt.token');
|
|
71
|
+
expect(result).toBe(false);
|
|
72
|
+
});
|
|
73
|
+
});
|
|
74
|
+
describe('singleton pattern', () => {
|
|
75
|
+
it('should return same instance when called multiple times', async () => {
|
|
76
|
+
// Mock successful initialization
|
|
77
|
+
global.fetch.mockResolvedValue({
|
|
78
|
+
ok: true,
|
|
79
|
+
json: jest.fn().mockResolvedValue({
|
|
80
|
+
issuer: TEST_ISSUER,
|
|
81
|
+
jwks_uri: TEST_JWKS_URI
|
|
82
|
+
})
|
|
83
|
+
});
|
|
84
|
+
const instance1 = await TokenVerifier_1.TokenVerifier.getInitializedInstance();
|
|
85
|
+
const instance2 = await TokenVerifier_1.TokenVerifier.getInitializedInstance();
|
|
86
|
+
expect(instance1).toBe(instance2);
|
|
87
|
+
});
|
|
88
|
+
it('should call correct prod OAuth2 authorization server discovery URL', async () => {
|
|
89
|
+
const fetchSpy = jest.spyOn(global, 'fetch').mockResolvedValue({
|
|
90
|
+
ok: true,
|
|
91
|
+
json: jest.fn().mockResolvedValue({
|
|
92
|
+
issuer: TEST_ISSUER,
|
|
93
|
+
jwks_uri: TEST_JWKS_URI
|
|
94
|
+
})
|
|
95
|
+
});
|
|
96
|
+
await TokenVerifier_1.TokenVerifier.getInitializedInstance();
|
|
97
|
+
expect(fetchSpy).toHaveBeenCalledWith('https://login.optimizely.com/oauth2/default/.well-known/oauth-authorization-server');
|
|
98
|
+
});
|
|
99
|
+
it('should call correct prep OAuth2 authorization server discovery URL', async () => {
|
|
100
|
+
// Set environment variable to staging
|
|
101
|
+
process.env.environment = 'staging';
|
|
102
|
+
const fetchSpy = jest.spyOn(global, 'fetch').mockResolvedValue({
|
|
103
|
+
ok: true,
|
|
104
|
+
json: jest.fn().mockResolvedValue({
|
|
105
|
+
issuer: TEST_ISSUER,
|
|
106
|
+
jwks_uri: TEST_JWKS_URI
|
|
107
|
+
})
|
|
108
|
+
});
|
|
109
|
+
await TokenVerifier_1.TokenVerifier.getInitializedInstance();
|
|
110
|
+
expect(fetchSpy).toHaveBeenCalledWith('https://prep.login.optimizely.com/oauth2/default/.well-known/oauth-authorization-server');
|
|
111
|
+
});
|
|
112
|
+
});
|
|
113
|
+
});
|
|
114
|
+
//# sourceMappingURL=TokenVerifier.test.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TokenVerifier.test.js","sourceRoot":"","sources":["../../src/auth/TokenVerifier.test.ts"],"names":[],"mappings":"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"}
|
|
@@ -18,14 +18,11 @@ export declare abstract class ToolFunction extends Function {
|
|
|
18
18
|
*/
|
|
19
19
|
perform(): Promise<Response>;
|
|
20
20
|
/**
|
|
21
|
-
*
|
|
21
|
+
* Authenticate the incoming request by validating the OptiID token and organization ID
|
|
22
22
|
*
|
|
23
|
-
*
|
|
24
|
-
* Subclasses can override this method to implement custom bearer token validation logic.
|
|
25
|
-
*
|
|
26
|
-
* @param _bearerToken - The bearer token extracted from the Authorization header
|
|
27
|
-
* @returns true if the token is valid and the request should proceed, false to return 403 Forbidden
|
|
23
|
+
* @throws true if authentication succeeds
|
|
28
24
|
*/
|
|
29
|
-
|
|
25
|
+
private authorizeRequest;
|
|
26
|
+
private validateAccessToken;
|
|
30
27
|
}
|
|
31
28
|
//# sourceMappingURL=ToolFunction.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ToolFunction.d.ts","sourceRoot":"","sources":["../../src/function/ToolFunction.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,QAAQ,
|
|
1
|
+
{"version":3,"file":"ToolFunction.d.ts","sourceRoot":"","sources":["../../src/function/ToolFunction.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,QAAQ,EAA0C,MAAM,mBAAmB,CAAC;AAK/F;;;GAGG;AACH,8BAAsB,YAAa,SAAQ,QAAQ;IAEjD;;;;;OAKG;IACH,SAAS,CAAC,KAAK,IAAI,OAAO,CAAC,OAAO,CAAC;IAInC;;;;OAIG;IACU,OAAO,IAAI,OAAO,CAAC,QAAQ,CAAC;IAczC;;;;OAIG;YACW,gBAAgB;YA2BhB,mBAAmB;CAalC"}
|
|
@@ -3,6 +3,7 @@ Object.defineProperty(exports, "__esModule", { value: true });
|
|
|
3
3
|
exports.ToolFunction = void 0;
|
|
4
4
|
const app_sdk_1 = require("@zaiusinc/app-sdk");
|
|
5
5
|
const Service_1 = require("../service/Service");
|
|
6
|
+
const TokenVerifier_1 = require("../auth/TokenVerifier");
|
|
6
7
|
/**
|
|
7
8
|
* Abstract base class for tool-based function execution
|
|
8
9
|
* Provides a standard interface for processing requests through registered tools
|
|
@@ -24,8 +25,7 @@ class ToolFunction extends app_sdk_1.Function {
|
|
|
24
25
|
*/
|
|
25
26
|
async perform() {
|
|
26
27
|
(0, app_sdk_1.amendLogContext)({ opalThreadId: this.request.headers.get('x-opal-thread-id') || '' });
|
|
27
|
-
|
|
28
|
-
if (bearerToken && !this.validateBearerToken(bearerToken)) {
|
|
28
|
+
if (!(await this.authorizeRequest())) {
|
|
29
29
|
return new app_sdk_1.Response(403, { error: 'Forbidden' });
|
|
30
30
|
}
|
|
31
31
|
if (this.request.path === '/ready') {
|
|
@@ -36,16 +36,44 @@ class ToolFunction extends app_sdk_1.Function {
|
|
|
36
36
|
return Service_1.toolsService.processRequest(this.request, this);
|
|
37
37
|
}
|
|
38
38
|
/**
|
|
39
|
-
*
|
|
39
|
+
* Authenticate the incoming request by validating the OptiID token and organization ID
|
|
40
40
|
*
|
|
41
|
-
*
|
|
42
|
-
* Subclasses can override this method to implement custom bearer token validation logic.
|
|
43
|
-
*
|
|
44
|
-
* @param _bearerToken - The bearer token extracted from the Authorization header
|
|
45
|
-
* @returns true if the token is valid and the request should proceed, false to return 403 Forbidden
|
|
41
|
+
* @throws true if authentication succeeds
|
|
46
42
|
*/
|
|
47
|
-
|
|
48
|
-
|
|
43
|
+
async authorizeRequest() {
|
|
44
|
+
if (this.request.path === '/discovery' || this.request.path === '/ready') {
|
|
45
|
+
return true;
|
|
46
|
+
}
|
|
47
|
+
const authData = this.request.bodyJSON?.auth;
|
|
48
|
+
const accessToken = authData?.credentials?.access_token;
|
|
49
|
+
if (!accessToken || authData?.provider?.toLowerCase() !== 'optiid') {
|
|
50
|
+
app_sdk_1.logger.error('OptiID token is required but not provided');
|
|
51
|
+
return false;
|
|
52
|
+
}
|
|
53
|
+
const customerId = authData.credentials?.customer_id;
|
|
54
|
+
if (!customerId) {
|
|
55
|
+
app_sdk_1.logger.error('Organisation ID is required but not provided');
|
|
56
|
+
return false;
|
|
57
|
+
}
|
|
58
|
+
const appOrganisationId = (0, app_sdk_1.getAppContext)().account.organizationId;
|
|
59
|
+
if (customerId !== appOrganisationId) {
|
|
60
|
+
app_sdk_1.logger.error(`Invalid organisation ID: expected ${appOrganisationId}, received ${customerId}`);
|
|
61
|
+
return false;
|
|
62
|
+
}
|
|
63
|
+
return await this.validateAccessToken(accessToken);
|
|
64
|
+
}
|
|
65
|
+
async validateAccessToken(accessToken) {
|
|
66
|
+
try {
|
|
67
|
+
if (!accessToken) {
|
|
68
|
+
return false;
|
|
69
|
+
}
|
|
70
|
+
const tokenVerifier = await (0, TokenVerifier_1.getTokenVerifier)();
|
|
71
|
+
return await tokenVerifier.verify(accessToken);
|
|
72
|
+
}
|
|
73
|
+
catch (error) {
|
|
74
|
+
app_sdk_1.logger.error('OptiID token validation failed:', error);
|
|
75
|
+
return false;
|
|
76
|
+
}
|
|
49
77
|
}
|
|
50
78
|
}
|
|
51
79
|
exports.ToolFunction = ToolFunction;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"ToolFunction.js","sourceRoot":"","sources":["../../src/function/ToolFunction.ts"],"names":[],"mappings":";;;AAAA,+
|
|
1
|
+
{"version":3,"file":"ToolFunction.js","sourceRoot":"","sources":["../../src/function/ToolFunction.ts"],"names":[],"mappings":";;;AAAA,+CAA+F;AAC/F,gDAAkD;AAClD,yDAAyD;AAGzD;;;GAGG;AACH,MAAsB,YAAa,SAAQ,kBAAQ;IAEjD;;;;;OAKG;IACO,KAAK;QACb,OAAO,OAAO,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IAC/B,CAAC;IAED;;;;OAIG;IACI,KAAK,CAAC,OAAO;QAClB,IAAA,yBAAe,EAAC,EAAE,YAAY,EAAE,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC,GAAG,CAAC,kBAAkB,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;QACtF,IAAI,CAAC,CAAC,MAAM,IAAI,CAAC,gBAAgB,EAAE,CAAC,EAAE,CAAC;YACrC,OAAO,IAAI,kBAAQ,CAAC,GAAG,EAAE,EAAE,KAAK,EAAE,WAAW,EAAE,CAAC,CAAC;QACnD,CAAC;QAED,IAAI,IAAI,CAAC,OAAO,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;YACnC,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,KAAK,EAAE,CAAC;YACnC,OAAO,IAAI,kBAAQ,CAAC,GAAG,EAAE,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC,CAAC;QAC/C,CAAC;QACD,4EAA4E;QAC5E,OAAO,sBAAY,CAAC,cAAc,CAAC,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,CAAC;IACzD,CAAC;IAED;;;;OAIG;IACK,KAAK,CAAC,gBAAgB;QAC5B,IAAI,IAAI,CAAC,OAAO,CAAC,IAAI,KAAK,YAAY,IAAI,IAAI,CAAC,OAAO,CAAC,IAAI,KAAK,QAAQ,EAAE,CAAC;YACzE,OAAO,IAAI,CAAC;QACd,CAAC;QAED,MAAM,QAAQ,GAAG,IAAI,CAAC,OAAO,CAAC,QAAQ,EAAE,IAAsB,CAAC;QAC/D,MAAM,WAAW,GAAG,QAAQ,EAAE,WAAW,EAAE,YAAY,CAAC;QACxD,IAAI,CAAC,WAAW,IAAI,QAAQ,EAAE,QAAQ,EAAE,WAAW,EAAE,KAAK,QAAQ,EAAE,CAAC;YACnE,gBAAM,CAAC,KAAK,CAAC,2CAA2C,CAAC,CAAC;YAC1D,OAAO,KAAK,CAAC;QACf,CAAC;QAED,MAAM,UAAU,GAAG,QAAQ,CAAC,WAAW,EAAE,WAAW,CAAC;QACrD,IAAI,CAAC,UAAU,EAAE,CAAC;YAChB,gBAAM,CAAC,KAAK,CAAC,8CAA8C,CAAC,CAAC;YAC7D,OAAO,KAAK,CAAC;QACf,CAAC;QAED,MAAM,iBAAiB,GAAG,IAAA,uBAAa,GAAE,CAAC,OAAO,CAAC,cAAc,CAAC;QACjE,IAAI,UAAU,KAAK,iBAAiB,EAAE,CAAC;YACrC,gBAAM,CAAC,KAAK,CAAC,qCAAqC,iBAAiB,cAAc,UAAU,EAAE,CAAC,CAAC;YAC/F,OAAO,KAAK,CAAC;QACf,CAAC;QAED,OAAO,MAAM,IAAI,CAAC,mBAAmB,CAAC,WAAW,CAAC,CAAC;IACrD,CAAC;IAEO,KAAK,CAAC,mBAAmB,CAAC,WAA+B;QAC/D,IAAI,CAAC;YACH,IAAI,CAAC,WAAW,EAAE,CAAC;gBACjB,OAAO,KAAK,CAAC;YACf,CAAC;YACD,MAAM,aAAa,GAAG,MAAM,IAAA,gCAAgB,GAAE,CAAC;YAC/C,OAAO,MAAM,aAAa,CAAC,MAAM,CAAC,WAAW,CAAC,CAAC;QACjD,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,gBAAM,CAAC,KAAK,CAAC,iCAAiC,EAAE,KAAK,CAAC,CAAC;YACvD,OAAO,KAAK,CAAC;QACf,CAAC;IACH,CAAC;CAEF;AA5ED,oCA4EC"}
|