FlowiseAI/Flowise · error · Error

MCP server "${serverRecord.name}" is not authorized. Please

Error message

MCP server "${serverRecord.name}" is not authorized. Please authorize it in the Tools page first.

What it means

Thrown by CustomMcpServerTool.getTools when serverRecord.status !== 'AUTHORIZED'. Managed MCP servers go through an explicit authorization step on the Tools page (e.g. completing OAuth, validating headers, confirming the SSE handshake) before they are usable. Until status flips to AUTHORIZED, the tool refuses to load them — this prevents half-configured or revoked servers from breaking the agent's tool set. The server name is included to identify it in the UI.

Source

Thrown at packages/components/nodes/tools/MCP/CustomMcpServerTool/CustomMcpServerTool.ts:142

        const appDataSource = options.appDataSource as DataSource
        const databaseEntities = options.databaseEntities as IDatabaseEntity
        if (!appDataSource || !databaseEntities?.['CustomMcpServer']) {
            throw new Error('Database not available')
        }

        const workspaceId =
            (options.workspaceId as string | undefined) ??
            ((options.searchOptions as ICommonObject | undefined)?.workspaceId as string | undefined)
        if (!workspaceId) {
            throw new Error('Workspace context is required to load MCP server')
        }

        const serverRecord = await appDataSource.getRepository(databaseEntities['CustomMcpServer']).findOneBy({ id: serverId, workspaceId })
        if (!serverRecord) {
            throw new Error(`MCP server ${serverId} not found`)
        }
        if (serverRecord.status !== 'AUTHORIZED') {
            throw new Error(`MCP server "${serverRecord.name}" is not authorized. Please authorize it in the Tools page first.`)
        }

        // Build headers from encrypted authConfig — only when authType explicitly requires them
        let headers: Record<string, string> = {}
        if (serverRecord.authType === 'CUSTOM_HEADERS' && serverRecord.authConfig) {
            try {
                const decrypted = await decryptCredentialData(serverRecord.authConfig)
                if (decrypted?.headers && typeof decrypted.headers === 'object') {
                    headers = decrypted.headers as Record<string, string>
                }
            } catch {
                // authConfig decryption failed — proceed without headers
            }
        }

        const serverParams: any = {
            url: serverRecord.serverUrl,
            ...(Object.keys(headers).length > 0 ? { headers } : {})

View on GitHub (pinned to abe4a8601a)

Solutions

  1. Go to the Tools page, find the named server, and click Authorize; complete any OAuth/credential prompt.
  2. If authorization repeatedly fails, re-enter the authConfig (headers/client secret) and re-authorize.
  3. Confirm the server's serverUrl is reachable and the MCP endpoint responds.
  4. After a provider-side revocation, re-authorize to mint a fresh token.

Example fix

// before — status 'PENDING'
serverRecord.status === 'PENDING'  // throws
// after — authorize on Tools page
serverRecord.status === 'AUTHORIZED'  // passes
Defensive patterns

Strategy: validation

Validate before calling

async function assertAuthorized(ds: DataSource, entity: any, serverId: string, workspaceId: string) {
  const rec = await ds.getRepository(entity).findOneBy({ id: serverId, workspaceId })
  if (!rec) throw new Error('server not found')
  if (rec.status !== 'AUTHORIZED') throw new Error(`server '${rec.name}' status is ${rec.status} — authorize on the Tools page`)
  return rec
}

Type guard

function isAuthorized(rec: { status?: string } | null): rec is { status: 'AUTHORIZED' } {
  return !!rec && rec.status === 'AUTHORIZED'
}

Try / catch

try {
  return await tool.getTools(nodeData, options)
} catch (e) {
  if (e instanceof Error && /not authorized/i.test(e.message)) {
    return promptUserToAuthorize(e.message) // surface the Tools-page action
  }
  throw e
}

Prevention

When it happens

Trigger: A newly created server that was never authorized; an authorization that expired or was revoked (token refresh failure, user disconnected OAuth); a server in PENDING/UNAUTHORIZED/DISABLED state selected on a node.

Common situations: User creates a server entry but doesn't finish the OAuth flow; the upstream MCP provider revoked the token; an admin disabled the server; the authConfig decryption silently left the server unusable.

Related errors


AI-assisted analysis of FlowiseAI/Flowise@abe4a8601a (2026-08-12). Data as JSON: /api/errors/bfce251963e815b2. Report an issue: GitHub.