FlowiseAI/Flowise · error · InternalFlowiseError

Error: chatflowsController.checkIfChatflowHasChanged -…

Error message

Error: chatflowsController.checkIfChatflowHasChanged - active workspace ID not found!

What it means

Thrown by checkIfChatflowHasChanged when req.user?.activeWorkspaceId is falsy. Flowise is multi-tenant by workspace; every chatflow operation must be scoped to the caller's active workspace. The guard returns NOT_FOUND (404). The optional chaining means it fires both when the auth middleware never attached req.user and when the user genuinely has no active workspace set.

Solutions

  1. Confirm the route is behind the auth middleware that sets req.user.activeWorkspaceId (e.g. the Flowise workspace auth guard) and that the client sends a valid session cookie / API key.
  2. If the user legitimately lacks a workspace, set/switch their active workspace before retrying (Flowise workspace selection flow).
  3. For automated tests, inject req.user = { activeWorkspaceId: '<wsid>' } on the supertest request.

Example fix

// before - calling the endpoint with no auth context
await request(app).get(`/api/v1/chatflows/${id}/chatflow-changed/${ts}`)
// after - authenticate so req.user.activeWorkspaceId is set
await request(app)
  .get(`/api/v1/chatflows/${id}/chatflow-changed/${ts}`)
  .set('Cookie', sessionCookie)
Defensive patterns

Strategy: validation

Validate before calling

function assertWorkspace(req: { user?: { activeWorkspaceId?: string } }): string {
  const ws = req.user?.activeWorkspaceId
  if (!ws) throw new Error('no active workspace - authenticate or select a workspace')
  return ws
}

Type guard

const hasActiveWorkspace = (u: unknown): u is { activeWorkspaceId: string } =>
  typeof u === 'object' && u !== null && typeof (u as any).activeWorkspaceId === 'string' && !!(u as any).activeWorkspaceId

Try / catch

try { await api.checkIfChanged(id, ts) }
catch (e) {
  if (e.statusCode === 404 && /workspace/i.test(e.message)) { await reAuth(); await api.checkIfChanged(id, ts) }
}

Prevention

When it happens

Trigger: The request reaches the controller without authentication middleware populating req.user.activeWorkspaceId, or the authenticated user has no activeWorkspaceId in their session/JWT, or the workspace was deleted while the session stayed valid.

Common situations: Auth middleware misordering (the route is public or the guard runs before auth), an expired/partial JWT missing the activeWorkspaceId claim, a freshly created user who has not been assigned an active workspace, or a test harness that calls the controller with a stubbed req that omits req.user.

Related errors


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

Appendix: source

Thrown at packages/server/src/controllers/chatflows/index.ts:290

}

const checkIfChatflowHasChanged = async (req: Request, res: Response, next: NextFunction) => {
    try {
        if (typeof req.params === 'undefined' || !req.params.id) {
            throw new InternalFlowiseError(
                StatusCodes.PRECONDITION_FAILED,
                `Error: chatflowsController.checkIfChatflowHasChanged - id not provided!`
            )
        }
        if (!req.params.lastUpdatedDateTime) {
            throw new InternalFlowiseError(
                StatusCodes.PRECONDITION_FAILED,
                `Error: chatflowsController.checkIfChatflowHasChanged - lastUpdatedDateTime not provided!`
            )
        }
        const workspaceId = req.user?.activeWorkspaceId
        if (!workspaceId) {
            throw new InternalFlowiseError(
                StatusCodes.NOT_FOUND,
                'Error: chatflowsController.checkIfChatflowHasChanged - active workspace ID not found!'
            )
        }
        const apiResponse = await chatflowsService.checkIfChatflowHasChanged(req.params.id, req.params.lastUpdatedDateTime, workspaceId)
        return res.json(apiResponse)
    } catch (error) {
        next(error)
    }
}

const setWebhookSecret = async (req: Request, res: Response, next: NextFunction) => {
    try {
        if (!req.params.id) {
            throw new InternalFlowiseError(
                StatusCodes.PRECONDITION_FAILED,
                `Error: chatflowsController.setWebhookSecret - id not provided!`
            )

View on GitHub (pinned to abe4a8601a)