{"record":{"id":"5925a5f455a96ab6","repo":"phacility/phabricator","slug":"storage-patch-s-specifies-attribute-s-but-t","errorCode":null,"errorMessage":"Storage patch \"%s\" specifies attribute \"%s\", but this attribute is unknown.","messagePattern":"Storage patch \"(.+?)\" specifies attribute \"(.+?)\", but this attribute is unknown\\.","errorType":"exception","errorClass":"Exception","httpStatus":null,"severity":"error","filePath":"src/infrastructure/storage/patch/PhabricatorSQLPatchList.php","lineNumber":325,"sourceCode":"                    $phase_name,\n                    implode(', ', $phase_list)));\n              }\n\n              if (isset($attributes['phase'])) {\n                throw new Exception(\n                  pht(\n                    'Storage patch \"%s\" specifies a \"@phase\" value (\"%s\"), '.\n                    'but it already has a specified phase (\"%s\"). Patches '.\n                    'may not specify multiple phases.',\n                    $patch_name,\n                    $phase_name,\n                    $attributes['phase']));\n              }\n\n              $attributes[$attr_key] = $phase_name;\n              break;\n            default:\n              throw new Exception(\n                pht(\n                  'Storage patch \"%s\" specifies attribute \"%s\", but this '.\n                  'attribute is unknown.',\n                  $patch_name,\n                  $attr_key));\n          }\n        }\n        continue;\n      }\n\n      // If this is anything else, we're all done. Attributes must be marked\n      // in the header of the file.\n      break;\n    }\n\n\n    return $attributes;\n  }","sourceCodeStart":307,"sourceCodeEnd":343,"githubUrl":"https://github.com/phacility/phabricator/blob/5720a38cfe95b00ca4be5016dd0d2f3195f4fa04/src/infrastructure/storage/patch/PhabricatorSQLPatchList.php#L307-L343","documentation":"Inside a PHP patch's header comment block, any line of the form '// @word ...' is parsed as a structured attribute, and the only supported attribute is '@phase'. Anything else ('@group', '@author', '@note', '@TODO') reaches the switch's default case and is rejected, because unknown attributes would silently affect nothing.","triggerScenarios":"The leading '//' comment block of a .php patch starts a line with '@' followed by a word — e.g. '// @group storage' or '// @author someone' — while still inside the header (before any non-comment line). The '@x' shape is reserved; the parser treats it as an attribute, not a comment.","commonSituations":"Copying phpdoc-style '@author'/'@group' tags from regular source files into a migration header; annotating patch files the way old Phabricator source was annotated; adding '// @TODO' notes at the top of the file.","solutions":["Remove the '@' sigil from the offending line (write '// Author: ...' or '// TODO ...' instead of '// @author ...').","Keep structured '@' attributes out of the header block entirely unless it is a valid '// @phase value' line.","Re-run 'bin/storage status' to confirm the file parses."],"exampleFix":"// before (top of patch file)\n<?php\n// @author adrin\n// @phase worker\n\n// after\n<?php\n// Author: adrin\n// @phase worker","handlingStrategy":"validation","validationCode":"// Only '@phase' is a legal header attribute; reject any other '@word' line:\nforeach (file($patch_path) as $line) {\n  if (!preg_match('(^^\\s*//)', $line)) { break; } // header block ended\n  if (preg_match('^\\s*//\\s*@(\\S+)^', $line, $m) && $m[1] !== 'phase') {\n    throw new Exception(\"Unknown header attribute '@{$m[1]}' in {$patch_path}\");\n  }\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Keep phpdoc-style tags ('@author', '@group', '@param') out of patch file headers; write them without the '@' sigil.","Put TODO/authorship notes after code starts or below the header block, not in it."],"tags":["phabricator","database-migration","file-header","attributes"],"backgroundTag":"database-migration-validation","analyzedSha":"5720a38cfe95b00ca4be5016dd0d2f3195f4fa04","analyzedAt":"2026-08-21T05:07:25.672Z","schemaVersion":2},"datasetVersion":"2026-08-21T11:28:35.574Z"}