{"record":{"id":"62c4057cbd792ad3","repo":"nextcloud/server","slug":"principal-not-found-62c405","errorCode":null,"errorMessage":"Principal not found","messagePattern":"Principal not found","errorType":"exception","errorClass":"Sabre\\DAV\\Exception","httpStatus":500,"severity":"error","filePath":"apps/dav/lib/DAV/SystemPrincipalBackend.php","lineNumber":142,"sourceCode":"\t * @return array\n\t */\n\t#[\\Override]\n\tpublic function searchPrincipals($prefixPath, array $searchProperties, $test = 'allof') {\n\t\treturn [];\n\t}\n\n\t/**\n\t * Returns the list of members for a group-principal\n\t *\n\t * @param string $principal\n\t * @return array\n\t */\n\t#[\\Override]\n\tpublic function getGroupMemberSet($principal) {\n\t\t// TODO: for now the group principal has only one member, the user itself\n\t\t$principal = $this->getPrincipalByPath($principal);\n\t\tif (!$principal) {\n\t\t\tthrow new \\Sabre\\DAV\\Exception('Principal not found');\n\t\t}\n\n\t\treturn [$principal['uri']];\n\t}\n\n\t/**\n\t * Returns the list of groups a principal is a member of\n\t *\n\t * @param string $principal\n\t * @return array\n\t */\n\t#[\\Override]\n\tpublic function getGroupMembership($principal) {\n\t\t[$prefix, ] = \\Sabre\\Uri\\split($principal);\n\n\t\tif ($prefix === 'principals/system') {\n\t\t\t$principal = $this->getPrincipalByPath($principal);\n\t\t\tif (!$principal) {","sourceCodeStart":124,"sourceCodeEnd":160,"githubUrl":"https://github.com/nextcloud/server/blob/ecdeb153ffdf227235c9a7e2d13dbe0f9c817bc3/apps/dav/lib/DAV/SystemPrincipalBackend.php#L124-L160","documentation":"SystemPrincipalBackend::getGroupMemberSet() (apps/dav/lib/DAV/SystemPrincipalBackend.php:142) throws \\Sabre\\DAV\\Exception('Principal not found') when getPrincipalByPath() returns null for the requested system principal. System principals (like the system calendar or scheduling inboxes) are a fixed, enumerated set; asking for the member set of any path not exactly matching one of those known principals fails here.","triggerScenarios":"A DAV client or Sabre internal ACL check calling getGroupMemberSet() for a malformed or nonexistent system principal path, e.g. principals/system/typo or a principals/groups/... URI routed to this backend after a path/prefix change.","commonSituations":"Client caches holding old principal URIs across server upgrades; typos in constructed URLs; refactoring that changed principal prefixes; tools enumerating 'principals/system' children with wrong casing.","solutions":["Re-discover valid principal URIs with a PROPFIND on /remote.php/dav/principals/system/ (depth 1) and use exactly those.","Clear stale cached principal paths on the client and re-run discovery.","Verify the prefix: system principals live under principals/system/, not principals/users/.","Confirm the requested feature actually exists in this server version (some system principals were added/renamed across versions)."],"exampleFix":null,"handlingStrategy":"validation","validationCode":"// resolve via discovery instead of assuming a URI exists\n$principals = $backend->getPrincipalsByPrefix('principals/system');\n$valid = array_column($principals, 'uri');\nif (!in_array($principalUri, $valid, true)) {\n    $this->skip('Unknown system principal: ' . $principalUri);\n    return [];\n}","typeGuard":"function isKnownSystemPrincipal(array $validUris, string $uri): bool {\n    return in_array(rtrim($uri, '/'), $validUris, true);\n}","tryCatchPattern":"try {\n    $members = $backend->getGroupMemberSet($principalUri);\n} catch (\\Sabre\\DAV\\Exception $e) {\n    if (str_contains($e->getMessage(), 'Principal not found')) {\n        $members = []; // skip stale/malformed system principal URIs\n    } else {\n        throw $e;\n    }\n}","preventionTips":["Discover principal URIs with PROPFIND on the principals collection at runtime.","Drop hard-coded system principal URIs from client code and caches.","Use exact casing and no trailing slashes in principal paths."],"tags":["dav","principal","system-principal","not-found"],"backgroundTag":"principal-not-found","analyzedSha":"ecdeb153ffdf227235c9a7e2d13dbe0f9c817bc3","analyzedAt":"2026-08-17T01:36:13.386Z","schemaVersion":2},"datasetVersion":"2026-08-17T04:17:16.089Z"}