Serving resources from Jenkins

3 minute readSecurity

Jenkins serves many user-created files that may not be fully trusted, such as files in project workspaces or archived artifacts. By default, Jenkins only serves these files with the HTTP header Content-Security-Policy ("CSP") set to a value that disallows many modern web features, in order to prevent cross-site scripting attacks on Jenkins users who access these files. While the specific value for the CSP header is user-configurable and can be disabled, doing so is a trade-off between security and functionality.

The Resource Root URL option enables Jenkins to serve user-generated static resources like workspace files or archived artifacts without the need for CSP headers. If you configure this option, Jenkins redirects requests for user-created resource files to URLs, starting with the URL you configure.

To use this option, you should keep the following things in mind:

  • The Jenkins root URL must be configured as a different URL than the resource root. It requires a different host name.

  • Jenkins only serves resource URL requests via the resource root URL. All other requests receive HTTP 404 Not Found responses.

  • The resource root URL must be equivalent to the Jenkins root URL. If there were no restrictions on responses, the resource root URL would be a valid alternative to the Jenkins root URL.

Once you have configured the URL, Jenkins redirects requests to workspaces, archived artifacts, and similar collections of files to URLs that start with the resource root URL. Instead of a path like job/name_here/ws</code>, resource URLs contain a long hexadecimal string encoding that path, the user for which the URL was created, and when the URL was created. These resource URLs access static files as if the user for which they were created was accessing them. If the user’s permission to access the files is removed, the corresponding resource URLs would not have access either.

Security considerations

You should consider the following:

  • Resource URLs do not require authentication. Users do not have a valid session for the resource root URL. Also, sharing a resource URL with another user, even one lacking Overall/Read permissions from Jenkins, grants that user access to these files until the URLs expire.

  • Resource URLs expire after 30 minutes, by default. Expired resource URLs redirect users to the equivalent Jenkins URLs so that users can authenticate again, if necessary. Then they redirect users to a new resource URL that is valid for another 30 minutes. This is generally transparent to users if they have a valid Jenkins session. If they do not have a valid session, they will have to authenticate with Jenkins again.

    The login form cannot appear in an HTML frame. If you are viewing HTML pages with frames, you must reload the top-level frame to make the login form appear.
  • Resource URLs encode the URL, the user for which they were created, and their creation timestamp. Additionally, this string contains a hash-based message authentication code (HMAC) to verify the authenticity of the URL to prevent attackers from forging URLs and obtaining access to resource files as if they were another user.

Configuring the resource URL

To configure the resource URL:

  1. Configure a new DNS route with a CNAME (alias) for your resource domain to your current Jenkins domain.

  2. Once the route and DNS record are ready, go to <master_url>/configure, scroll down to the Serve resource files from another domain section, and enter the resource URL.

    If you were successful, you will see something like the following in your configuration settings:

    Resource root URL

In August 2020, the Jenkins project voted to replace the term master with controller. We have taken a pragmatic approach to cleaning these up, ensuring the least amount of downstream impact as possible. CloudBees is committed to ensuring a culture and environment of inclusiveness and acceptance - this includes ensuring the changes are not just cosmetic ones, but pervasive. As this change happens, please note that the term master has been replaced through the latest versions of the CloudBees documentation with controller (as in managed controller, client controller, team controller) except when still used in the UI or in code.