Skip to content

Give test functions a limited view object instead of the full Test instance #147

Description

@DmitrySharabin

Problem

Currently, user-authored functions (run, beforeEach, afterEach, map, check, getName, getExpect) receive the full Test instance as this. This exposes internals that test authors should not need to access or mutate.

A more limited object would:

  • Restrict what test functions can see and do
  • Give flexibility around what this means — it can be different per function, tailored to each function's role
  • Decouple user-authored code from Test implementation details

Example of what this enables

One concrete benefit: the this.parent resolution problem. When a function is inherited and calls this.parent.run(x), it re-enters itself because this.parent resolves to the literal parent (which has the same inherited function):

{
    name: "Test",
    run (x) { return x * 2 },    // Level 0: defines run
    tests: [
        {
            name: "Level 1",
            run (x) {             // Level 1: defines its own run, calls parent's
                return this.parent.run(x) + 1;
            },
            tests: [
                {
                    name: "Level 2",
                    // No run here — inherited from Level 1
                    arg: 3,
                    expect: 7,    // Actual: 8
                },
            ],
        },
    ],
}

Level 2 inherits Level 1's run. The runner calls it with this = Level 2. Inside, this.parent.run(3) hits Level 1's own run (same function), which runs again with this = Level 1, calls Level 0's run(3) = 6, +1 = 7, +1 = 8.

A view object could define this.parent differently per function — e.g., skipping to the nearest ancestor with a different version — without special-casing parent resolution on Test itself.

Source

Proposed by @LeaVerou in the discussion on PR #141.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions