TUnit.Engine/Discovery/ConstructorHelper.cs:129, 148 detect required properties via string name comparison:
return properties.Any(p => p.GetCustomAttributes().Any(a => a.GetType().Name == "RequiredAttribute"));
var isRequired = property.GetCustomAttribute<System.Runtime.CompilerServices.RequiredMemberAttribute>() != null ||
property.GetCustomAttributes().Any(a => a.GetType().Name == "RequiredAttribute");
Each check:
- Allocates
object[] from GetCustomAttributes()
- Allocates an
Any iterator + lambda
- Calls
GetType() per attribute, then string-compares .Name
The "older approach" RequiredAttribute mentioned in the comment likely refers to System.ComponentModel.DataAnnotations.RequiredAttribute (or a TUnit one). Use a real type check:
foreach (var attr in property.GetCustomAttributes())
{
if (attr is System.ComponentModel.DataAnnotations.RequiredAttribute) return true;
}
(Or whichever RequiredAttribute is meant — confirm with git blame.)
Why hot: Per property per type during reflection-mode construction. Compounds with the GetCustomAttributes() allocation noted in the sibling issue.
TFM: No gating.
TUnit.Engine/Discovery/ConstructorHelper.cs:129, 148detect required properties via string name comparison:Each check:
object[]fromGetCustomAttributes()Anyiterator + lambdaGetType()per attribute, then string-compares.NameThe "older approach"
RequiredAttributementioned in the comment likely refers toSystem.ComponentModel.DataAnnotations.RequiredAttribute(or a TUnit one). Use a real type check:(Or whichever
RequiredAttributeis meant — confirm withgit blame.)Why hot: Per property per type during reflection-mode construction. Compounds with the
GetCustomAttributes()allocation noted in the sibling issue.TFM: No gating.