phacility/phabricator · error · Exception
Invalid changeset ID "%s"!
Error message
Invalid changeset ID "%s"!
What it means
After the revision resolves, the controller loads the changeset named by the changeset id. A null, wrong, or deleted changeset ID throws 'Invalid changeset ID'. The most common source is a stale page that still references changesets from an older diff of the revision.
Source
Thrown at src/applications/differential/controller/DifferentialInlineCommentEditController.php:46
}
return $revision;
}
protected function createComment() {
// Verify revision and changeset correspond to actual objects, and are
// connected to one another.
$changeset_id = $this->getChangesetID();
$viewer = $this->getViewer();
$revision = $this->loadRevision();
$changeset = id(new DifferentialChangesetQuery())
->setViewer($viewer)
->withIDs(array($changeset_id))
->executeOne();
if (!$changeset) {
throw new Exception(
pht(
'Invalid changeset ID "%s"!',
$changeset_id));
}
$diff = $changeset->getDiff();
if ($diff->getRevisionID() != $revision->getID()) {
throw new Exception(
pht(
'Changeset ID "%s" is part of diff ID "%s", but that diff '.
'is attached to revision "%s", not revision "%s".',
$changeset_id,
$diff->getID(),
$diff->getRevisionID(),
$revision->getID()));
}
return id(new DifferentialInlineComment())View on GitHub (pinned to 5720a38cfe)
Solutions
- Reload the revision and diff view, then re-submit the comment.
- Ensure the changeset id comes from the same diff you are viewing.
- In automation, resolve changeset IDs from the current diff via the API, never from cached pages.
Defensive patterns
Strategy: try-catch
Try / catch
try {
// submit the inline comment with revision id + changeset id
} catch (Exception $ex) {
if (preg_match('/Invalid changeset ID/', $ex->getMessage())) {
// stale view: reload the diff and resubmit with a current changeset id
} else {
throw $ex;
}
} Prevention
- Take the changeset id from the diff currently rendered, not from a cached page.
- Reload the revision view after the author updates the diff.
- In automation, resolve changeset ids from the current diff via the API.
When it happens
Trigger: Inline comment requests whose changeset id does not exist or is invisible: posting from a page rendered before the diff was replaced or deleted, or constructing requests manually.
Common situations: Commenting from a stale diff view after the author updated the revision; automation replaying captured inline-comment requests against new revisions.
Understand the failure class
Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.
Related errors
AI-assisted analysis of phacility/phabricator@5720a38cfe (2026-08-21).
Data as JSON: /api/errors/a4a7a42011af332a.
Report an issue: GitHub.