{"record":{"id":"f9df95dce44896e7","repo":"Budibase/budibase","slug":"user-id-or-revision-missing","errorCode":null,"errorMessage":"User ID or revision missing","messagePattern":"User ID or revision missing","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/builder/src/settings/pages/people/users/workspaceInviteUtils.ts","lineNumber":284,"sourceCode":"          rev = saved?._rev || rev\n        }\n        if (!user._id) {\n          throw new Error(\"User ID missing\")\n        }\n        if (groupIdsToAdd.length) {\n          await Promise.all(\n            groupIdsToAdd.map(groupId => groupStore.addUser(groupId, user._id!))\n          )\n        }\n        if (!role) {\n          return email\n        }\n        if (groupIdsToAdd.length || !rev) {\n          const loaded = await users.get(user._id)\n          rev = loaded?._rev\n        }\n        if (!user._id || !rev) {\n          throw new Error(\"User ID or revision missing\")\n        }\n        await users.addUserToWorkspace(user._id, role, rev)\n        return email\n      }\n    )\n  )\n\n  const assignedUsers = assignmentResults\n    .filter(\n      (result): result is PromiseFulfilledResult<string> =>\n        result.status === \"fulfilled\"\n    )\n    .map(result => result.value)\n  const addedToWorkspaceEmails = [...groupManagedUsers, ...assignedUsers]\n\n  return {\n    usersToInvite,\n    addedToWorkspaceEmails,","sourceCodeStart":266,"sourceCodeEnd":302,"githubUrl":"https://github.com/Budibase/budibase/blob/a81a902e9a8fe55b467d106765f6638f12e35c49/packages/builder/src/settings/pages/people/users/workspaceInviteUtils.ts#L266-L302","documentation":"In assignExistingUsersToWorkspace, after resolving groups the code needs both user._id and a current _rev to call users.addUserToWorkspace. If either is missing (the user vanished, or the fetched document has no revision) it throws 'User ID or revision missing'. _rev is required for optimistic-concurrency document updates.","triggerScenarios":"user._id exists but the rev lookup failed: groupIdsToAdd.length > 0 or rev was falsy, so users.get(user._id) was called and returned undefined or a doc without _rev — e.g. the user was deleted concurrently or the get API returned an error object.","commonSituations":"Concurrent deletion of the user by another admin; the earlier users.save call returned a response without _rev; permission issues preventing the user fetch; stale user objects after another tab saved changes.","solutions":["Re-fetch the user before assignment to get a fresh _id/_rev and retry.","Verify the user still exists and the current user has permission to read it.","Check the users.get/users.save responses actually include _rev and surface API errors instead of continuing with undefined."],"exampleFix":"// before\nif (!user._id || !rev) { throw new Error(\"User ID or revision missing\") }\n// after\nconst fresh = await users.get(user._id)\nif (!fresh?._id || !fresh?._rev) { return null } // skip missing/deleted users instead of failing the whole batch","handlingStrategy":"try-catch","validationCode":"const withIds = users.filter(u => !!u._id)\nconst revs = await Promise.all(withIds.map(u => users.get(u._id!).then(l => l?._rev)))\nconst ready = withIds.filter((u, i) => !!revs[i])","typeGuard":"const canAssign = (u: Partial<User>, rev?: string): u is User & { _id: string } =>\n  typeof u._id === \"string\" && typeof rev === \"string\" && rev.length > 0","tryCatchPattern":"try {\n  await users.addUserToWorkspace(user._id, role, rev)\n} catch (e) {\n  if (e.message === \"User ID or revision missing\") {\n    console.warn(`Skipping user ${user.email}: deleted or unreadable`)\n    return null\n  }\n  throw e\n}","preventionTips":["Re-fetch the user immediately before workspace assignment to get a fresh _rev.","Treat missing _rev as 'user deleted concurrently' and skip rather than fail the batch.","Check users.get responses for errors/undefined before proceeding."],"tags":["users","workspace","revision","builder"],"backgroundTag":"missing-document-rev","analyzedSha":"a81a902e9a8fe55b467d106765f6638f12e35c49","analyzedAt":"2026-08-29T01:03:10.972Z","schemaVersion":2},"datasetVersion":"2026-08-29T02:17:18.158Z"}