nitrostack 1.0.23 → 1.0.24
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/dist/cli/commands/dev.d.ts.map +1 -1
- package/dist/cli/commands/dev.js +3 -1
- package/dist/cli/commands/dev.js.map +1 -1
- package/dist/cli/mcp-dev-wrapper.js +2 -1
- package/dist/cli/mcp-dev-wrapper.js.map +1 -1
- package/dist/core/app-decorator.d.ts.map +1 -1
- package/dist/core/app-decorator.js +24 -2
- package/dist/core/app-decorator.js.map +1 -1
- package/dist/core/di/container.d.ts.map +1 -1
- package/dist/core/di/container.js +14 -1
- package/dist/core/di/container.js.map +1 -1
- package/dist/core/oauth-module.d.ts +15 -42
- package/dist/core/oauth-module.d.ts.map +1 -1
- package/dist/core/oauth-module.js +130 -5
- package/dist/core/oauth-module.js.map +1 -1
- package/dist/core/server.d.ts +7 -1
- package/dist/core/server.d.ts.map +1 -1
- package/dist/core/server.js +99 -23
- package/dist/core/server.js.map +1 -1
- package/dist/core/transports/discovery-http-server.d.ts +13 -0
- package/dist/core/transports/discovery-http-server.d.ts.map +1 -0
- package/dist/core/transports/discovery-http-server.js +54 -0
- package/dist/core/transports/discovery-http-server.js.map +1 -0
- package/dist/core/transports/http-server.d.ts +6 -0
- package/dist/core/transports/http-server.d.ts.map +1 -1
- package/dist/core/transports/http-server.js +8 -0
- package/dist/core/transports/http-server.js.map +1 -1
- package/dist/core/transports/streamable-http.d.ts +5 -0
- package/dist/core/transports/streamable-http.d.ts.map +1 -1
- package/dist/core/transports/streamable-http.js +7 -0
- package/dist/core/transports/streamable-http.js.map +1 -1
- package/package.json +1 -1
- package/src/studio/app/api/auth/fetch-metadata/route.ts +2 -2
- package/src/studio/app/auth/page.tsx +16 -3
- package/src/studio/next.config.js +4 -0
- package/templates/typescript-auth/package.json +2 -1
- package/templates/typescript-auth/src/index.ts +6 -25
- package/templates/typescript-auth-api-key/package.json +3 -1
- package/templates/typescript-auth-api-key/src/index.ts +6 -26
- package/templates/typescript-oauth/.env.example +35 -24
- package/templates/typescript-oauth/OAUTH_SETUP.md +306 -120
- package/templates/typescript-oauth/README.md +75 -31
- package/templates/typescript-oauth/package.json +3 -1
- package/templates/typescript-oauth/src/index.ts +6 -27
- package/templates/typescript-starter/package.json +2 -1
- package/templates/typescript-starter/src/index.ts +6 -25
|
@@ -21,53 +21,72 @@ npm install
|
|
|
21
21
|
|
|
22
22
|
### 2. Setup Auth0 (Recommended for Quick Testing)
|
|
23
23
|
|
|
24
|
+
**⚠️ IMPORTANT:** Follow the steps in **exact order** to avoid common issues!
|
|
25
|
+
|
|
26
|
+
#### Create Auth0 API (Do This First!)
|
|
27
|
+
|
|
28
|
+
1. Auth0 Dashboard → **Applications** → **APIs** → **Create API**
|
|
29
|
+
2. **Settings:**
|
|
30
|
+
- **Name**: `MCP Server API`
|
|
31
|
+
- **Identifier**: `https://mcplocal` (your RESOURCE_URI - can be any unique URI)
|
|
32
|
+
- **Signing Algorithm**: **RS256**
|
|
33
|
+
- **JWT Profile**: **RFC 9068** (OAuth 2.0 Access Token JWT Profile)
|
|
34
|
+
3. **Permissions** tab → **Add Scopes:**
|
|
35
|
+
- `read` - Read access to resources
|
|
36
|
+
- `write` - Write/modify resources
|
|
37
|
+
- `admin` - Administrative operations
|
|
38
|
+
4. **Save**
|
|
39
|
+
|
|
24
40
|
#### Create Auth0 Application
|
|
25
41
|
|
|
26
42
|
1. Go to [Auth0 Dashboard](https://manage.auth0.com/)
|
|
27
43
|
2. **Applications** → **Create Application**
|
|
28
|
-
3. Choose **"Regular Web Application"**
|
|
44
|
+
3. Choose **"Regular Web Application"** ← **CRITICAL!** (Not SPA or M2M)
|
|
29
45
|
4. **Application Settings:**
|
|
30
|
-
- **Name**: `
|
|
31
|
-
- **Allowed Callback URLs**: `http://localhost:3000/auth/callback`
|
|
32
|
-
- **Allowed Logout URLs**: `http://localhost:3000`
|
|
33
|
-
- **Allowed Web Origins**: `http://localhost:3000`
|
|
34
|
-
- **Grant Types**:
|
|
46
|
+
- **Name**: `MCP Server OAuth`
|
|
47
|
+
- **Allowed Callback URLs**: `http://localhost:3005/auth/callback,http://localhost:3000/auth/callback`
|
|
48
|
+
- **Allowed Logout URLs**: `http://localhost:3005,http://localhost:3000`
|
|
49
|
+
- **Allowed Web Origins**: `http://localhost:3005,http://localhost:3000`
|
|
50
|
+
- **Advanced Settings → Grant Types**:
|
|
51
|
+
- ✅ Authorization Code
|
|
52
|
+
- ✅ Refresh Token
|
|
53
|
+
- ❌ Implicit (disable)
|
|
54
|
+
- **Advanced Settings → ID Token Tab**:
|
|
55
|
+
- ❌ ID Token Encryption: **DISABLED** or **NONE**
|
|
35
56
|
5. **Save** and copy:
|
|
36
57
|
- **Domain** (e.g., `dev-xxx.us.auth0.com`)
|
|
37
58
|
- **Client ID**
|
|
38
59
|
- **Client Secret**
|
|
39
60
|
|
|
40
|
-
####
|
|
61
|
+
#### Link Application to API
|
|
41
62
|
|
|
42
|
-
1.
|
|
43
|
-
2. **
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
- `read` - Read access to resources
|
|
49
|
-
- `write` - Write/modify resources
|
|
50
|
-
- `admin` - Administrative operations
|
|
51
|
-
4. **Save**
|
|
63
|
+
1. Go to **Applications** → **APIs** → **MCP Server API**
|
|
64
|
+
2. Click **"Machine to Machine Applications"** tab
|
|
65
|
+
3. Find your `MCP Server OAuth` application
|
|
66
|
+
4. Toggle to **"Authorized"** (green)
|
|
67
|
+
5. Expand and select all scopes (`read`, `write`, `admin`)
|
|
68
|
+
6. Click **"Update"**
|
|
52
69
|
|
|
53
70
|
### 3. Configure Environment Variables
|
|
54
71
|
|
|
55
72
|
Edit `.env` with your Auth0 settings:
|
|
56
73
|
|
|
57
74
|
```bash
|
|
58
|
-
# Your MCP server's resource URI (
|
|
59
|
-
RESOURCE_URI=
|
|
75
|
+
# Your MCP server's resource URI (MUST match Auth0 API Identifier EXACTLY)
|
|
76
|
+
RESOURCE_URI=https://mcplocal
|
|
60
77
|
|
|
61
78
|
# Your Auth0 domain (with https://)
|
|
62
79
|
AUTH_SERVER_URL=https://YOUR-TENANT.auth0.com
|
|
63
80
|
|
|
64
|
-
# Token audience (
|
|
65
|
-
TOKEN_AUDIENCE=
|
|
81
|
+
# Token audience (MUST match RESOURCE_URI)
|
|
82
|
+
TOKEN_AUDIENCE=https://mcplocal
|
|
66
83
|
|
|
67
|
-
# Token issuer (Auth0 domain with trailing slash)
|
|
84
|
+
# Token issuer (Auth0 domain with trailing slash - don't forget the /)
|
|
68
85
|
TOKEN_ISSUER=https://YOUR-TENANT.auth0.com/
|
|
69
86
|
```
|
|
70
87
|
|
|
88
|
+
**⚠️ Replace `YOUR-TENANT` with your actual Auth0 domain!**
|
|
89
|
+
|
|
71
90
|
**See `OAUTH_SETUP.md` for other providers** (Okta, Keycloak, Azure AD).
|
|
72
91
|
|
|
73
92
|
### 4. Start the Server
|
|
@@ -78,14 +97,19 @@ npm run dev
|
|
|
78
97
|
|
|
79
98
|
You should see:
|
|
80
99
|
```
|
|
81
|
-
|
|
82
|
-
🔐 OAuth 2.1 enabled
|
|
100
|
+
🚀 OAuth discovery server running at http://localhost:3005
|
|
101
|
+
NITRO_LOG::{"level":"info","message":"🔐 OAuth 2.1 enabled"}
|
|
102
|
+
NITRO_LOG::{"level":"info","message":" Resource URI: https://mcplocal"}
|
|
103
|
+
NITRO_LOG::{"level":"info","message":" Auth Servers: https://YOUR-TENANT.auth0.com"}
|
|
83
104
|
🚀 Server started successfully (DUAL: STDIO + HTTP)
|
|
84
105
|
📡 MCP Protocol: STDIO (for Studio/Claude)
|
|
85
|
-
🌐 OAuth Metadata: HTTP (port
|
|
106
|
+
🌐 OAuth Metadata: HTTP (port 3005)
|
|
86
107
|
```
|
|
87
108
|
|
|
88
|
-
**Note:** The server runs in **DUAL mode
|
|
109
|
+
**Note:** The server runs in **DUAL mode**:
|
|
110
|
+
- **STDIO**: For MCP protocol communication
|
|
111
|
+
- **HTTP (port 3005)**: For OAuth discovery in dev mode
|
|
112
|
+
- **HTTP (port 3000)**: For OAuth discovery in prod mode
|
|
89
113
|
|
|
90
114
|
### 5. Complete OAuth Flow in Studio
|
|
91
115
|
|
|
@@ -94,10 +118,11 @@ Navigate to `http://localhost:3000`
|
|
|
94
118
|
|
|
95
119
|
#### Step 1: Discover OAuth Server
|
|
96
120
|
1. Go to **Auth → OAuth 2.1** tab
|
|
97
|
-
2. Enter Server URL: `http://localhost:
|
|
121
|
+
2. Enter Server URL: `http://localhost:3005` (dev mode uses port 3005)
|
|
98
122
|
3. Click **"Discover Auth Config"**
|
|
99
123
|
4. ✅ Should show: **Discovery Successful**
|
|
100
124
|
5. You'll see the discovered metadata (resource URI, auth server, scopes)
|
|
125
|
+
6. ✅ Check browser console for: `🎯 Setting audience parameter: https://mcplocal`
|
|
101
126
|
|
|
102
127
|
#### Step 2: Enter Client Credentials
|
|
103
128
|
1. Scroll to **"2a. Use Existing Client"** section
|
|
@@ -298,20 +323,39 @@ This template works with any RFC-compliant OAuth 2.1 provider:
|
|
|
298
323
|
|
|
299
324
|
## 🚨 Common Issues
|
|
300
325
|
|
|
326
|
+
### "Received JWE (encrypted) token instead of JWT!"
|
|
327
|
+
|
|
328
|
+
**Symptoms:** Server logs show:
|
|
329
|
+
```
|
|
330
|
+
[DEBUG] Token header: {"alg":"dir","enc":"A256GCM",...}
|
|
331
|
+
[ERROR] Received JWE (encrypted) token instead of JWT!
|
|
332
|
+
```
|
|
333
|
+
|
|
334
|
+
**Fix:**
|
|
335
|
+
1. Go to Applications → Your Application → Settings → Advanced Settings
|
|
336
|
+
2. Click "ID Token" tab
|
|
337
|
+
3. Disable "ID Token Encryption" or set to "None"
|
|
338
|
+
4. Save and re-authorize in Studio
|
|
339
|
+
|
|
301
340
|
### "OAuth token validation failed: Token audience mismatch"
|
|
302
341
|
|
|
303
|
-
**Fix:** Ensure `TOKEN_AUDIENCE` in `.env`
|
|
342
|
+
**Fix:** Ensure `RESOURCE_URI` and `TOKEN_AUDIENCE` in `.env` match the Auth0 API Identifier **EXACTLY**.
|
|
304
343
|
|
|
305
344
|
```bash
|
|
306
345
|
# .env
|
|
307
|
-
|
|
346
|
+
RESOURCE_URI=https://mcplocal
|
|
347
|
+
TOKEN_AUDIENCE=https://mcplocal
|
|
308
348
|
|
|
309
|
-
# Token
|
|
349
|
+
# Token will have:
|
|
310
350
|
{
|
|
311
|
-
"aud": "https://
|
|
351
|
+
"aud": "https://mcplocal" # ← Must match exactly
|
|
312
352
|
}
|
|
313
353
|
```
|
|
314
354
|
|
|
355
|
+
### "Application doesn't show in API's Machine to Machine tab"
|
|
356
|
+
|
|
357
|
+
**Fix:** Application type must be "Regular Web Application", not "Single Page Application". Delete and recreate the application with correct type.
|
|
358
|
+
|
|
315
359
|
### "Missing required environment variables"
|
|
316
360
|
|
|
317
361
|
**Fix:** Copy `.env.example` to `.env` and configure all required variables.
|
|
@@ -6,10 +6,12 @@
|
|
|
6
6
|
"scripts": {
|
|
7
7
|
"dev": "nitrostack dev",
|
|
8
8
|
"build": "nitrostack build",
|
|
9
|
-
"start": "nitrostack start",
|
|
9
|
+
"start": "npm run build && nitrostack start",
|
|
10
|
+
"start:prod": "nitrostack start",
|
|
10
11
|
"widget": "npm --prefix src/widgets"
|
|
11
12
|
},
|
|
12
13
|
"dependencies": {
|
|
14
|
+
"dotenv": "^16.4.5",
|
|
13
15
|
"nitrostack": "^1",
|
|
14
16
|
"zod": "^3.23.8"
|
|
15
17
|
},
|
|
@@ -1,7 +1,11 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
+
import { config } from 'dotenv';
|
|
2
3
|
import { McpApplicationFactory } from 'nitrostack';
|
|
3
4
|
import { AppModule } from './app.module.js';
|
|
4
5
|
|
|
6
|
+
// Load environment variables from .env file
|
|
7
|
+
config();
|
|
8
|
+
|
|
5
9
|
/**
|
|
6
10
|
* OAuth 2.1 MCP Server
|
|
7
11
|
*
|
|
@@ -56,33 +60,8 @@ async function bootstrap() {
|
|
|
56
60
|
console.error(` Scopes: read, write, admin`);
|
|
57
61
|
console.error(` Audience: ${process.env.TOKEN_AUDIENCE || process.env.RESOURCE_URI}\n`);
|
|
58
62
|
|
|
59
|
-
//
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
if (isDevelopment) {
|
|
63
|
-
// Development: STDIO only (for local testing)
|
|
64
|
-
await app.start('stdio');
|
|
65
|
-
console.error('🚀 Server running in DEVELOPMENT mode (STDIO only)');
|
|
66
|
-
console.error(' Use MCP Inspector for testing OAuth flows\n');
|
|
67
|
-
} else {
|
|
68
|
-
// Production: Dual transport (STDIO + HTTP SSE)
|
|
69
|
-
// OAuth servers typically need HTTP transport for token validation
|
|
70
|
-
const port = parseInt(process.env.PORT || '3002');
|
|
71
|
-
const host = process.env.HOST || '0.0.0.0';
|
|
72
|
-
|
|
73
|
-
await app.start('dual', {
|
|
74
|
-
port,
|
|
75
|
-
host,
|
|
76
|
-
endpoint: '/mcp',
|
|
77
|
-
enableCors: process.env.ENABLE_CORS !== 'false', // Enable by default, disable with ENABLE_CORS=false
|
|
78
|
-
});
|
|
79
|
-
|
|
80
|
-
console.error('🚀 Server running in PRODUCTION mode (DUAL)');
|
|
81
|
-
console.error(` 📡 STDIO: Ready for direct connections`);
|
|
82
|
-
console.error(` 🌐 HTTP SSE: http://${host}:${port}/mcp`);
|
|
83
|
-
console.error(' Open NitroStack Studio to test OAuth 2.1 flow');
|
|
84
|
-
console.error(' Configure OAuth in Studio → Auth → OAuth 2.1 tab\n');
|
|
85
|
-
}
|
|
63
|
+
// Start the server
|
|
64
|
+
await app.start();
|
|
86
65
|
|
|
87
66
|
} catch (error) {
|
|
88
67
|
console.error('❌ Failed to start server:', error);
|
|
@@ -9,39 +9,20 @@
|
|
|
9
9
|
* - Production (NODE_ENV=production): Dual transport (STDIO + HTTP SSE)
|
|
10
10
|
*/
|
|
11
11
|
|
|
12
|
+
import { config } from 'dotenv';
|
|
12
13
|
import { McpApplicationFactory } from 'nitrostack';
|
|
13
14
|
import { AppModule } from './app.module.js';
|
|
14
15
|
|
|
16
|
+
// Load environment variables from .env file
|
|
17
|
+
config();
|
|
18
|
+
|
|
15
19
|
/**
|
|
16
20
|
* Bootstrap the application
|
|
17
21
|
*/
|
|
18
22
|
async function bootstrap() {
|
|
19
|
-
// Create the MCP server
|
|
23
|
+
// Create and start the MCP server
|
|
20
24
|
const server = await McpApplicationFactory.create(AppModule);
|
|
21
|
-
|
|
22
|
-
// Determine transport based on environment
|
|
23
|
-
const isDevelopment = process.env.NODE_ENV === 'development' || !process.env.NODE_ENV;
|
|
24
|
-
|
|
25
|
-
if (isDevelopment) {
|
|
26
|
-
// Development: STDIO only (for local testing with MCP Inspector, Claude Desktop)
|
|
27
|
-
await server.start('stdio');
|
|
28
|
-
console.error('🚀 Server running in DEVELOPMENT mode (STDIO only)');
|
|
29
|
-
} else {
|
|
30
|
-
// Production: Dual transport (STDIO + HTTP SSE)
|
|
31
|
-
const port = parseInt(process.env.PORT || '3000');
|
|
32
|
-
const host = process.env.HOST || 'localhost';
|
|
33
|
-
|
|
34
|
-
await server.start('dual', {
|
|
35
|
-
port,
|
|
36
|
-
host,
|
|
37
|
-
endpoint: '/mcp',
|
|
38
|
-
enableCors: process.env.ENABLE_CORS !== 'false', // Enable by default, disable with ENABLE_CORS=false
|
|
39
|
-
});
|
|
40
|
-
|
|
41
|
-
console.error('🚀 Server running in PRODUCTION mode (DUAL)');
|
|
42
|
-
console.error(` 📡 STDIO: Ready for direct connections`);
|
|
43
|
-
console.error(` 🌐 HTTP SSE: http://${host}:${port}/mcp`);
|
|
44
|
-
}
|
|
25
|
+
await server.start();
|
|
45
26
|
}
|
|
46
27
|
|
|
47
28
|
// Start the application
|