Esempio n. 1
0
        private CompilerResults BuildAssembly(GatewayLoader gatewayLoader, string code, AssemblyName name, string ns)
        {
            var sb = new StringBuilder();

            sb.AppendLine("using System;");
            sb.AppendLine("using System.Collections.Generic;");
            sb.AppendLine("using System.Collections;");
            sb.AppendLine("using System.Linq;");
            sb.AppendLine("using UmbracoLinqPad;");
            sb.AppendLine("using UmbracoLinqPad.Proxies;");
            sb.AppendLine("using System.IO;");
            sb.AppendLine("using System.Reflection;");
            sb.AppendLine("using UmbracoLinqPad.Gateway;");
            sb.Append("namespace ");
            sb.Append(ns);
            sb.AppendLine(" {"); //open ns
            sb.AppendLine(code);
            sb.Append("}");      //end ns

            // Use the CSharpCodeProvider to compile the generated code:
            CompilerResults results;

            using (var codeProvider = new CSharpCodeProvider(new Dictionary <string, string>()
            {
                { "CompilerVersion", "v4.0" }
            }))
            {
                var options = new CompilerParameters(
                    "System.dll System.Core.dll System.Xml.dll".Split(),
                    name.CodeBase,
                    true);

                //add this assembly reference (UmbracoLinqPad)
                options.ReferencedAssemblies.Add(typeof(UmbracoDynamicDriver).Assembly.Location);
                //add the UmbracoLinqPad.Gateway assembly reference
                options.ReferencedAssemblies.Add(gatewayLoader.GatewayAssembly.Location);
                //add the IQToolkit assembly reference
                options.ReferencedAssemblies.Add(gatewayLoader.IqToolkitAssembly.Location);
                //add the Umbraco.Core assembly reference
                options.ReferencedAssemblies.Add(gatewayLoader.UmbracoCoreAssembly.Location);

                results = codeProvider.CompileAssemblyFromSource(options, sb.ToString());
            }
            if (results.Errors.Count > 0)
            {
                throw new Exception
                          ("Cannot compile typed context: " + results.Errors[0].ErrorText + " (line " + results.Errors[0].Line + ")" + "\r\n\r\n" + sb.ToString());
            }

            return(results);
        }
Esempio n. 2
0
        public override List <ExplorerItem> GetSchemaAndBuildAssembly(IConnectionInfo cxInfo, AssemblyName assemblyToBuild, ref string nameSpace, ref string typeName)
        {
            nameSpace = "Umbraco.Generated";
            typeName  = "GeneratedUmbracoDataContext";

            var umbFolder = new DirectoryInfo(cxInfo.AppConfigPath);

            //load all assemblies in the umbraco bin folder
            var loadedAssemblies = Directory.GetFiles(Path.Combine(umbFolder.FullName, "bin"), "*.dll").Select(LoadAssemblySafely).ToList();

            //we'll need to manually resolve any assemblies loaded above
            AppDomain.CurrentDomain.AssemblyResolve += (sender, args) =>
            {
                //This is stupid but is required becaue the TypeFinder is looking for an App_Code assembly, so we'll generate an empty one
                if (args.Name == "App_Code")
                {
                    return(ResolveAppCode());
                }

                var found = loadedAssemblies.FirstOrDefault(x => x.GetName().Name == new AssemblyName(args.Name).Name);

                return(found);
            };

            //Create a loader to startup the umbraco app to create the schema and the generated DataContext class

            var driverFolder = GetDriverFolder();

            var gatewayLoader = new GatewayLoader(
                LoadAssemblySafely(Path.Combine(driverFolder, "UmbracoLinqPad.Gateway.dll")),
                loadedAssemblies.Single(x => x.GetName().Name == "Umbraco.Core"),
                LoadAssemblySafely(Path.Combine(driverFolder, "IQToolkit.dll")));

            using (var app = gatewayLoader.StartUmbracoApplication(new DirectoryInfo(cxInfo.AppConfigPath)))
            {
                using (var appCtx = app.ApplicationContext)
                {
                    var contentItemsCompiler = (IContentItemsCompiler)Activator.CreateInstance(
                        gatewayLoader.GatewayAssembly.GetType("UmbracoLinqPad.Gateway.Compilers.ContentItemsCompiler"));
                    var dataContextCompiler = (IDataContextCompiler)Activator.CreateInstance(
                        gatewayLoader.GatewayAssembly.GetType("UmbracoLinqPad.Gateway.Compilers.DataContextCompiler"));

                    var sb = new StringBuilder();

                    //create the content type classes
                    foreach (var compiled in contentItemsCompiler.GenerateClasses(appCtx.RealUmbracoApplicationContext))
                    {
                        sb.Append(compiled);
                    }

                    //add the data context class
                    sb.Append(dataContextCompiler.GenerateClass(typeName, appCtx.RealUmbracoApplicationContext));

                    var result = BuildAssembly(gatewayLoader, sb.ToString(), assemblyToBuild, nameSpace);

                    var dataContextType = result.CompiledAssembly.GetType(string.Format("{0}.{1}", nameSpace, typeName));

                    var properties = dataContextType.GetProperties()
                                                                          //Get all properties of enumerable IGeneratedContentBase
                                     .Where(x => typeof(IEnumerable <Models.IGeneratedContentBase>).IsAssignableFrom(x.PropertyType))
                                     .GroupBy(x => x.Name.Split('_')[0]); //group on 'category' property name

                    return(properties.Select(category =>
                                             new ExplorerItem(category.Key, ExplorerItemKind.Category, ExplorerIcon.Table)
                    {
                        Children = category
                                   .Select(x => new ExplorerItem(x.Name, ExplorerItemKind.QueryableObject, ExplorerIcon.View)
                        {
                            IsEnumerable = true
                        }).ToList()
                    }).ToList());
                }
            }
        }