Esempio n. 1
0
        protected void AddConstructorAssignedField(
            TypeReferenceBuilder type,
            string fieldName,
            ClassBuilder classBuilder,
            ConstructorBuilder constructorBuilder,
            bool skipNullCheck = false)
        {
            var paramName = fieldName.TrimStart('_');

            classBuilder.AddField(
                FieldBuilder
                .New()
                .SetReadOnly()
                .SetName(fieldName)
                .SetType(type));

            var assignment = AssignmentBuilder
                             .New()
                             .SetLefthandSide(fieldName)
                             .SetRighthandSide(paramName);

            if (!skipNullCheck)
            {
                assignment.AssertNonNull();
            }

            constructorBuilder
            .AddCode(assignment)
            .AddParameter(paramName, b => b.SetType(type));
        }
Esempio n. 2
0
        protected override void Generate(
            CodeWriter writer,
            InputObjectTypeDescriptor namedTypeDescriptor,
            out string fileName)
        {
            fileName = namedTypeDescriptor.Name;
            ClassBuilder classBuilder = ClassBuilder.New()
                                        .SetName(fileName);

            foreach (var prop in namedTypeDescriptor.Properties)
            {
                TypeReferenceBuilder propTypeBuilder = prop.Type.ToBuilder();

                // Add Property to class
                PropertyBuilder propBuilder = PropertyBuilder
                                              .New()
                                              .MakeSettable()
                                              .SetName(prop.Name)
                                              .SetType(propTypeBuilder)
                                              .SetAccessModifier(AccessModifier.Public);
                classBuilder.AddProperty(propBuilder);
            }

            CodeFileBuilder
            .New()
            .SetNamespace(namedTypeDescriptor.RuntimeType.NamespaceWithoutGlobal)
            .AddType(classBuilder)
            .Build(writer);
        }
        public static TypeReferenceBuilder ToTypeReference(
            this ITypeDescriptor typeReferenceDescriptor,
            TypeReferenceBuilder?builder = null)
        {
            TypeReferenceBuilder actualBuilder = builder ?? TypeReferenceBuilder.New();

            if (typeReferenceDescriptor is NonNullTypeDescriptor n)
            {
                typeReferenceDescriptor = n.InnerType;
            }
            else
            {
                actualBuilder.SetIsNullable(true);
            }

            return(typeReferenceDescriptor switch
            {
                ListTypeDescriptor list =>
                ToTypeReference(list.InnerType, actualBuilder.SetListType()),

                EnumTypeDescriptor @enum =>
                actualBuilder.SetName(@enum.RuntimeType.ToString()),

                ILeafTypeDescriptor leaf =>
                actualBuilder.SetName(leaf.RuntimeType.ToString()),

                INamedTypeDescriptor named =>
                actualBuilder.SetName(named.RuntimeType.ToString()),

                _ => throw new ArgumentOutOfRangeException(nameof(typeReferenceDescriptor))
            });
        public static TypeReferenceBuilder ToEntityIdBuilder(
            this ITypeDescriptor typeDescriptor,
            TypeReferenceBuilder?builder = null,
            bool isNonNull = false)
        {
            TypeReferenceBuilder actualBuilder = builder ?? TypeReferenceBuilder.New();

            switch (typeDescriptor)
            {
            case ListTypeDescriptor listTypeDescriptor:
                actualBuilder.SetIsNullable(!isNonNull);
                actualBuilder.SetListType();
                ToEntityIdBuilder(
                    listTypeDescriptor.InnerType,
                    actualBuilder);
                break;

            case NamedTypeDescriptor namedTypeDescriptor:
                actualBuilder.SetIsNullable(!isNonNull);
                if (namedTypeDescriptor.IsLeafType() && !namedTypeDescriptor.IsEnum)
                {
                    actualBuilder.SetName(
                        $"{namedTypeDescriptor.Namespace}.{namedTypeDescriptor.Name}");
                }
                else if (namedTypeDescriptor.IsDataType())
                {
                    actualBuilder.SetName(
                        namedTypeDescriptor.Kind == TypeKind.ComplexDataType
                                ? $"global::{namedTypeDescriptor.Namespace}.State.I" +
                        DataTypeNameFromTypeName(
                            namedTypeDescriptor.ComplexDataTypeParent !)
                                : $"global::{namedTypeDescriptor.Namespace}.State." +
                        DataTypeNameFromTypeName(
                            namedTypeDescriptor.GraphQLTypeName !));
                }
                else if (namedTypeDescriptor.IsEntityType())
                {
                    actualBuilder.SetName(TypeNames.EntityId);
                }
                else
                {
                    actualBuilder.SetName(typeDescriptor.Name);
                }
                break;

            case NonNullTypeDescriptor nonNullTypeDescriptor:
                ToEntityIdBuilder(
                    nonNullTypeDescriptor.InnerType,
                    actualBuilder,
                    true);
                break;

            default:
                throw new ArgumentOutOfRangeException(nameof(typeDescriptor));
            }

            return(actualBuilder);
        }
Esempio n. 5
0
        private void AddBuildMethod(
            InterfaceTypeDescriptor resultNamedType,
            ClassBuilder classBuilder)
        {
            var responseParameterName = "response";

            var buildMethod = MethodBuilder
                              .New()
                              .SetAccessModifier(AccessModifier.Public)
                              .SetName("Build")
                              .SetReturnType(
                TypeReferenceBuilder.New()
                .SetName(TypeNames.IOperationResult)
                .AddGeneric(resultNamedType.RuntimeType.Name))
                              .AddParameter(
                ParameterBuilder.New()
                .SetType(
                    TypeReferenceBuilder.New()
                    .SetName(TypeNames.Response)
                    .AddGeneric(TypeNames.JsonDocument)
                    .SetName(TypeNames.Response))
                .SetName(responseParameterName));

            var concreteResultType =
                CreateResultInfoName(resultNamedType.ImplementedBy.First().RuntimeType.Name);

            buildMethod.AddCode(
                AssignmentBuilder.New()
                .SetLefthandSide(
                    $"({resultNamedType.RuntimeType.Name} Result, {concreteResultType} " +
                    "Info)? data")
                .SetRighthandSide("null"));

            buildMethod.AddEmptyLine();
            buildMethod.AddCode(
                IfBuilder.New()
                .SetCondition(
                    ConditionBuilder.New()
                    .Set("response.Body is not null")
                    .And("response.Body.RootElement.TryGetProperty(\"data\"," +
                         $" out {TypeNames.JsonElement} obj)"))
                .AddCode("data = BuildData(obj);"));

            buildMethod.AddEmptyLine();
            buildMethod.AddCode(
                MethodCallBuilder.New()
                .SetPrefix("return new ")
                .SetMethodName(
                    TypeNames.OperationResult.WithGeneric(resultNamedType.RuntimeType.Name))
                .AddArgument("data?.Result")
                .AddArgument("data?.Info")
                .AddArgument(_resultDataFactoryFieldName)
                .AddArgument("null"));

            classBuilder.AddMethod(buildMethod);
        }
Esempio n. 6
0
        /// <inheritdoc />
        public virtual void Describe(TypeReferenceBuilder builder)
        {
            switch (builder.Source)
            {
            case ValueTuple <Type, PropertyInfo> propertySource:
                DescribeFromPropertyInfo(builder, propertySource.Item2);
                break;

            case ValueTuple <Type, FieldInfo> fieldSource:
                DescribeFromFieldInfo(builder, fieldSource.Item2);
                break;

            case PropertyInfo propertyInfo:
                DescribeFromPropertyInfo(builder, propertyInfo);
                break;

            case FieldInfo fieldInfo:
                DescribeFromFieldInfo(builder, fieldInfo);
                break;

            case MethodInfo methodInfo:
                if (builder.SourceIndex == 0)
                {
                    if (methodInfo.ReturnParameter?.IsNonNullable() == true)
                    {
                        builder.IsNullable = false;
                    }
                }
                else
                {
                    if (methodInfo.ReturnParameter?.IsGenericArgumentNonNullable(builder.SourceIndex - 1) == true)
                    {
                        builder.IsNullable = false;
                    }
                }
                break;

            case ParameterInfo parameterInfo:
                if (builder.SourceIndex == 0)
                {
                    if (parameterInfo.IsNonNullable())
                    {
                        builder.IsNullable = false;
                    }
                }
                else
                {
                    if (parameterInfo.IsGenericArgumentNonNullable(builder.SourceIndex - 1))
                    {
                        builder.IsNullable = false;
                    }
                }
                break;
            }
        }
Esempio n. 7
0
        protected override void Generate(
            CodeWriter writer,
            OperationDescriptor operationDescriptor,
            out string fileName)
        {
            var(classBuilder, constructorBuilder) = CreateClassBuilder();

            fileName = operationDescriptor.Name;
            classBuilder.SetName(fileName);
            constructorBuilder.SetTypeName(fileName);

            var resultTypeReference =
                (INamedTypeDescriptor)operationDescriptor.ResultTypeReference.NamedType();

            AddConstructorAssignedField(
                TypeReferenceBuilder.New()
                .SetName(TypeNames.IOperationExecutor)
                .AddGeneric(resultTypeReference.RuntimeType.Name),
                OperationExecutorFieldName,
                classBuilder,
                constructorBuilder);

            var neededSerializers = operationDescriptor.Arguments
                                    .ToLookup(x => x.Type.Name)
                                    .Select(x => x.First())
                                    .ToDictionary(x => x.Type.Name);

            if (neededSerializers.Any())
            {
                constructorBuilder
                .AddParameter(
                    "serializerResolver",
                    x => x.SetType(TypeNames.ISerializerResolver));

                foreach (var property in neededSerializers.Values)
                {
                    if (property.Type.GetName().Value is { } name)
                    {
                        MethodCallBuilder call = MethodCallBuilder.New()
                                                 .SetMethodName("serializerResolver." +
                                                                nameof(ISerializerResolver.GetInputValueFormatter))
                                                 .AddArgument(name.AsStringToken() ?? "")
                                                 .SetPrefix($"{GetFieldName(name)}Formatter = ");

                        constructorBuilder.AddCode(call);
                    }
                    else
                    {
                        throw new InvalidOperationException(
                                  $"Serialized for property {operationDescriptor.Name}.{property.Name} " +
                                  $"could not be created. GraphQLTypeName was empty");
                    }
                }
        protected override void Generate(
            CodeWriter writer,
            ObjectTypeDescriptor descriptor,
            out string fileName,
            out string?path)
        {
            fileName = descriptor.RuntimeType.Name;
            path     = null;

            ClassBuilder classBuilder = ClassBuilder
                                        .New()
                                        .SetComment(descriptor.Description)
                                        .SetName(fileName)
                                        .AddEquality(fileName, descriptor.Properties);

            ConstructorBuilder constructorBuilder = classBuilder
                                                    .AddConstructor()
                                                    .SetTypeName(fileName);

            foreach (var prop in descriptor.Properties)
            {
                TypeReferenceBuilder propTypeBuilder = prop.Type.ToTypeReference();

                // Add Property to class
                classBuilder
                .AddProperty(prop.Name)
                .SetComment(prop.Description)
                .SetName(prop.Name)
                .SetType(propTypeBuilder)
                .SetPublic();

                // Add initialization of property to the constructor
                var paramName = GetParameterName(prop.Name);
                constructorBuilder
                .AddParameter(paramName, x => x.SetType(propTypeBuilder))
                .AddCode(AssignmentBuilder
                         .New()
                         .SetLefthandSide(
                             (prop.Name.Value is WellKnownNames.TypeName
                                ? "this."
                                : string.Empty) +
                             prop.Name)
                         .SetRighthandSide(paramName));
            }

            classBuilder.AddImplementsRange(descriptor.Implements.Select(x => x.Value));

            CodeFileBuilder
            .New()
            .SetNamespace(descriptor.RuntimeType.NamespaceWithoutGlobal)
            .AddType(classBuilder)
            .Build(writer);
        }
Esempio n. 9
0
        public void Describe(TypeReferenceBuilder builder)
        {
            switch (builder.Source)
            {
            case ReflectedJsonRpcMethod reflectedJsonRpcMethod:
                DescribeJsonRpcMethod(builder, reflectedJsonRpcMethod);
                break;

            case ReflectedJsonRpcParameter reflectedJsonRpcParameter:
                DescribeJsonRpcParameter(builder, reflectedJsonRpcParameter);
                break;
            }
        }
Esempio n. 10
0
 protected void AddConstructorAssignedField(
     string typename,
     string fieldName,
     ClassBuilder classBuilder,
     ConstructorBuilder constructorBuilder,
     bool skipNullCheck = false)
 {
     AddConstructorAssignedField(
         TypeReferenceBuilder.New().SetName(typename),
         fieldName,
         classBuilder,
         constructorBuilder,
         skipNullCheck);
 }
Esempio n. 11
0
        private DelegateInfo GetDelegateInfo(INamedTypeSymbol typeSymbol, SemanticModel semanticModel)
        {
            string        delegateType = "";
            TypeReference returnType   = null;

            bool isFunc = typeSymbol.Name == "Func";

            if (isFunc)
            {
                delegateType = "Func";
            }
            else
            {
                delegateType = "Action";
            }

            var typeParameters = new List <TypeReference>();

            if (typeSymbol.IsGenericType)
            {
                for (int i = 0; i < typeSymbol.TypeArguments.Count(); i++)
                {
                    var typeArgument  = typeSymbol.TypeArguments[i];
                    var typeReference = TypeReferenceGenerator.GenerateTypeReference(typeArgument, semanticModel, isInGenericContext: true);
                    typeParameters.Add(typeReference);
                    if (!(isFunc && i == 0))
                    {
                        delegateType += "T";
                    }
                }
                delegateType = TypeReferenceBuilder.BuildTypeReference(new string[] { "by.besmart.cross.delegates", delegateType },
                                                                       typeParameters);
            }
            else
            {
                delegateType = TypeReferenceBuilder.BuildTypeReference(new string[] { "by.besmart.cross.delegates", delegateType },
                                                                       new List <TypeReference>());
            }

            returnType = isFunc ? typeParameters.Last() : JavaTypeReferences.Void;
            return(new DelegateInfo
            {
                ReturnType = returnType,
                JavaDelegateType = delegateType,
                TypeParameters = typeParameters,
                IsFunc = isFunc
            });
        }
        public static TypeReferenceBuilder ToBuilder(
            this ITypeDescriptor typeReferenceDescriptor,
            string?nameOverride          = null,
            TypeReferenceBuilder?builder = null,
            bool isNonNull = false)
        {
            var actualBuilder = builder ?? TypeReferenceBuilder.New();

            switch (typeReferenceDescriptor)
            {
            case ListTypeDescriptor listTypeDescriptor:
                actualBuilder.SetIsNullable(!isNonNull);
                actualBuilder.SetListType();
                ToBuilder(
                    listTypeDescriptor.InnerType,
                    nameOverride,
                    actualBuilder);
                break;

            case NamedTypeDescriptor namedTypeDescriptor:
                actualBuilder.SetIsNullable(!isNonNull);
                if (namedTypeDescriptor.IsLeafType() && !namedTypeDescriptor.IsEnum)
                {
                    actualBuilder.SetName(
                        $"{namedTypeDescriptor.Namespace}." +
                        (nameOverride ?? namedTypeDescriptor.Name));
                }
                else
                {
                    actualBuilder.SetName(nameOverride ?? namedTypeDescriptor.Name);
                }
                break;

            case NonNullTypeDescriptor nonNullTypeDescriptor:
                ToBuilder(
                    nonNullTypeDescriptor.InnerType,
                    nameOverride,
                    actualBuilder,
                    true);
                break;

            default:
                throw new ArgumentOutOfRangeException(nameof(typeReferenceDescriptor));
            }

            return(actualBuilder);
        }
Esempio n. 13
0
 protected virtual void DescribeFromFieldInfo(TypeReferenceBuilder builder, FieldInfo fieldInfo)
 {
     if (builder.SourceIndex == 0)
     {
         if (fieldInfo.IsNonNullable())
         {
             builder.IsNullable = false;
         }
     }
     else
     {
         if (fieldInfo.IsGenericArgumentNonNullable(builder.SourceIndex - 1))
         {
             builder.IsNullable = false;
         }
     }
 }
Esempio n. 14
0
 protected virtual void DescribeJsonRpcParameter(TypeReferenceBuilder builder, ReflectedJsonRpcParameter reflectedJsonRpcParameter)
 {
     if (builder.SourceIndex == 0)
     {
         if (reflectedJsonRpcParameter.Parameter.IsNonNullable())
         {
             builder.IsNullable = false;
         }
     }
     else
     {
         if (reflectedJsonRpcParameter.Parameter.IsGenericArgumentNonNullable(builder.SourceIndex - 1))
         {
             builder.IsNullable = false;
         }
     }
 }
Esempio n. 15
0
 protected virtual void DescribeJsonRpcMethod(TypeReferenceBuilder builder, ReflectedJsonRpcMethod reflectedJsonRpcMethod)
 {
     if (builder.SourceIndex == 0)
     {
         if (reflectedJsonRpcMethod.Method.ReturnParameter?.IsNonNullable() == true)
         {
             builder.IsNullable = false;
         }
     }
     else
     {
         if (reflectedJsonRpcMethod.Method.ReturnParameter?.IsGenericArgumentNonNullable(builder.SourceIndex - 1) == true)
         {
             builder.IsNullable = false;
         }
     }
 }
Esempio n. 16
0
        protected override void Generate(
            CodeWriter writer,
            ObjectTypeDescriptor descriptor,
            out string fileName)
        {
            fileName = descriptor.RuntimeType.Name;
            ClassBuilder classBuilder = ClassBuilder
                                        .New()
                                        .SetName(fileName);

            ConstructorBuilder constructorBuilder = classBuilder
                                                    .AddConstructor()
                                                    .SetTypeName(fileName);

            foreach (var prop in descriptor.Properties)
            {
                TypeReferenceBuilder propTypeBuilder = prop.Type.ToBuilder();

                // Add Property to class
                classBuilder
                .AddProperty(prop.Name)
                .SetName(prop.Name)
                .SetType(propTypeBuilder)
                .SetPublic()
                .SetValue(prop.Type.IsNullableType() ? "default!" : null);

                // Add initialization of property to the constructor
                var paramName = GetParameterName(prop.Name);
                constructorBuilder
                .AddParameter(paramName, x => x.SetType(propTypeBuilder))
                .AddCode(AssignmentBuilder
                         .New()
                         .SetLefthandSide(prop.Name)
                         .SetRighthandSide(paramName));
            }

            classBuilder.AddImplementsRange(descriptor.Implements.Select(x => x.Value));

            CodeFileBuilder
            .New()
            .SetNamespace(descriptor.RuntimeType.NamespaceWithoutGlobal)
            .AddType(classBuilder)
            .Build(writer);
        }
        public TypeReference BuildDelegateReference(INamedTypeSymbol namedTypeSymbol, SemanticModel semanticModel)
        {
            var    fullyQualifiedPropertyTypeNameParts = SyntaxTreeHelper.GetFullyQualifiedNameParts(namedTypeSymbol);
            string name     = namedTypeSymbol.Name;
            bool   isAction = name == "Action";
            bool   isFunc   = name == "Func";

            if (namedTypeSymbol.IsGenericType)
            {
                var typeParameters = new List <TypeReference>();
                var args           = namedTypeSymbol.TypeArguments.ToList();
                for (int i = 0; i < args.Count; i++)
                {
                    var typeArgument  = args[i];
                    var typeReference = GenerateTypeReference(typeArgument, semanticModel, isInGenericContext: true);
                    typeParameters.Add(typeReference);
                    if (!(isFunc && i == 0))
                    {
                        name += "T";
                    }
                }
                string typeReferenceText = TypeReferenceBuilder
                                           .BuildTypeReference(new[] { "by.besmart.cross.delegates", name }, typeParameters);
                return(new TypeReference
                {
                    Text = typeReferenceText,
                    IsReferenceType = namedTypeSymbol.IsReferenceType,
                    IsGeneric = true
                });
            }
            string typeReferenceTextNonGeneric = TypeReferenceBuilder
                                                 .BuildTypeReference(new[] { "by.besmart.cross.delegates", name }, new List <TypeReference>());

            return(new TypeReference
            {
                Text = typeReferenceTextNonGeneric,
                IsReferenceType = namedTypeSymbol.IsReferenceType
            });
        }
Esempio n. 18
0
        protected override void Generate(ITypeDescriptor typeDescriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            ComplexTypeDescriptor complexTypeDescriptor =
                typeDescriptor as ComplexTypeDescriptor ??
                throw new InvalidOperationException(
                          "A result entity mapper can only be generated for complex types");

            var className = CreateResultInfoName(complexTypeDescriptor.RuntimeType.Name);

            fileName = className;
            path     = State;
            ns       = CreateStateNamespace(complexTypeDescriptor.RuntimeType.NamespaceWithoutGlobal);

            ClassBuilder classBuilder = ClassBuilder
                                        .New()
                                        .AddImplements(TypeNames.IOperationResultDataInfo)
                                        .SetName(fileName);

            ConstructorBuilder constructorBuilder = classBuilder
                                                    .AddConstructor()
                                                    .SetTypeName(complexTypeDescriptor.RuntimeType.Name);

            foreach (var prop in complexTypeDescriptor.Properties)
            {
                TypeReferenceBuilder propTypeBuilder = prop.Type.ToStateTypeReference();

                // Add Property to class
                classBuilder
                .AddProperty(prop.Name)
                .SetComment(prop.Description)
                .SetType(propTypeBuilder)
                .SetPublic();

                // Add initialization of property to the constructor
                var paramName = GetParameterName(prop.Name);
                constructorBuilder.AddParameter(paramName).SetType(propTypeBuilder);
                constructorBuilder.AddCode(
                    AssignmentBuilder
                    .New()
                    .SetLefthandSide(prop.Name)
                    .SetRighthandSide(paramName));
            }

            classBuilder
            .AddProperty("EntityIds")
            .SetType(TypeNames.IReadOnlyCollection.WithGeneric(TypeNames.EntityId))
            .AsLambda(settings.IsStoreEnabled()
                    ? CodeInlineBuilder.From(_entityIds)
                    : MethodCallBuilder.Inline()
                      .SetMethodName(TypeNames.Array, "Empty")
                      .AddGeneric(TypeNames.EntityId));

            classBuilder
            .AddProperty("Version")
            .SetType(TypeNames.UInt64)
            .AsLambda(settings.IsStoreEnabled() ? _version : "0");

            if (settings.IsStoreEnabled())
            {
                AddConstructorAssignedField(
                    TypeNames.IReadOnlyCollection.WithGeneric(TypeNames.EntityId),
                    _entityIds,
                    entityIds,
                    classBuilder,
                    constructorBuilder);

                AddConstructorAssignedField(
                    TypeNames.UInt64,
                    _version,
                    version,
                    classBuilder,
                    constructorBuilder,
                    true);
            }

            // WithVersion
            classBuilder
            .AddMethod("WithVersion")
            .SetAccessModifier(AccessModifier.Public)
            .SetReturnType(TypeNames.IOperationResultDataInfo)
            .AddParameter(version, x => x.SetType(TypeNames.UInt64))
            .AddCode(MethodCallBuilder
                     .New()
                     .SetReturn()
                     .SetNew()
                     .SetMethodName(className)
                     .AddArgumentRange(
                         complexTypeDescriptor.Properties.Select(x => x.Name.Value))
                     .If(settings.IsStoreEnabled(),
                         x => x.AddArgument(_entityIds).AddArgument(version)));

            classBuilder.Build(writer);
        }
Esempio n. 19
0
        protected override void Generate(
            CodeWriter writer,
            ResultBuilderDescriptor resultBuilderDescriptor,
            out string fileName)
        {
            var processed            = new HashSet <string>();
            var resultTypeDescriptor =
                resultBuilderDescriptor.ResultNamedType as InterfaceTypeDescriptor
                ?? throw new InvalidOperationException(
                          "A result type can only be generated for complex types");

            var(classBuilder, constructorBuilder) = CreateClassBuilder();

            fileName = resultBuilderDescriptor.RuntimeType.Name;
            classBuilder.SetName(fileName);

            constructorBuilder.SetTypeName(fileName);

            classBuilder.AddImplements(
                $"{TypeNames.IOperationResultBuilder}<{TypeNames.JsonDocument}," +
                $" {resultTypeDescriptor.RuntimeType.Name}>");

            AddConstructorAssignedField(
                TypeNames.IEntityStore,
                _entityStoreFieldName,
                classBuilder,
                constructorBuilder);

            AddConstructorAssignedField(
                TypeReferenceBuilder.New()
                .SetName(TypeNames.Func)
                .AddGeneric(TypeNames.JsonElement)
                .AddGeneric(TypeNames.EntityId),
                _extractIdFieldName,
                classBuilder,
                constructorBuilder);

            AddConstructorAssignedField(
                TypeReferenceBuilder.New()
                .SetName(TypeNames.IOperationResultDataFactory)
                .AddGeneric(resultTypeDescriptor.RuntimeType.Name),
                _resultDataFactoryFieldName,
                classBuilder,
                constructorBuilder);

            constructorBuilder.AddParameter(
                ParameterBuilder.New()
                .SetName(_serializerResolverParamName)
                .SetType(TypeNames.ISerializerResolver));

            IEnumerable <ValueParserDescriptor> valueParsers = resultBuilderDescriptor
                                                               .ValueParsers
                                                               .GroupBy(t => t.Name)
                                                               .Select(t => t.First());

            foreach (ValueParserDescriptor valueParser in valueParsers)
            {
                var parserFieldName = $"{GetFieldName(valueParser.Name)}Parser";

                classBuilder.AddField(
                    FieldBuilder.New()
                    .SetReadOnly()
                    .SetName(parserFieldName)
                    .SetType(
                        TypeReferenceBuilder.New()
                        .SetName(TypeNames.ILeafValueParser)
                        .AddGeneric(valueParser.SerializedType.ToString())
                        .AddGeneric(valueParser.RuntimeType.ToString())));

                constructorBuilder.AddCode(
                    AssignmentBuilder.New()
                    .SetAssertNonNull()
                    .SetAssertException(
                        TypeNames.ArgumentException +
                        $"(\"No serializer for type `{valueParser.Name}` found.\")")
                    .SetLefthandSide(parserFieldName)
                    .SetRighthandSide(
                        MethodCallBuilder.New()
                        .SetPrefix(_serializerResolverParamName + ".")
                        .SetDetermineStatement(false)
                        .SetMethodName(
                            $"GetLeafValueParser<{valueParser.SerializedType}, " +
                            $"{valueParser.RuntimeType}>")
                        .AddArgument($"\"{valueParser.Name}\"")));
            }

            AddBuildMethod(
                resultTypeDescriptor,
                classBuilder);

            AddBuildDataMethod(
                resultTypeDescriptor,
                classBuilder);

            AddRequiredDeserializeMethods(
                resultBuilderDescriptor.ResultNamedType,
                classBuilder,
                processed);

            CodeFileBuilder.New()
            .SetNamespace(
                resultBuilderDescriptor.ResultNamedType.RuntimeType.NamespaceWithoutGlobal)
            .AddType(classBuilder)
            .Build(writer);
        }
Esempio n. 20
0
 public static void Describe(this IList <ITypeReferenceDescriptor> descriptors, TypeReferenceBuilder builder)
 {
     for (var i = 0; i < descriptors.Count; i++)
     {
         descriptors[i].Describe(builder);
     }
 }
        private void AddBuildMethod(
            InterfaceTypeDescriptor resultNamedType,
            ClassBuilder classBuilder)
        {
            var buildMethod = classBuilder
                              .AddMethod()
                              .SetAccessModifier(AccessModifier.Public)
                              .SetName("Build")
                              .SetReturnType(
                TypeReferenceBuilder
                .New()
                .SetName(TypeNames.IOperationResult)
                .AddGeneric(resultNamedType.RuntimeType.Name));

            buildMethod
            .AddParameter(_response)
            .SetType(TypeNames.Response.WithGeneric(TypeNames.JsonDocument));

            var concreteResultType =
                CreateResultInfoName(resultNamedType.ImplementedBy.First().RuntimeType.Name);

            buildMethod.AddCode(
                AssignmentBuilder
                .New()
                .SetLefthandSide(
                    $"({resultNamedType.RuntimeType.Name} Result, {concreteResultType} " +
                    "Info)? data")
                .SetRighthandSide("null"));
            buildMethod.AddCode(
                AssignmentBuilder
                .New()
                .SetLefthandSide(
                    TypeNames.IReadOnlyList
                    .WithGeneric(TypeNames.IClientError)
                    .MakeNullable() + " errors")
                .SetRighthandSide("null"));

            buildMethod.AddEmptyLine();
            buildMethod.AddCode(
                TryCatchBuilder
                .New()
                .AddTryCode(
                    IfBuilder
                    .New()
                    .SetCondition(
                        ConditionBuilder
                        .New()
                        .Set("response.Body != null"))
                    .AddCode(
                        IfBuilder
                        .New()
                        .SetCondition(
                            ConditionBuilder
                            .New()
                            .Set("response.Body.RootElement.TryGetProperty(" +
                                 $"\"data\", out {TypeNames.JsonElement} " +
                                 "dataElement) && dataElement.ValueKind == " +
                                 $"{TypeNames.JsonValueKind}.Object"))
                        .AddCode("data = BuildData(dataElement);"))
                    .AddCode(
                        IfBuilder
                        .New()
                        .SetCondition(
                            ConditionBuilder
                            .New()
                            .Set(
                                "response.Body.RootElement.TryGetProperty(" +
                                $"\"errors\", out {TypeNames.JsonElement} " +
                                "errorsElement)"))
                        .AddCode($"errors = {TypeNames.ParseError}(errorsElement);")))
                .AddCatchBlock(
                    CatchBlockBuilder
                    .New()
                    .SetExceptionVariable("ex")
                    .AddCode(
                        AssignmentBuilder.New()
                        .SetLefthandSide("errors")
                        .SetRighthandSide(
                            ArrayBuilder.New()
                            .SetDetermineStatement(false)
                            .SetType(TypeNames.IClientError)
                            .AddAssigment(
                                MethodCallBuilder
                                .Inline()
                                .SetNew()
                                .SetMethodName(TypeNames.ClientError)
                                .AddArgument("ex.Message")
                                .AddArgument("exception: ex"))))));

            buildMethod.AddEmptyLine();
            buildMethod.AddCode(
                MethodCallBuilder
                .New()
                .SetReturn()
                .SetNew()
                .SetMethodName(TypeNames.OperationResult)
                .AddGeneric(resultNamedType.RuntimeType.Name)
                .AddArgument("data?.Result")
                .AddArgument("data?.Info")
                .AddArgument(_resultDataFactory)
                .AddArgument("errors"));
        }
Esempio n. 22
0
        protected override void Generate(
            CodeWriter writer,
            DataTypeDescriptor descriptor,
            out string fileName)
        {
            fileName = descriptor.RuntimeType.Name;
            AbstractTypeBuilder typeBuilder;
            ConstructorBuilder? constructorBuilder = null;

            if (descriptor.IsInterface)
            {
                typeBuilder = InterfaceBuilder
                              .New()
                              .SetName(fileName);

                typeBuilder
                .AddProperty(__typename)
                .SetType(TypeNames.String);
            }
            else
            {
                ClassBuilder classBuilder = ClassBuilder
                                            .New()
                                            .SetName(fileName);

                typeBuilder = classBuilder;

                classBuilder
                .AddProperty(__typename)
                .SetPublic()
                .SetType(TypeNames.String);

                constructorBuilder = classBuilder
                                     .AddConstructor()
                                     .SetTypeName(fileName);

                constructorBuilder
                .AddParameter(_typename)
                .SetType(TypeNames.String)
                .SetName(_typename);

                constructorBuilder
                .AddCode(
                    AssignmentBuilder
                    .New()
                    .SetLefthandSide(__typename)
                    .SetRighthandSide(_typename)
                    .AssertNonNull());
            }

            // Add Properties to class
            foreach (PropertyDescriptor property in descriptor.Properties)
            {
                TypeReferenceBuilder propertyType = property.Type.Kind switch
                {
                    TypeKind.LeafType => property.Type.ToBuilder(),
                    TypeKind.DataType => property.Type.ToBuilder(property.Type.Name),
                    TypeKind.EntityType => property.Type.ToEntityIdBuilder(),
                    _ => throw new ArgumentOutOfRangeException()
                };

                typeBuilder
                .AddProperty(property.Name)
                .SetType(propertyType)
                .SetPublic();

                var parameterName = GetParameterName(property.Name);

                constructorBuilder?
                .AddParameter(parameterName)
                .SetType(propertyType)
                .SetDefault("null");

                constructorBuilder?
                .AddCode(AssignmentBuilder
                         .New()
                         .SetLefthandSide(property.Name)
                         .SetRighthandSide(parameterName));
            }

            // implement interfaces
            typeBuilder.AddImplementsRange(descriptor.Implements.Select(CreateDataTypeName));

            CodeFileBuilder
            .New()
            .SetNamespace(descriptor.RuntimeType.NamespaceWithoutGlobal)
            .AddType(typeBuilder)
            .Build(writer);
        }
    }
        private void AddBuildMethod(
            InterfaceTypeDescriptor resultNamedType,
            ClassBuilder classBuilder)
        {
            var buildMethod = classBuilder
                              .AddMethod()
                              .SetAccessModifier(AccessModifier.Public)
                              .SetName("Build")
                              .SetReturnType(
                TypeReferenceBuilder
                .New()
                .SetName(TypeNames.IOperationResult)
                .AddGeneric(resultNamedType.RuntimeType.Name));

            buildMethod
            .AddParameter(_response)
            .SetType(TypeNames.Response.WithGeneric(TypeNames.JsonDocument));

            var concreteResultType =
                CreateResultInfoName(resultNamedType.ImplementedBy.First().RuntimeType.Name);

            // (IGetFooResult Result, GetFooResultInfo Info)? data = null;
            buildMethod.AddCode(
                AssignmentBuilder
                .New()
                .SetLefthandSide(
                    $"({resultNamedType.RuntimeType.Name} Result, {concreteResultType} " +
                    "Info)? data")
                .SetRighthandSide("null"));

            // IReadOnlyList<IClientError>? errors = null;
            buildMethod.AddCode(
                AssignmentBuilder
                .New()
                .SetLefthandSide(
                    TypeNames.IReadOnlyList
                    .WithGeneric(TypeNames.IClientError)
                    .MakeNullable() + " errors")
                .SetRighthandSide("null"));

            buildMethod.AddEmptyLine();



            buildMethod.AddEmptyLine();
            buildMethod.AddCode(
                IfBuilder.New()
                .SetCondition("response.Exception is null")
                .AddCode(CreateBuildDataSerialization())
                .AddElse(CreateDataError("response.Exception"))
                );

            buildMethod.AddEmptyLine();
            buildMethod.AddCode(
                MethodCallBuilder
                .New()
                .SetReturn()
                .SetNew()
                .SetMethodName(TypeNames.OperationResult)
                .AddGeneric(resultNamedType.RuntimeType.Name)
                .AddArgument("data?.Result")
                .AddArgument("data?.Info")
                .AddArgument(_resultDataFactory)
                .AddArgument("errors"));
        }
Esempio n. 24
0
        protected override void Generate(
            CodeWriter writer,
            ITypeDescriptor typeDescriptor,
            out string fileName)
        {
            ComplexTypeDescriptor complexTypeDescriptor =
                typeDescriptor as ComplexTypeDescriptor ??
                throw new InvalidOperationException(
                          "A result entity mapper can only be generated for complex types");

            var className = CreateResultInfoName(complexTypeDescriptor.RuntimeType.Name);

            fileName = className;

            ClassBuilder classBuilder = ClassBuilder
                                        .New()
                                        .AddImplements(TypeNames.IOperationResultDataInfo)
                                        .SetName(fileName);

            ConstructorBuilder constructorBuilder = classBuilder
                                                    .AddConstructor()
                                                    .SetTypeName(complexTypeDescriptor.RuntimeType.Name);

            foreach (var prop in complexTypeDescriptor.Properties)
            {
                TypeReferenceBuilder propTypeBuilder = prop.Type.ToEntityIdBuilder();

                // Add Property to class
                classBuilder
                .AddProperty(prop.Name)
                .SetType(propTypeBuilder)
                .SetPublic();

                // Add initialization of property to the constructor
                var paramName = GetParameterName(prop.Name);
                constructorBuilder.AddParameter(paramName).SetType(propTypeBuilder);
                constructorBuilder.AddCode(
                    AssignmentBuilder
                    .New()
                    .SetLefthandSide(prop.Name)
                    .SetRighthandSide(paramName));
            }

            classBuilder
            .AddProperty("EntityIds")
            .SetType(TypeNames.IReadOnlyCollection.WithGeneric(TypeNames.EntityId))
            .AsLambda(_entityIds);

            classBuilder
            .AddProperty("Version")
            .SetType(TypeNames.UInt64)
            .AsLambda(_version);

            AddConstructorAssignedField(
                TypeNames.IReadOnlyCollection.WithGeneric(TypeNames.EntityId),
                _entityIds,
                classBuilder,
                constructorBuilder);

            AddConstructorAssignedField(
                TypeNames.UInt64,
                _version,
                classBuilder,
                constructorBuilder,
                true);


            // WithVersion
            const string version = nameof(version);

            classBuilder
            .AddMethod("WithVersion")
            .SetAccessModifier(AccessModifier.Public)
            .SetReturnType(TypeNames.IOperationResultDataInfo)
            .AddParameter(version, x => x.SetType(TypeNames.UInt64))
            .AddCode(MethodCallBuilder
                     .New()
                     .SetReturn()
                     .SetNew()
                     .SetMethodName(className)
                     .AddArgumentRange(
                         complexTypeDescriptor.Properties.Select(x => x.Name.Value))
                     .AddArgument(_entityIds)
                     .AddArgument(version));

            CodeFileBuilder
            .New()
            .SetNamespace(complexTypeDescriptor.RuntimeType.NamespaceWithoutGlobal)
            .AddType(classBuilder)
            .Build(writer);
        }
        public TypeReference GenerateTypeReference(ITypeSymbol typeSymbol, SemanticModel semanticModel, bool isInGenericContext = false)
        {
            if (typeSymbol is ITypeParameterSymbol)
            {
                return(new TypeReference
                {
                    Text = GenericTypeReferenceBuilder.BuildReference(typeSymbol as ITypeParameterSymbol),
                    IsGeneric = true,
                    IsReferenceType = typeSymbol.IsReferenceType
                });
            }
            var    namedTypeSymbol    = (INamedTypeSymbol)typeSymbol;
            string fullyQualifiedName = SyntaxTreeHelper.GetFullyQualifiedName(namedTypeSymbol);
            var    fullyQualifiedPropertyTypeNameParts = SyntaxTreeHelper.GetFullyQualifiedNameParts(namedTypeSymbol);

            var typeParameters = new List <TypeReference>();

            if (namedTypeSymbol.IsGenericType)
            {
                foreach (var typeArgument in namedTypeSymbol.TypeArguments)
                {
                    var typeReference = GenerateTypeReference(typeArgument, semanticModel, isInGenericContext: true);
                    typeParameters.Add(typeReference);
                }
            }

            if (PredefinedTypes.IsPredefined(fullyQualifiedName))
            {
                return(new TypeReference
                {
                    Text = isInGenericContext ? PredefinedTypes.GetInGenericContext(fullyQualifiedName)
                                              : PredefinedTypes.Get(fullyQualifiedName),
                    IsPredefined = true,
                    IsReferenceType = typeSymbol.IsReferenceType
                });
            }
            if (IsCustomImplementedType(fullyQualifiedName))
            {
                if (namedTypeSymbol.IsGenericType)
                {
                }
                string typeReferenceText = "by.misharp." + (namedTypeSymbol.IsGenericType
                    ? TypeReferenceBuilder.BuildTypeReference(fullyQualifiedPropertyTypeNameParts, typeParameters)
                    : TypeReferenceBuilder.BuildTypeReference(fullyQualifiedPropertyTypeNameParts));
                return(new TypeReference
                {
                    Text = typeReferenceText,
                    IsReferenceType = typeSymbol.IsReferenceType
                });
            }
            if (IsDelegateType(namedTypeSymbol))
            {
                return(BuildDelegateReference(namedTypeSymbol, semanticModel));
            }

            if (namedTypeSymbol.IsGenericType)
            {
                string typeReferenceText = TypeReferenceBuilder.BuildTypeReference(fullyQualifiedPropertyTypeNameParts, typeParameters);
                return(new TypeReference
                {
                    Text = typeReferenceText,
                    IsReferenceType = typeSymbol.IsReferenceType
                });
            }
            else
            {
                string typeReferenceText = TypeReferenceBuilder.BuildTypeReference(fullyQualifiedPropertyTypeNameParts);

                return(new TypeReference
                {
                    Text = typeReferenceText,
                    IsReferenceType = typeSymbol.IsReferenceType
                });
            }
        }
Esempio n. 26
0
        protected override void Generate(
            CodeWriter writer,
            DataTypeDescriptor descriptor,
            out string fileName,
            out string?path)
        {
            fileName = descriptor.RuntimeType.Name;
            path     = State;

            AbstractTypeBuilder typeBuilder;
            ConstructorBuilder? constructorBuilder = null;

            if (descriptor.IsInterface)
            {
                typeBuilder = InterfaceBuilder
                              .New()
                              .SetComment(descriptor.Documentation)
                              .SetName(fileName);

                typeBuilder
                .AddProperty(WellKnownNames.TypeName)
                .SetType(TypeNames.String);
            }
            else
            {
                ClassBuilder classBuilder = ClassBuilder
                                            .New()
                                            .SetComment(descriptor.Documentation)
                                            .SetName(fileName);

                typeBuilder = classBuilder;

                classBuilder
                .AddProperty(WellKnownNames.TypeName)
                .SetPublic()
                .SetType(TypeNames.String);

                constructorBuilder = classBuilder
                                     .AddConstructor()
                                     .SetTypeName(fileName);

                constructorBuilder
                .AddParameter(WellKnownNames.TypeName)
                .SetType(TypeNames.String)
                .SetName(WellKnownNames.TypeName);

                constructorBuilder
                .AddCode(
                    AssignmentBuilder
                    .New()
                    .SetLefthandSide("this." + WellKnownNames.TypeName)
                    .SetRighthandSide(WellKnownNames.TypeName)
                    .AssertNonNull());
            }

            // Add Properties to class
            foreach (PropertyDescriptor property in descriptor.Properties)
            {
                if (property.Name.Value.EqualsOrdinal(WellKnownNames.TypeName))
                {
                    continue;
                }

                TypeReferenceBuilder propertyType = property.Type.ToStateTypeReference();

                typeBuilder
                .AddProperty(property.Name)
                .SetComment(property.Description)
                .SetType(propertyType)
                .SetPublic();

                var parameterName = GetParameterName(property.Name);

                constructorBuilder?
                .AddParameter(parameterName)
                .SetType(propertyType)
                .SetDefault("null");

                constructorBuilder?
                .AddCode(AssignmentBuilder
                         .New()
                         .SetLefthandSide(property.Name)
                         .SetRighthandSide(parameterName));
            }

            // implement interfaces
            typeBuilder.AddImplementsRange(descriptor.Implements.Select(CreateDataTypeName));

            CodeFileBuilder
            .New()
            .SetNamespace(descriptor.RuntimeType.NamespaceWithoutGlobal)
            .AddType(typeBuilder)
            .Build(writer);
        }
        protected override void Generate(
            CodeWriter writer,
            ResultBuilderDescriptor resultBuilderDescriptor, out string fileName)
        {
            var processed            = new HashSet <string>();
            var resultTypeDescriptor = resultBuilderDescriptor.ResultNamedType;

            var(classBuilder, constructorBuilder) = CreateClassBuilder();

            fileName = resultBuilderDescriptor.Name;
            classBuilder.SetName(fileName);

            constructorBuilder.SetTypeName(fileName);

            classBuilder.AddImplements(
                $"{TypeNames.IOperationResultBuilder}<{TypeNames.JsonDocument}," +
                $" {resultTypeDescriptor.Name}>");

            AddConstructorAssignedField(
                TypeNames.IEntityStore,
                _entityStoreFieldName,
                classBuilder,
                constructorBuilder);

            AddConstructorAssignedField(
                TypeReferenceBuilder.New()
                .SetName(TypeNames.Func)
                .AddGeneric(TypeNames.JsonElement)
                .AddGeneric(TypeNames.EntityId),
                _extractIdFieldName,
                classBuilder,
                constructorBuilder);

            AddConstructorAssignedField(
                TypeReferenceBuilder.New()
                .SetName(TypeNames.IOperationResultDataFactory)
                .AddGeneric(resultTypeDescriptor.Name),
                _resultDataFactoryFieldName,
                classBuilder,
                constructorBuilder);

            constructorBuilder.AddParameter(
                ParameterBuilder.New()
                .SetName(_serializerResolverParamName)
                .SetType(TypeNames.ISerializerResolver));

            IEnumerable <ValueParserDescriptor> neededSerializers = resultBuilderDescriptor
                                                                    .ValueParsers
                                                                    .ToLookup(x => x.RuntimeType)
                                                                    .Select(x => x.First());

            foreach (ValueParserDescriptor valueParser in neededSerializers)
            {
                var parserFieldName =
                    $"_{valueParser.RuntimeType.Split('.').Last().WithLowerFirstChar()}Parser";
                classBuilder.AddField(
                    FieldBuilder.New().SetName(parserFieldName).SetType(
                        TypeReferenceBuilder.New()
                        .SetName(TypeNames.ILeafValueParser)
                        .AddGeneric(valueParser.SerializedType)
                        .AddGeneric(valueParser.RuntimeType)));

                constructorBuilder.AddCode(
                    AssignmentBuilder.New()
                    .AssertNonNull(parserFieldName)
                    .SetLefthandSide(parserFieldName)
                    .SetRighthandSide(
                        MethodCallBuilder.New()
                        .SetPrefix(_serializerResolverParamName + ".")
                        .SetDetermineStatement(false)
                        .SetMethodName(
                            $"GetLeafValueParser<{valueParser.SerializedType}, " +
                            $"{valueParser.RuntimeType}>")
                        .AddArgument($"\"{valueParser.GraphQLTypeName}\"")));
            }

            AddBuildMethod(
                resultTypeDescriptor,
                classBuilder);

            AddBuildDataMethod(
                resultTypeDescriptor,
                classBuilder);

            AddRequiredDeserializeMethods(
                resultBuilderDescriptor.ResultNamedType,
                classBuilder,
                processed);

            CodeFileBuilder.New()
            .SetNamespace(resultBuilderDescriptor.ResultNamedType.Namespace)
            .AddType(classBuilder)
            .Build(writer);
        }