@optimizely-opal/opal-tools-sdk 0.1.3-dev → 0.1.6-dev
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/.prettierignore +5 -0
- package/.prettierrc +1 -0
- package/README.md +227 -198
- package/dist/auth.d.ts +5 -5
- package/dist/auth.js +2 -2
- package/dist/block.d.ts +4760 -0
- package/dist/block.js +104 -0
- package/dist/decorators.d.ts +8 -8
- package/dist/decorators.js +3 -43
- package/dist/index.d.ts +9 -5
- package/dist/index.js +10 -5
- package/dist/models.d.ts +125 -118
- package/dist/models.js +88 -80
- package/dist/registerTool.d.ts +68 -0
- package/dist/registerTool.js +57 -0
- package/dist/registry.d.ts +1 -1
- package/dist/registry.js +1 -1
- package/dist/service.d.ts +10 -8
- package/dist/service.js +50 -22
- package/eslint.config.js +20 -0
- package/package.json +21 -12
- package/scripts/generate-block.ts +167 -0
- package/scripts/lint.sh +7 -0
- package/src/auth.ts +21 -16
- package/src/block.ts +11761 -0
- package/src/decorators.ts +28 -67
- package/src/index.ts +9 -5
- package/src/models.ts +117 -105
- package/src/registerTool.ts +181 -0
- package/src/registry.ts +2 -2
- package/src/service.ts +80 -37
- package/tests/block.test.ts +115 -0
- package/tests/integration.test.ts +318 -0
- package/tsconfig.build.json +5 -0
- package/tsconfig.json +3 -3
- package/vitest.config.ts +7 -0
package/.prettierignore
ADDED
package/.prettierrc
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{}
|
package/README.md
CHANGED
|
@@ -4,36 +4,83 @@ This SDK simplifies the creation of tools services compatible with the Opal Tool
|
|
|
4
4
|
|
|
5
5
|
## Features
|
|
6
6
|
|
|
7
|
-
-
|
|
8
|
-
-
|
|
9
|
-
-
|
|
7
|
+
- Modern `registerTool` API with Zod schemas for type-safe tool definitions
|
|
8
|
+
- Legacy `@tool` decorator API for backwards compatibility
|
|
9
|
+
- Automatic type inference with Zod (registerTool only)
|
|
10
|
+
- Adaptive Block Document support for rich interactive UIs
|
|
11
|
+
- Runtime validation with Zod (registerTool only)
|
|
12
|
+
- Automatic discovery endpoint generation
|
|
10
13
|
- Authentication helpers
|
|
11
14
|
- Express integration
|
|
12
|
-
- Island components for interactive UI responses
|
|
13
15
|
|
|
14
16
|
## Installation
|
|
15
17
|
|
|
16
18
|
```bash
|
|
17
|
-
npm install @optimizely-opal/opal-tools-sdk
|
|
19
|
+
npm install @optimizely-opal/opal-tools-sdk express zod
|
|
18
20
|
```
|
|
19
21
|
|
|
20
|
-
##
|
|
22
|
+
## Quick Start
|
|
23
|
+
|
|
24
|
+
### `registerTool`
|
|
21
25
|
|
|
22
26
|
```typescript
|
|
23
|
-
import
|
|
24
|
-
import
|
|
27
|
+
import express from "express";
|
|
28
|
+
import { z } from "zod";
|
|
29
|
+
import { ToolsService, registerTool } from "@optimizely-opal/opal-tools-sdk";
|
|
25
30
|
|
|
26
31
|
const app = express();
|
|
27
32
|
const toolsService = new ToolsService(app);
|
|
28
33
|
|
|
34
|
+
// ✨ Types are automatically inferred from the inputSchema!
|
|
35
|
+
const getWeather = registerTool(
|
|
36
|
+
"get_weather",
|
|
37
|
+
{
|
|
38
|
+
description: "Gets current weather for a location",
|
|
39
|
+
inputSchema: {
|
|
40
|
+
location: z.string().describe("City name or location"),
|
|
41
|
+
units: z
|
|
42
|
+
.enum(["metric", "imperial"])
|
|
43
|
+
.optional()
|
|
44
|
+
.describe("Temperature units"),
|
|
45
|
+
},
|
|
46
|
+
},
|
|
47
|
+
async (params) => {
|
|
48
|
+
// params.location is typed as string
|
|
49
|
+
// params.units is typed as 'metric' | 'imperial' | undefined
|
|
50
|
+
return { temperature: 22, condition: "sunny" };
|
|
51
|
+
},
|
|
52
|
+
);
|
|
53
|
+
|
|
54
|
+
app.listen(3000);
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
### Legacy `@tool` Decorator API
|
|
58
|
+
|
|
59
|
+
```typescript
|
|
60
|
+
import { ToolsService, tool, ParameterType } from '@optimizely-opal/opal-tools-sdk';
|
|
61
|
+
|
|
29
62
|
interface WeatherParameters {
|
|
30
63
|
location: string;
|
|
31
|
-
units
|
|
64
|
+
units?: string;
|
|
32
65
|
}
|
|
33
66
|
|
|
34
67
|
@tool({
|
|
35
68
|
name: 'get_weather',
|
|
36
|
-
description: 'Gets current weather for a location'
|
|
69
|
+
description: 'Gets current weather for a location',
|
|
70
|
+
parameters: [
|
|
71
|
+
{
|
|
72
|
+
name: 'location',
|
|
73
|
+
type: ParameterType.String,
|
|
74
|
+
description: 'City name or location',
|
|
75
|
+
required: true,
|
|
76
|
+
},
|
|
77
|
+
{
|
|
78
|
+
name: 'units',
|
|
79
|
+
type: ParameterType.String,
|
|
80
|
+
description: 'Temperature units',
|
|
81
|
+
required: false,
|
|
82
|
+
},
|
|
83
|
+
],
|
|
37
84
|
})
|
|
38
85
|
async function getWeather(parameters: WeatherParameters) {
|
|
39
86
|
// Implementation...
|
|
@@ -45,228 +92,210 @@ async function getWeather(parameters: WeatherParameters) {
|
|
|
45
92
|
|
|
46
93
|
## Authentication
|
|
47
94
|
|
|
48
|
-
The
|
|
95
|
+
Both APIs support authentication. The second parameter of your handler receives the extra context object containing auth data.
|
|
49
96
|
|
|
50
|
-
###
|
|
97
|
+
### With `registerTool`
|
|
51
98
|
|
|
52
99
|
```typescript
|
|
53
|
-
import {
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
return { events: ['Meeting at 10:00', 'Lunch at 12:00'] };
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
// Multiple authentication requirements (tool can work with either provider)
|
|
82
|
-
@requiresAuth({ provider: 'google', scopeBundle: 'calendar', required: true })
|
|
83
|
-
@requiresAuth({ provider: 'microsoft', scopeBundle: 'outlook', required: true })
|
|
84
|
-
@tool({
|
|
85
|
-
name: 'get_calendar_availability',
|
|
86
|
-
description: 'Check calendar availability'
|
|
87
|
-
})
|
|
88
|
-
async function getCalendarAvailability(parameters: CalendarParameters, authData?: any) {
|
|
89
|
-
const provider = authData?.provider || '';
|
|
90
|
-
const token = authData?.credentials?.token || '';
|
|
91
|
-
|
|
92
|
-
if (provider === 'google') {
|
|
93
|
-
// Use Google Calendar API
|
|
94
|
-
} else if (provider === 'microsoft') {
|
|
95
|
-
// Use Microsoft Outlook API
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
return { available: true, provider_used: provider };
|
|
99
|
-
}
|
|
100
|
+
import { z } from "zod";
|
|
101
|
+
|
|
102
|
+
const getCalendarEvents = registerTool(
|
|
103
|
+
"get_calendar_events",
|
|
104
|
+
{
|
|
105
|
+
description: "Gets calendar events for a date",
|
|
106
|
+
inputSchema: {
|
|
107
|
+
date: z.string().describe("Date in YYYY-MM-DD format"),
|
|
108
|
+
},
|
|
109
|
+
authRequirements: {
|
|
110
|
+
provider: "google",
|
|
111
|
+
scopeBundle: "calendar",
|
|
112
|
+
required: true,
|
|
113
|
+
},
|
|
114
|
+
},
|
|
115
|
+
async (params, extra) => {
|
|
116
|
+
// Access auth data from extra context
|
|
117
|
+
const token = extra?.auth?.credentials?.access_token;
|
|
118
|
+
// Check execution mode if needed
|
|
119
|
+
const mode = extra?.mode; // 'headless' | 'interactive'
|
|
120
|
+
|
|
121
|
+
// Use token to make authenticated requests
|
|
122
|
+
return { events: ["Meeting at 10:00", "Lunch at 12:00"] };
|
|
123
|
+
},
|
|
124
|
+
);
|
|
100
125
|
```
|
|
101
126
|
|
|
102
|
-
###
|
|
127
|
+
### With `@tool` Decorator
|
|
103
128
|
|
|
104
129
|
```typescript
|
|
105
|
-
interface EmailParameters {
|
|
106
|
-
limit?: number;
|
|
107
|
-
folder?: string;
|
|
108
|
-
}
|
|
109
|
-
|
|
110
130
|
@tool({
|
|
111
|
-
name: '
|
|
112
|
-
description: 'Gets
|
|
131
|
+
name: 'get_calendar_events',
|
|
132
|
+
description: 'Gets calendar events',
|
|
133
|
+
parameters: [
|
|
134
|
+
{
|
|
135
|
+
name: 'date',
|
|
136
|
+
type: ParameterType.String,
|
|
137
|
+
description: 'Date in YYYY-MM-DD format',
|
|
138
|
+
required: true,
|
|
139
|
+
},
|
|
140
|
+
],
|
|
113
141
|
authRequirements: {
|
|
114
142
|
provider: 'google',
|
|
115
|
-
scopeBundle: '
|
|
116
|
-
required: true
|
|
117
|
-
}
|
|
143
|
+
scopeBundle: 'calendar',
|
|
144
|
+
required: true,
|
|
145
|
+
},
|
|
118
146
|
})
|
|
119
|
-
async function
|
|
120
|
-
|
|
121
|
-
return {
|
|
147
|
+
async function getCalendarEvents(params: any, environment?: any) {
|
|
148
|
+
const token = environment?.auth?.credentials?.access_token;
|
|
149
|
+
return { events: [] };
|
|
122
150
|
}
|
|
123
151
|
```
|
|
124
152
|
|
|
125
|
-
##
|
|
126
|
-
|
|
127
|
-
The SDK provides authentication support for tools that require user credentials:
|
|
153
|
+
## Adaptive Block Documents
|
|
128
154
|
|
|
129
|
-
|
|
130
|
-
import { ToolsService, tool, requiresAuth, AuthData } from '@optimizely-opal/opal-tools-sdk';
|
|
131
|
-
import express from 'express';
|
|
132
|
-
|
|
133
|
-
interface CalendarParameters {
|
|
134
|
-
date: string;
|
|
135
|
-
timezone?: string;
|
|
136
|
-
}
|
|
155
|
+
Adaptive Block Documents enable rich, interactive UI responses with forms, buttons, and dynamic content.
|
|
137
156
|
|
|
138
|
-
|
|
139
|
-
const toolsService = new ToolsService(app);
|
|
157
|
+
### Creating Adaptive Block Responses
|
|
140
158
|
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
}
|
|
159
|
+
```typescript
|
|
160
|
+
import { z } from "zod";
|
|
161
|
+
import { registerTool, Block } from "@optimizely-opal/opal-tools-sdk";
|
|
162
|
+
|
|
163
|
+
const createTask = registerTool(
|
|
164
|
+
"create_task",
|
|
165
|
+
{
|
|
166
|
+
description: "Create a new task",
|
|
167
|
+
type: "block", // Specify this is an Adaptive Block tool
|
|
168
|
+
inputSchema: {
|
|
169
|
+
title: z.string().describe("Task title"),
|
|
170
|
+
description: z.string().optional().describe("Task description"),
|
|
171
|
+
},
|
|
172
|
+
},
|
|
173
|
+
async (params) => {
|
|
174
|
+
// Return a BlockResponse (plain object with content/data/artifact/etc)
|
|
175
|
+
return {
|
|
176
|
+
content: Block.Document({
|
|
177
|
+
children: [
|
|
178
|
+
Block.Heading({ children: "Task Created!", level: "1" }),
|
|
179
|
+
Block.Text({ children: `Created: ${params.title}` }),
|
|
180
|
+
Block.Input({
|
|
181
|
+
name: "notes",
|
|
182
|
+
placeholder: "Add notes...",
|
|
183
|
+
value: params.description || "",
|
|
184
|
+
}),
|
|
185
|
+
],
|
|
186
|
+
actions: [
|
|
187
|
+
Block.Action({ name: "save", children: "Save Changes" }),
|
|
188
|
+
Block.Action({
|
|
189
|
+
name: "delete",
|
|
190
|
+
children: "Delete",
|
|
191
|
+
variant: "danger",
|
|
192
|
+
}),
|
|
193
|
+
],
|
|
194
|
+
}),
|
|
195
|
+
data: { task_id: "123", created_at: new Date().toISOString() },
|
|
196
|
+
artifact: {
|
|
197
|
+
type: "task",
|
|
198
|
+
id: "task-123",
|
|
199
|
+
data: { title: params.title },
|
|
200
|
+
},
|
|
201
|
+
};
|
|
202
|
+
},
|
|
203
|
+
);
|
|
155
204
|
```
|
|
156
205
|
|
|
157
|
-
|
|
206
|
+
### Adaptive Block Components
|
|
158
207
|
|
|
159
|
-
The SDK
|
|
208
|
+
The SDK provides a type-safe `Block` namespace with factory functions for all components:
|
|
160
209
|
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
210
|
+
- `Block.Document()` - Root container with children and actions
|
|
211
|
+
- `Block.Heading()` - Headings with levels 1-6
|
|
212
|
+
- `Block.Text()` - Text content
|
|
213
|
+
- `Block.Input()` - Text input fields
|
|
214
|
+
- `Block.Textarea()` - Multi-line text areas
|
|
215
|
+
- `Block.Checkbox()` - Checkbox inputs
|
|
216
|
+
- `Block.Select()` - Dropdown selects
|
|
217
|
+
- `Block.Button()` - Action buttons
|
|
218
|
+
- `Block.Action()` - Document-level actions
|
|
219
|
+
- `Block.List()` - Ordered/unordered lists
|
|
220
|
+
- `Block.Table()` - Data tables
|
|
221
|
+
- And more...
|
|
169
222
|
|
|
170
|
-
|
|
171
|
-
location: string;
|
|
172
|
-
units?: string;
|
|
173
|
-
}
|
|
223
|
+
See the generated [src/block.ts](./src/block.ts) for the complete list and TypeScript types.
|
|
174
224
|
|
|
175
|
-
|
|
176
|
-
const toolsService = new ToolsService(app);
|
|
225
|
+
### Regenerating Adaptive Block Types
|
|
177
226
|
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
async function getWeather(parameters: WeatherParameters) {
|
|
183
|
-
// Get weather data (implementation details omitted)
|
|
184
|
-
const weatherData = { temperature: 22, condition: 'sunny', humidity: 65 };
|
|
185
|
-
|
|
186
|
-
// Create an interactive island for weather settings
|
|
187
|
-
const island = new IslandConfig(
|
|
188
|
-
[
|
|
189
|
-
new IslandConfig.Field(
|
|
190
|
-
'location',
|
|
191
|
-
'Location',
|
|
192
|
-
'string',
|
|
193
|
-
parameters.location
|
|
194
|
-
),
|
|
195
|
-
new IslandConfig.Field(
|
|
196
|
-
'units',
|
|
197
|
-
'Temperature Units',
|
|
198
|
-
'string',
|
|
199
|
-
parameters.units || 'metric',
|
|
200
|
-
false,
|
|
201
|
-
['metric', 'imperial', 'kelvin']
|
|
202
|
-
),
|
|
203
|
-
new IslandConfig.Field(
|
|
204
|
-
'current_temp',
|
|
205
|
-
'Current Temperature',
|
|
206
|
-
'string',
|
|
207
|
-
`${weatherData.temperature}°${parameters.units === 'metric' ? 'C' : 'F'}`
|
|
208
|
-
)
|
|
209
|
-
],
|
|
210
|
-
[
|
|
211
|
-
new IslandConfig.Action(
|
|
212
|
-
'refresh_weather',
|
|
213
|
-
'Refresh Weather',
|
|
214
|
-
'button',
|
|
215
|
-
'/tools/get_weather',
|
|
216
|
-
'update'
|
|
217
|
-
)
|
|
218
|
-
]
|
|
219
|
-
);
|
|
220
|
-
|
|
221
|
-
return IslandResponse.create([island]);
|
|
222
|
-
}
|
|
227
|
+
The Adaptive Block types are auto-generated from the JSON schema. To regenerate:
|
|
228
|
+
|
|
229
|
+
```bash
|
|
230
|
+
npm run generate:block
|
|
223
231
|
```
|
|
224
232
|
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
Fields represent data inputs in the UI:
|
|
229
|
-
- `name`: Programmatic field identifier
|
|
230
|
-
- `label`: Human-readable label
|
|
231
|
-
- `type`: Field type (`'string'`, `'boolean'`, `'json'`)
|
|
232
|
-
- `value`: Current field value (optional)
|
|
233
|
-
- `hidden`: Whether to hide from user (optional, default: false)
|
|
234
|
-
- `options`: Available options for selection (optional)
|
|
235
|
-
|
|
236
|
-
#### IslandConfig.Action
|
|
237
|
-
Actions represent buttons or operations:
|
|
238
|
-
- `name`: Programmatic action identifier
|
|
239
|
-
- `label`: Human-readable button label
|
|
240
|
-
- `type`: UI element type (typically `'button'`)
|
|
241
|
-
- `endpoint`: API endpoint to call
|
|
242
|
-
- `operation`: Operation type (default: `'create'`)
|
|
243
|
-
|
|
244
|
-
#### IslandConfig
|
|
245
|
-
Contains the complete island configuration:
|
|
246
|
-
- `fields`: Array of IslandConfig.Field objects
|
|
247
|
-
- `actions`: Array of IslandConfig.Action objects
|
|
248
|
-
|
|
249
|
-
#### IslandResponse
|
|
250
|
-
The response wrapper for islands:
|
|
251
|
-
- Use `IslandResponse.create([islands])` to create responses
|
|
252
|
-
- Supports multiple islands per response
|
|
233
|
+
This reads `block-document-spec.json` and generates TypeScript interfaces and factory functions in [src/block.ts](./src/block.ts).
|
|
234
|
+
|
|
235
|
+
**Note:** Don't edit `src/block.ts` manually - it will be overwritten on regeneration.
|
|
253
236
|
|
|
254
237
|
## Type Definitions
|
|
255
238
|
|
|
256
239
|
The SDK provides comprehensive TypeScript type definitions:
|
|
257
240
|
|
|
258
241
|
### Authentication Types
|
|
259
|
-
|
|
260
|
-
- `
|
|
261
|
-
- `
|
|
242
|
+
|
|
243
|
+
- `AuthData` - Provider and credentials information
|
|
244
|
+
- `Credentials` - Access tokens and org details
|
|
245
|
+
- `Environment` - Execution context with auth data
|
|
262
246
|
|
|
263
247
|
### Parameter Types
|
|
264
|
-
- `ParameterType`: Enum for supported parameter types
|
|
265
|
-
- `Parameter`: Class for tool parameter definitions
|
|
266
|
-
- `Function`: Class for complete tool function definitions
|
|
267
248
|
|
|
268
|
-
|
|
249
|
+
- `ParameterType` - Enum for parameter types (String, Number, Boolean, List, Dictionary)
|
|
250
|
+
- `Parameter` - Tool parameter definitions
|
|
251
|
+
- `Function` - Complete tool function definitions
|
|
252
|
+
|
|
253
|
+
### Block Types
|
|
254
|
+
|
|
255
|
+
All Block Document components have full TypeScript interfaces with type checking and IDE autocomplete.
|
|
256
|
+
|
|
257
|
+
## API Reference
|
|
258
|
+
|
|
259
|
+
### `registerTool<TSchema, TReturn>(name, options, handler)`
|
|
260
|
+
|
|
261
|
+
Modern API for defining tools with Zod schemas.
|
|
262
|
+
|
|
263
|
+
**Parameters:**
|
|
264
|
+
|
|
265
|
+
- `name: string` - Tool name (required)
|
|
266
|
+
- `options: ToolOptions` - Configuration object
|
|
267
|
+
- `description: string` - Tool description (required)
|
|
268
|
+
- `inputSchema: Record<string, z.ZodTypeAny>` - Zod schema for parameters (required)
|
|
269
|
+
- `type?: 'json' | 'block'` - Response type (default: 'json')
|
|
270
|
+
- `authRequirements?` - Authentication requirements
|
|
271
|
+
- `handler: (params, extra?) => Result` - Tool implementation
|
|
272
|
+
- `params` - Validated input parameters (typed from schema)
|
|
273
|
+
- `extra?` - Optional extra context
|
|
274
|
+
- `mode: 'headless' | 'interactive'` - Execution mode
|
|
275
|
+
- `auth?: { provider, credentials }` - Auth data if provided
|
|
276
|
+
|
|
277
|
+
**Returns:** The handler function with full type inference
|
|
278
|
+
|
|
279
|
+
### `@tool(options)`
|
|
280
|
+
|
|
281
|
+
Legacy decorator for defining tools.
|
|
282
|
+
|
|
283
|
+
**Options:**
|
|
284
|
+
|
|
285
|
+
- `name: string` - Tool name
|
|
286
|
+
- `description: string` - Tool description
|
|
287
|
+
- `parameters: ParameterDefinition[]` - Parameter definitions
|
|
288
|
+
- `authRequirements?` - Authentication requirements
|
|
289
|
+
|
|
290
|
+
### `ToolsService`
|
|
291
|
+
|
|
292
|
+
Express service that manages tool registration and creates discovery endpoints.
|
|
293
|
+
|
|
294
|
+
```typescript
|
|
295
|
+
const toolsService = new ToolsService(app);
|
|
296
|
+
// Automatically creates /discovery endpoint
|
|
297
|
+
```
|
|
269
298
|
|
|
270
|
-
##
|
|
299
|
+
## License
|
|
271
300
|
|
|
272
|
-
|
|
301
|
+
MIT
|
package/dist/auth.d.ts
CHANGED
|
@@ -1,3 +1,8 @@
|
|
|
1
|
+
interface AuthOptions {
|
|
2
|
+
provider: string;
|
|
3
|
+
required?: boolean;
|
|
4
|
+
scopeBundle: string;
|
|
5
|
+
}
|
|
1
6
|
/**
|
|
2
7
|
* Middleware to handle authentication requirements
|
|
3
8
|
* @param req Express request
|
|
@@ -5,11 +10,6 @@
|
|
|
5
10
|
* @param next Express next function
|
|
6
11
|
*/
|
|
7
12
|
export declare function authMiddleware(req: any, res: any, next: any): any;
|
|
8
|
-
interface AuthOptions {
|
|
9
|
-
provider: string;
|
|
10
|
-
scopeBundle: string;
|
|
11
|
-
required?: boolean;
|
|
12
|
-
}
|
|
13
13
|
/**
|
|
14
14
|
* Decorator to indicate that a tool requires authentication
|
|
15
15
|
* @param options Authentication options
|
package/dist/auth.js
CHANGED
|
@@ -11,7 +11,7 @@ exports.requiresAuth = requiresAuth;
|
|
|
11
11
|
function authMiddleware(req, res, next) {
|
|
12
12
|
const authHeader = req.headers.authorization;
|
|
13
13
|
if (!authHeader && req.authRequired) {
|
|
14
|
-
return res.status(401).json({ error:
|
|
14
|
+
return res.status(401).json({ error: "Authentication required" });
|
|
15
15
|
}
|
|
16
16
|
// The Tools Management Service will provide the appropriate token
|
|
17
17
|
// in the Authorization header
|
|
@@ -31,8 +31,8 @@ function requiresAuth(options) {
|
|
|
31
31
|
const fn = originalMethod;
|
|
32
32
|
fn.__authRequirements__ = {
|
|
33
33
|
provider: options.provider,
|
|
34
|
+
required: options.required ?? true,
|
|
34
35
|
scopeBundle: options.scopeBundle,
|
|
35
|
-
required: options.required ?? true
|
|
36
36
|
};
|
|
37
37
|
return originalMethod.apply(this, args);
|
|
38
38
|
};
|