Exemplo n.º 1
0
        public List <string> GenerateUnitTestsForClass(string solutionPath,
                                                       string generatedUnitTestProject, List <string> projClasses)
        {
            List <string> generatedTestClasses = new List <string>();

            // analyze solution, discover basic information about each project
            var            solutionAnalyzer = new SolutionAnalyzer(solutionPath);
            var            analyedSolution  = solutionAnalyzer.AnalyzeSolution();
            CompilerHelper compileHelper    = new CompilerHelper(_generatedTestClassesDirectory);

            foreach (AnalyzedProject proj in analyedSolution.Projects)
            {
                if (proj.Name != generatedUnitTestProject)
                {
                    var assembly = Assembly.LoadFile(proj.OutputFilePath); //TODO: what if the assembly does not exist because the project is not compiled??
                    _assemblyExportedTypes = assembly.GetExportedTypes();
                    inputParamGenerator    = new InputParamGenerator(_assemblyExportedTypes);

                    foreach (Type type in _assemblyExportedTypes)
                    {
                        if (projClasses.Any(pc => pc == type.Name))
                        {
                            if (!type.IsInterface) // don't want to write unit tests for interfaces
                            {
                                // create a class
                                CodeTypeDeclaration targetClass = new CodeTypeDeclaration
                                                                      (string.Format("{0}UnitTestsClass", type.Name))
                                {
                                    IsClass        = true,
                                    TypeAttributes = TypeAttributes.Public
                                };

                                // create a code unit (the in-memory representation of a class)
                                CodeCompileUnit codeUnit        = CreateCodeCompileUnit(proj.Name, type.Name, targetClass);
                                string          classSourceName = string.Format("{0}UnitTestsClass.cs", type.Name);

                                // generate the constructor for the unit test class in which all the
                                // external dependencies/calls will be mocked
                                var cut_ConstructorGenerator = new CUT_AddConstructor(inputParamGenerator, selectedProjectName);
                                cut_ConstructorGenerator.AddTestClassConstructor(classSourceName, targetClass, type, analyedSolution);

                                // generate a unit test for each method
                                // the method will be called and a Assert.NotNull assertion will be added
                                var methods = type.GetMethods(BindingFlags.Public
                                                              | BindingFlags.Instance | BindingFlags.DeclaredOnly);

                                foreach (MethodInfo m in methods)
                                {
                                    // randomly generate method parameters
                                    var methodParameters        = m.GetParameters();
                                    CodeExpression[] parameters = new CodeExpression[methodParameters.Length];
                                    int j = 0;
                                    foreach (ParameterInfo p in methodParameters)
                                    {
                                        // TODO: Rethink this !!!
                                        if (p.ParameterType.Name == "String" || p.ParameterType.Name == "Int32")
                                        {
                                            parameters[j] = new CodePrimitiveExpression(
                                                inputParamGenerator.ResolveParameter(p.ParameterType.Name));
                                        }
                                        else
                                        {
                                            CodeObjectCreateExpression createObjectExpression =
                                                inputParamGenerator.CreateCustomType(p.ParameterType.Name);
                                            parameters[j] = createObjectExpression;
                                        }
                                        j++;
                                    }

                                    var cut_addTestMethod = new CUT_AddTestMethod(inputParamGenerator);

                                    // Assert.NotNull(result);
                                    // Assert.NotThrow(() => targetObj.SomePublicMethod())
                                    cut_addTestMethod.AddTestMethod_ShouldNotThrowExceptionResultShouldNotBeNull(targetClass, m.Name,
                                                                                                                 parameters, type, "CallShouldNotThrowExceptionAndResultShouldNotBeNull");

                                    // Assert.AreEqual(result, "Insert expected value here.");
                                    cut_addTestMethod.AddTestMethod_ExpectedResultPlaceholder(targetClass, m.Name,
                                                                                              parameters, type, "ResultShouldBeAsExpected");
                                }

                                // generate the c# code based on the created code unit
                                string generatedTestClassPath = compileHelper.GenerateCSharpCode(codeUnit, classSourceName);

                                // compile the above generated code into a DLL/EXE
                                bool isGeneratedClassCompiled = compileHelper.CompileAsDLL(classSourceName, new List <string>()
                                {
                                    string.Format("{0}\\{1}", _packagesFolder, "NUnit.3.10.1\\lib\\net45\\nunit.framework.dll"),
                                    string.Format("{0}\\{1}", _packagesFolder, "Moq.4.10.0\\lib\\net45\\Moq.dll"),
                                    proj.OutputFilePath,
                                    typeof(System.Linq.Enumerable).Assembly.Location
                                });

                                if (!string.IsNullOrEmpty(generatedTestClassPath) && isGeneratedClassCompiled)
                                {
                                    generatedTestClasses.Add(generatedTestClassPath);
                                }
                            }
                        }
                    }
                }
            }

            return(generatedTestClasses);
        }
Exemplo n.º 2
0
 public CUT_AddConstructor(InputParamGenerator inputParamGenerator, string selectedProjectName)
 {
     _inputParamGenerator = inputParamGenerator;
     _selectedProjectName = selectedProjectName;
 }
Exemplo n.º 3
0
 public CUT_AddTestMethod(InputParamGenerator inputParamGenerator)
 {
     _inputParamGenerator = inputParamGenerator;
 }