Header menu logo testify

Global Configuration

This page is about the suite-wide defaults that Testify uses when individual calls do not override them.

Conceptually, this is the part of the DSL that shapes the environment around checks rather than the checks themselves.

The main entry points are:

Why Global Configuration Exists

Global configuration is useful when you want one stable default setup for a whole test suite:

This keeps ordinary Assert and Check calls small while still letting the suite behave consistently.

The Core API

Install a suite-wide default

Testify.configure (
    TestifyConfig.defaults
    |> TestifyConfig.withHintPacks BuiltInHintPacks.beginner
    |> TestifyConfig.addCheckConfigTransformer CheckConfig.addMiniArbs
)

Inspect the current configuration

let active = Testify.currentConfiguration()

Reset back to neutral defaults

Testify.resetConfiguration()

What TestifyConfig Controls

TestifyConfig is the global container for:

Useful helpers include:

Precedence: Local Beats Global

Use this rule:

That means:

Global config is for broad suite behavior, not for replacing precise local control.

Good Default Setup

This is a good “make the whole suite friendlier” setup:

let suiteDefaults =
    TestifyConfig.defaults
    |> TestifyConfig.withHintPacks BuiltInHintPacks.beginner
    |> TestifyConfig.addCheckConfigTransformer CheckConfig.addMiniArbs

Testify.configure suiteDefaults

This does three useful things:

Report Formatting Defaults

Global report formatting is a good fit for:

Example:

let reportingDefaults =
    TestifyConfig.defaults
    |> TestifyConfig.withOutputFormat OutputFormat.Json

Testify.configure reportingDefaults

Hint Defaults

Global hints are often better than per-test hints because they act like teaching rules for the whole suite.

Example:

let configWithHints =
    TestifyConfig.defaults
    |> TestifyConfig.withHintPacks BuiltInHintPacks.beginner

Testify.configure configWithHints

If you need domain-specific hints too:

let domainRule =
    TestifyHintRule.create "Course.RecursionMissing" (fun report ->
        if report.Actual |> Option.exists (fun text -> text.Contains "while") then
            Some "This task may expect a recursive solution rather than an imperative loop."
        else
            None)

let domainPack =
    TestifyHintPack.create "course" [ domainRule ]

Testify.configure (
    TestifyConfig.defaults
    |> TestifyConfig.withHintPacks (BuiltInHintPacks.beginner @ [ domainPack ])
)

When To Prefer Local Overrides

Prefer local runner arguments when:

Prefer global configuration when:

Relationship To Local Property Configuration

This page is about suite-wide defaults.

For per-check shaping of property runs with CheckConfig, Arbitraries, Generators, and resultBy / shouldBy, continue with Configuration, Arbitraries, and Generators.

val active: obj
val suiteDefaults: obj
val reportingDefaults: obj
val configWithHints: obj
val domainRule: obj
module Option from Microsoft.FSharp.Core
val exists: predicate: ('T -> bool) -> option: 'T option -> bool
union case Option.Some: Value: 'T -> Option<'T>
union case Option.None: Option<'T>
val domainPack: obj

Type something to start searching.