opf/openproject · error · Import::JiraClient::ApiError

Jira API returned a 429 error. It means token owner has been

Error message

Jira API returned a 429 error. It means token owner has been rate limited by the Jira instance. Please disable rate limiting for this user.

What it means

Import::JiraClient#handle_response maps HTTP 429 to an ApiError with the admin.jira.client.429_error message. Jira (Data Center/Server has a user-level rate limer) throttled the token owner, so the importer's rapid sequential GET/POST loop is being rejected. The client has no automatic backoff, so the error aborts the current operation.

Source

Thrown at app/services/import/jira_client.rb:309

        params:,
        http_options: HTTP_OPTIONS
      )
    rescue SsrfFilter::PrivateIPAddress
      raise SsrfError, I18n.t("admin.jira.client.ssrf_blocked")
    rescue SsrfFilter::Error, SocketError, Errno::ECONNREFUSED, Errno::EHOSTUNREACH => e
      raise ConnectionError, I18n.t("admin.jira.client.connection_error", message: e.message)
    rescue OpenSSL::SSL::SSLError => e
      raise ConnectionError, I18n.t("admin.jira.client.ssl_error", message: e.message)
    rescue Timeout::Error => e
      raise ConnectionError, I18n.t("admin.jira.client.connection_timeout", message: e.message)
    end

    def handle_response(response)
      status = response.code.to_i
      if response.is_a?(Net::HTTPSuccess)
        parse_json(response)
      else
        raise ApiError.new(
          I18n.t("admin.jira.client.#{status}_error", status:, default: :"admin.jira.client.api_error"),
          status:,
          response_body: response.body.to_s
        )
      end
    end

    def parse_json(response)
      JSON.parse(response.body)
    rescue JSON::ParserError => e
      raise ParseError, I18n.t("admin.jira.client.parse_error", message: e.message)
    end
  end
end

View on GitHub (pinned to d9742c43f3)

Solutions

  1. As the message instructs: in Jira DC go to Administration → System → Rate limiting and disable it (or raise limits) for the importing user, then retry the run.
  2. If disabling is not possible, wait for the limit window to reset and retry the import run during off-peak hours.
  3. Reduce concurrent Jira integrations using the same account so the import run has headroom.

Example fix

# before
retries = 0
begin
  client.get('/rest/api/2/mypermissions')
rescue Import::JiraClient::ApiError => e
  retries += 1
  retry
end

# after (backoff only on 429)
retries = 0
begin
  client.get('/rest/api/2/mypermissions')
rescue Import::JiraClient::ApiError => e
  raise if e.status != 429 || retries >= 5
  retries += 1
  sleep(2**retries)
  retry
end
Defensive patterns

Strategy: retry

Try / catch

retries = 0
begin
  client.get('/rest/api/2/mypermissions')
rescue Import::JiraClient::ApiError => e
  raise unless e.status == 429 && retries < 5
  retries += 1
  sleep(2**retries)
  retry
end

Prevention

When it happens

Trigger: A Jira import run (bulk project/issue/custom-field fetching) against a Jira DC instance where 'Rate limiting' is enabled for the importing user or globally, causing /rest/api/2 calls to return 429 mid-run.

Common situations: Jira DC rate limiting introduced/enabled by an admin after initial testing; large Jira instances where the import volume trips the default limits; shared token also used by other tooling consuming the quota.

Related errors


AI-assisted analysis of opf/openproject@d9742c43f3 (2026-08-21). Data as JSON: /api/errors/57370ab678725edd. Report an issue: GitHub.