{"record":{"id":"2074ecd1b7c8af8f","repo":"phacility/phabricator","slug":"expected-a-query-key-or-a-set-of-query-constraints","errorCode":null,"errorMessage":"Expected a query key or a set of query constraints.","messagePattern":"Expected a query key or a set of query constraints\\.","errorType":"validation","errorClass":"Exception","httpStatus":null,"severity":"error","filePath":"src/applications/transactions/bulk/PhabricatorBulkEngine.php","lineNumber":174,"sourceCode":"    if ($query_key !== null && strlen($query_key)) {\n      if ($search_engine->isBuiltinQuery($query_key)) {\n        $saved = $search_engine->buildSavedQueryFromBuiltin($query_key);\n      } else {\n        $saved = id(new PhabricatorSavedQueryQuery())\n          ->setViewer($viewer)\n          ->withQueryKeys(array($query_key))\n          ->executeOne();\n        if (!$saved) {\n          return new Aphront404Response();\n        }\n      }\n    } else {\n      // TODO: For now, since we don't deal gracefully with queries which\n      // match a huge result set, just bail if we don't have any query\n      // parameters instead of querying for a trillion tasks and timing out.\n      $request_data = $request->getPassthroughRequestData();\n      if (!$request_data) {\n        throw new Exception(\n          pht(\n            'Expected a query key or a set of query constraints.'));\n      }\n\n      $saved = $search_engine->buildSavedQueryFromRequest($request);\n      $search_engine->saveQuery($saved);\n    }\n\n    $object_query = $search_engine->buildQueryFromSavedQuery($saved)\n      ->setViewer($viewer);\n    $object_list = $object_query->execute();\n    $object_list = mpull($object_list, null, 'getPHID');\n\n    // If the user has submitted the bulk edit form, select only the objects\n    // they checked.\n    if ($request->getBool('bulkEngine')) {\n      $target_phids = $request->getArr('bulkTargetPHIDs');\n","sourceCodeStart":156,"sourceCodeEnd":192,"githubUrl":"https://github.com/phacility/phabricator/blob/5720a38cfe95b00ca4be5016dd0d2f3195f4fa04/src/applications/transactions/bulk/PhabricatorBulkEngine.php#L156-L192","documentation":"PhabricatorBulkEngine's bulk-edit flow needs either a saved query key or passthrough request data carrying query constraints. With neither, it refuses to run rather than execute an unconstrained query that could match every object in the install and time out. This is a deliberate guard inherited from a TODO about huge result sets.","triggerScenarios":"A bare GET to the bulk edit endpoint with no query key in the URI and no POSTed search parameters; custom controllers linking into the bulk flow without forwarding either.","commonSituations":"Bookmarked or hand-built bulk-edit URLs missing the query parameter; integrations that open the bulk editor without the user running a search first.","solutions":["Enter bulk edit from a saved/engine search results page so the query key is carried in the URI","If building a custom flow, POST the search constraints as passthrough request data or pass a saved query key explicitly","Verify the search engine actually parsed and stored the constraints you intended"],"exampleFix":"// before: linking straight to the bulk flow\nreturn id(new AphrontRedirectResponse())->setURI('/bulk/edit/');\n\n// after: carry a saved query key from the search that produced the set\n$uri = '/bulk/edit/?queryKey='.$saved_query->getQueryKey();\nreturn id(new AphrontRedirectResponse())->setURI($uri);","handlingStrategy":"validation","validationCode":"// Dispatch to the bulk flow only when a query is actually specified.\n$query_key = $request->getStr('queryKey');\n$request_data = $request->getPassthroughRequestData();\nif (!strlen($query_key) && !$request_data) {\n  // redirect the user to the search UI to pick a query first\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Always link into bulk edit from a search results page carrying the query key","Forward query constraints as passthrough data when building custom entry points"],"tags":["bulk-edit","query","search","workflow"],"backgroundTag":"missing-query-parameters","analyzedSha":"5720a38cfe95b00ca4be5016dd0d2f3195f4fa04","analyzedAt":"2026-08-21T05:07:25.672Z","schemaVersion":2},"datasetVersion":"2026-08-21T11:28:35.574Z"}