Storing Metadata on DOM Nodes
In this page:
$(selector).data("key", value);
$(selector).data("key");
$(selector).removeData("key");
What is data()?
The data() method attaches arbitrary JavaScript values to a DOM element without writing them into visible HTML attributes, storing them in an internal cache tied to that element instead. This keeps application state associated with the right element without cluttering the markup or exposing it in the page source.
Example: What is data()?
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<style>
body { font-family: sans-serif; padding: 12px; }
button { padding:6px 14px; margin:4px; background:#2c6aa0; color:white; border:none; border-radius:4px; cursor:pointer; }
button.secondary, #resetBtn { background:white; color:#2c6aa0; border:1px solid #2c6aa0; }
input[type=text] { padding: 6px 8px; margin: 0 6px 8px 0; border: 1px solid #888; border-radius: 4px; font: 14px sans-serif; }
.stage { border: 2px dashed #888; border-radius: 4px; padding: 10px; margin: 8px 0; min-height: 40px; background: #fafafa; }
.stage::before { content: attr(data-label); display: block; font-size: 12px; color: #666; margin-bottom: 6px; }
.item { border: 1px solid #4a7fb5; background: #eaf2fb; padding: 6px 10px; margin: 4px 0; border-radius: 4px; }
.fresh { background: #ffe066 !important; border-color: #d4a600 !important; }
.done { text-decoration: line-through; color: #a33; }
ul.stage { padding-left: 32px; }
ul.stage:empty::after { content: "(empty)"; color: #999; }
ul.stage > li { border: 1px solid #4a7fb5; background: #eaf2fb; padding: 6px 10px; margin: 4px 0; border-radius: 4px; }
.box { border: 2px solid #4a7fb5; background: #f3f8fd; border-radius: 4px; padding: 8px 10px; margin: 8px 0; min-height: 54px; }
.box .label { display: block; font-weight: bold; margin-bottom: 6px; color: #2c6aa0; }
#output { margin-top:10px; padding:8px; border:1px solid #ccc; border-radius:4px; background:#f7f7f7; font-family:monospace; min-height:24px; white-space:pre-wrap; }
#output:empty::before { content: "Output appears here"; color: #888; }
</style>
</head>
<body>
<button id="runBtn">Store data</button><button id="resetBtn" class="secondary">Reset</button>
<div id="card" class="item">Card</div>
<div id="output"></div>
<script>
$("#runBtn").click(function () {
$("#card").data("userId", 42);
$("#output").text('$("#card").data("userId") -> ' + $("#card").data("userId"));
});
$("#resetBtn").click(function () {
$("#card").removeData("userId");
$("#output").text('$("#card").data("userId") -> ' + $("#card").data("userId"));
});
</script>
</body>
</html>
Read Data
Use data() with a key to read back stored information, and the value can be a string, number, object, array, or virtually any other JavaScript value — not just text, unlike a plain HTML data-* attribute. This makes it possible to attach rich structured data, like an entire object, directly to an element.
Example: Read Data
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<style>
button { padding:6px 14px; margin:4px; background:#2c6aa0; color:white; border:none; border-radius:4px; cursor:pointer; }
#resetBtn { background:white; color:#2c6aa0; border:1px solid #2c6aa0; }
#output { margin-top:10px; padding:8px; border:1px solid #ccc; border-radius:4px; background:#f7f7f7; font-family:monospace; min-height:24px; }
#demo :where(p, div, span, li, h1, h2, h3, h4, td, th, blockquote, label, section, article, aside) { border:1px solid #4a7fb5; background:#eaf2fb; padding:6px 10px; margin:4px 0; border-radius:4px; }
#demo :where(ul, ol) { border:1px dashed #888; background:#fafafa; padding:8px 8px 8px 32px; margin:6px 0; }
#demo :where(table) { border-collapse:collapse; }
#demo :where(td, th) { border-radius:0; }
#demo :where(input, select, textarea) { margin:4px 0; }
</style>
</head>
<body>
<button id="runBtn">Run</button>
<button id="resetBtn">Reset</button>
<section id="demo">
<div id="card">Card</div>
</section>
<div id="output"></div>
<script>
var original = $("#demo").html();
$("#runBtn").click(function() {
$("#card").data("userId", 42);
$("#output").text(String($("#card").data("userId")));
});
$("#resetBtn").click(function() {
$("#demo").html(original);
$("#output").empty();
});
</script>
</body>
</html>
Store Multiple Values
You can store more than one piece of metadata on the same DOM element by calling data() with different keys, effectively giving that element its own small collection of custom properties. This is useful when a single element needs to track several unrelated pieces of state at once, like both a status and a timestamp.
Example: Store Multiple Values
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<style>
button { padding:6px 14px; margin:4px; background:#2c6aa0; color:white; border:none; border-radius:4px; cursor:pointer; }
#resetBtn { background:white; color:#2c6aa0; border:1px solid #2c6aa0; }
#output { margin-top:10px; padding:8px; border:1px solid #ccc; border-radius:4px; background:#f7f7f7; font-family:monospace; min-height:24px; }
#demo :where(p, div, span, li, h1, h2, h3, h4, td, th, blockquote, label, section, article, aside) { border:1px solid #4a7fb5; background:#eaf2fb; padding:6px 10px; margin:4px 0; border-radius:4px; }
#demo :where(ul, ol) { border:1px dashed #888; background:#fafafa; padding:8px 8px 8px 32px; margin:6px 0; }
#demo :where(table) { border-collapse:collapse; }
#demo :where(td, th) { border-radius:0; }
#demo :where(input, select, textarea) { margin:4px 0; }
</style>
</head>
<body>
<button id="runBtn">Run</button>
<button id="resetBtn">Reset</button>
<section id="demo">
<div id="card">Card</div>
</section>
<div id="output"></div>
<script>
var original = $("#demo").html();
$("#runBtn").click(function() {
$("#card").data("userId", 42);
$("#card").data("status", "active");
$("#output").text(JSON.stringify($("#card").data()));
});
$("#resetBtn").click(function() {
$("#demo").html(original);
$("#output").empty();
});
</script>
</body>
</html>
Remove Stored Data
The removeData method deletes previously stored metadata from an element, which is useful once that information is no longer relevant — for example, clearing a loading flag once a request finishes. Leaving stale data attached can lead to confusing bugs if old state is accidentally read later.
Example: Remove Stored Data
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<style>
body { font-family: sans-serif; padding: 12px; }
button { padding:6px 14px; margin:4px; background:#2c6aa0; color:white; border:none; border-radius:4px; cursor:pointer; }
button.secondary, #resetBtn { background:white; color:#2c6aa0; border:1px solid #2c6aa0; }
input[type=text] { padding: 6px 8px; margin: 0 6px 8px 0; border: 1px solid #888; border-radius: 4px; font: 14px sans-serif; }
.stage { border: 2px dashed #888; border-radius: 4px; padding: 10px; margin: 8px 0; min-height: 40px; background: #fafafa; }
.stage::before { content: attr(data-label); display: block; font-size: 12px; color: #666; margin-bottom: 6px; }
.item { border: 1px solid #4a7fb5; background: #eaf2fb; padding: 6px 10px; margin: 4px 0; border-radius: 4px; }
.fresh { background: #ffe066 !important; border-color: #d4a600 !important; }
.done { text-decoration: line-through; color: #a33; }
ul.stage { padding-left: 32px; }
ul.stage:empty::after { content: "(empty)"; color: #999; }
ul.stage > li { border: 1px solid #4a7fb5; background: #eaf2fb; padding: 6px 10px; margin: 4px 0; border-radius: 4px; }
.box { border: 2px solid #4a7fb5; background: #f3f8fd; border-radius: 4px; padding: 8px 10px; margin: 8px 0; min-height: 54px; }
.box .label { display: block; font-weight: bold; margin-bottom: 6px; color: #2c6aa0; }
#output { margin-top:10px; padding:8px; border:1px solid #ccc; border-radius:4px; background:#f7f7f7; font-family:monospace; min-height:24px; white-space:pre-wrap; }
#output:empty::before { content: "Output appears here"; color: #888; }
</style>
</head>
<body>
<button id="runBtn">Store, then remove data</button><button id="resetBtn" class="secondary">Reset</button>
<div id="card" class="item">Card</div>
<div id="output"></div>
<script>
$("#runBtn").click(function () {
$("#output").empty();
$("#card").data("loading", true);
$("#output").append($("<div>").text('after data("loading", true): ' + $("#card").data("loading")));
$("#card").removeData("loading");
$("#output").append($("<div>").text('after removeData("loading"): ' + $("#card").data("loading")));
});
$("#resetBtn").click(function () { $("#output").empty(); });
</script>
</body>
</html>
Small data() Project
Attaching hidden metadata this way is especially useful for buttons, product cards, and other repeated UI elements where each instance needs to remember something — like an ID or a status — without adding extra visible markup or custom attributes for every piece of state.
Example: Small data() Project
<!DOCTYPE html>
<html>
<head>
<script src="https://code.jquery.com/jquery-3.7.1.min.js"></script>
<style>
button { padding:6px 14px; margin:4px; background:#2c6aa0; color:white; border:none; border-radius:4px; cursor:pointer; }
#resetBtn { background:white; color:#2c6aa0; border:1px solid #2c6aa0; }
#output { margin-top:10px; padding:8px; border:1px solid #ccc; border-radius:4px; background:#f7f7f7; font-family:monospace; min-height:24px; }
#demo :where(p, div, span, li, h1, h2, h3, h4, td, th, blockquote, label, section, article, aside) { border:1px solid #4a7fb5; background:#eaf2fb; padding:6px 10px; margin:4px 0; border-radius:4px; }
#demo :where(ul, ol) { border:1px dashed #888; background:#fafafa; padding:8px 8px 8px 32px; margin:6px 0; }
#demo :where(table) { border-collapse:collapse; }
#demo :where(td, th) { border-radius:0; }
#demo :where(input, select, textarea) { margin:4px 0; }
</style>
</head>
<body>
<button id="resetBtn">Reset</button>
<section id="demo">
<button class="product" data-id="7">Buy</button>
</section>
<div id="output"></div>
<script>
var original = $("#demo").html();
function init() {
$(".product").on("click", function() {
$("#output").append($("<div>").text("Product ID: " + $(this).data("id")));
});
}
init();
$("#resetBtn").click(function() {
$("#demo").html(original);
$("#output").empty();
init();
});
</script>
</body>
</html>
- Expecting
.data("id", 5)to change thedata-idattribute in the HTML, when it only stores the value in memory and the attribute stays the same. - Calling
.data("key")on a selection with many elements and expecting all values, when it returns the value for the first element only. - Reading
data-user-idwith.data("user_id"), when jQuery converts hyphenated attributes to camelCase:.data("userId").
- Type checking utilities identify what kind of value you have.
trim()cleans strings, and array helpers work with lists.extend()merges objects,proxy()binds context, and metadata can be stored on DOM nodes.
Chapter Quiz — Complete all 6 topics to unlock
0/6 topics done
Complete these topics first: