コード例 #1
0
        public void Execute(GeneratorExecutionContext context)
        {
            var @class = new CodeGenClass("GeneratedClass", Scope.Public, ClassType.Normal);

            @class.Methods.Add(new CodeGenMethod("GeneratedMethod", null, Scope.Public, MethodType.Static, null, null, @"System.Console.WriteLine(""Hello World 123"");"));

            var @namespace = new CodeGenNamespace("GeneratedNamespace");

            @namespace.Content.Add(@class);

            string codeString = @namespace.GenerateCode();

            //            string codeString = @"
            //namespace GeneratedNamespace
            //{
            //    public class GeneratedClass
            //    {
            //        public static void GeneratedMethod()
            //        {
            //            System.Console.WriteLine(""Hello World once more"");
            //        }
            //    }
            //}
            //";

            context.AddSource("myGeneratedFile.cs", SourceText.From(codeString, Encoding.UTF8));
        }
コード例 #2
0
        private void GenerateDecoratorUsingTemplate(
            GeneratorExecutionContext context,
            DecoratorNamespaceInformation factoryInformation)
        {
            CodeGenNamespace generatedNamespace  = _NamespaceFactory.Create(factoryInformation);
            string           generatedCodeString = generatedNamespace.GenerateCode();

            SourceText sourceText = SourceText.From(generatedCodeString, Encoding.UTF8);

            context.AddSource($"{factoryInformation.DecoratorName}.cs", sourceText);
        }
