protected override CSharpSyntaxGeneratorResult Generate(
            InputObjectTypeDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings)
        {
            string name = NamingConventions.CreateInputValueInfo(descriptor.Name);

            InterfaceDeclarationSyntax interfaceDeclaration =
                SyntaxFactory.InterfaceDeclaration(name)
                .AddModifiers(SyntaxFactory.Token(SyntaxKind.InternalKeyword))
                .AddGeneratedAttribute();

            foreach (var prop in descriptor.Properties)
            {
                interfaceDeclaration = interfaceDeclaration.AddMembers(
                    SyntaxFactory.PropertyDeclaration(
                        SyntaxFactory.ParseTypeName(TypeNames.Boolean),
                        NamingConventions.CreateIsSetProperty(prop.Name))
                    .WithGetter());
            }

            return(new(
                       name,
                       State,
                       $"{descriptor.RuntimeType.NamespaceWithoutGlobal}.{State}",
                       interfaceDeclaration));
        }
        private MethodCallBuilder CreateResultInfoMethodCall(
            CSharpSyntaxGeneratorSettings settings,
            InterfaceTypeDescriptor resultNamedType,
            string concreteType)
        {
            MethodCallBuilder resultInfoConstructor = MethodCallBuilder
                                                      .Inline()
                                                      .SetMethodName($"new {concreteType}");

            foreach (PropertyDescriptor property in resultNamedType.Properties)
            {
                if (property.Type.IsOrContainsEntity())
                {
                    resultInfoConstructor.AddArgument($"{GetParameterName(property.Name)}Id");
                }
                else
                {
                    resultInfoConstructor.AddArgument(BuildUpdateMethodCall(property));
                }
            }

            if (settings.IsStoreEnabled())
            {
                resultInfoConstructor
                .AddArgument(_entityIds)
                .AddArgument($"{_snapshot}.Version");
            }

            return(resultInfoConstructor);
        }
Beispiel #3
0
        private static IReadOnlyList <GeneratorResult> GenerateCSharpDocuments(
            MapperContext context,
            CSharpGeneratorSettings settings)
        {
            var generatorSettings = new CSharpSyntaxGeneratorSettings(
                settings.NoStore,
                settings.InputRecords,
                settings.EntityRecords,
                settings.RazorComponents);

            var results = new List <GeneratorResult>();

            foreach (var descriptor in context.GetAllDescriptors())
            {
                foreach (var generator in _generators)
                {
                    if (generator.CanHandle(descriptor, generatorSettings))
                    {
                        CSharpSyntaxGeneratorResult result =
                            generator.Generate(descriptor, generatorSettings);
                        results.Add(new(generator.GetType(), result));
                    }
                }
            }

            return(results);
        }
        protected override void Generate(ClientDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            fileName = descriptor.InterfaceType.Name;
            path     = null;
            ns       = descriptor.InterfaceType.NamespaceWithoutGlobal;

            InterfaceBuilder interfaceBuilder = InterfaceBuilder
                                                .New()
                                                .SetName(fileName)
                                                .SetComment(descriptor.Documentation);

            foreach (OperationDescriptor operation in descriptor.Operations)
            {
                interfaceBuilder
                .AddProperty(NameUtils.GetPropertyName(operation.Name))
                .SetOnlyDeclaration()
                .SetType(operation.InterfaceType.ToString());
            }

            interfaceBuilder.Build(writer);
        }
Beispiel #5
0
        protected override CSharpSyntaxGeneratorResult Generate(
            OperationDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings)
        {
            string componentName = descriptor.Name.Value + "Renderer";
            string resultType    = descriptor.ResultTypeReference.GetRuntimeType().ToString();

            ClassDeclarationSyntax classDeclaration =
                ClassDeclaration(componentName)
                .AddImplements(TypeNames.QueryBase.WithGeneric(resultType))
                .AddModifiers(
                    Token(SyntaxKind.PublicKeyword),
                    Token(SyntaxKind.PartialKeyword))
                .AddGeneratedAttribute()
                .AddMembers(CreateOperationProperty(descriptor.RuntimeType.ToString()));

            foreach (var argument in descriptor.Arguments)
            {
                classDeclaration = classDeclaration.AddMembers(
                    CreateArgumentProperty(argument));
            }

            classDeclaration = classDeclaration.AddMembers(
                CreateLifecycleMethodMethod("OnInitialized", descriptor.Arguments));
            classDeclaration = classDeclaration.AddMembers(
                CreateLifecycleMethodMethod("OnParametersSet", descriptor.Arguments));

            return(new CSharpSyntaxGeneratorResult(
                       componentName,
                       Components,
                       $"{descriptor.RuntimeType.NamespaceWithoutGlobal}.{Components}",
                       classDeclaration,
                       isRazorComponent: true));
        }
