Module @tapjs/reporter - v1.2.0

@tapjs/reporter

A set of ink based reporters for tap, and utilities you can use to write your own.

The modern reincarnation of treport.

Reporters in Node-Tap

The following reporters are built into this module, and always available in node-tap.

base

--reporter=base is the default. It provides a reasonable amount of information about what's going on, without too much noise. If you run tap with --passes, then it'll show all the passing assertions, though that's often excessive, so it's off by default.

terse

As the name suggests, the terse report shows much less information than base. But otherwise, they are very similar. If tests pass, it shows a very brief summary. When tests fail, it shows the same diffs, traces, and so on.

min

More terse than terse. Shows information about failures and todo items, but no summaries, counts, etc. For successful test runs, this is equivalent to silent.

silent

The silent report prints nothing at all to the terminal, but still exits with an error status code if the tests did not pass.

tap

The --reporter=tap option will output raw the TAP content, similar to just running the test programs directly.

junit

XML output format used by JUnit. The testmoapp/junitxml repo has a good description of the format.

json

A single JSON object, somewhat similar in shape to the XML produced by the junit reporter.

Suite objects contain metadata about a test, and a list of suites and cases (ie, test point assertions). Suites can contain other suites.

jsonstream

The same data as the json format, but streamed as newline-delimited JSON.

Each line is an array with two members. The first is a string, one of 'start', 'end', 'pass', 'fail', 'skip' or 'todo'. The second is a data object, as follows:

  • start Initial metadata about a suite, before it has loaded any sub-suites or test cases.
  • end Final data about a suite, with counts and summary data.
  • pass, fail, skip, todo A test point of the specified type.

markdown

Similar data as shown by the jsonstream report, but formatted in Markdown.

Other Reporters

The reporter config option can also be set to:

  • Any executable program - The TAP stream will be written to the program's standard input.
  • A module that exports a Stream class - The class will be instantiated, and the TAP stream piped into it.
  • A module that exports a React component - The component will be rendered using Ink, with the TAP object provided as the test prop, and the LoadedConfig as the config prop.

Writing Custom Reporters

For streams and command-line reporters written in JavaScript, the tap-parser module is the best way to parse the incoming TAP stream. For other languages, there are many other TAP consumer libraries available.

For React component reporters, the components, hooks, and utilities in this package are likely very useful.

The easiest way to write a custom React reporter is as an ESM-only module that default exports its Reporter function on the main package module. Then, users can do --reporter <package-name> in their configs to use it.

Another way, if a reporter comes along with some other plugin functionality, is to add it to the default set via the API presented here. However, some care must be taken in that case, because @tapjs/reporter is ESM-only, and plugins must be compatible with both CommonJS and ESM. The @tapjs/dummy-plugin package contains an example of this.

@tapjs/reporter API

The API available at import '@tapjs/reporter'.

interface TapReportOpts

The options provided to reports.

interface TapReportOpts {
test: TestBase
config: LoadedConfig
}

type Reporter

Alias for React.FC<TapReportOpts>

types: Record<string, Reporter>

A record of all the known reporters, indexed by their config name.

addType(name: string, reporter: Reporter)

Add a reporter at the name provided, so that it can be used on the --reporter config.

report(Type: string | Reporter, tap: TAP, config: LoadedConfig)

Render the specified reporter with the tap object and loaded config.

Base

The --reporter=base implementation

Terse

The --reporter=terse implementation

hooks

Alias for the @tapjs/reporter/hooks module

components

Alias for the @tapjs/reporter/components module

utils

Alias for the @tapjs/reporter/utils module

@tapjs/reporter/components API

This provides a collection of useful components for building tap reports.

The relevant tags are listed here, but this module also exports several types and interfaces that they use for their property definitions.

BailedOut

<BailedOut test={tap} />

Print a bold red "Bailout!" message if the test bails out.

Diff

<Diff diff={diffString} />

Create a colorized diff from a patch string.

HangingIndent

<HangingIndent indent={4}>
Some very long string, which might wrap to multiple lines. Every
line after the first is indented.
</HangingIndent>

Indent every line after the first, useful when printing long stack frame lines.

Any ink Text properties are allowed.

Log

<Log includeTests test={tap} config={loadedConfig} />

Creates an ink <Static /> component containing console output, standard output, and (if includeTests is set) tests as they complete.

TestLogLine

The component used by <Log /> to show lines for each test as it completes.

ConsoleLogLine

The component used by <Log /> to show console output in the runner process.

StdioLogLine

The component used by <Log /> to show stdio output from child test processes.

ResultDetailList

