grafana/k6 · error

getting text content of element: unexpected type %T (expecti

Error message

getting text content of element: unexpected type %T (expecting string)

What it means

Internal invariant break inside TextContent: the evaluation succeeded and returned a non-nil value, but it was not a Go string. The injected-script contract says textContent evaluation returns by-value strings; a number/bool/object result means the page-side evaluation behaved unexpectedly (e.g. page JavaScript overriding prototypes that the injected script relies on, or a divergent injected-script version).

Source

Thrown at internal/js/modules/k6/browser/common/element_handle.go:1536

// The second return value is true if the text content exists, and false otherwise.
func (h *ElementHandle) TextContent() (string, bool, error) {
	textContent := func(apiCtx context.Context, handle *ElementHandle) (any, error) {
		return handle.textContent(apiCtx)
	}
	opts := NewElementHandleBaseOptions(h.DefaultTimeout())
	textContentAction := h.newAction(
		[]string{}, textContent, opts.Force, withRetry, opts.NoWaitAfter, opts.Timeout,
	)
	v, err := call(h.ctx, textContentAction, opts.Timeout)
	if err != nil {
		return "", false, fmt.Errorf("getting text content of element: %w", err)
	}
	if v == nil {
		return "", false, nil
	}
	s, ok := v.(string)
	if !ok {
		return "", false, fmt.Errorf(
			"getting text content of element: unexpected type %T (expecting string)",
			v,
		)
	}

	return s, true, nil
}

// Timeout will return the default timeout or the one set by the user.
// It's an internal method not to be exposed as a JS API.
func (h *ElementHandle) Timeout() time.Duration {
	return h.DefaultTimeout()
}

// Type scrolls element into view, focuses element and types text.
func (h *ElementHandle) Type(text string, opts *ElementHandleTypeOptions) error {
	typ := func(apiCtx context.Context, handle *ElementHandle) (any, error) {
		return nil, handle.typ(apiCtx, text, KeyboardOptions{})

View on GitHub (pinned to 93accf6570)

Solutions

  1. Re-run once to rule out a transient context issue
  2. If reproducible, capture K6_BROWSER_LOG=debug and report it as a k6 browser bug, including the %T type printed in the message
  3. As a workaround, read the text via page.evaluate with document.querySelector(sel).textContent

Example fix

// workaround when textContent() keeps failing
const text = page.evaluate(() => document.querySelector('#el').textContent);
Defensive patterns

Strategy: retry

Try / catch

try {
  return el.textContent();
} catch (e) {
  if (String(e).includes('unexpected type')) {
    // invariant break: fall back to in-page evaluation
    return page.evaluate((s) => document.querySelector(s).textContent, sel);
  }
  throw e;
}

Prevention

When it happens

Trigger: Page scripts polluting Object.prototype or Function prototypes that the injected script uses; execution-context weirdness after cross-origin iframe swaps returning handles instead of values; version mismatch between embedded injected_script.js and the Go wrapper.

Common situations: Testing third-party pages that patch built-ins; very old/new chromium builds against an unupdated k6; almost never seen on ordinary pages.

Related errors


AI-assisted analysis of grafana/k6@93accf6570 (2026-08-15). Data as JSON: /api/errors/283b239218a88931. Report an issue: GitHub.