Beispiel #6
0
        private IfBuilder GenerateComplexDataInterfaceIfClause(
            CSharpSyntaxGeneratorSettings settings,
            ObjectTypeDescriptor objectTypeDescriptor,
            string variableName)
        {
            var matchedTypeName = GetParameterName(objectTypeDescriptor.Name);

            // since we want to create the data name we will need to craft the type name
            // by hand by using the GraphQL type name and the state namespace.
            var dataTypeName = new RuntimeTypeInfo(
                CreateDataTypeName(objectTypeDescriptor.Name),
                $"{objectTypeDescriptor.RuntimeType.Namespace}.State");

            var block = CodeBlockBuilder.New();

            MethodCallBuilder constructorCall = MethodCallBuilder
                                                .Inline()
                                                .SetNew()
                                                .SetMethodName(objectTypeDescriptor.RuntimeType.ToString());

            foreach (PropertyDescriptor prop in objectTypeDescriptor.Properties)
            {
                if (prop.Type.IsEntityType() || prop.Type.IsDataType())
                {
                    constructorCall.AddArgument(
                        BuildMapMethodCall(settings, matchedTypeName, prop));
                }
                else if (prop.Type.IsNonNullableType())
                {
                    if (prop.Type.NamedType() is ILeafTypeDescriptor
                    {
                        RuntimeType: { IsValueType: true }
                    })
 private static ICode GenerateMethodBody(
     CSharpSyntaxGeneratorSettings settings,
     DependencyInjectionDescriptor descriptor) =>
 CodeBlockBuilder
 .New()
 .AddMethodCall(x => x
                .SetMethodName(TypeNames.AddSingleton)
                .AddArgument(_services)
                .AddArgument(LambdaBuilder
                             .New()
                             .SetBlock(true)
                             .AddArgument(_sp)
                             .SetCode(GenerateClientServiceProviderFactory(descriptor))))
 .AddEmptyLine()
 .AddCode(RegisterStoreAccessor(settings, descriptor.StoreAccessor))
 .AddEmptyLine()
 .ForEach(
     descriptor.Operations,
     (builder, operation) =>
     builder.AddCode(ForwardSingletonToClientServiceProvider(
                         operation.RuntimeType.ToString())))
 .AddEmptyLine()
 .AddCode(ForwardSingletonToClientServiceProvider(
              descriptor.ClientDescriptor.RuntimeType.ToString()))
 .AddCode(ForwardSingletonToClientServiceProvider(
              descriptor.ClientDescriptor.InterfaceType.ToString()))
 .AddEmptyLine()
 .AddMethodCall(x => x
                .SetReturn()
                .SetNew()
                .SetMethodName(
                    TypeNames.ClientBuilder.WithGeneric(descriptor.StoreAccessor.RuntimeType))
                .AddArgument(descriptor.Name.AsStringToken())
                .AddArgument(_services));
        protected override void Generate(InterfaceTypeDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            fileName = descriptor.RuntimeType.Name;
            path     = null;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            InterfaceBuilder interfaceBuilder = InterfaceBuilder
                                                .New()
                                                .SetComment(descriptor.Description)
                                                .SetName(fileName);

            foreach (var prop in descriptor.Properties)
            {
                interfaceBuilder
                .AddProperty(prop.Name)
                .SetComment(prop.Description)
                .SetType(prop.Type.ToTypeReference())
                .SetPublic();
            }

            interfaceBuilder.AddImplementsRange(descriptor.Implements.Select(x => x.Value));
            interfaceBuilder.Build(writer);
        }
        protected override CSharpSyntaxGeneratorResult Generate(
            InputObjectTypeDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings)
        {
            if (settings.InputRecords)
            {
                RecordDeclarationSyntax recordDeclarationSyntax =
                    RecordDeclaration(Token(SyntaxKind.RecordKeyword), descriptor.Name.Value)
                    .AddModifiers(
                        Token(SyntaxKind.PublicKeyword),
                        Token(SyntaxKind.PartialKeyword))
                    .AddGeneratedAttribute()
                    .AddSummary(descriptor.Documentation)
                    .WithOpenBraceToken(Token(SyntaxKind.OpenBraceToken));

                foreach (var prop in descriptor.Properties)
                {
                    recordDeclarationSyntax = recordDeclarationSyntax.AddMembers(
                        PropertyDeclaration(prop.Type.ToTypeSyntax(), prop.Name)
                        .AddModifiers(Token(SyntaxKind.PublicKeyword))
                        .AddSummary(prop.Description)
                        .WithGetterAndInit()
                        .WithSuppressNullableWarningExpression());
                }

                recordDeclarationSyntax = recordDeclarationSyntax.WithCloseBraceToken(
                    Token(SyntaxKind.CloseBraceToken));

                return(new(
                           descriptor.Name,
                           null,
                           descriptor.RuntimeType.NamespaceWithoutGlobal,
                           recordDeclarationSyntax));
            }

            ClassDeclarationSyntax classDeclaration =
                ClassDeclaration(descriptor.Name.Value)
                .AddModifiers(
                    Token(SyntaxKind.PublicKeyword),
                    Token(SyntaxKind.PartialKeyword))
                .AddGeneratedAttribute()
                .AddSummary(descriptor.Documentation);

            foreach (var prop in descriptor.Properties)
            {
                classDeclaration = classDeclaration.AddMembers(
                    PropertyDeclaration(prop.Type.ToTypeSyntax(), prop.Name)
                    .AddModifiers(Token(SyntaxKind.PublicKeyword))
                    .AddSummary(prop.Description)
                    .WithGetterAndSetter()
                    .WithSuppressNullableWarningExpression());
            }

            return(new(
                       descriptor.Name,
                       null,
                       descriptor.RuntimeType.NamespaceWithoutGlobal,
                       classDeclaration));
        }
        protected override void Generate(
            InputObjectTypeDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings,
            CodeWriter writer,
            out string fileName,
            out string?path,
            out string ns)
        {
            const string serializerResolver = nameof(serializerResolver);
            const string runtimeValue       = nameof(runtimeValue);
            const string input     = nameof(input);
            const string inputInfo = nameof(inputInfo);
            const string fields    = nameof(fields);

            fileName = CreateInputValueFormatter(descriptor);
            path     = Serialization;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            string stateNamespace    = $"{descriptor.RuntimeType.Namespace}.{State}";
            string infoInterfaceType = $"{stateNamespace}.{CreateInputValueInfo(descriptor.Name)}";

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

            var neededSerializers = descriptor
                                    .Properties
                                    .GroupBy(x => x.Type.Name)
                                    .ToDictionary(x => x, x => x.First());

            //  Initialize Method

            CodeBlockBuilder initialize = classBuilder
                                          .AddMethod("Initialize")
                                          .SetPublic()
                                          .AddParameter(serializerResolver, x => x.SetType(TypeNames.ISerializerResolver))
                                          .AddBody();

            foreach (var property in neededSerializers.Values)
            {
                if (property.Type.GetName().Value is { } name)
                {
                    var propertyName = GetFieldName(name) + "Formatter";

                    initialize
                    .AddAssigment(propertyName)
                    .AddMethodCall()
                    .SetMethodName(serializerResolver, "GetInputValueFormatter")
                    .AddArgument(name.AsStringToken());

                    classBuilder
                    .AddField(propertyName)
                    .SetAccessModifier(AccessModifier.Private)
                    .SetType(TypeNames.IInputValueFormatter)
                    .SetValue("default!");
                }
Beispiel #11
0
        protected override CSharpSyntaxGeneratorResult Generate(
            DataTypeDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings)
        {
            if (descriptor.IsInterface)
            {
                return(GenerateDataInterface(descriptor));
            }

            return(GenerateDataClass(descriptor, settings));
        }
Beispiel #12
0
        private void AddComplexDataHandler(
            CSharpSyntaxGeneratorSettings settings,
            ClassBuilder classBuilder,
            ConstructorBuilder constructorBuilder,
            MethodBuilder method,
            ComplexTypeDescriptor complexTypeDescriptor,
            HashSet <string> processed,
            bool isNonNullable)
        {
            if (complexTypeDescriptor.ParentRuntimeType is null)
            {
                throw new InvalidOperationException();
            }

            method
            .AddParameter(_dataParameterName)
            .SetType(complexTypeDescriptor.ParentRuntimeType
                     .ToString()
                     .MakeNullable(!isNonNullable))
            .SetName(_dataParameterName);

            if (settings.IsStoreEnabled())
            {
                method
                .AddParameter(_snapshot)
                .SetType(TypeNames.IEntityStoreSnapshot);
            }

            if (!isNonNullable)
            {
                method.AddCode(EnsureProperNullability(_dataParameterName, isNonNullable));
            }

            const string returnValue = nameof(returnValue);

            method.AddCode($"{complexTypeDescriptor.RuntimeType.Name}? {returnValue};");
            method.AddEmptyLine();

            GenerateIfForEachImplementedBy(
                method,
                complexTypeDescriptor,
                o => GenerateComplexDataInterfaceIfClause(settings, o, returnValue));

            method.AddCode($"return {returnValue};");

            AddRequiredMapMethods(
                settings,
                _dataParameterName,
                complexTypeDescriptor,
                classBuilder,
                constructorBuilder,
                processed);
        }
Beispiel #13
0
        protected override void Generate(
            DependencyInjectionDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings,
            CodeWriter writer,
            out string fileName,
            out string?path,
            out string ns)
        {
            fileName = CreateServiceCollectionExtensions(descriptor.Name);
            path     = DependencyInjection;
            ns       = TypeNames.DependencyInjectionNamespace;

            ClassBuilder factory = ClassBuilder
                                   .New(fileName)
                                   .SetStatic()
                                   .SetAccessModifier(AccessModifier.Public);

            MethodBuilder addClientMethod = factory
                                            .AddMethod($"Add{descriptor.Name}")
                                            .SetPublic()
                                            .SetStatic()
                                            .SetReturnType(
                TypeNames.IClientBuilder.WithGeneric(descriptor.StoreAccessor.RuntimeType))
                                            .AddParameter(
                _services,
                x => x.SetThis().SetType(TypeNames.IServiceCollection))
                                            .AddParameter(
                _strategy,
                x => x.SetType(TypeNames.ExecutionStrategy)
                .SetDefault(TypeNames.ExecutionStrategy + "." + "NetworkOnly"))
                                            .AddCode(GenerateMethodBody(settings, descriptor));

            if (descriptor.TransportProfiles.Count > 1)
            {
                addClientMethod
                .AddParameter(_profile)
                .SetType(CreateProfileEnumReference(descriptor))
                .SetDefault(CreateProfileEnumReference(descriptor) + "." +
                            descriptor.TransportProfiles[0].Name);
            }

            foreach (var profile in descriptor.TransportProfiles)
            {
                GenerateClientForProfile(settings, factory, descriptor, profile);
            }


            factory.AddClass(_clientServiceProvider);

            factory.Build(writer);
        }
        protected override void Generate(ObjectTypeDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            fileName = descriptor.RuntimeType.Name;
            path     = null;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            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));
            classBuilder.Build(writer);
        }
        protected override CSharpSyntaxGeneratorResult Generate(
            InputObjectTypeDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings)
        {
            string stateNamespace    = $"{descriptor.RuntimeType.Namespace}.{State}";
            string infoInterfaceType = $"{stateNamespace}.{CreateInputValueInfo(descriptor.Name)}";

            return(new(
                       descriptor.Name,
                       null,
                       descriptor.RuntimeType.NamespaceWithoutGlobal,
                       settings.InputRecords
                    ? GenerateRecord(descriptor, infoInterfaceType)
                    : GenerateClass(descriptor, infoInterfaceType)));
        }
        /// <summary>
        /// Adds all required deserializers of the given type descriptors properties
        /// </summary>
        protected void AddRequiredMapMethods(
            CSharpSyntaxGeneratorSettings settings,
            string propAccess,
            ComplexTypeDescriptor typeDescriptor,
            ClassBuilder classBuilder,
            ConstructorBuilder constructorBuilder,
            HashSet <string> processed,
            bool stopAtEntityMappers = false)
        {
            if (typeDescriptor is InterfaceTypeDescriptor interfaceType)
            {
                foreach (var objectTypeDescriptor in interfaceType.ImplementedBy)
                {
                    AddRequiredMapMethods(
                        settings,
                        propAccess,
                        objectTypeDescriptor,
                        classBuilder,
                        constructorBuilder,
                        processed);
                }
            }
            else
            {
                foreach (var property in typeDescriptor.Properties)
                {
                    AddMapMethod(
                        settings,
                        propAccess,
                        property.Type,
                        classBuilder,
                        constructorBuilder,
                        processed);

                    if (property.Type.NamedType() is ComplexTypeDescriptor ct &&
                        !ct.IsLeafType() && !stopAtEntityMappers)
                    {
                        AddRequiredMapMethods(
                            settings,
                            propAccess,
                            ct,
                            classBuilder,
                            constructorBuilder,
                            processed);
                    }
                }
            }
        }
Beispiel #17
0
        protected override void Generate(
            ClientDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings,
            CodeWriter writer,
            out string fileName,
            out string?path,
            out string ns)
        {
            fileName = descriptor.Name;
            path     = null;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            ClassBuilder classBuilder = ClassBuilder
                                        .New()
                                        .SetName(fileName)
                                        .SetComment(descriptor.Documentation)
                                        .AddImplements(descriptor.InterfaceType.ToString());

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

            classBuilder
            .AddProperty("ClientName")
            .SetPublic()
            .SetStatic()
            .SetType(TypeNames.String)
            .AsLambda(descriptor.Name.Value.AsStringToken());

            foreach (OperationDescriptor operation in descriptor.Operations)
            {
                AddConstructorAssignedField(
                    operation.InterfaceType.ToString(),
                    GetFieldName(operation.Name),
                    GetParameterName(operation.Name),
                    classBuilder,
                    constructorBuilder);

                classBuilder
                .AddProperty(GetPropertyName(operation.Name))
                .SetPublic()
                .SetType(operation.InterfaceType.ToString())
                .AsLambda(GetFieldName(operation.Name));
            }

            classBuilder.Build(writer);
        }
Beispiel #18
0
        protected override void Generate(DependencyInjectionDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            fileName = NamingConventions.CreateClientProfileKind(descriptor.Name);
            path     = null;
            ns       = descriptor.ClientDescriptor.RuntimeType.NamespaceWithoutGlobal;

            EnumBuilder
            .New()
            .SetName(fileName)
            .AddElements(descriptor.TransportProfiles.Select(x => x.Name))
            .Build(writer);
        }
Beispiel #19
0
        protected override void Generate(
            StoreAccessorDescriptor descriptor,
            CSharpSyntaxGeneratorSettings settings,
            CodeWriter writer,
            out string fileName,
            out string?path,
            out string ns)
        {
            fileName = descriptor.Name;
            path     = State;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            ClassBuilder factory = ClassBuilder
                                   .New(fileName)
                                   .SetAccessModifier(AccessModifier.Public)
                                   .AddImplements(TypeNames.IStoreAccessor);

            AddThrowNotValidWithoutStore(factory, "OperationStore", TypeNames.IOperationStore);
            AddThrowNotValidWithoutStore(factory, "EntityStore", TypeNames.IEntityStore);
            AddThrowNotValidWithoutStore(factory,
                                         "EntityIdSerializer",
                                         TypeNames.IEntityIdSerializer);

            factory
            .AddMethod("GetOperationRequestFactory")
            .SetPublic()
            .SetReturnType(TypeNames.IOperationRequestFactory)
            .AddParameter("resultType", x => x.SetType(TypeNames.Type))
            .AddCode(ExceptionBuilder
                     .New(TypeNames.NotSupportedException)
                     .AddArgument(
                         "\"GetOperationRequestFactory is not supported in store less mode\""));

            factory
            .AddMethod("GetOperationResultDataFactory")
            .SetPublic()
            .SetReturnType(TypeNames.IOperationResultDataFactory)
            .AddParameter("resultType", x => x.SetType(TypeNames.Type))
            .AddCode(ExceptionBuilder
                     .New(TypeNames.NotSupportedException)
                     .AddArgument(
                         "\"GetOperationResultDataFactory is not supported in store less mode\""));

            factory.Build(writer);
        }
 private static void GenerateClientForProfile(
     CSharpSyntaxGeneratorSettings settings,
     ClassBuilder factory,
     DependencyInjectionDescriptor descriptor,
     TransportProfile profile)
 {
     factory
     .AddMethod("ConfigureClient" + profile.Name)
     .SetPrivate()
     .SetStatic()
     .SetReturnType(TypeNames.IServiceCollection)
     .AddParameter(_parentServices, x => x.SetType(TypeNames.IServiceProvider))
     .AddParameter(
         _strategy,
         x => x.SetType(TypeNames.ExecutionStrategy)
         .SetDefault(TypeNames.ExecutionStrategy + "." + "NetworkOnly"))
     .AddCode(GenerateInternalMethodBody(settings, descriptor, profile));
 }
        protected override void Generate(EnumTypeDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            const string serializedValue = nameof(serializedValue);
            const string runtimeValue    = nameof(runtimeValue);

            fileName = CreateEnumParserName(descriptor.Name);
            path     = Serialization;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            ClassBuilder classBuilder = ClassBuilder
                                        .New(fileName)
                                        .AddImplements(IInputValueFormatter)
                                        .AddImplements(ILeafValueParser.WithGeneric(String, descriptor.Name));

            classBuilder
            .AddMethod("Parse")
            .AddParameter(serializedValue, x => x.SetType(String))
            .SetAccessModifier(AccessModifier.Public)
            .SetReturnType(descriptor.Name)
            .AddCode(CreateEnumParsingSwitch(serializedValue, descriptor));

            classBuilder
            .AddMethod("Format")
            .SetAccessModifier(AccessModifier.Public)
            .SetReturnType(Object)
            .AddParameter(runtimeValue, x => x.SetType(Object.MakeNullable()))
            .AddCode(CreateEnumFormattingSwitch(runtimeValue, descriptor));

            classBuilder
            .AddProperty("TypeName")
            .AsLambda(descriptor.Name.AsStringToken())
            .SetPublic()
            .SetType(String);

            classBuilder.Build(writer);
        }
        protected override void Generate(StoreAccessorDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            fileName = descriptor.Name;
            path     = State;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            ClassBuilder factory = ClassBuilder
                                   .New(fileName)
                                   .SetAccessModifier(AccessModifier.Public)
                                   .AddImplements(TypeNames.StoreAccessor);

            factory
            .AddConstructor()
            .SetTypeName(fileName)
            .SetPublic()
            .AddParameter(_operationStore, x => x.SetType(TypeNames.IOperationStore))
            .AddParameter(_entityStore, x => x.SetType(TypeNames.IEntityStore))
            .AddParameter(_entityIdSerializer, x => x.SetType(TypeNames.IEntityIdSerializer))
            .AddParameter(
                _requestFactories,
                x => x.SetType(
                    TypeNames.IEnumerable.WithGeneric(TypeNames.IOperationRequestFactory)))
            .AddParameter(
                _resultDataFactories,
                x => x.SetType(
                    TypeNames.IEnumerable.WithGeneric(TypeNames.IOperationResultDataFactory)))
            .AddBase(_operationStore)
            .AddBase(_entityStore)
            .AddBase(_entityIdSerializer)
            .AddBase(_requestFactories)
            .AddBase(_resultDataFactories);

            factory.Build(writer);
        }
        protected override void Generate(OperationDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            fileName = descriptor.InterfaceType.Name;
            path     = null;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            InterfaceBuilder interfaceBuilder = InterfaceBuilder
                                                .New()
                                                .SetComment(
                XmlCommentBuilder
                .New()
                .SetSummary(
                    string.Format(
                        CodeGenerationResources.OperationServiceDescriptor_Description,
                        descriptor.Name))
                .AddCode(descriptor.BodyString))
                                                .AddImplements(TypeNames.IOperationRequestFactory)
                                                .SetName(fileName);

            var runtimeTypeName =
                descriptor.ResultTypeReference.GetRuntimeType().Name;

            if (descriptor is not SubscriptionOperationDescriptor)
            {
                interfaceBuilder.AddMethod(CreateExecuteMethod(descriptor, runtimeTypeName));
            }

            interfaceBuilder.AddMethod(CreateWatchMethod(descriptor, runtimeTypeName));

            interfaceBuilder.Build(writer);
        }
Beispiel #24
0
        protected override void Generate(EnumTypeDescriptor descriptor,
                                         CSharpSyntaxGeneratorSettings settings,
                                         CodeWriter writer,
                                         out string fileName,
                                         out string?path,
                                         out string ns)
        {
            fileName = descriptor.Name;
            path     = null;
            ns       = descriptor.RuntimeType.NamespaceWithoutGlobal;

            EnumBuilder enumBuilder = EnumBuilder
                                      .New()
                                      .SetComment(descriptor.Documentation)
                                      .SetName(descriptor.RuntimeType.Name)
                                      .SetUnderlyingType(descriptor.UnderlyingType);

            foreach (EnumValueDescriptor element in descriptor.Values)
            {
                enumBuilder.AddElement(element.RuntimeValue, element.Value, element.Documentation);
            }

            enumBuilder.Build(writer);
        }
Beispiel #25
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);
        }
Beispiel #26
0
 protected override bool CanHandle(ITypeDescriptor descriptor,
                                   CSharpSyntaxGeneratorSettings settings)
 {
     return(descriptor.Kind == TypeKind.ResultType && !descriptor.IsInterface());
 }
Beispiel #27
0
 protected override bool CanHandle(DependencyInjectionDescriptor descriptor,
                                   CSharpSyntaxGeneratorSettings settings)
 {
     return(descriptor.TransportProfiles.Count > 1);
 }
Beispiel #28
0
 private static ICode RegisterOperation(
     CSharpSyntaxGeneratorSettings settings,
     string connectionKind,
     string operationFullName,
     string operationInterfaceName,
     string resultInterface,
     string factory,
     string resultBuilder)
 {
     return(CodeBlockBuilder
            .New()
            .AddCode(
                MethodCallBuilder
                .New()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(
                    TypeNames.IOperationResultDataFactory.WithGeneric(resultInterface))
                .AddGeneric(factory)
                .AddArgument(_services))
            .AddCode(
                MethodCallBuilder
                .New()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(TypeNames.IOperationResultDataFactory)
                .AddArgument(_services)
                .AddArgument(LambdaBuilder
                             .New()
                             .AddArgument(_sp)
                             .SetCode(MethodCallBuilder
                                      .Inline()
                                      .SetMethodName(TypeNames.GetRequiredService)
                                      .AddGeneric(
                                          TypeNames.IOperationResultDataFactory
                                          .WithGeneric(resultInterface))
                                      .AddArgument(_sp))))
            .AddCode(
                MethodCallBuilder
                .New()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(TypeNames.IOperationRequestFactory)
                .AddArgument(_services)
                .AddArgument(LambdaBuilder
                             .New()
                             .AddArgument(_sp)
                             .SetCode(MethodCallBuilder
                                      .Inline()
                                      .SetMethodName(TypeNames.GetRequiredService)
                                      .AddGeneric(operationInterfaceName)
                                      .AddArgument(_sp))))
            .AddCode(MethodCallBuilder
                     .New()
                     .SetMethodName(TypeNames.AddSingleton)
                     .AddGeneric(
                         TypeNames.IOperationResultBuilder
                         .WithGeneric(TypeNames.JsonDocument, resultInterface))
                     .AddGeneric(resultBuilder)
                     .AddArgument(_services))
            .AddCode(
                MethodCallBuilder
                .New()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(TypeNames.IOperationExecutor.WithGeneric(resultInterface))
                .AddArgument(_services)
                .AddArgument(LambdaBuilder
                             .New()
                             .AddArgument(_sp)
                             .SetCode(MethodCallBuilder
                                      .Inline()
                                      .SetNew()
                                      .SetMethodName(settings.IsStoreEnabled()
                             ? TypeNames.OperationExecutor
                             : TypeNames.StorelessOperationExecutor)
                                      .AddGeneric(TypeNames.JsonDocument)
                                      .AddGeneric(resultInterface)
                                      .AddArgument(
                                          MethodCallBuilder
                                          .Inline()
                                          .SetMethodName(TypeNames.GetRequiredService)
                                          .AddGeneric(connectionKind)
                                          .AddArgument(_sp))
                                      .AddArgument(
                                          LambdaBuilder
                                          .New()
                                          .SetCode(
                                              MethodCallBuilder
                                              .Inline()
                                              .SetMethodName(
                                                  TypeNames.GetRequiredService)
                                              .AddGeneric(
                                                  TypeNames.IOperationResultBuilder.WithGeneric(
                                                      TypeNames.JsonDocument,
                                                      resultInterface))
                                              .AddArgument(_sp)))
                                      .If(settings.IsStoreEnabled(),
                                          x => x
                                          .AddArgument(
                                              MethodCallBuilder
                                              .Inline()
                                              .SetMethodName(TypeNames.GetRequiredService)
                                              .AddGeneric(TypeNames.IOperationStore)
                                              .AddArgument(_sp))
                                          .AddArgument(_strategy)))))
            .AddCode(MethodCallBuilder
                     .New()
                     .SetMethodName(TypeNames.AddSingleton)
                     .AddGeneric(operationFullName)
                     .AddArgument(_services))
            .AddCode(MethodCallBuilder
                     .New()
                     .SetMethodName(TypeNames.AddSingleton)
                     .AddGeneric(operationInterfaceName)
                     .AddArgument(_services)
                     .AddArgument(LambdaBuilder
                                  .New()
                                  .AddArgument(_sp)
                                  .SetCode(MethodCallBuilder
                                           .Inline()
                                           .SetMethodName(TypeNames.GetRequiredService)
                                           .AddGeneric(operationFullName)
                                           .AddArgument(_sp)))));
 }
Beispiel #29
0
        private static ICode GenerateInternalMethodBody(
            CSharpSyntaxGeneratorSettings settings,
            DependencyInjectionDescriptor descriptor,
            TransportProfile profile)
        {
            var rootNamespace = descriptor.ClientDescriptor.RuntimeType.Namespace;

            var hasSubscriptions =
                descriptor.Operations.OfType <SubscriptionOperationDescriptor>().Any();
            var hasQueries =
                descriptor.Operations.OfType <QueryOperationDescriptor>().Any();
            var hasMutations =
                descriptor.Operations.OfType <MutationOperationDescriptor>().Any();

            CodeBlockBuilder body = CodeBlockBuilder
                                    .New()
                                    .AddCode(CreateBaseCode(settings));

            var generatedConnections = new HashSet <TransportType>();

            if (hasSubscriptions)
            {
                generatedConnections.Add(profile.Subscription);
                body.AddCode(
                    RegisterConnection(profile.Subscription, descriptor.Name));
            }

            if (hasQueries && !generatedConnections.Contains(profile.Query))
            {
                generatedConnections.Add(profile.Query);
                body.AddCode(RegisterConnection(profile.Query, descriptor.Name));
            }

            if (hasMutations && !generatedConnections.Contains(profile.Mutation))
            {
                generatedConnections.Add(profile.Mutation);
                body.AddCode(RegisterConnection(profile.Mutation, descriptor.Name));
            }

            body.AddEmptyLine();

            foreach (var typeDescriptor in descriptor.TypeDescriptors
                     .OfType <INamedTypeDescriptor>())
            {
                if (typeDescriptor.Kind == TypeKind.Entity && !typeDescriptor.IsInterface())
                {
                    INamedTypeDescriptor namedTypeDescriptor =
                        (INamedTypeDescriptor)typeDescriptor.NamedType();
                    NameString className = namedTypeDescriptor.ExtractMapperName();

                    var interfaceName =
                        TypeNames.IEntityMapper.WithGeneric(
                            namedTypeDescriptor.ExtractType().ToString(),
                            $"{rootNamespace}.{typeDescriptor.RuntimeType.Name}");

                    body.AddMethodCall()
                    .SetMethodName(TypeNames.AddSingleton)
                    .AddGeneric(interfaceName)
                    .AddGeneric($"{CreateStateNamespace(rootNamespace)}.{className}")
                    .AddArgument(_services);
                }
            }

            body.AddEmptyLine();

            foreach (var enumType in descriptor.EnumTypeDescriptor)
            {
                body.AddMethodCall()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(TypeNames.ISerializer)
                .AddGeneric(CreateEnumParserName($"{rootNamespace}.{enumType.Name}"))
                .AddArgument(_services);
            }

            foreach (var serializer in _serializers)
            {
                body.AddMethodCall()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(TypeNames.ISerializer)
                .AddGeneric(serializer)
                .AddArgument(_services);
            }

            RuntimeTypeInfo stringTypeInfo = new RuntimeTypeInfo(TypeNames.String);

            foreach (var scalar in descriptor.TypeDescriptors.OfType <ScalarTypeDescriptor>())
            {
                if (scalar.RuntimeType.Equals(stringTypeInfo) &&
                    scalar.SerializationType.Equals(stringTypeInfo) &&
                    !BuiltInScalarNames.IsBuiltInScalar(scalar.Name))
                {
                    body.AddMethodCall()
                    .SetMethodName(TypeNames.AddSingleton)
                    .AddGeneric(TypeNames.ISerializer)
                    .AddArgument(_services)
                    .AddArgument(MethodCallBuilder
                                 .Inline()
                                 .SetNew()
                                 .SetMethodName(TypeNames.StringSerializer)
                                 .AddArgument(scalar.Name.AsStringToken()));
                }
            }

            foreach (var inputTypeDescriptor in descriptor.TypeDescriptors
                     .Where(x => x.Kind is TypeKind.Input))
            {
                var formatter =
                    CreateInputValueFormatter(
                        (InputObjectTypeDescriptor)inputTypeDescriptor.NamedType());

                body.AddMethodCall()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(TypeNames.ISerializer)
                .AddGeneric($"{rootNamespace}.{formatter}")
                .AddArgument(_services);
            }

            body.AddCode(RegisterSerializerResolver());

            body.AddEmptyLine();

            foreach (var operation in descriptor.Operations)
            {
                if (!(operation.ResultTypeReference is InterfaceTypeDescriptor typeDescriptor))
                {
                    continue;
                }

                TransportType operationKind = operation switch
                {
                    SubscriptionOperationDescriptor => profile.Subscription,
                    QueryOperationDescriptor => profile.Query,
                    MutationOperationDescriptor => profile.Mutation,
                    _ => throw ThrowHelper.DependencyInjection_InvalidOperationKind(operation)
                };

                string connectionKind = operationKind switch
                {
                    TransportType.Http => TypeNames.IHttpConnection,
                    TransportType.WebSocket => TypeNames.IWebSocketConnection,
                    TransportType.InMemory => TypeNames.IInMemoryConnection,
                    { } v => throw ThrowHelper.DependencyInjection_InvalidTransportType(v)
                };

                string operationName          = operation.Name;
                string fullName               = operation.RuntimeType.ToString();
                string operationInterfaceName = operation.InterfaceType.ToString();
                string resultInterface        = typeDescriptor.RuntimeType.ToString();

                // The factories are generated based on the concrete result type, which is the
                // only implementee of the result type interface.

                var factoryName =
                    CreateResultFactoryName(
                        typeDescriptor.ImplementedBy.First().RuntimeType.Name);

                var builderName = CreateResultBuilderName(operationName);
                body.AddCode(
                    RegisterOperation(
                        settings,
                        connectionKind,
                        fullName,
                        operationInterfaceName,
                        resultInterface,
                        $"{CreateStateNamespace(operation.RuntimeType.Namespace)}.{factoryName}",
                        $"{CreateStateNamespace(operation.RuntimeType.Namespace)}.{builderName}"));
            }

            if (settings.IsStoreEnabled())
            {
                body.AddCode(
                    MethodCallBuilder
                    .New()
                    .SetMethodName(TypeNames.AddSingleton)
                    .AddGeneric(TypeNames.IEntityIdSerializer)
                    .AddGeneric(descriptor.EntityIdFactoryDescriptor.Type.ToString())
                    .AddArgument(_services));
            }

            body.AddCode(
                MethodCallBuilder
                .New()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(descriptor.ClientDescriptor.RuntimeType.ToString())
                .AddArgument(_services));

            body.AddCode(
                MethodCallBuilder
                .New()
                .SetMethodName(TypeNames.AddSingleton)
                .AddGeneric(descriptor.ClientDescriptor.InterfaceType.ToString())
                .AddArgument(_services)
                .AddArgument(LambdaBuilder
                             .New()
                             .AddArgument(_sp)
                             .SetCode(MethodCallBuilder
                                      .Inline()
                                      .SetMethodName(TypeNames.GetRequiredService)
                                      .AddGeneric(descriptor.ClientDescriptor.RuntimeType.ToString())
                                      .AddArgument(_sp))));

            body.AddLine($"return {_services};");

            return(body);
        }
Beispiel #30
0
        private static ICode RegisterStoreAccessor(
            CSharpSyntaxGeneratorSettings settings,
            StoreAccessorDescriptor storeAccessor)
        {
            if (settings.IsStoreDisabled())
            {
                return(MethodCallBuilder
                       .New()
                       .SetMethodName(TypeNames.AddSingleton)
                       .AddArgument(_services)
                       .AddArgument(LambdaBuilder
                                    .New()
                                    .AddArgument(_sp)
                                    .SetCode(MethodCallBuilder
                                             .Inline()
                                             .SetNew()
                                             .SetMethodName(storeAccessor.RuntimeType.ToString()))));
            }

            return(MethodCallBuilder
                   .New()
                   .SetMethodName(TypeNames.AddSingleton)
                   .AddArgument(_services)
                   .AddArgument(LambdaBuilder
                                .New()
                                .AddArgument(_sp)
                                .SetCode(MethodCallBuilder
                                         .Inline()
                                         .SetNew()
                                         .SetMethodName(storeAccessor.RuntimeType.ToString())
                                         .AddArgument(MethodCallBuilder
                                                      .Inline()
                                                      .SetMethodName(TypeNames.GetRequiredService)
                                                      .SetWrapArguments()
                                                      .AddArgument(MethodCallBuilder
                                                                   .Inline()
                                                                   .SetMethodName(TypeNames.GetRequiredService)
                                                                   .AddGeneric("ClientServiceProvider")
                                                                   .AddArgument(_sp))
                                                      .AddGeneric(TypeNames.IOperationStore))
                                         .AddArgument(MethodCallBuilder
                                                      .Inline()
                                                      .SetMethodName(TypeNames.GetRequiredService)
                                                      .SetWrapArguments()
                                                      .AddArgument(MethodCallBuilder
                                                                   .Inline()
                                                                   .SetMethodName(TypeNames.GetRequiredService)
                                                                   .AddGeneric("ClientServiceProvider")
                                                                   .AddArgument(_sp))
                                                      .AddGeneric(TypeNames.IEntityStore))
                                         .AddArgument(MethodCallBuilder
                                                      .Inline()
                                                      .SetMethodName(TypeNames.GetRequiredService)
                                                      .SetWrapArguments()
                                                      .AddArgument(MethodCallBuilder
                                                                   .Inline()
                                                                   .SetMethodName(TypeNames.GetRequiredService)
                                                                   .AddGeneric("ClientServiceProvider")
                                                                   .AddArgument(_sp))
                                                      .AddGeneric(TypeNames.IEntityIdSerializer))
                                         .AddArgument(MethodCallBuilder
                                                      .Inline()
                                                      .SetMethodName(TypeNames.GetRequiredService)
                                                      .SetWrapArguments()
                                                      .AddArgument(MethodCallBuilder
                                                                   .Inline()
                                                                   .SetMethodName(TypeNames.GetRequiredService)
                                                                   .AddGeneric("ClientServiceProvider")
                                                                   .AddArgument(_sp))
                                                      .AddGeneric(
                                                          TypeNames.IEnumerable.WithGeneric(
                                                              TypeNames.IOperationRequestFactory)))
                                         .AddArgument(MethodCallBuilder
                                                      .Inline()
                                                      .SetMethodName(TypeNames.GetRequiredService)
                                                      .SetWrapArguments()
                                                      .AddArgument(MethodCallBuilder
                                                                   .Inline()
                                                                   .SetMethodName(TypeNames.GetRequiredService)
                                                                   .AddGeneric("ClientServiceProvider")
                                                                   .AddArgument(_sp))
                                                      .AddGeneric(
                                                          TypeNames.IEnumerable.WithGeneric(
                                                              TypeNames.IOperationResultDataFactory))))));
        }