The issue history gives us both the name and id of any statuses that the ticket has moved through. Sometimes that’s enough but often we then need to know more about that status, such as what status category it belongs to and for that, we need to call a different API.

There are two different API’s that we might use for this. The first retrieves the statuses for one specific project and the other returns all statuses across the entire instance.

I used to use the project specific API and found numerous places where it just wouldn’t return some statuses that had been found in the historical data. So now I use the second, although even that one is flaky, as you’ll see.

  • Get statuses for one project: /rest/api/2/project/{projectIdOrKey}/statuses
  • Get all statuses across the Jira instance: /rest/api/2/status

Note that the Atlassian documentation is wrong for this second API. They say it’s /rest/api/2/statuses (plural) and in fact it’s the singular /rest/api/2/status.

In theory, this API will return every status across the Jira instance. In practice, we’ve seen this to be user specific. One person can call this and get a large list of statuses and a second person can call it at the same time and get a subset of those statuses. We’ve been unable to determine what permission is in use to affect this. Bottom line is that this API is unreliable, but it’s the best we have.

An interesting point about both is that they will only return statuses that are current in the instance. So if a status has been deleted by an admin then it’s really gone, even if the historical data still references it. What this mean for practical purposes, is that if you find a status in the history that has been deleted, and you want to then find out what category it belongs to, you can’t. That information is gone. This makes looking at historical data more difficult than it should be.

For a status in use by a classic project (the vast majority of projects out there), the results for a status will look like this.

{
  "self": "https://improvingflow.atlassian.net/rest/api/2/status/10000",
  "description": "",
  "iconUrl": "https://improvingflow.atlassian.net/",
  "name": "Backlog",
  "untranslatedName": "Backlog",
  "id": "10000",
  "statusCategory": {
    "self": "https://improvingflow.atlassian.net/rest/api/2/statuscategory/2",
    "id": 2,
    "key": "new",
    "colorName": "blue-gray",
    "name": "To Do"
  }
}

For the statusCategory, by definition there are only three possible values. To Do, In Progress, and Done. It shouldn’t be possible to have anything else and yet, I’ve seen at least once case where a status didn’t have a category at all. I have no idea how that would even be possible.

If you have a team-managed project (formerly called NextGen) anywhere in your instance then you may find a status that looks like this. Note the extra scope section.

{
  "self": "https://improvingflow.atlassian.net/rest/api/2/status/10017",
  "description": "",
  "iconUrl": "https://improvingflow.atlassian.net/",
  "name": "Review",
  "untranslatedName": "Review",
  "id": "10017",
  "statusCategory": {
    "self": "https://improvingflow.atlassian.net/rest/api/2/statuscategory/4",
    "id": 4,
    "key": "indeterminate",
    "colorName": "yellow",
    "name": "In Progress"
  },
  "scope": {
    "type": "PROJECT",
    "project": {
      "id": "10002"
    }
  }
}

The scope section tells you that this status is specific to one project. What makes it ugly is that we may now have two different statuses with exactly the same name, one global (without the scope) and one specifically for one project. If you’re expecting all status names to be unique, which I used to, this can come as an ugly surprise.

In the case, where there are two with the same name, the project specific one wins for that project and the global one wins in every other case.

As you can see, even with an API as simple as listing statuses, there is a lot that isn’t obvious.


Other articles about the Jira API: