Hey everyone! I’m having a tough time with Puppeteer. I’m trying to change the innerHTML of an element’s parent, but I keep getting null or undefined errors. Here’s what I’ve tried:
await page.$eval('.someClass' + myVar + ' img.anotherClass', elem => elem.parentElement.innerHTML = 'new text');
await page.evaluate((myVar) => {
const elem = document.querySelector('.someClass' + myVar + ' img.anotherClass');
elem.parentElement.innerHTML = 'new text';
});
Both attempts fail. The first one says the parent is undefined, the second says it’s null. I’ve checked my selectors in the browser console and they work fine there. The parent is a table cell, if that matters.
I’ve tried hardcoding the variable, using console.log to debug, and even simplified the selector. Still no luck. Any ideas what I’m doing wrong? I’m totally stumped!
Have you considered using JavaScript’s native DOM manipulation methods instead of modifying innerHTML directly? This approach can be more robust and less prone to errors. Here’s an example:
await page.evaluate((myVar) => {
const img = document.querySelector(‘.someClass’ + myVar + ’ img.anotherClass’);
if (img && img.parentElement) {
while (img.parentElement.firstChild) {
img.parentElement.removeChild(img.parentElement.firstChild);
}
img.parentElement.appendChild(document.createTextNode(‘new text’));
}
});
This method clears the parent element’s contents and adds the new text as a text node. It’s safer and avoids potential issues with innerHTML. Also, make sure you’re allowing enough time for the page to load fully before running your script. Adding a short delay or waiting for a specific element to appear might help resolve timing-related issues.
I’ve run into similar issues with Puppeteer before. One thing that often helps is making sure the page has fully loaded before trying to manipulate elements. Try adding a wait condition like this:
await page.waitForSelector(‘.someClass’ + myVar + ’ img.anotherClass’);
before your element selection code. This ensures the element actually exists in the DOM before you try to access it.
Another trick I’ve found useful is to break down complex selectors into steps. Instead of selecting the element and modifying its parent in one go, try something like:
const img = await page.$(‘.someClass’ + myVar + ’ img.anotherClass’);
const parent = await img.evaluateHandle(el => el.parentElement);
await parent.evaluate(el => el.innerHTML = ‘new text’);
This approach gives you more control and makes it easier to debug where things might be going wrong. Hope this helps!
hey mate, have u tried using page.waitForSelector() before ur code? sometimes puppeteer is too quick and elements arent loaded yet. also, maybe try breaking it down:
const img = await page.$(‘.someClass’ + myVar + ’ img.anotherClass’);
if (img) {
await page.evaluate(el => el.parentElement.textContent = ‘new text’, img);
}
this way u can check if the img exists first. hope it helps!