phacility/phabricator · error · Exception
Buildkite did not return a "%s"!
Error message
Buildkite did not return a "%s"!
What it means
After POSTing to Buildkite's create-build endpoint and receiving a non-error status, the step decodes the JSON response and requires a web_url key, which becomes the URI artifact linking to the created Buildkite build. If the decoded payload lacks web_url (API behavior change, or an unexpected 2xx payload), the step throws and the build fails. The full HTTP response is logged to the build log first, so the payload can be inspected.
Source
Thrown at src/applications/harbormaster/step/HarbormasterBuildkiteBuildStepImplementation.php:175
$this->resolveFutures(
$build,
$build_target,
array($future));
$this->logHTTPResponse($build, $build_target, $future, pht('Buildkite'));
list($status, $body) = $future->resolve();
if ($status->isError()) {
throw new HarbormasterBuildFailureException();
}
$response = phutil_json_decode($body);
$uri_key = 'web_url';
$build_uri = idx($response, $uri_key);
if (!$build_uri) {
throw new Exception(
pht(
'Buildkite did not return a "%s"!',
$uri_key));
}
$target_phid = $build_target->getPHID();
$api_method = 'harbormaster.createartifact';
$api_params = array(
'buildTargetPHID' => $target_phid,
'artifactType' => HarbormasterURIArtifact::ARTIFACTCONST,
'artifactKey' => 'buildkite.uri',
'artifactData' => array(
'uri' => $build_uri,
'name' => pht('View in Buildkite'),
'ui.external' => true,
),
);View on GitHub (pinned to 5720a38cfe)
Solutions
- Inspect the logged HTTP response on the failed target to see exactly what Buildkite returned
- Retry the build once: transient API anomalies usually do not repeat
- If Buildkite permanently changed the field, update Phabricator/the step so $uri_key matches the new response shape
Defensive patterns
Strategy: retry
Try / catch
try {
// execute the Buildkite step
} catch (HarbormasterBuildFailureException $ex) {
// expected failure path (e.g. HTTP error status): mark target failed, no retry
} catch (Exception $ex) {
// unexpected payload (e.g. missing web_url): log and retry the build once
} Prevention
- Keep Phabricator updated so response parsing tracks Buildkite API changes
- Check the logged HTTP response on the failed target to distinguish payload drift from transient faults
- Monitor Buildkite API status before investigating local configuration
When it happens
Trigger: Buildkite returning a success status with a payload that has no web_url field (API drift); a proxy or middleware rewriting the response body while preserving the status code.
Common situations: Buildkite API changes after a long-lived integration; exotic proxy setups that alter response bodies. Rare in practice.
Related errors
- This object does not support builds with Buildkite.
- Unable to load API token ("%s")!
- CircleCI did not return a "%s"!
- Failed to JSON decode response.
- Expected JSON response from Twilio.
AI-assisted analysis of phacility/phabricator@5720a38cfe (2026-08-21).
Data as JSON: /api/errors/a3c92b356a1e686a.
Report an issue: GitHub.