Guides

Transients

Build an entity and return it, without saving it.

Inputs the code under test should create

When you test an insert, saving the input during setup would do the work the test is supposed to exercise. You still want the blueprint's valid defaults, though. Mark the entity transient to build and return it while excluding it from Biome's save list.

await TestBiome
    .Start(_db, out _)
    .AddOne(
        Blueprints.PendingInvitation,
        out var invitation,
        i => i.InvitedEmail = "new@example.test"
    )
    .Transient() // put it right after the step it marks
    .BuildAsync();
// act: await invitations.CreateAsync(invitation);

Two ways to mark one

FormScopeUse
.Transient() on the builderThe most recent Add stepOne test needs an unsaved input.
bp.AsTransient() on a blueprintEvery use of that blueprintThe entity is always an input.
Blueprints.cs
// Request DTOs can be built alongside stored
// entities; transient is a blueprint variant.
internal static readonly ChildBlueprint<
    CommerceSeed,
    Order,
    CheckoutInput
> Checkout = Blueprint
    .ChildOf<CommerceSeed, Order, CheckoutInput>(
        (order, _) => new() { Order = order }
    )
    .Derive(i => i.Reference, (i, _) => i.Order.Reference)
    .AsTransient();
Builders share a session, and .Transient() marks that session's most recent Add step. Place it immediately after the intended step so its scope is clear, even if you keep an earlier builder in a variable.

Transient entities are still inspectable: biome.All<T>() includes them, and out variables hold them. A transient aggregate excludes all of its parts from the save.

CommerceTests.cs
await biome
    .AddCustomers(out var customers, 2)
    .AddOrders(out var orders, 3)
    .AddLineItems(out var lines, 4)
    // Jump back to orders: checkout inputs are siblings
    // of lines, not children of the last step.
    .Under(orders)
    .AddCheckoutInputs(out var inputs, 1) // AsTransient lives on the blueprint
    .BuildAsync();
// biome.All<CheckoutInput>().Count == 6, but the store never receives them
Excluding a row from Biome's save list does not stop EF Core from discovering it through a saved row's navigation. If the input must stay unsaved, remove that reference or make the referencing row transient too.