<ResultDetailList
test={tap}
filter={t =>
!!t.counts.fail ||
!!t.counts.skip ||
!!t.counts.todo ||
!t.parser.ok
}
Banner={
<Box>
<Text>tests complete</Text>
</Box>
}
/>

When the test suite is completed, this prints the Banner if provided, and then the detailed results of all tests that pass the filter.

By default, passing tests are excluded from this report.

ResultDetails

<ResultDetails result={result} />

Print detailed information about a test point's diagnostics.

Runs

<Runs test={tap} />

Print a line for each test in progress, removing the line when it completes.

Source

<Source source={result.diag.source} at={result.diag.at} />

Pass in a test result.diag that has a source and callsite, and it'll return a prettied up source line with the callsite highlighted.

Stack

<Stack stack={stackString} />

Print a stack string nicely.

Long lines are given a hanging indent, and local filenames are highlighted.

SuiteSummary

<SuiteSummary test={tap} />

The 10 pass 3 fail 2 skip of 18 complete lines at the bottom of the test run.

Also prints Bailout! and Timeout messages.

TestBadge

<TestBadge test={subtest} />

The PASS, FAIL, etc. badges for a subtest.

TestResultsList

<TestResultsList test={subtest} details />

Show the list of results for a completed test. (Shows nothing if the test is not yet complete.)

details is set in the display in the final test summary, false when used in the log.

TestSummary

<TestSummary test={subtest} details omitPassing />

Show the summary for a completed test with its test badge, result details, and so on.

The details flag will cause it to print the full diagnostic output for failing test points. It is set false when printing in the log, true when printing in the final test results report.

TimedOut

<TimedOut test={tap} />

Print a bold red Timeout message when the suite times out.

@tapjs/reporter/hooks API

Hook functions that can be used in components providing helpful test information that updates at the appropriate times.

useAssertTotals(test: TestBase)

An up to date test.assertTotals

useBailedOut(test: Base)

true or the bailout reason if/when the test bails out. false otherwise.

useCleanup(effect: CleanupEffect, deps: any[])

The CleanupEffect type is a function that may take an array of cleanup methods as its first argument, and a doCleanup function as its second, and can optionally return a cleanup function as well.

By pushing onto the array, or returning a cleanup function of its own, the effect will be properly disposed as needed.

Useful in cases where you need to listen to multiple events, and clean them all up at the appropriate time.

Example:

import { useCleanup } from '@tapjs/reporter/hooks'
import { listenCleanup } from '@tapjs/reporter/utils'
const useMyHook = emitter => {
const [firsts, updateFirsts] = useState([])
const [seconds, updateSeconds] = useState([])
useCleanup((list, doCleanup) => {
// these event handlers will be cleaned up properly now
list.push(
listenCleanup(emitter, 'first', f =>
updateFirsts(firsts.concat([f]))
)
)
list.push(
listenCleanup(emitter, 'second', f =>
updateSeconds(seconds.concat([f]))
)
)
}, emitter)

return [firsts, seconds]
}

useComments(test: Base) => string[]

Returns a list of the comments made by the test.

useCountsLists(test: Base) => [Counts, Lists]

Up to date t.counts and t.lists properties.

useIsDone(test: Base)

True if the test is done, false otherwise.

useLog(test: TestBase, config: LoadedConfig, includeTests: boolean)

Returns an array of LogEntry items describing each entry in the log.

useSubtests(test: TestBase, which: 'active'|'finished'|'all') => Base[]

Return an array of all subtests meeting the which criteria.

  • active Tests that have started, but not completed.
  • finished Tests that have completed.
  • all All of the above.

useSuiteTotals(test: Base) => Counts

Return a Counts object describing the suites in the test run.

useTestTime(test: Base, interval: MILLISECONDS = 247) => number

The time this test has taken to complete, updated every interval milliseconds. 247 chosen as a default because it's fast and un-round enough to feel organic, without taxing the system with excessive time checks.

useTimedOut(t: Base): undefined | Extra

If the test has not timed out, returns undefined.

Otherwise, returns the Extra object describing the timeout failure. (Typically, extra.signal is the thing to care about.)

@tapjs/reporter/utils API

Some helpful utilities that are useful to have when creating reports.

assertName(r: Result, t: Base)

Returns the appropriate full result name, including the test name, without repeating it.

listenCleanup(e: EventEmitter, ev: string, fn: Function) => cleanupMethod

Add the function as an event listener, returning a function that will remove the listener, for use with useEffect and useLayoutEffect hooks.

ms(n: number)

A slightly more granular form of the ms module from npm.

Very small float values are printed in ┬Ás, and only 3 digits of precision are ever shown.

Index

Modules

Generated using TypeDoc