Reading and Changing Text Content
Once you have a reference to an element, you can read what is inside it and replace it with new content. The two main properties for this are textContent and innerHTML.
element.textContent
Section titled “element.textContent”textContent reads or sets the plain text content of an element. All HTML tags are stripped — you see only the text:
const heading = document.querySelector('h1');console.log(heading.textContent); // 'Summit Trail Outfitters'Setting textContent replaces everything inside the element with the new text:
const priceEl = document.querySelector('.tour-price');priceEl.textContent = '$149.00';If the new string contains HTML characters like <, they are treated as literal text — not rendered as tags. This makes textContent safe for user-generated content.
element.innerHTML
Section titled “element.innerHTML”innerHTML reads or sets the HTML content of an element. Tags in the string are parsed and rendered:
const card = document.querySelector('.tour-card');console.log(card.innerHTML); // returns the full HTML inside the element
card.innerHTML = '<h3>Cascade Ridge Hike</h3><p>$149.00</p>';innerHTML is powerful for inserting markup — but it comes with a significant risk.
XSS security warning
Section titled “XSS security warning”Never use innerHTML with untrusted user input. If a user submits text containing <script> tags or malicious HTML attributes, and you insert that text with innerHTML, the browser executes it. This attack is called Cross-Site Scripting (XSS).
// Dangerous — do not do thisconst userInput = '<img src=x onerror="stealCookies()">';container.innerHTML = userInput; // the onerror handler runsThe rule is simple: use innerHTML only with strings you wrote yourself or that come from your own trusted data source. Use textContent for anything that comes from user input.
element.innerText
Section titled “element.innerText”innerText is similar to textContent but respects CSS visibility. Hidden elements (via display: none or visibility: hidden) are excluded from innerText but included in textContent.
const el = document.querySelector('.tour-card');console.log(el.textContent); // includes all text including hidden elementsconsole.log(el.innerText); // only text visible to the userIn most cases textContent is what you need. Reach for innerText when you specifically want the user-visible text, matching what getComputedStyle would show.
When to use each
Section titled “When to use each”| Property | When to use |
|---|---|
textContent | Reading or setting plain text. Always safe. Default choice. |
innerHTML | Inserting HTML markup you control. Never with user input. |
innerText | When you need only the visible text, respecting CSS hide/show. |
Using formatPrice() with textContent
Section titled “Using formatPrice() with textContent”This is where Module 04 helper functions connect to the DOM. Instead of a static price string, compute it:
const formatPrice = price => '$' + price.toFixed(2);
const priceEl = document.querySelector('.tour-price');if (priceEl) { priceEl.textContent = formatPrice(149); // '$149.00'}Exercise
Section titled “Exercise”On the STO site in the Console:
// Read text content of the first h1const heading = document.querySelector('h1');console.log(heading.textContent);
// Update a price displayconst formatPrice = price => '$' + price.toFixed(2);const priceEl = document.querySelector('.tour-price');if (priceEl) { console.log('Before:', priceEl.textContent); priceEl.textContent = formatPrice(149); console.log('After:', priceEl.textContent);}
// Observe the XSS risk — read only, do not run in production// Try inserting markup with innerHTML on a non-critical elementconst testEl = document.querySelector('footer');if (testEl) { testEl.innerHTML = '<strong>Updated via innerHTML</strong>';}Verify the changes visually in the browser, then reload to reset the page to its original state.
textContentreads or sets plain text. All HTML tags are stripped. Safe for user-generated content. Default choice.innerHTMLreads or sets HTML markup. Tags are parsed and rendered. Never use with untrusted user input — XSS risk.innerTextreturns only user-visible text, respecting CSS visibility. Use when you need the rendered result.- Rule of thumb:
textContentfor plain text,innerHTMLfor trusted HTML markup you control.