Skip to content

Generated property injection assigns dependencies to a copy of struct arguments #7609

Closed

Description

@thomhurst

Struct arguments with [ClassDataSource<T>] properties receive a null dependency when generated property metadata is used. The generated setter casts the boxed argument into a local struct copy and assigns the property on that copy, so tests never receive the injected value.

Reproduction

using TUnit.Core;

public class StructInjectionTests
{
    public static Func<Fixture> Row() => () => new Fixture();

    [Test, MethodDataSource(nameof(Row))]
    public void Test(Fixture fixture)
    {
        if (fixture.Dependency is null)
            throw new InvalidOperationException("Dependency was not injected");
    }

    public struct Fixture
    {
        [ClassDataSource<Dependency>]
        public Dependency? Dependency { get; set; }
    }
    public sealed class Dependency;
}

Expected and actual

The test should receive a fixture with a non-null dependency. PropertyInjectionSourceGenerator.GeneratePropertyMetadata emits var typedInstance = (Fixture)instance; typedInstance.Dependency = ..., leaving the original box unchanged. See the generated setter emission.

Environment

SDK 10.0.403, net10.0, macOS arm64. Observed while testing #7608: async initializer and event-receiver mutations on the retained box survive, while the generated property assignment does not. The existing MutableTuplePropertyInjectionTests explicitly replaces generated property metadata to exercise the reflection setter, so it does not cover this case.

Please make generated property setters mutate the original boxed struct and cover ordinary struct arguments as well as tuple elements.

Metadata

Metadata

Assignees

No one assigned

    Labels

    P2Medium: edge case, mode divergence, flaky test, or workaround existsbugSomething isn't workingin-progressWork is in progress

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions