{"record":{"id":"0e32a19be6c73a8c","repo":"grafana/k6","slug":"checking-element-is-hidden-w","errorCode":null,"errorMessage":"checking element is hidden: %w","messagePattern":"checking element is hidden: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/js/modules/k6/browser/common/element_handle.go","lineNumber":1102,"sourceCode":"}\n\n// IsEnabled checks if the element is enabled.\nfunc (h *ElementHandle) IsEnabled() (bool, error) {\n\tok, err := h.isEnabled(h.ctx, 0)\n\t// We don't care anout timeout errors here!\n\tif err != nil && !errors.Is(err, ErrTimedOut) {\n\t\treturn false, fmt.Errorf(\"checking element is enabled: %w\", err)\n\t}\n\n\treturn ok, nil\n}\n\n// IsHidden checks if the element is hidden.\nfunc (h *ElementHandle) IsHidden() (bool, error) {\n\tok, err := h.isHidden(h.ctx)\n\t// We don't care anout timeout errors here!\n\tif err != nil && !errors.Is(err, ErrTimedOut) {\n\t\treturn false, fmt.Errorf(\"checking element is hidden: %w\", err)\n\t}\n\n\treturn ok, nil\n}\n\n// IsVisible checks if the element is visible.\nfunc (h *ElementHandle) IsVisible() (bool, error) {\n\tok, err := h.isVisible(h.ctx)\n\t// We don't care anout timeout errors here!\n\tif err != nil && !errors.Is(err, ErrTimedOut) {\n\t\treturn false, fmt.Errorf(\"checking element is visible: %w\", err)\n\t}\n\n\treturn ok, nil\n}\n\n// OwnerFrame returns the frame containing this element.\nfunc (h *ElementHandle) OwnerFrame() (_ *Frame, rerr error) {","sourceCodeStart":1084,"sourceCodeEnd":1120,"githubUrl":"https://github.com/grafana/k6/blob/3fcf5388d78cb382f0c0d42ec556a06bfd1b8dee/internal/js/modules/k6/browser/common/element_handle.go#L1084-L1120","documentation":"ElementHandle.isHidden() runs waitForElementState(['hidden']) with a zero timeout and deliberately ignores ErrTimedOut, returning a boolean for hidden/visible. A wrapped error is therefore a transport-level failure: the element handle is detached, the execution context was destroyed by navigation, or the session/frame is gone.","triggerScenarios":"The node was removed or replaced by a re-render before the check; the page navigated and the old context is gone; the element's frame was detached; the page was closed while the check ran.","commonSituations":"Asserting that toast/banner elements are hidden after SPAs remove them from the DOM entirely (removal is not 'hidden'); cached handles after route changes; teardown races at iteration end.","solutions":["Use a live locator: await page.locator(sel).isHidden(), which re-resolves","Check presence separately: const el = await page.$(sel); if (el === null) -> it is gone, not hidden","Catch the error and treat it as 'no longer in DOM' when that matches the intent","Re-acquire handles after any navigation or long wait"],"exampleFix":"// before\nconst el = await page.$('.toast');\nawait closeToast();\nconst hidden = await el.isHidden(); // throws: node removed from DOM\n\n// after\nawait closeToast();\nconst gone = await page.$('.toast') === null;\nconst hidden = gone || await page.locator('.toast').isHidden();","handlingStrategy":"try-catch","validationCode":"// Distinguish 'removed from DOM' from 'hidden' before checking\nconst gone = (await page.$('.toast')) === null;\nconst hidden = gone || (await page.locator('.toast').isHidden());","typeGuard":null,"tryCatchPattern":"let hidden = true;\ntry {\n  hidden = await el.isHidden();\n} catch (e) {\n  if (/not attached|Execution context|Could not find object/i.test(String(e.message))) {\n    hidden = (await page.$(sel)) === null; // removed counts as hidden here\n  } else throw e;\n}","preventionTips":["Remember SPAs often remove (not hide) elements - page.$(sel) === null is the check for that","Use live locators for visibility assertions","Do not reuse handles after the flow that removes the element has run"],"tags":["browser","element-state","hidden","stale-element","k6"],"backgroundTag":"stale-element-reference","analyzedSha":"3fcf5388d78cb382f0c0d42ec556a06bfd1b8dee","analyzedAt":"2026-08-18T03:05:52.393Z","contentChangedAt":"2026-08-18T03:05:52.393Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}