SurrogateAttribute.Fody
0.6.3
See the version list below for details.
dotnet add package SurrogateAttribute.Fody --version 0.6.3
NuGet\Install-Package SurrogateAttribute.Fody -Version 0.6.3
<PackageReference Include="SurrogateAttribute.Fody" Version="0.6.3" />
<PackageVersion Include="SurrogateAttribute.Fody" Version="0.6.3" />
<PackageReference Include="SurrogateAttribute.Fody" />
paket add SurrogateAttribute.Fody --version 0.6.3
#r "nuget: SurrogateAttribute.Fody, 0.6.3"
#:package SurrogateAttribute.Fody@0.6.3
#addin nuget:?package=SurrogateAttribute.Fody&version=0.6.3
#tool nuget:?package=SurrogateAttribute.Fody&version=0.6.3
![]()
A Fody add-in that allows creating C# attributes composed of other attributes, thus making C#'s attributes a bit more useful.
Installation
Install Fody and SurrogateAttribute.Fody to each project in which you want to use surrogate attributes:
Install-Package Fody
Install-Package SurrogateAttribute.Fody
And make sure both dependencies have PrivateAssets="All" like so, because they are only needed during build:
<PackageReference Include="Fody" Version="???" PrivateAssets="All" />
<PackageReference Include="SurrogateAttribute.Fody" Version="???" PrivateAssets="All" />
A FodyWeavers.xml file will be added automatically to the project on rebuild. If not, create the file with the following content:
<Weavers>
<SurrogateAttribute />
</Weavers>
This includes SurrogateAttribute Fody add-in to the IL weaving process.
In case your project (most likely a library) has no surrogate attribute usages but has surrogate attribute implementations, you may want to install SurrogateAttribute.Core instead, which has the required types for implementing surrogate attributes but does not include Fody as a dependency:
Install-Package SurrogateAttribute.Core
See Samples for a working solution.
In a nutshell
Instead of having:
class Cat
{
[Required(ErrorMessageResourceType = typeof(Translations), ErrorMessageResourceName = nameof(Translations.NameRequired))]
[MinLength(3, ErrorMessageResourceType = typeof(Translations), ErrorMessageResourceName = nameof(Translations.NameBadLength))]
[MaxLength(10, ErrorMessageResourceType = typeof(Translations), ErrorMessageResourceName = nameof(Translations.NameBadLength))]
[DisplayAttribute(ResourceType = typeof(Translations), Name = nameof(Translations.CatName))]
public string Name { get; set; }
}
you can create attributes that implement ISurrogateAttribute and have reusable abstractions suitable to your requirements, e.g.
[AttributeUsage(AttributeTargets.Property)]
class RequiredWithLengthAttribute : Attribute, ISurrogateAttribute
{
[PropertyDefaultValue(1)]
public int MinLength { get; set; }
[PropertyDefaultValue(10)]
public int MaxLength { get; set; }
[PropertyDefaultValue(typeof(Translations))]
Type TranslationResourceType { get; }
Attribute[] ISurrogateAttribute.TargetAttributes => [
new RequiredAttribute { ErrorMessageResourceType = TranslationResourceType, ErrorMessageResourceName = nameof(Translations.NameRequired) },
new MinLengthAttribute(MinLength) { ErrorMessageResourceType = TranslationResourceType, ErrorMessageResourceName = nameof(Translations.NameBadLength) },
new MaxLengthAttribute(MaxLength) { ErrorMessageResourceType = TranslationResourceType, ErrorMessageResourceName = nameof(Translations.NameBadLength) },
];
}
[AttributeUsage(AttributeTargets.Property)]
class TranslationAttribute(string translationKey) : Attribute, ISurrogateAttribute
{
Attribute[] ISurrogateAttribute.TargetAttributes => [
new DisplayAttribute { ResourceType = typeof(Translations), Name = translationKey }
];
}
so Cat can be simplified:
class Cat
{
[RequiredWithLength(MinLength = 3)]
[Translation(nameof(Translations.CatName))]
public string Name { get; set; }
}
Usages of attributes that implement ISurrogateAttribute are replaced by their corresponding TargetAttributes and then removed from the assembly at build time using IL weaving.
Supported features
TODO
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net5.0 was computed. net5.0-windows was computed. net6.0 was computed. net6.0-android was computed. net6.0-ios was computed. net6.0-maccatalyst was computed. net6.0-macos was computed. net6.0-tvos was computed. net6.0-windows was computed. net7.0 was computed. net7.0-android was computed. net7.0-ios was computed. net7.0-maccatalyst was computed. net7.0-macos was computed. net7.0-tvos was computed. net7.0-windows was computed. net8.0 was computed. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 was computed. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 was computed. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
| .NET Core | netcoreapp2.0 was computed. netcoreapp2.1 was computed. netcoreapp2.2 was computed. netcoreapp3.0 was computed. netcoreapp3.1 was computed. |
| .NET Standard | netstandard2.0 is compatible. netstandard2.1 is compatible. |
| .NET Framework | net461 is compatible. net462 was computed. net463 was computed. net47 was computed. net471 was computed. net472 was computed. net48 was computed. net481 was computed. |
| MonoAndroid | monoandroid was computed. |
| MonoMac | monomac was computed. |
| MonoTouch | monotouch was computed. |
| Tizen | tizen40 was computed. tizen60 was computed. |
| Xamarin.iOS | xamarinios was computed. |
| Xamarin.Mac | xamarinmac was computed. |
| Xamarin.TVOS | xamarintvos was computed. |
| Xamarin.WatchOS | xamarinwatchos was computed. |
-
.NETFramework 4.6.1
- Fody (>= 6.8.1)
- SurrogateAttribute.Core (>= 0.6.3)
-
.NETStandard 2.0
- Fody (>= 6.8.1)
- SurrogateAttribute.Core (>= 0.6.3)
-
.NETStandard 2.1
- Fody (>= 6.8.1)
- SurrogateAttribute.Core (>= 0.6.3)
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.