コード例 #3
0
        public void Execute(GeneratorExecutionContext context)
        {
            var generatedClass = new CodeGenClass("XmlPrinter", Scope.Public, ClassType.Static);

            var xmlFiles = context.AdditionalFiles.Where(f => f.Path.EndsWith(".xml"));

            foreach (var xmlFile in xmlFiles)
            {
                var itemElements = XDocument.Load(xmlFile.Path)?.Root?.Elements("item");

                if (itemElements == null)
                {
                    continue;
                }

                foreach (var itemElement in itemElements)
                {
                    string name  = itemElement.Attribute("name")?.Value;
                    string value = itemElement.Value;

                    if (!string.IsNullOrWhiteSpace(name) && !string.IsNullOrWhiteSpace(value))
                    {
                        var generatedMethod = new CodeGenMethod(
                            $"Print{name}",
                            null,
                            Scope.Public,
                            MethodType.Static,
                            null,
                            null,
                            $@"
Console.WriteLine($""Hello, {value}"");
");

                        generatedClass.Methods.Add(generatedMethod);
                    }
                }
            }

            var generatedNamespace = new CodeGenNamespace("GeneratedNamespace");

            generatedNamespace.Usings.Add("System");
            generatedNamespace.Content.Add(generatedClass);

            var generatedCodeString = generatedNamespace.GenerateCode();

            var sourceText = SourceText.From(generatedCodeString, Encoding.UTF8);

            context.AddSource("XmlPrinter.cs", sourceText);
        }
コード例 #4
0
        public void Execute(GeneratorExecutionContext context)
        {
            var defFiles = context.AdditionalFiles.Where(f => f.Path.EndsWith("ControllerDefinition.json"));

            foreach (AdditionalText defFile in defFiles)
            {
                ApiDefinition definition;

                string definitionString = File.ReadAllText(defFile.Path);
                definition = JsonConvert.DeserializeObject <ApiDefinition>(definitionString);

                var controllerClass = GenerateController(definition);
                var modelClasses    = GenerateModels(definition);

                if (string.IsNullOrWhiteSpace(definition.Name))
                {
                    throw new ArgumentException("Invalid definition name");
                }

                string controllerNamespaceName = $"{definition.Namespace}.Controllers";
                string modelNamespaceName      = $"{definition.Namespace}.Models";

                // Controller
                var controllerNamespace = new CodeGenNamespace(controllerNamespaceName);

                controllerNamespace.Content.Add(controllerClass);
                controllerNamespace.Usings.Add("System");
                controllerNamespace.Usings.Add("System.Threading.Tasks");
                controllerNamespace.Usings.Add("Microsoft.AspNetCore.Mvc");
                controllerNamespace.Usings.Add("Microsoft.Extensions.DependencyInjection");
                controllerNamespace.Usings.Add(definition.Namespace);
                controllerNamespace.Usings.Add(modelNamespaceName);

                context.Add(controllerNamespace, $"{definition.Name}Controller.cs");

                // Models
                foreach (CodeGenClass modelClass in modelClasses)
                {
                    var modelNamespace = new CodeGenNamespace(modelNamespaceName);
                    modelNamespace.Content.Add(modelClass);
                    context.Add(modelNamespace, $"{modelClass.Name}.cs");
                }
            }
        }
コード例 #5
0
        public void Execute(GeneratorExecutionContext context)
        {
            var generatedClass = new CodeGenClass(
                _ClassName,
                Scope.Public,
                ClassType.Static);

            generatedClass.Comment = new CodeGenComment($@"Class: {_ClassName}
Description: {_ClassDescription}
Auto-generated on {DateTime.Now}");

            var generatedNamespace = new CodeGenNamespace(_Namespace);

            GenerateClassMethods(context, generatedNamespace, generatedClass);
            generatedNamespace.Content.Add(generatedClass);

            var generatedCodeString = generatedNamespace.GenerateCode();

            var sourceText = SourceText.From(generatedCodeString, Encoding.UTF8);

            context.AddSource($"{_ClassName}.cs", sourceText);
        }
コード例 #6
0
 protected abstract void GenerateClassMethods(GeneratorExecutionContext context, CodeGenNamespace @namespace, CodeGenClass @class);
コード例 #7
0
 private void ModifyNamespace(CodeGenNamespace @namespace)
 {
     @namespace.Usings.Add("System");
     @namespace.Usings.Add("System.Collections.Generic");
 }
コード例 #8
0
        protected override void GenerateClassMethods(GeneratorExecutionContext context, CodeGenNamespace @namespace, CodeGenClass @class)
        {
            StaticMethodCallSyntaxReceiver syntaxReceiver = (StaticMethodCallSyntaxReceiver)context.SyntaxReceiver;

            // singleton store
            @class.Variables.Add(new CodeGenVariable("_SingletonLock", "object", Scope.Private, VariableType.Static, true, "new object()"));
            @class.Variables.Add(new CodeGenVariable("_Singletons", "IDictionary<Type, object>", Scope.Private, VariableType.Static, true, "new Dictionary<Type, object>()"));

            // static methods
            AddRegistrationMethods(@class);
            AddGetTMethod(@class);

            // get registrations
            IDictionary <string, DIRegistration> registrations = ProcessCalls(context, syntaxReceiver.Calls);

            // Function dictionary used by get method
            AddGetFunctionsDictionary(@class, registrations);

            foreach (DIRegistration registration in registrations.Values)
            {
                // Build stack contining the initialization of this registered resource, including any dependencies.
                Stack <DIDependencyInitialization> initStack = BuildInitStack(registration, registrations);

                // Use init stack to generate body
                string body = BuildTypedGetMethodBody(initStack);

                var method = new CodeGenMethod(
                    registration.DirectGetMethodName,
                    registration.IdentifierType,
                    Scope.Private,
                    MethodType.Static,
                    null,
                    null,
                    body);

                @class.Methods.Add(method);
            }

            ModifyNamespace(@namespace);
        }
コード例 #9
0
        protected override void GenerateClassMethods(GeneratorExecutionContext context, CodeGenNamespace @namespace, CodeGenClass @class)
        {
            StaticMethodCallSyntaxReceiver syntaxReceiver = (StaticMethodCallSyntaxReceiver)context.SyntaxReceiver;

            var generatedHandlers = new HashSet <string>();

            GenerateStub(@class);

            foreach (StaticMethodCall call in syntaxReceiver.Calls)
            {
                SemanticModel semanticModel = context.Compilation.GetSemanticModel(call.Invocation.SyntaxTree);

                Dictionary <string, string> genericTypes = call.GenericTypes
                                                           .Select(gt => semanticModel.GetTypeInfo(gt))
                                                           .ToDictionary(typeInfo => typeInfo.Type.ToString(), typeInfo => typeInfo.Type.Name);

                string   handlerName = $"{string.Join(string.Empty, genericTypes.Values)}Handler";
                string[] argList     = genericTypes.Keys.Select((type, i) => $"{type} arg{i}").ToArray();
                string[] argNameList = genericTypes.Select((type, i) => $"arg{i}").ToArray();

                if (generatedHandlers.Contains(handlerName))
                {
                    continue;
                }

                generatedHandlers.Add(handlerName);

                // delegate
                @namespace.Content.Add(new CodeGenDelegate(
                                           handlerName,
                                           null,
                                           Scope.Public,
                                           null,
                                           argList));

                // private delegate variable
                @class.Variables.Add(new CodeGenVariable(
                                         $"_{handlerName}",
                                         handlerName,
                                         Scope.Private,
                                         VariableType.Static));

                // register method
                @class.Methods.Add(new CodeGenMethod(
                                       MethodName,
                                       null,
                                       Scope.Public,
                                       MethodType.Static,
                                       genericTypes.Keys.Select((gt, i) => new CodeGenGeneric($"TPayload{i}", gt)),
                                       new[] { $"Action<{string.Join(", ", genericTypes.Keys)}> handler" },
                                       $"_{handlerName} += new {handlerName}(handler);"));

                // notify method
                @class.Methods.Add(new CodeGenMethod(
                                       "Notify",
                                       null,
                                       Scope.Public,
                                       MethodType.Static,
                                       null,
                                       argList,
                                       $"_{handlerName}?.Invoke({string.Join(", ", argNameList)});"));
            }

            @namespace.Usings.Add("System");
        }
コード例 #10
0
        public void Execute(GeneratorExecutionContext context)
        {
            ClassWithAttributeSyntaxReciever syntaxReceiver = (ClassWithAttributeSyntaxReciever)context.SyntaxReceiver;

            foreach ((ClassDeclarationSyntax classDeclaration, AttributeSyntax decorateAttribute) in syntaxReceiver.Classes)
            {
                SemanticModel semanticModel = context.Compilation.GetSemanticModel(classDeclaration.SyntaxTree);
                ISymbol       classSymbol   = semanticModel.GetDeclaredSymbol(classDeclaration);

                TypeInfo      attrType = semanticModel.GetTypeInfo(decorateAttribute.Name);
                AttributeData decorateAttributeData = classSymbol.GetAttributes().First(attrData => attrData.AttributeClass.Equals(attrType.Type, SymbolEqualityComparer.Default));

                INamedTypeSymbol decoratedTypeSymbol = decorateAttributeData.ConstructorArguments.FirstOrDefault().Value as INamedTypeSymbol;

                Dictionary <string, string> constraints = classDeclaration.ConstraintClauses.ToDictionary(
                    constraintClause => constraintClause.Name.Identifier.Text,
                    constraintClause => constraintClause.Constraints.ToString());

                IEnumerable <CodeGenGeneric> generics = classDeclaration.TypeParameterList?.Parameters.Select(parameter => GenerateMethodParameter(parameter, constraints));

                string decoratorName = $"{classDeclaration.Identifier.Text}Decorator";
                string decoratedType = decoratedTypeSymbol?.ToString() ?? classSymbol.ToString();

                var generatedClass = new CodeGenClass(
                    decoratorName,
                    Scope.Public,
                    ClassType.Normal,
                    genericTypes: generics,
                    derivedFrom: decoratedTypeSymbol != null ? new[] { decoratedTypeSymbol.ToString() } : null);

                generatedClass.Comment = new CodeGenComment($@"Class: {decoratorName}
Description: 
Decorator for {classSymbol}
Auto-generated on {DateTime.Now}");

                // Constructor
                generatedClass.Constructors.Add(new CodeGenConstructor(
                                                    decoratorName,
                                                    Scope.Public,
                                                    new[] { $"{decoratedType} decorated" },
                                                    "_Decorated = decorated ?? throw new ArgumentNullException(nameof(decorated));"));

                // Decorated variable
                generatedClass.Variables.Add(new CodeGenVariable(
                                                 "_Decorated",
                                                 decoratedType,
                                                 Scope.Private,
                                                 readOnly: true));

                GenerateDecoratorMethods(classDeclaration, generatedClass, semanticModel);

                var generatedNamespace = new CodeGenNamespace($"{classSymbol.ContainingNamespace.Name}.Decorators");
                generatedNamespace.Content.Add(generatedClass);
                generatedNamespace.Usings.Add("System");

                var generatedCodeString = generatedNamespace.GenerateCode();

                var sourceText = SourceText.From(generatedCodeString, Encoding.UTF8);
                context.AddSource($"{decoratorName}.cs", sourceText);
            }
        }
コード例 #11
0
        protected override void GenerateClassMethods(GeneratorExecutionContext context, CodeGenNamespace @namespace, CodeGenClass @class)
        {
            StaticMethodCallSyntaxReceiver syntaxReceiver = (StaticMethodCallSyntaxReceiver)context.SyntaxReceiver;

            var foundTypes = new HashSet <string>();

            // No calls? Generate stub for intellisence.
            if (!syntaxReceiver.Calls.Any())
            {
                @class.Methods.Add(new CodeGenMethod(
                                       MethodName,
                                       "object",
                                       Scope.Public,
                                       MethodType.Static,
                                       null,
                                       new[] { "object arg" },
                                       @"// Stub method for intellisence.
return arg;"));

                return;
            }

            foreach (StaticMethodCall call in syntaxReceiver.Calls)
            {
                if (call.Arguments.Length != 1)
                {
                    continue;
                }

                var           argExpression = call.Arguments[0];
                SemanticModel semanticModel = context.Compilation.GetSemanticModel(argExpression.SyntaxTree);
                string        argumentType  = semanticModel.GetTypeInfo(argExpression).Type.ToString();

                if (argumentType == null || foundTypes.Contains(argumentType))
                {
                    continue;
                }

                foundTypes.Add(argumentType);

                @class.Methods.Add(new CodeGenMethod(
                                       MethodName,
                                       argumentType.ToString(),
                                       Scope.Public,
                                       MethodType.Static,
                                       null,
                                       new[] { $"{argumentType} arg" },
                                       "return arg;"));
            }
        }