CVE-2023-43495 is a critical stored Cross-Site Scripting (XSS) vulnerability identified in Jenkins, up to version 2.423 and LTS 2.414.1. This vulnerability lives in the UI component called ExpandableDetailsNote, and results from failing to correctly escape the caption parameter provided upon construction.
With this bug, any attacker who can supply a custom caption value — for example, through automation, plugin, or a crafted UI action — can inject malicious HTML and JavaScript that executes whenever another Jenkins user views the message.
> References:
> - Jenkins Security Advisory
> - CVE Details
How the Vulnerability Works
Jenkins uses a class called ExpandableDetailsNote, which is meant to display information with a clickable "expand for details" section. The caption parameter is what the user sees before clicking. However, this parameter is injected directly into the DOM without proper HTML escaping or filtering.
Imagine a Jenkins plugin or process allows users to input custom text messages (for notifications, release notes, etc.). An attacker could supply a caption like this:
<script>alert('XSS Attacked!')</script>
When another user loads a page showing this note, the browser executes this script.
Let's look at a simplified code snippet that illustrates this vulnerability
public class ExpandableDetailsNote extends Note {
private final String caption;
public ExpandableDetailsNote(String caption) {
this.caption = caption;
}
@Override
public String toHtml() {
// BAD: No escaping of caption!
return "<div class='warning'>" +
"<span class='caption'>" + caption + "</span>" +
"</div>";
}
}
Problem: The caption is inserted directly. If it's attacker-controlled, anything goes.
Suppose a custom Jenkins plugin allows users to submit a job note. The backend does this
ExpandableDetailsNote note = new ExpandableDetailsNote(request.getParameter("caption"));
saveNoteForJob(job, note);
As an attacker, you POST the following data to the plugin’s endpoint
caption=<img src=x onerror=alert(1)>
An administrator opens the affected job page. The HTML renders like so
<div class="warning">
<span class="caption"><img src=x onerror=alert(1)></span>
</div>
The JavaScript runs as soon as the image fails to load — pop! — stored XSS.
Real-World Impact
- Privilege Escalation: Attackers can steal session cookies, impersonate admins, or trigger harmful actions.
- Stored XSS: Unlike reflected XSS, this payload persists in Jenkins and attacks everyone who sees it.
The fix is simple — always escape or sanitize user-supplied content before putting it on the page
import org.apache.commons.text.StringEscapeUtils;
public class ExpandableDetailsNote extends Note {
private final String caption;
public ExpandableDetailsNote(String caption) {
this.caption = caption;
}
@Override
public String toHtml() {
return "<div class='warning'>" +
"<span class='caption'>" + StringEscapeUtils.escapeHtml4(caption) + "</span>" +
"</div>";
}
}
Conclusion
CVE-2023-43495 is a simple mistake with huge impact. If you’re running Jenkins, make sure to update your instance immediately, and always check for user input that may be rendered in the UI.
Further Reading
- Jenkins CVE List
- Preventing XSS in Jenkins Plugins
- Understanding Stored XSS
Timeline
Published on: 09/20/2023 17:15:00 UTC
Last modified on: 09/23/2023 03:45:00 UTC