{"record":{"id":"8ddd8c0e2438fc41","repo":"Budibase/budibase","slug":"replacing-members-is-not-allowed","errorCode":null,"errorMessage":"Replacing members is not allowed","messagePattern":"Replacing members is not allowed","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"packages/worker/src/api/controllers/global/scim/groups.ts","lineNumber":136,"sourceCode":"          for (const u of value) {\n            usersToAdd.push(await scimUsers.find(u.value))\n          }\n          break\n        case \"remove\":\n        case \"Remove\":\n          for (const u of value) {\n            try {\n              usersToRemove.push(await scimUsers.find(u.value))\n            } catch (e: any) {\n              if (e.status !== 404) {\n                throw e\n              }\n            }\n          }\n          break\n        case \"replace\":\n        case \"Replace\":\n          throw new Error(\"Replacing members is not allowed\")\n        default:\n          utils.unreachable(op)\n      }\n    }\n\n    if (usersToAdd.length) {\n      await groups.addUsers(\n        id,\n        usersToAdd.map(u => u._id!)\n      )\n    }\n    if (usersToRemove.length) {\n      await groups.removeUsers(\n        id,\n        usersToRemove.map(u => u._id!)\n      )\n    }\n  }","sourceCodeStart":118,"sourceCodeEnd":154,"githubUrl":"https://github.com/Budibase/budibase/blob/a81a902e9a8fe55b467d106765f6638f12e35c49/packages/worker/src/api/controllers/global/scim/groups.ts#L118-L154","documentation":"SCIM group member updates support \"add\" and \"remove\" operations only. When a PATCH operation has op \"replace\" (or \"Replace\") targeting members, update throws this error because replacing the entire member list is not a supported mutation in this implementation. The switch then falls through to utils.unreachable for unknown ops.","triggerScenarios":"Sending a SCIM PATCH /Groups request whose Operations array contains {\"op\": \"replace\", \"path\": \"members\", ...} — typically from an SCIM client (Okta, Azure AD/Entra) configured to sync full group membership instead of incremental adds/removes.","commonSituations":"An identity provider SCIM integration set to \"sync all members\" mode sends replace ops; a client application builds PATCH payloads with replace instead of add/remove; SCIM spec-conformance tooling tests replace semantics.","solutions":["Reconfigure the identity provider SCIM app to send incremental add/remove member operations instead of full-membership replace","Translate replace operations on the client into explicit add and remove operations per member","If you control the server and need replace support, implement it by diffing current vs desired members and applying add/remove","Check the IdP's SCIM connector settings (e.g. Okta 'Group Member' push mode) for a delta-sync option"],"exampleFix":"// before (client PATCH payload)\n{ \"Operations\": [{ \"op\": \"replace\", \"path\": \"members\", \"value\": [...] }] }\n// after\n{ \"Operations\": [\n  { \"op\": \"add\", \"path\": \"members\", \"value\": [{ \"value\": \"userId1\" }] },\n  { \"op\": \"remove\", \"path\": \"members[value eq \\\"userId2\\\"]\" }\n] }","handlingStrategy":"validation","validationCode":"const ops = patchBody.Operations || []\nconst hasReplace = ops.some(o => String(o.op).toLowerCase() === \"replace\" &&\n  (!o.path || o.path.startsWith(\"members\")))\nif (hasReplace) throw new Error(\"Convert replace member ops to add/remove before sending\")","typeGuard":"function isMemberReplaceOp(op: { op: string; path?: string }): boolean {\n  return op.op.toLowerCase() === \"replace\" && (!op.path || op.path === \"members\")\n}","tryCatchPattern":"try {\n  await scim.patchGroup(groupId, body)\n} catch (e) {\n  if (e.message.includes(\"Replacing members\")) {\n    // recompute diff and resend as add/remove operations\n  }\n}","preventionTips":["Configure your IdP SCIM connector for delta/incremental group member sync","Always translate desired membership to add/remove diffs client-side","Test SCIM payloads against the server's supported operations before enabling sync"],"tags":["scim","api","validation","groups"],"backgroundTag":"scim-unsupported-operation","analyzedSha":"a81a902e9a8fe55b467d106765f6638f12e35c49","analyzedAt":"2026-08-29T01:03:10.972Z","schemaVersion":2},"datasetVersion":"2026-08-29T02:17:18.158Z"}