Skip to content

Smartass Assertion Functions

Smartass is an npm package that provides type-narrowing assertion functions for TypeScript projects.

Terminal window
npm install -D @kensio/smartass

See TypeScript assertion functions / assertion signatures

The fluent expect().toBe() interface in Jest and Vitest is readable, but is unable to provide type information to TypeScript and IntelliSense.

This library provides assertion functions with assertion signatures so that you can benefit from the extra type information.

import { assertNonNullable } from "@kensio/smartass";
const user: { name: string } | undefined = getUser();
assertNonNullable(user);
// TypeScript now knows user is neither null nor undefined,
// so no need for ? or ! operators.
const userName = user.name;
import { assertOneOf } from "@kensio/smartass";
const status = getStatus();
assertOneOf(status, ["pending", "active", "completed"]);
// TypeScript now knows status is of type 'pending' | 'active' | 'completed'

As well as the standalone assertion functions, you can also use type narrowing matcher functions to compose an object structure.

import {
assertObjectMatches,
arrayIncluding,
oneOf,
stringOfLength,
} from "@kensio/smartass";
const user = getUser();
assertObjectMatches(user, {
role: oneOf(["admin", "editor", "viewer"]),
tags: arrayIncluding("beta"),
id: stringOfLength(8),
});
// TypeScript knows:
// user.role is 'admin' | 'editor' | 'viewer'
// user.tags is an array with at least one string element
// user.id is a string of length 8 with safe indexing

This applies the same type narrowing effect as the assertion functions but in a composable object structure.

The @kensio/smartass package also exports an optional ESLint flat config that discourages less specific assertion usage. For example:

assertIdentical(foo.length, 2);
// suggested improvement:
assertArrayLength(foo, 2);

You can use this in your ESLint config like this:

import { defineConfig } from "eslint/config";
import tseslint from "typescript-eslint";
import { smartassPreferSpecificAssertions } from "@kensio/smartass/eslint";
export default defineConfig(
...tseslint.configs.recommended,
...smartassPreferSpecificAssertions,
);