Black Friday 2025 – NPI EA (cat = Baeldung on Ops)
announcement - icon

Yes, we're now running our Black Friday Sale. All Access and Pro are 33% off until 2nd December, 2025:

>> EXPLORE ACCESS NOW

Partner – Orkes – NPI EA (cat=Kubernetes)
announcement - icon

Modern software architecture is often broken. Slow delivery leads to missed opportunities, innovation is stalled due to architectural complexities, and engineering resources are exceedingly expensive.

Orkes is the leading workflow orchestration platform built to enable teams to transform the way they develop, connect, and deploy applications, microservices, AI agents, and more.

With Orkes Conductor managed through Orkes Cloud, developers can focus on building mission critical applications without worrying about infrastructure maintenance to meet goals and, simply put, taking new products live faster and reducing total cost of ownership.

Try a 14-Day Free Trial of Orkes Conductor today.

1. Overview

Jenkins remote access API is one of the powerful tools that allows automating Jenkins tasks. We can use the API to retrieve information about builds, trigger a Jenkins job, or create a new pipeline. Since the API can provide access to a wide range of Jenkins functionality, securing this API is crucial to protect the Jenkins instance from unwanted actions. Jenkins implements this security in multiple ways; one of them is requiring tokens to be included in the requests sent to the API.

In this tutorial, we’ll cover the fundamentals of using the Jenkins API and how to secure our requests using tokens. We’ll also explain the CSRF protection in Jenkins and how to solve the “No Valid Crumb in Request” error that it causes.

2. Using the Jenkins API

We can use an HTTP client to send requests for the Jenkins API. The request needs to include the Jenkins instance’s IP, the API endpoint for the request, and authentication information. The authentication information consists of the username and an API token or a password. It’s recommended to always use API tokens instead of real passwords. So, let’s first generate the token for our user.

From the Jenkins dashboard, under the username, we select the Security tab:

Create Jenkins API token

In the Security section, we select Add new Token:

Jenkins user security

Finally, we provide a name for the token and select Generate:

generate Jenkins API token

We’ll need to copy and store the generated token somewhere to be able to use it later.

Now that we have our token ready, let’s use curl to send a request to our Jenkins instance:

$ curl --user {username}:{apiToken} http://{JENKINS-IP}:{JENKINS-PORT}/api/json?pretty=true

In the above command, we use the –user option to provide the authentication information with the username and the apiToken. Then we specify the Jenkins instance URL with the IP address and port number. Finally, we add the /api endpoint and specify the data format as json.

This request returns information about the Jenkins instance in the JSON format:

---------- OUTPUT TRIMMED ----------------
  "nodeDescription" : "the Jenkins controller's built-in node",
  "nodeName" : "",
  "numExecutors" : 2,
  "description" : null,
  "jobs" : [
    {
      "_class" : "hudson.model.FreeStyleProject",
      "name" : "sample-job",
      "url" : "https://8085-port-e7xgmenbzvw4pkcu./job/sample-job/",
      "color" : "blue"
    }

In the output, we can see the description of the Jenkins instance, its number of executors, and the current jobs it has.

3. Jenkins CSRF Protection

CSRF is a type of security attack where a malicious actor sends an unwanted request to a web application on behalf of the user. By default, Jenkins enables protection against these types of attacks by requiring an additional token to be sent along with an API request. This additional token is called the crumb token.

The crumb token is required when we’re authenticating our API requests using the real password of the user and not an API token.

We can verify the CSRF protection by checking the Jenkins security configuration:

Jenkins security configuration

We’ll be able to see a CSRF protection section and the crumb token provider:

Jenkins CSRF protection

This means that the Jenkins instance is using the CSRF protection feature.

In our Jenkins instance, we currently have a single job called sample-job. Let’s try to trigger this job with an API request:

$ curl -X POST --user {username}:{password} http://{JENKINS-IP}:{JENKINS-PORT}/job/sample-job/build
<title>Error 403 No valid crumb was included in the request</title>
</head>
<body><h2>HTTP ERROR 403 No valid crumb was included in the request</h2>
<table>
<tr><th>URI:</th><td>/job/sample-job/build</td></tr>
<tr><th>STATUS:</th><td>403</td></tr>
<tr><th>MESSAGE:</th><td>No valid crumb was included in the request</td></tr>
<tr><th>SERVLET:</th><td>Stapler</td></tr>
</table>

As we can see in the output, Jenkins rejected our request because it doesn’t contain a valid crumb token.

4. Fixing the No Valid Crumb Issue

There are multiple ways we can fix this issue when sending API requests to Jenkins. We can choose the best method depending on our needs and the use case.

4.1. Generating a Crumb Token for the User

We can simply generate a crumb token for our user by sending a request to the /crumbIssuer/api/ Jenkins endpoint. After generating the crumb token, we can include it with the original API request using the Jenkins-Crumb header

Let’s check this with an example:

$ curl http://{JENKINS-IP}:{JENKINS-PORT}/crumbIssuer/api/json?pretty=true --user {username}:{password}
{
  "_class" : "hudson.security.csrf.DefaultCrumbIssuer",
  "crumb" : "8454e33c1ce5482a0ea4603a5379a12a9c31eafd65696685c93be5e463db55f8",
  "crumbRequestField" : "Jenkins-Crumb"
}

In the above command, we sent a request using curl to the API endpoint /crumbIssuer/api on the Jenkins instance. We provided the username and password with the request using the –user option. In the output, the response contains a “crumb” key which is the crumb token that we can use for our user.

Now let’s trigger our sample-job again by adding the crumb token in the request:

$ curl -X POST http://{JENKINS-IP}:{JENKINS-PORT}/job/sample-job/build --user {username}:{password} -H "Jenkins-Crumb: 8454e33c1ce5482a0ea4603a5379a12a9c31eafd65696685c93be5e463db55f8"

In the above command, we used the -H option to provide a header in the request. We provided the Jenkins-Crumb header name and then the crumb token. Now let’s check our job:

trigger jenkins job with API

As we can see, the job trigger was successful.

4.2. Using an API Token Instead of Password

As we mentioned previously, Jenkins requires the crumb token for API requests that use a password for authentication. If we don’t have a strict requirement for using passwords, we can generate an API token for the user and use it for sending the request:

$ curl -X POST http://{JENKINS-IP}:{JENKINS-PORT}/job/sample-job/build --user {username}:{apiToken}

Now let’s check our job again:

trigger jenkins build with API token

We can see that the job trigger was successful again, and this time we didn’t need to include a crumb token in the request.

5. Conclusion

In this article, we explained how to solve the No valid crumb issue when sending API requests to Jenkins. We covered the fundamentals of CSRF protection in Jenkins, which requires using additional crumb token with API requests authenticated with passwords. We also showed how to generate the crumb token for our user and pass it along with our API request. As an alternative, we replaced our password-based authentication with an API token, which removes the need for using a crumb token.