{"record":{"id":"7abb856691f91575","repo":"phacility/phabricator","slug":"unable-to-change-ownership-of-an-identity-file-to","errorCode":null,"errorMessage":"Unable to change ownership of an identity file to daemon user \"%s\". Run this command as %s or root.","messagePattern":"Unable to change ownership of an identity file to daemon user \"(.+?)\"\\. Run this command as (.+?) or root\\.","errorType":"console","errorClass":"PhutilArgumentUsageException","httpStatus":null,"severity":"error","filePath":"src/applications/almanac/management/AlmanacManagementRegisterWorkflow.php","lineNumber":96,"sourceCode":"    if (!Filesystem::pathExists($private_key_path)) {\n      throw new PhutilArgumentUsageException(\n        pht('No private key exists at path \"%s\"!', $private_key_path));\n    }\n\n    $raw_private_key = Filesystem::readFile($private_key_path);\n\n    $phd_user = PhabricatorEnv::getEnvConfig('phd.user');\n    if (!$phd_user) {\n      throw new PhutilArgumentUsageException(\n        pht(\n          'Config option \"phd.user\" is not set. You must set this option '.\n          'so the private key can be stored with the correct permissions.'));\n    }\n\n    $tmp = new TempFile();\n    list($err) = exec_manual('chown %s %s', $phd_user, $tmp);\n    if ($err) {\n      throw new PhutilArgumentUsageException(\n        pht(\n          'Unable to change ownership of an identity file to daemon user '.\n          '\"%s\". Run this command as %s or root.',\n          $phd_user,\n          $phd_user));\n    }\n\n    $stored_public_path = AlmanacKeys::getKeyPath('device.pub');\n    $stored_private_path = AlmanacKeys::getKeyPath('device.key');\n    $stored_device_path = AlmanacKeys::getKeyPath('device.id');\n\n    if (!$args->getArg('force')) {\n      if (Filesystem::pathExists($stored_public_path)) {\n        throw new PhutilArgumentUsageException(\n          pht(\n            'This host already has a registered public key (\"%s\"). '.\n            'Remove this key before registering the host, or use '.\n            '--force to overwrite it.',","sourceCodeStart":78,"sourceCodeEnd":114,"githubUrl":"https://github.com/phacility/phabricator/blob/5720a38cfe95b00ca4be5016dd0d2f3195f4fa04/src/applications/almanac/management/AlmanacManagementRegisterWorkflow.php#L78-L114","documentation":"Usage exception from `bin/almanac register`: exec_manual('chown <phd.user> <tmpfile>') returned a non-zero exit code, meaning the current user cannot change ownership of the identity temp file to the daemon user. The workflow then writes device.pub/device.key/device.id with daemon ownership, so it aborts and tells you to run as the daemon user or root.","triggerScenarios":"Running bin/almanac register as an ordinary admin shell user; running under sudo but with a phd.user whose name is misspelled so chown fails; containerized environments where chown is restricted by capability settings.","commonSituations":"Operators running register from their own account out of habit; hardened/immutable images without CAP_CHOWN; the phd.user account renamed after config was written.","solutions":["Rerun as root: sudo bin/almanac register ... (or as the phd.user account itself).","Confirm phd.user spells an existing local account; fix with bin/config set phd.user <correct-user> if not.","In restricted containers, run registration in an init/entrypoint step that has CAP_CHOWN, or pre-place the key files with correct ownership and skip re-registration."],"exampleFix":"# before\n$ bin/almanac register --device web-001 --private-key ./device.key\nUsage Exception: Unable to change ownership of an identity file to daemon user \"phd-daemon\". ...\n\n# after\n$ sudo bin/almanac register --device web-001 --private-key ./device.key","handlingStrategy":"try-catch","validationCode":"// Guard: registration needs root or the phd user to chown identity files\n$u = posix_getpwuid(posix_geteuid());\n$phd_user = (string)PhabricatorEnv::getEnvConfig('phd.user');\nif ($u['name'] !== 'root' && $u['name'] !== $phd_user) {\n  throw new RuntimeException('Run register as root or '.$phd_user);\n}","typeGuard":null,"tryCatchPattern":"# shell wrapper\ncase \"$(id -un)\" in\n  root|$PHD_USER) exec bin/almanac register \"$@\" ;;\n  *) echo \"re-run as root or $PHD_USER\" >&2; exit 1 ;;\nesac","preventionTips":["Standardize on `sudo bin/almanac register` in all runbooks.","Verify phd.user exists on the host before registration (getent passwd).","In containers, ensure the entrypoint holds CAP_CHOWN or pre-stage key files."],"tags":["phabricator","almanac","permissions","cli","register","unix"],"backgroundTag":"chown-permission-denied","analyzedSha":"5720a38cfe95b00ca4be5016dd0d2f3195f4fa04","analyzedAt":"2026-08-21T05:07:25.672Z","schemaVersion":2},"datasetVersion":"2026-08-21T11:28:35.574Z"}