andrewlock / StronglyTypedId

A Rosyln-powered generator for strongly-typed IDs
MIT License
1.56k stars 81 forks source link

Allow support for nested StrongleTypeIds #153

Open Moo-Juice opened 3 weeks ago

Moo-Juice commented 3 weeks ago

Really like this library and have began integrating it in to my engine. However, there's a part of my project I cannot use this library easily, and that's where the strongly typed Id could be used as a nested class.

Essentially, what i want to do is this:

public class Factory<T> where T : ISomeInterface
{
    [StronglyTypedId(generateJsonConverter: false, StronglyTypedIdBackingType.Guid)]
    public partial struct Handle { }
}

Is this sort of thing possible? If I need to make Factory<T> partial also, I'd not be against it.

andrewlock commented 2 weeks ago

Yes, this is supported in the latest version 🙂

https://github.com/andrewlock/StronglyTypedId/blob/1a9d82af1238b1d36a67dd8f0ee0414ca5757c75/test/StronglyTypedIds.Tests/StronglyTypedIdGeneratorTests.cs#L165

Moo-Juice commented 2 weeks ago

Hi there, it appears I am using the latest version. When I add the handle, I get 2 errors. This is the relevant generated section:

image

And the two errors:

error CS0101: The namespace 'Jigsaw.Memory' already contains a definition for 'Factory' error CS0416: 'Jigsaw.Memory.Factory<T>.Handle.HandleTypeConverter': an attribute argument cannot use type parameters

I am probably doing something obviously wrong. Thanks for you assistance! :)

Oh, and the original source:

image

andrewlock commented 2 weeks ago

Ah, add partial to your Factory<T> type 🙂

Moo-Juice commented 2 weeks ago

Thanks for your prompt response, but I still had this issue :)

[System.ComponentModel.TypeConverter(typeof(HandleTypeConverter))]

error CS0416: 'Jigsaw.Memory.Factory<T>.Handle.HandleTypeConverter': an attribute argument cannot use type parameters

image

Hope you're well :)

andrewlock commented 2 weeks ago

Yeah unfortunately, that's not valid c# to use that attribute, because the attribute is defined as a nested type, which means the full name has a generic type parameter in it, and you can't use that. Your only options are to remove the attribute or to not nest it in the generic unfortunately

Moo-Juice commented 2 weeks ago

Ok, understood! Do I need to remove it from the generated file, or is there an option I can use to to have it removed as part of the source generation? Have a good day :)

andrewlock commented 2 weeks ago

Unfortunately you will need to use a custom template to remove the attribute from the generated code. You can read about how to use the codefix provider to create a custom template in the README and you can read more about what you can do with them here. Hope that helps!