{"record":{"id":"2d2c854f6193759a","repo":"phacility/phabricator","slug":"type-specification-s-duplicates-type-specificat","errorCode":null,"errorMessage":"Type specification \"%s\" duplicates type specification \"%s\". Specify each type only once.","messagePattern":"Type specification \"(.+?)\" duplicates type specification \"(.+?)\"\\. Specify each type only once\\.","errorType":"console","errorClass":"PhutilArgumentUsageException","httpStatus":null,"severity":"warning","filePath":"src/applications/search/management/PhabricatorSearchManagementIndexWorkflow.php","lineNumber":330,"sourceCode":"    }\n\n    return mpull($objects, 'getPHID');\n  }\n\n  private function getIndexableObjectsByTypes(array $types) {\n    $objects = id(new PhutilClassMapQuery())\n      ->setAncestorClass('PhabricatorIndexableInterface')\n      ->execute();\n\n    $type_map = array();\n    $normal_map = array();\n    foreach ($types as $type) {\n      $normalized_type = phutil_utf8_strtolower($type);\n      $type_map[$type] = $normalized_type;\n\n      if (isset($normal_map[$normalized_type])) {\n        $old_type = $normal_map[$normalized_type];\n        throw new PhutilArgumentUsageException(\n          pht(\n            'Type specification \"%s\" duplicates type specification \"%s\". '.\n            'Specify each type only once.',\n            $type,\n            $old_type));\n      }\n\n      $normal_map[$normalized_type] = $type;\n    }\n\n    $object_matches = array();\n\n    $matches_map = array();\n    $exact_map = array();\n    foreach ($objects as $object) {\n      $object_class = get_class($object);\n\n      if (!$types) {","sourceCodeStart":312,"sourceCodeEnd":348,"githubUrl":"https://github.com/phacility/phabricator/blob/5720a38cfe95b00ca4be5016dd0d2f3195f4fa04/src/applications/search/management/PhabricatorSearchManagementIndexWorkflow.php#L312-L348","documentation":"In `bin/search index --type`, each value is normalized with phutil_utf8_strtolower and tracked in a map keyed by the normalized name. When a later --type value lowercases to the same key as an earlier one, this usage exception is thrown listing the duplicate pair (e.g. \"TASK\" duplicates \"task\"). Case differences do not create distinct types.","triggerScenarios":"`bin/search index --type task --type TASK`, `--type ManiphestTask --type maniphesttask`, or any repeated --type whose values differ only by case.","commonSituations":"Generated command lines that append flags in a loop without normalizing; merging flag lists from multiple sources; copy-paste duplication of examples with different casing.","solutions":["Remove the duplicate so each type appears once","In scripts, normalize the type list first: lowercase + array_unique before building the command","Use the canonical class name or documented short forms (\"task\", \"commit\", \"revision\") consistently"],"exampleFix":"# before\nbin/search index --type task --type TASK\n\n# after\nbin/search index --type task","handlingStrategy":"validation","validationCode":"// Normalize and dedupe before building the command line\n$types = array_values(array_unique(array_map('strtolower', $rawTypes)));","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Dedupe and lowercase type lists in scripts","Build --type arguments programmatically, never by string concatenation","Adopt one canonical casing for every type in tooling"],"tags":["cli","bin-search","usage-error","duplicate-argument"],"backgroundTag":"duplicate-cli-option","analyzedSha":"5720a38cfe95b00ca4be5016dd0d2f3195f4fa04","analyzedAt":"2026-08-21T05:07:25.672Z","schemaVersion":2},"datasetVersion":"2026-08-21T11:28:35.574Z"}