ReactiveX/rxjs · error · ArgumentOutOfRangeError
argument out of range
Error message
argument out of range
What it means
elementAt(index) throws ArgumentOutOfRangeError ('argument out of range') immediately when index is negative — a negative index can never match a zero-based emission, so it fails fast at call time rather than erroring per-subscriber. (A separate out-of-range error occurs at completion when no default is supplied.)
Source
Thrown at packages/rxjs/src/element-at.ts:17
import { create } from './create.js';
import { ArgumentOutOfRangeError } from './argument-out-of-range-error.js';
import '@rxjs/observable-polyfill';
import { subscribeToSource } from './util/observable-helpers.js';
export const elementAt: unique symbol = Symbol('elementAt');
declare global {
interface Observable<T> {
[elementAt](index: number): Observable<T>;
[elementAt]<D>(index: number, defaultValue: D): Observable<T | D>;
}
}
Observable.prototype[elementAt] = function <T, D>(this: Observable<T>, index: number, ...defaultValue: [] | [D]): Observable<T | D> {
if (index < 0) {
throw new ArgumentOutOfRangeError();
}
const hasDefault = defaultValue.length === 1;
return this[create]((subscriber) => {
let count = 0;
subscribeToSource(this, subscriber, {
next: (value) => {
if (count === index) {
subscriber.next(value);
subscriber.complete();
return;
}
count++;
},
complete: () => {
if (hasDefault) {
subscriber.next(defaultValue[0]);
subscriber.complete();View on GitHub (pinned to 54796b38a5)
Solutions
- Guard the index before calling: Math.max(0, index)
- Use first()/last() operators instead of elementAt for those semantics
- If the source may be empty, supply a default: elementAt(0, fallback)
Example fix
// before obs[elementAt](items.length - 1); // -1 when items is empty // after obs[elementAt](Math.max(0, items.length - 1), undefined);
Defensive patterns
Strategy: validation
Validate before calling
if (!Number.isInteger(index) || index < 0) throw new RangeError('index must be a non-negative integer');
obs[elementAt](index); Type guard
const isNonNegativeInt = (n: unknown): n is number => Number.isInteger(n) && (n as number) >= 0;
Prevention
- Clamp computed indices with Math.max(0, index)
- Use first/last operators for those semantics
- Supply a default value when the source may be empty
When it happens
Trigger: observable[elementAt](-1), or elementAt(someIndex) where someIndex is computed (e.g. list.length - counter) and goes negative on empty input.
Common situations: Off-by-one bugs with computed indices (length - 1 on an empty collection), porting code that assumed Python-style negative indexing, or clamping logic that never runs before the call.
Related errors
- Migration result was refused for source: ${sourcePath}
- ${message}
- ${label} is not a directory: ${path}
- An output path ancestor is not a directory: ${existing}
- --harness requires codex, claude, or cursor
AI-assisted analysis of ReactiveX/rxjs@54796b38a5 (2026-08-28).
Data as JSON: /api/errors/2e26238bd3f5edb6.
Report an issue: GitHub.