Question

We are writing a proxy generator using CodeDom and it appears that generic types in a recursive constraint are not being generated.

The code in question should just pass the constraint through as it is:

    void AddGenericConstraints(CodeTypeDeclaration generatedType, Type type)
    {
        var genericTypes = type.GetGenericArguments();

        foreach (var genericType in genericTypes)
        {
            var codeTypeParameter = new CodeTypeParameter(genericType.Name);
            if (genericType.IsGenericParameter)
            {
                // Get the constraints if the constraint is of user defined type
                var genericParameterConstraints = genericType.GetGenericParameterConstraints();
                foreach (var constraint in genericParameterConstraints)
                {
                    if (!string.Equals(constraint.Name, "ValueType"))
                    {
                        codeTypeParameter.Constraints.Add(constraint);
                    }
                }
            }

            generatedType.TypeParameters.Add(codeTypeParameter);
        }

But the input:

interface ISomething<T, out TSelf> where TSelf : ISomething<T, TSelf>
{
}

Produces the output (which does not compile):

interface ISomething<T, TSelf> where TSelf : ISomething<, >
{
}
Was it helpful?

Solution

For the reasons unknown, Add method doesn't use type parameter name then it's passed as a Type type, but it will generate them from a string. Apparently difference is in the CodeTypeReference class constructor (which is ultimate item type in Constraints collection). So

codeTypeParameter.Constraints.Add(constraint.ToString());

should give you an expected result.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top