Exemple #1
0
        private void CopyContentFiles(PackRoot root, Project project, string appFolderName)
        {
            Console.WriteLine("Copying contents of project dependency {0} to {1}",
                              _libraryDescription.Identity.Name, appFolderName);

            var appFolderPath = Path.Combine(root.OutputPath, appFolderName);

            Console.WriteLine("  Source {0}", project.ProjectDirectory);
            Console.WriteLine("  Target {0}", appFolderPath);

            // A set of content files that should be copied
            var contentFiles = new HashSet <string>(project.ContentFiles, StringComparer.OrdinalIgnoreCase);

            root.Operations.Copy(project.ProjectDirectory, appFolderPath, (isRoot, filePath) =>
            {
                // We always explore a directory
                if (Directory.Exists(filePath))
                {
                    return(true);
                }

                var fileName = Path.GetFileName(filePath);
                // Public app folder doesn't need project.json
                if (string.Equals(fileName, "project.json", StringComparison.OrdinalIgnoreCase))
                {
                    return(false);
                }

                return(contentFiles.Contains(filePath));
            });
        }
Exemple #2
0
        public void PostProcess(PackRoot root)
        {
            // If --wwwroot-out doesn't have a non-empty value, we don't need a public app folder in output
            if (string.IsNullOrEmpty(WwwRootOut))
            {
                return;
            }

            Runtime.Project project;
            if (!_projectResolver.TryResolveProject(_libraryDescription.Identity.Name, out project))
            {
                throw new Exception("TODO: unable to resolve project named " + _libraryDescription.Identity.Name);
            }

            // Construct path to public app folder, which contains content files and tool dlls
            // The name of public app folder is specified with "--appfolder" option
            // Default name of public app folder is the same as main project
            var wwwRootOutPath = Path.Combine(root.OutputPath, WwwRootOut);

            // Delete old public app folder because we don't want leftovers from previous operations
            root.Operations.Delete(wwwRootOutPath);
            Directory.CreateDirectory(wwwRootOutPath);

            // Copy content files (e.g. html, js and images) of main project into public app folder
            CopyContentFiles(root, project, wwwRootOutPath);

            GenerateWebConfigFileForWwwrootOut(root, wwwRootOutPath);

            CopyAspNetLoaderDll(root, wwwRootOutPath);
        }
Exemple #3
0
        private void EmitSource(PackRoot root)
        {
            root.Reports.Quiet.WriteLine("  Copying source code from {0} dependency {1}",
                                         _libraryDescription.Type, _libraryDescription.Identity.Name);

            Runtime.Project project;
            if (!_projectResolver.TryResolveProject(_libraryDescription.Identity.Name, out project))
            {
                throw new Exception("TODO: unable to resolve project named " + _libraryDescription.Identity.Name);
            }

            var targetName = project.Name;

            TargetPath = Path.Combine(root.OutputPath, PackRoot.AppRootName, "src", targetName);

            // If root.OutputPath is specified by --out option, it might not be a full path
            TargetPath = Path.GetFullPath(TargetPath);

            root.Reports.Quiet.WriteLine("    Source {0}", _libraryDescription.Path.Bold());
            root.Reports.Quiet.WriteLine("    Target {0}", TargetPath);

            root.Operations.Delete(TargetPath);

            CopyProject(root, project, TargetPath, includeSource: true);

            CopyRelativeSources(project);

            UpdateWebRoot(root, TargetPath);

            _applicationBase = Path.Combine("..", PackRoot.AppRootName, "src", project.Name);
        }
        public bool BuildNativeImages(PackRoot root)
        {
            var success = true;

            foreach (var runtime in root.Runtimes)
            {
                NuGetDependencyResolver resolver;
                if (!_resolverLookup.TryGetValue(runtime.Framework, out resolver))
                {
                    throw new InvalidOperationException("No matching framework is found for " + runtime.Framework);
                }

                var runtimeBin = Path.Combine(runtime.TargetPath, "bin");

                var options = new CrossgenOptions()
                {
                    CrossgenPath = Path.Combine(runtimeBin, "crossgen.exe"),
                    InputPaths   = ResolveOutputAssemblies(root, resolver),
                    RuntimePath  = runtimeBin,
                    Symbols      = false
                };

                var crossgenManager = new CrossgenManager(options);
                success &= crossgenManager.GenerateNativeImages();

                if (!success)
                {
                    return(false);
                }
            }
            return(success);
        }
Exemple #5
0
 public PackRuntime(PackRoot root, FrameworkName frameworkName, string kreNupkgPath)
 {
     _frameworkName = frameworkName;
     _kreNupkgPath  = kreNupkgPath;
     Name           = Path.GetFileName(Path.GetDirectoryName(_kreNupkgPath));
     TargetPath     = Path.Combine(root.TargetPackagesPath, Name);
 }
Exemple #6
0
        private static string GetBootstrapperVersion(PackRoot root)
        {
            // Use version of Microsoft.AspNet.Loader.IIS.Interop as version of bootstrapper
            var package = root.Packages.SingleOrDefault(
                x => string.Equals(x.Library.Name, "Microsoft.AspNet.Loader.IIS.Interop"));

            return(package == null ? string.Empty : package.Library.Version.ToString());
        }
Exemple #7
0
 public void Emit(PackRoot root)
 {
     root.Reports.Quiet.WriteLine("Using {0} dependency {1}", _libraryDescription.Type, Library);
     foreach (var context in root.LibraryDependencyContexts[Library])
     {
         root.Reports.Quiet.WriteLine("  Copying files for {0}",
                                      context.FrameworkName.ToString().Yellow().Bold());
         Emit(root, context.PackageAssemblies[Library.Name]);
         root.Reports.Quiet.WriteLine();
     }
 }
Exemple #8
0
        private void CopyContentFiles(PackRoot root, Runtime.Project project, string targetFolderPath)
        {
            root.Reports.Quiet.WriteLine("Copying contents of {0} dependency {1} to {2}",
                                         _libraryDescription.Type, _libraryDescription.Identity.Name, targetFolderPath);

            var contentSourcePath = GetWwwRootSourcePath(project.ProjectDirectory, WwwRoot);

            root.Reports.Quiet.WriteLine("  Source {0}", contentSourcePath);
            root.Reports.Quiet.WriteLine("  Target {0}", targetFolderPath);

            root.Operations.Copy(contentSourcePath, targetFolderPath);
        }
Exemple #9
0
        private void CopyProject(PackRoot root, Runtime.Project project, string targetPath, bool includeSource)
        {
            // A set of excluded files/directories used as a filter when doing copy
            var excludeSet   = new HashSet <string>(project.PackExcludeFiles, StringComparer.OrdinalIgnoreCase);
            var contentFiles = new HashSet <string>(project.ContentFiles, StringComparer.OrdinalIgnoreCase);

            // If a public folder is specified with 'webroot' or '--wwwroot', we ignore it when copying project files
            var wwwRootPath = string.Empty;

            if (!string.IsNullOrEmpty(WwwRoot))
            {
                wwwRootPath = Path.Combine(project.ProjectDirectory, WwwRoot);
                wwwRootPath = PathUtility.EnsureTrailingSlash(wwwRootPath);
            }

            // If project root is used as value of '--wwwroot', we shouldn't exclude it when copying
            if (string.Equals(wwwRootPath, PathUtility.EnsureTrailingSlash(project.ProjectDirectory)))
            {
                wwwRootPath = string.Empty;
            }

            root.Operations.Copy(project.ProjectDirectory, targetPath, itemPath =>
            {
                // If current file/folder is in the exclusion list, we don't copy it
                if (excludeSet.Contains(itemPath))
                {
                    return(false);
                }

                // If current file is in the public folder, we don't copy it to destination project
                if (!string.IsNullOrEmpty(wwwRootPath) && itemPath.StartsWith(wwwRootPath))
                {
                    return(false);
                }

                // The full path of target generated by copy operation should also be excluded
                var targetFullPath = itemPath.Replace(project.ProjectDirectory, TargetPath);
                excludeSet.Add(targetFullPath);

                if (includeSource)
                {
                    return(true);
                }

                if (Directory.Exists(itemPath))
                {
                    return(true);
                }

                return(contentFiles.Contains(itemPath));
            });
        }
Exemple #10
0
        private void UpdateWebRoot(PackRoot root, string targetPath)
        {
            // Update the 'webroot' property, which was specified with '--wwwroot-out' option
            if (!string.IsNullOrEmpty(WwwRootOut))
            {
                var targetProjectJson = Path.Combine(targetPath, Runtime.Project.ProjectFileName);

                UpdateJson(targetProjectJson, jsonObj =>
                {
                    var targetWebRootPath = Path.Combine(root.OutputPath, WwwRootOut);
                    jsonObj["webroot"]    = PathUtility.GetRelativePath(targetProjectJson, targetWebRootPath);
                });
            }
        }
Exemple #11
0
        public void Emit(PackRoot root)
        {
            var package = _nugetDependencyResolver.FindCandidate(
                _libraryDescription.Identity.Name,
                _libraryDescription.Identity.Version);

            Console.WriteLine("Packing nupkg dependency {0} {1}", package.Id, package.Version);

            var resolver = new DefaultPackagePathResolver(root.PackagesPath);

            TargetPath = resolver.GetInstallPath(package.Id, package.Version);

            if (Directory.Exists(TargetPath))
            {
                if (root.Overwrite)
                {
                    root.Operations.Delete(TargetPath);
                }
                else
                {
                    Console.WriteLine("  {0} already exists.", TargetPath);
                    return;
                }
            }

            Console.WriteLine("  Target {0}", TargetPath);

            var targetNupkgPath = resolver.GetPackageFilePath(package.Id, package.Version);
            var hashPath        = resolver.GetHashPath(package.Id, package.Version);

            using (var sourceStream = package.GetStream())
            {
                using (var archive = new ZipArchive(sourceStream, ZipArchiveMode.Read))
                {
                    root.Operations.ExtractNupkg(archive, TargetPath);
                }
            }
            using (var sourceStream = package.GetStream())
            {
                using (var targetStream = new FileStream(targetNupkgPath, FileMode.Create, FileAccess.Write, FileShare.None))
                {
                    sourceStream.CopyTo(targetStream);
                }

                sourceStream.Seek(0, SeekOrigin.Begin);
                var sha512Bytes = SHA512.Create().ComputeHash(sourceStream);
                File.WriteAllText(hashPath, Convert.ToBase64String(sha512Bytes));
            }
        }
Exemple #12
0
        public void Emit(PackRoot root)
        {
            root.Reports.Quiet.WriteLine("Using {0} dependency {1} for {2}", _libraryDescription.Type,
                                         _libraryDescription.Identity, _libraryDescription.Framework.ToString().Yellow().Bold());

            if (root.NoSource)
            {
                EmitNupkg(root);
            }
            else
            {
                EmitSource(root);
            }
            root.Reports.Quiet.WriteLine();
        }
        /// <summary>
        /// This is a helper method for looking up directories that directly contains assemblies that would be loaded
        /// given the packed runtime framework. We should run crossgen on these folders
        /// </summary>
        private IEnumerable <string> ResolveOutputAssemblies(PackRoot root, NuGetDependencyResolver resolver)
        {
            var outputPathsMap = root.Packages
                                 .ToDictionary(
                pkg => pkg.Library,
                pkg => pkg.TargetPath
                );

            var result              = new HashSet <string>();
            var libraryNotInOutput  = new List <Library>();
            var missingOutputFolder = new List <string>();

            foreach (var dependency in resolver.PackageAssemblyLookup.Values)
            {
                var    libId             = dependency.Library.Identity;
                var    libPath           = dependency.Library.Path;
                var    assemblyDir       = Path.GetDirectoryName(dependency.Path);
                var    assemblySelection = assemblyDir.Substring(libPath.Length);
                string outputLibLocation;
                if (!outputPathsMap.TryGetValue(libId, out outputLibLocation))
                {
                    libraryNotInOutput.Add(libId);
                    continue;
                }
                var output = outputLibLocation + assemblySelection;

                if (!Directory.Exists(output))
                {
                    missingOutputFolder.Add(output);
                }
                else
                {
                    result.Add(output);
                }
            }

            if (libraryNotInOutput.Any())
            {
                throw new InvalidOperationException(string.Format("Library {0} cannot be found in the packed output.", string.Join(", ", libraryNotInOutput)));
            }

            if (missingOutputFolder.Any())
            {
                throw new InvalidOperationException("Packed output does not contain directory:\n" + string.Join("\n", missingOutputFolder));
            }

            return(result);
        }
Exemple #14
0
        private void CopyContentFiles(PackRoot root, Runtime.Project project, string targetFolderPath)
        {
            root.Reports.Quiet.WriteLine("Copying contents of {0} dependency {1} to {2}",
                                         _libraryDescription.Type, _libraryDescription.Identity.Name, targetFolderPath);

            var contentSourceFolder = WwwRoot ?? string.Empty;
            var contentSourcePath   = Path.Combine(project.ProjectDirectory, contentSourceFolder);

            // If the value of '--wwwroot' is ".", we need to pack the project root dir
            // Use Path.GetFullPath() to get rid of the trailing "."
            contentSourcePath = Path.GetFullPath(contentSourcePath);

            root.Reports.Quiet.WriteLine("  Source {0}", contentSourcePath);
            root.Reports.Quiet.WriteLine("  Target {0}", targetFolderPath);

            root.Operations.Copy(contentSourcePath, targetFolderPath);
        }
Exemple #15
0
        bool TryAddRuntime(PackRoot root, FrameworkName frameworkName, string krePath)
        {
            if (!Directory.Exists(krePath))
            {
                return(false);
            }

            var kreName      = Path.GetFileName(Path.GetDirectoryName(Path.Combine(krePath, ".")));
            var kreNupkgPath = Path.Combine(krePath, kreName + ".nupkg");

            if (!File.Exists(kreNupkgPath))
            {
                return(false);
            }

            root.Runtimes.Add(new PackRuntime(root, frameworkName, kreNupkgPath));
            return(true);
        }
        /// <summary>
        /// This is the factory method to instantiate a PackNativeManager, if parameters are in invalid state and native
        /// generation cannot be performed, it would return null
        /// </summary>
        public static NativeImageGenerator Create(PackOptions options, PackRoot root, IEnumerable <DependencyContext> contexts)
        {
            if (options.Runtimes.Count() == 0)
            {
                options.Reports.Information.WriteLine(
                    "Please provide target CoreCLR runtimes using --runtime flags".Yellow());
                return(null);
            }

            foreach (var runtime in root.Runtimes)
            {
                var frameworkName = runtime.Framework;
                // NOTE: !IsDesktop == IsCore and only Core packages can be crossgened at least for now
                if (VersionUtility.IsDesktop(frameworkName))
                {
                    options.Reports.Information.WriteLine(
                        "Native image generation is only supported for KLR Core flavors.".Yellow());
                    return(null);
                }
            }

            var duplicates = options.Runtimes
                             .GroupBy(r => CrossgenManager.ResolveProcessorArchitecture(r))
                             .Where(g => g.Count() > 1);

            if (duplicates.Any())
            {
                var message = "The following runtimes will result in output conflicts. Please provide distinct KRE flavor for each processor architecture:\n"
                              + string.Join("\n", duplicates.Select(
                                                g => string.Format("Architecture: {0}\nRuntimes: {1}", g.Key, string.Join(", ", g))));
                options.Reports.Information.WriteLine(message.Yellow());
                return(null);
            }

            var contextMap = contexts.ToDictionary(
                context => context.FrameworkName,
                context => context.NuGetDependencyResolver
                );

            return(new NativeImageGenerator(contextMap));
        }
Exemple #17
0
        private void CopyFile(PackRoot root, string srcPath, string targetPath, bool overwrite)
        {
            var targetFolder = Path.GetDirectoryName(targetPath);

            Directory.CreateDirectory(targetFolder);

            if (File.Exists(targetPath))
            {
                if (overwrite)
                {
                    File.Delete(targetPath);
                }
                else
                {
                    root.Reports.Quiet.WriteLine("    {0} already exists", targetPath);
                    return;
                }
            }

            File.Copy(srcPath, targetPath);
        }
Exemple #18
0
        public void Emit(PackRoot root)
        {
            Name = Path.GetFileName(Path.GetDirectoryName(_kreNupkgPath));

            Console.WriteLine("Packing runtime {0}", Name);

            TargetPath = Path.Combine(root.PackagesPath, Name);

            if (Directory.Exists(TargetPath))
            {
                Console.WriteLine("  {0} already exists.", TargetPath);
                return;
            }

            if (!Directory.Exists(TargetPath))
            {
                Directory.CreateDirectory(TargetPath);
            }

            var targetNupkgPath = Path.Combine(TargetPath, Name + ".nupkg");

            using (var sourceStream = File.OpenRead(_kreNupkgPath))
            {
                using (var archive = new ZipArchive(sourceStream, ZipArchiveMode.Read))
                {
                    root.Operations.ExtractNupkg(archive, TargetPath);
                }
            }
            using (var sourceStream = File.OpenRead(_kreNupkgPath))
            {
                using (var targetStream = new FileStream(targetNupkgPath, FileMode.Create, FileAccess.Write, FileShare.None))
                {
                    sourceStream.CopyTo(targetStream);
                }

                sourceStream.Seek(0, SeekOrigin.Begin);
                var sha512Bytes = SHA512.Create().ComputeHash(sourceStream);
                File.WriteAllText(targetNupkgPath + ".sha512", Convert.ToBase64String(sha512Bytes));
            }
        }
Exemple #19
0
        public void EmitSource(PackRoot root)
        {
            Console.WriteLine("Packing project dependency {0}", _libraryDescription.Identity.Name);

            Runtime.Project project;
            if (!_projectResolver.TryResolveProject(_libraryDescription.Identity.Name, out project))
            {
                throw new Exception("TODO: unable to resolve project named " + _libraryDescription.Identity.Name);
            }

            var targetName = project.Name;

            TargetPath = Path.Combine(root.OutputPath, PackRoot.AppRootName, "src", targetName);

            // If root.OutputPath is specified by --out option, it might not be a full path
            TargetPath = Path.GetFullPath(TargetPath);

            Console.WriteLine("  Source {0}", project.ProjectDirectory);
            Console.WriteLine("  Target {0}", TargetPath);

            root.Operations.Delete(TargetPath);

            // A set of excluded files/directories used as a filter when doing copy
            var excludeSet = new HashSet <string>(project.PackExcludeFiles, StringComparer.OrdinalIgnoreCase);

            root.Operations.Copy(project.ProjectDirectory, TargetPath, (isRoot, filePath) =>
            {
                if (excludeSet.Contains(filePath))
                {
                    return(false);
                }

                // The full path of target generated by copy operation should also be excluded
                var targetFullPath = filePath.Replace(project.ProjectDirectory, TargetPath);
                excludeSet.Add(targetFullPath);

                return(true);
            });
        }
Exemple #20
0
        private void CopyFolder(PackRoot root, string srcFolder, string targetFolder)
        {
            if (!Directory.Exists(srcFolder))
            {
                return;
            }

            if (Directory.Exists(targetFolder))
            {
                if (root.Overwrite)
                {
                    root.Operations.Delete(targetFolder);
                }
                else
                {
                    root.Reports.Quiet.WriteLine("    {0} already exists", targetFolder);
                    return;
                }
            }

            Directory.CreateDirectory(targetFolder);
            root.Operations.Copy(srcFolder, targetFolder);
        }
Exemple #21
0
        private static void CopyAspNetLoaderDll(PackRoot root, string wwwRootOutPath)
        {
            // Tool dlls including AspNet.Loader.dll go to bin folder under public app folder
            var wwwRootOutBinPath = Path.Combine(wwwRootOutPath, "bin");

            // Copy Microsoft.AspNet.Loader.IIS.Interop/tools/*.dll into bin to support AspNet.Loader.dll
            var package = root.Packages.SingleOrDefault(
                x => string.Equals(x.Library.Name, "Microsoft.AspNet.Loader.IIS.Interop"));

            if (package == null)
            {
                return;
            }

            var resolver         = new DefaultPackagePathResolver(root.SourcePackagesPath);
            var packagePath      = resolver.GetInstallPath(package.Library.Name, package.Library.Version);
            var packageToolsPath = Path.Combine(packagePath, "tools");

            if (Directory.Exists(packageToolsPath))
            {
                foreach (var packageToolFile in Directory.EnumerateFiles(packageToolsPath, "*.dll").Select(Path.GetFileName))
                {
                    // Create the bin folder only when we need to put something inside it
                    if (!Directory.Exists(wwwRootOutBinPath))
                    {
                        Directory.CreateDirectory(wwwRootOutBinPath);
                    }

                    // Copy to bin folder under public app folder
                    File.Copy(
                        Path.Combine(packageToolsPath, packageToolFile),
                        Path.Combine(wwwRootOutBinPath, packageToolFile),
                        overwrite: true);
                }
            }
        }
Exemple #22
0
        private void Emit(PackRoot root, IEnumerable <PackageAssembly> assemblies)
        {
            var resolver = new DefaultPackagePathResolver(root.TargetPackagesPath);

            TargetPath = resolver.GetInstallPath(Library.Name, Library.Version);

            root.Reports.Quiet.WriteLine("    Source: {0}", _libraryDescription.Path);
            root.Reports.Quiet.WriteLine("    Target: {0}", TargetPath);

            Directory.CreateDirectory(TargetPath);

            // Copy nuspec
            var nuspecName = resolver.GetManifestFileName(Library.Name, Library.Version);

            root.Reports.Quiet.WriteLine("    File: {0}", nuspecName.Bold());
            CopyFile(root, Path.Combine(_libraryDescription.Path, nuspecName), Path.Combine(TargetPath, nuspecName), root.Overwrite);

            // Copy assemblies for current framework
            foreach (var assembly in assemblies)
            {
                root.Reports.Quiet.WriteLine("    File: {0}", assembly.RelativePath.Bold());

                var targetAssemblyPath = Path.Combine(TargetPath, assembly.RelativePath);
                CopyFile(root, assembly.Path, targetAssemblyPath, root.Overwrite);
            }

            // Special cases
            var specialFolders = new[] { "native", "InteropAssemblies", "redist", Path.Combine("lib", "contract") };

            foreach (var folder in specialFolders)
            {
                var srcFolder    = Path.Combine(_libraryDescription.Path, folder);
                var targetFolder = Path.Combine(TargetPath, folder);
                CopyFolder(root, srcFolder, targetFolder);
            }
        }
Exemple #23
0
        public bool Package()
        {
            Runtime.Project project;
            if (!Runtime.Project.TryGetProject(_options.ProjectDir, out project))
            {
                Console.WriteLine("Unable to locate {0}.'", Runtime.Project.ProjectFileName);
                return(false);
            }

            var sw = Stopwatch.StartNew();

            string outputPath = _options.OutputDir ?? Path.Combine(_options.ProjectDir, "bin", "output");

            var projectDir = project.ProjectDirectory;

            var dependencyContexts = new List <DependencyContext>();

            var root = new PackRoot(project, outputPath, _hostServices)
            {
                Overwrite     = _options.Overwrite,
                Configuration = _options.Configuration,
                NoSource      = _options.NoSource
            };

            Func <string, string> getVariable = key =>
            {
                return(null);
            };

            ScriptExecutor.Execute(project, "prepare", getVariable);

            ScriptExecutor.Execute(project, "prepack", getVariable);

            foreach (var runtime in _options.Runtimes)
            {
                var runtimeLocated = TryAddRuntime(root, runtime);

                var kreHome = Environment.GetEnvironmentVariable("KRE_HOME");
                if (string.IsNullOrEmpty(kreHome))
                {
                    kreHome = Environment.GetEnvironmentVariable("ProgramFiles") + @"\KRE;%USERPROFILE%\.kre";
                }

                foreach (var portion in kreHome.Split(new[] { ';' }, StringSplitOptions.RemoveEmptyEntries))
                {
                    var packagesPath = Path.Combine(
                        Environment.ExpandEnvironmentVariables(portion),
                        "packages",
                        runtime);

                    if (TryAddRuntime(root, packagesPath))
                    {
                        runtimeLocated = true;
                        break;
                    }
                }

                if (!runtimeLocated)
                {
                    Console.WriteLine(string.Format("Unable to locate runtime '{0}'", runtime));
                    return(false);
                }

                var frameworkName = DependencyContext.GetFrameworkNameForRuntime(Path.GetFileName(runtime));
                if (!dependencyContexts.Any(dc => dc.FrameworkName == frameworkName))
                {
                    var dependencyContext = new DependencyContext(projectDir, _options.Configuration, frameworkName);
                    dependencyContext.Walk(project.Name, project.Version);
                    dependencyContexts.Add(dependencyContext);
                }
            }

            if (!dependencyContexts.Any())
            {
                var frameworkName     = DependencyContext.GetFrameworkNameForRuntime("KRE-svr50-x86.*");
                var dependencyContext = new DependencyContext(projectDir, _options.Configuration, frameworkName);
                dependencyContext.Walk(project.Name, project.Version);
                dependencyContexts.Add(dependencyContext);
            }

            foreach (var dependencyContext in dependencyContexts)
            {
                foreach (var libraryDescription in dependencyContext.NuGetDependencyResolver.Dependencies)
                {
                    if (!root.Packages.Any(p => p.Library == libraryDescription.Identity))
                    {
                        root.Packages.Add(new PackPackage(dependencyContext.NuGetDependencyResolver, libraryDescription));
                    }
                }
                foreach (var libraryDescription in dependencyContext.ProjectReferenceDependencyProvider.Dependencies)
                {
                    if (!root.Projects.Any(p => p.Name == libraryDescription.Identity.Name))
                    {
                        var packProject = new PackProject(dependencyContext.ProjectReferenceDependencyProvider, dependencyContext.ProjectResolver, libraryDescription);
                        if (packProject.Name == project.Name)
                        {
                            packProject.AppFolder = _options.AppFolder;
                        }
                        root.Projects.Add(packProject);
                    }
                }
            }

            root.Emit();

            ScriptExecutor.Execute(project, "postpack", getVariable);

            sw.Stop();

            Console.WriteLine("Time elapsed {0}", sw.Elapsed);
            return(true);
        }
Exemple #24
0
        public void EmitNupkg(PackRoot root)
        {
            Console.WriteLine("Packing nupkg from project dependency {0}", _libraryDescription.Identity.Name);

            Runtime.Project project;
            if (!_projectResolver.TryResolveProject(_libraryDescription.Identity.Name, out project))
            {
                throw new Exception("TODO: unable to resolve project named " + _libraryDescription.Identity.Name);
            }

            var resolver = new DefaultPackagePathResolver(root.PackagesPath);

            var targetNupkg = resolver.GetPackageFileName(project.Name, project.Version);

            TargetPath = resolver.GetInstallPath(project.Name, project.Version);

            Console.WriteLine("  Source {0}", project.ProjectDirectory);
            Console.WriteLine("  Target {0}", TargetPath);

            if (Directory.Exists(TargetPath))
            {
                if (root.Overwrite)
                {
                    root.Operations.Delete(TargetPath);
                }
                else
                {
                    Console.WriteLine("  {0} already exists.", TargetPath);
                    return;
                }
            }

            // Generate nupkg from this project dependency
            var buildOptions = new BuildOptions();

            buildOptions.ProjectDir = project.ProjectDirectory;
            buildOptions.OutputDir  = Path.Combine(project.ProjectDirectory, "bin");
            buildOptions.Configurations.Add(root.Configuration);
            var buildManager = new BuildManager(root.HostServices, buildOptions);

            if (!buildManager.Build())
            {
                return;
            }

            // Extract the generated nupkg to target path
            var srcNupkgPath    = Path.Combine(buildOptions.OutputDir, root.Configuration, targetNupkg);
            var targetNupkgPath = resolver.GetPackageFilePath(project.Name, project.Version);
            var hashFile        = resolver.GetHashPath(project.Name, project.Version);

            using (var sourceStream = new FileStream(srcNupkgPath, FileMode.Open, FileAccess.Read))
            {
                using (var archive = new ZipArchive(sourceStream, ZipArchiveMode.Read))
                {
                    root.Operations.ExtractNupkg(archive, TargetPath);
                }
            }

            using (var sourceStream = new FileStream(srcNupkgPath, FileMode.Open, FileAccess.Read))
            {
                using (var targetStream = new FileStream(targetNupkgPath, FileMode.Create, FileAccess.Write, FileShare.None))
                {
                    sourceStream.CopyTo(targetStream);
                }

                sourceStream.Seek(0, SeekOrigin.Begin);
                var sha512Bytes = SHA512.Create().ComputeHash(sourceStream);
                File.WriteAllText(hashFile, Convert.ToBase64String(sha512Bytes));
            }
        }
Exemple #25
0
        public bool Package()
        {
            Runtime.Project project;
            if (!Runtime.Project.TryGetProject(_options.ProjectDir, out project))
            {
                _options.Reports.Error.WriteLine("Unable to locate {0}.'".Red(), Runtime.Project.ProjectFileName);
                return(false);
            }

            // '--wwwroot' option can override 'webroot' property in project.json
            _options.WwwRoot    = _options.WwwRoot ?? project.WebRoot;
            _options.WwwRootOut = _options.WwwRootOut ?? _options.WwwRoot;

            if (string.IsNullOrEmpty(_options.WwwRoot) && !string.IsNullOrEmpty(_options.WwwRootOut))
            {
                _options.Reports.Error.WriteLine(
                    "'--wwwroot-out' option can be used only when the '--wwwroot' option or 'webroot' in project.json is specified.".Red());
                return(false);
            }

            if (!string.IsNullOrEmpty(_options.WwwRoot) &&
                !Directory.Exists(Path.Combine(project.ProjectDirectory, _options.WwwRoot)))
            {
                _options.Reports.Error.WriteLine(
                    "The specified wwwroot folder '{0}' doesn't exist in the project directory.".Red(), _options.WwwRoot);
                return(false);
            }

            if (string.Equals(_options.WwwRootOut, PackRoot.AppRootName, StringComparison.OrdinalIgnoreCase))
            {
                _options.Reports.Error.WriteLine(
                    "'{0}' is a reserved folder name. Please choose another name for the wwwroot-out folder.".Red(),
                    PackRoot.AppRootName);
                return(false);
            }

            var sw = Stopwatch.StartNew();

            string outputPath = _options.OutputDir;

            var projectDir = project.ProjectDirectory;

            var frameworkContexts = new Dictionary <FrameworkName, DependencyContext>();

            var root = new PackRoot(project, outputPath, _hostServices, _options.Reports)
            {
                Overwrite     = _options.Overwrite,
                Configuration = _options.Configuration,
                NoSource      = _options.NoSource
            };

            Func <string, string> getVariable = key =>
            {
                return(null);
            };

            ScriptExecutor.Execute(project, "prepare", getVariable);

            ScriptExecutor.Execute(project, "prepack", getVariable);

            foreach (var runtime in _options.Runtimes)
            {
                var frameworkName  = DependencyContext.GetFrameworkNameForRuntime(Path.GetFileName(runtime));
                var runtimeLocated = TryAddRuntime(root, frameworkName, runtime);

                if (!runtimeLocated)
                {
                    var kreHome = Environment.GetEnvironmentVariable("KRE_HOME");
                    if (string.IsNullOrEmpty(kreHome))
                    {
#if ASPNETCORE50
                        kreHome = Environment.GetEnvironmentVariable("ProgramFiles") + @"\KRE;%USERPROFILE%\.kre";
#else
                        var userProfile = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile);
                        kreHome = Path.Combine(userProfile, ".kre");
                        if (!PlatformHelper.IsMono)
                        {
                            var programFilesPath = Environment.GetEnvironmentVariable("ProgramFiles");
                            kreHome = Path.Combine(programFilesPath, "KRE") + ";" + kreHome;
                        }
#endif
                    }

                    foreach (var portion in kreHome.Split(new[] { ';' }, StringSplitOptions.RemoveEmptyEntries))
                    {
                        var packagesPath = Path.Combine(
                            Environment.ExpandEnvironmentVariables(portion),
                            "packages",
                            runtime);

                        if (TryAddRuntime(root, frameworkName, packagesPath))
                        {
                            runtimeLocated = true;
                            break;
                        }
                    }
                }

                if (!runtimeLocated)
                {
                    _options.Reports.Error.WriteLine(string.Format("Unable to locate runtime '{0}'", runtime.Red().Bold()));
                    return(false);
                }

                if (!project.GetTargetFrameworks().Any(x => x.FrameworkName == frameworkName))
                {
                    _options.Reports.Error.WriteLine(
                        string.Format("'{0}' is not a target framework of the project being packed",
                                      frameworkName.ToString().Red().Bold()));
                    return(false);
                }

                if (!frameworkContexts.ContainsKey(frameworkName))
                {
                    frameworkContexts[frameworkName] = CreateDependencyContext(project, frameworkName);
                }
            }

            // If there is no target framework filter specified with '--runtime',
            // the packed output targets all frameworks specified in project.json
            if (!_options.Runtimes.Any())
            {
                foreach (var frameworkInfo in project.GetTargetFrameworks())
                {
                    if (!frameworkContexts.ContainsKey(frameworkInfo.FrameworkName))
                    {
                        frameworkContexts[frameworkInfo.FrameworkName] =
                            CreateDependencyContext(project, frameworkInfo.FrameworkName);
                    }
                }
            }

            if (!frameworkContexts.Any())
            {
                var frameworkName = DependencyContext.GetFrameworkNameForRuntime("KRE-CLR-x86.*");
                frameworkContexts[frameworkName] = CreateDependencyContext(project, frameworkName);
            }

            root.SourcePackagesPath = frameworkContexts.First().Value.PackagesDirectory;

            bool anyUnresolvedDependency = false;
            foreach (var dependencyContext in frameworkContexts.Values)
            {
                // If there's any unresolved dependencies then complain and keep working
                if (dependencyContext.DependencyWalker.Libraries.Any(l => !l.Resolved))
                {
                    anyUnresolvedDependency = true;
                    var message = "Warning: " +
                                  dependencyContext.DependencyWalker.GetMissingDependenciesWarning(
                        dependencyContext.FrameworkName);
                    _options.Reports.Quiet.WriteLine(message.Yellow());
                }

                foreach (var libraryDescription in dependencyContext.NuGetDependencyResolver.Dependencies)
                {
                    IList <DependencyContext> contexts;
                    if (!root.LibraryDependencyContexts.TryGetValue(libraryDescription.Identity, out contexts))
                    {
                        root.Packages.Add(new PackPackage(libraryDescription));
                        contexts = new List <DependencyContext>();
                        root.LibraryDependencyContexts[libraryDescription.Identity] = contexts;
                    }
                    contexts.Add(dependencyContext);
                }

                foreach (var libraryDescription in dependencyContext.ProjectReferenceDependencyProvider.Dependencies)
                {
                    if (!root.Projects.Any(p => p.Name == libraryDescription.Identity.Name))
                    {
                        var packProject = new PackProject(
                            dependencyContext.ProjectReferenceDependencyProvider,
                            dependencyContext.ProjectResolver,
                            libraryDescription);

                        if (packProject.Name == project.Name)
                        {
                            packProject.WwwRoot    = _options.WwwRoot;
                            packProject.WwwRootOut = _options.WwwRootOut;
                        }
                        root.Projects.Add(packProject);
                    }
                }
            }

            NativeImageGenerator nativeImageGenerator = null;
            if (_options.Native)
            {
                nativeImageGenerator = NativeImageGenerator.Create(_options, root, frameworkContexts.Values);
                if (nativeImageGenerator == null)
                {
                    _options.Reports.Error.WriteLine("Fail to initiate native image generation process.".Red());
                    return(false);
                }
            }

            root.Emit();

            ScriptExecutor.Execute(project, "postpack", getVariable);

            if (_options.Native && !nativeImageGenerator.BuildNativeImages(root))
            {
                _options.Reports.Error.WriteLine("Native image generation failed.");
                return(false);
            }

            sw.Stop();

            _options.Reports.Information.WriteLine("Time elapsed {0}", sw.Elapsed);
            return(!anyUnresolvedDependency);
        }
Exemple #26
0
        private void GenerateWebConfigFileForWwwrootOut(PackRoot root, string wwwRootOutPath)
        {
            // Generate k.ini for public app folder
            var wwwRootOutWebConfigFilePath = Path.Combine(wwwRootOutPath, "web.config");
            var webConfigFilePath           = Path.Combine(TargetPath, "web.config");

            XDocument xDoc;

            if (File.Exists(webConfigFilePath))
            {
                xDoc = XDocument.Parse(File.ReadAllText(webConfigFilePath));
            }
            else
            {
                xDoc = new XDocument();
            }

            if (xDoc.Root == null)
            {
                xDoc.Add(new XElement("configuration"));
            }

            if (xDoc.Root.Name != "configuration")
            {
                throw new InvalidDataException("'configuration' is the only valid name for root element of web.config file");
            }

            var appSettingsElement = GetOrAddElement(parent: xDoc.Root, name: "appSettings");

            var relativePackagesPath = PathUtility.GetRelativePath(wwwRootOutWebConfigFilePath, root.TargetPackagesPath);
            var defaultRuntime       = root.Runtimes.FirstOrDefault();

            var keyValuePairs = new Dictionary <string, string>()
            {
                { "kpm-package-path", relativePackagesPath },
                { "bootstrapper-version", GetBootstrapperVersion(root) },
                { "kre-package-path", relativePackagesPath },
                { "kre-version", GetRuntimeVersion(defaultRuntime) },
                { "kre-clr", GetRuntimeFlavor(defaultRuntime) },
                { "kre-app-base", _applicationBase },
            };

            foreach (var pair in keyValuePairs)
            {
                var addElement = appSettingsElement.Elements()
                                 .Where(x => x.Name == "add" && x.Attribute("key").Value == pair.Key)
                                 .SingleOrDefault();
                if (addElement == null)
                {
                    addElement = new XElement("add");
                    addElement.SetAttributeValue("key", pair.Key);
                    appSettingsElement.Add(addElement);
                }

                addElement.SetAttributeValue("value", pair.Value);
            }

            var xmlWriterSettings = new XmlWriterSettings
            {
                Indent           = true,
                ConformanceLevel = ConformanceLevel.Auto
            };

            using (var xmlWriter = XmlWriter.Create(File.Create(wwwRootOutWebConfigFilePath), xmlWriterSettings))
            {
                xDoc.WriteTo(xmlWriter);
            }
        }
Exemple #27
0
        private void EmitNupkg(PackRoot root)
        {
            root.Reports.Quiet.WriteLine("  Packing nupkg from {0} dependency {1}",
                                         _libraryDescription.Type, _libraryDescription.Identity.Name);

            Runtime.Project project;
            if (!_projectResolver.TryResolveProject(_libraryDescription.Identity.Name, out project))
            {
                throw new Exception("TODO: unable to resolve project named " + _libraryDescription.Identity.Name);
            }

            var resolver = new DefaultPackagePathResolver(root.TargetPackagesPath);

            var targetNupkg = resolver.GetPackageFileName(project.Name, project.Version);

            TargetPath = resolver.GetInstallPath(project.Name, project.Version);

            root.Reports.Quiet.WriteLine("    Source {0}", _libraryDescription.Path.Bold());
            root.Reports.Quiet.WriteLine("    Target {0}", TargetPath);

            if (Directory.Exists(TargetPath))
            {
                if (root.Overwrite)
                {
                    root.Operations.Delete(TargetPath);
                }
                else
                {
                    root.Reports.Quiet.WriteLine("  {0} already exists.", TargetPath);
                    return;
                }
            }

            // Generate nupkg from this project dependency
            var buildOptions = new BuildOptions();

            buildOptions.ProjectDir = project.ProjectDirectory;
            buildOptions.OutputDir  = Path.Combine(project.ProjectDirectory, "bin");
            buildOptions.Configurations.Add(root.Configuration);
            buildOptions.Reports = root.Reports;
            var buildManager = new BuildManager(root.HostServices, buildOptions);

            if (!buildManager.Build())
            {
                return;
            }

            // Extract the generated nupkg to target path
            var srcNupkgPath    = Path.Combine(buildOptions.OutputDir, root.Configuration, targetNupkg);
            var targetNupkgPath = resolver.GetPackageFilePath(project.Name, project.Version);
            var hashFile        = resolver.GetHashPath(project.Name, project.Version);

            using (var sourceStream = new FileStream(srcNupkgPath, FileMode.Open, FileAccess.Read))
            {
                using (var archive = new ZipArchive(sourceStream, ZipArchiveMode.Read))
                {
                    root.Operations.ExtractNupkg(archive, TargetPath);
                }
            }

            using (var sourceStream = new FileStream(srcNupkgPath, FileMode.Open, FileAccess.Read))
            {
                using (var targetStream = new FileStream(targetNupkgPath, FileMode.Create, FileAccess.Write, FileShare.None))
                {
                    sourceStream.CopyTo(targetStream);
                }

                sourceStream.Seek(0, SeekOrigin.Begin);
                var sha512Bytes = SHA512.Create().ComputeHash(sourceStream);
                File.WriteAllText(hashFile, Convert.ToBase64String(sha512Bytes));
            }

            // Copy content files (e.g. html, js and images) of main project into "root" folder of the exported package
            var rootFolderPath  = Path.Combine(TargetPath, "root");
            var rootProjectJson = Path.Combine(rootFolderPath, Runtime.Project.ProjectFileName);

            CopyProject(root, project, rootFolderPath, includeSource: false);

            UpdateWebRoot(root, rootFolderPath);

            UpdateJson(rootProjectJson, jsonObj =>
            {
                // Update the project entrypoint
                jsonObj["entryPoint"] = _libraryDescription.Identity.Name;

                // Set mark this as non loadable
                jsonObj["loadable"] = false;

                // Update the dependencies node to reference the main project
                var deps = new JObject();
                jsonObj["dependencies"] = deps;

                deps[_libraryDescription.Identity.Name] = _libraryDescription.Identity.Version.ToString();
            });

            _applicationBase = Path.Combine("..", PackRoot.AppRootName, "packages", resolver.GetPackageDirectory(_libraryDescription.Identity.Name, _libraryDescription.Identity.Version), "root");
        }
Exemple #28
0
        public void PostProcess(PackRoot root)
        {
            Project project;

            if (!_projectResolver.TryResolveProject(_libraryDescription.Identity.Name, out project))
            {
                throw new Exception("TODO: unable to resolve project named " + _libraryDescription.Identity.Name);
            }

            // Construct path to public app folder, which contains content files and tool dlls
            // The name of public app folder is specified with "--appfolder" option
            // Default name of public app folder is the same as main project
            var appFolderName = AppFolder ?? PackRoot.DefaultAppFolderName;
            var appFolderPath = Path.Combine(root.OutputPath, appFolderName);

            // Delete old public app folder because we don't want leftovers from previous operations
            root.Operations.Delete(appFolderPath);
            Directory.CreateDirectory(appFolderPath);

            // Copy content files (e.g. html, js and images) of main project into public app folder
            CopyContentFiles(root, project, appFolderName);

            // Tool dlls including AspNet.Loader.dll go to bin folder under public app folder
            var appFolderBinPath = Path.Combine(appFolderPath, "bin");

            var defaultRuntime = root.Runtimes.FirstOrDefault();
            var iniFilePath    = Path.Combine(TargetPath, "k.ini");

            if (defaultRuntime != null && !File.Exists(iniFilePath))
            {
                var parts = defaultRuntime.Name.Split(new[] { '.' }, 2);
                if (parts.Length == 2)
                {
                    var versionNumber = parts[1];
                    parts = parts[0].Split(new[] { '-' }, 3);
                    if (parts.Length == 3)
                    {
                        var flavor = parts[1];
                        File.WriteAllText(iniFilePath, string.Format(@"[Runtime]
KRE_VERSION={0}
KRE_FLAVOR={1}
KRE_CONFIGURATION={2}
",
                                                                     versionNumber,
                                                                     flavor == "svrc50" ? "CoreCLR" : "DesktopCLR",
                                                                     root.Configuration));
                    }
                }
            }

            // Generate k.ini for public app folder
            var appFolderIniFilePath = Path.Combine(appFolderPath, "k.ini");
            var appBaseLine          = string.Format("APP_BASE={0}",
                                                     Path.Combine("..", PackRoot.AppRootName, "src", project.Name));
            var iniContents = string.Empty;

            if (File.Exists(iniFilePath))
            {
                iniContents = File.ReadAllText(iniFilePath);
            }
            File.WriteAllText(appFolderIniFilePath,
                              string.Format("{0}{1}", iniContents, appBaseLine));

            // Copy tools/*.dll into bin to support AspNet.Loader.dll
            foreach (var package in root.Packages)
            {
                var packageToolsPath = Path.Combine(package.TargetPath, "tools");
                if (Directory.Exists(packageToolsPath))
                {
                    foreach (var packageToolFile in Directory.EnumerateFiles(packageToolsPath, "*.dll").Select(Path.GetFileName))
                    {
                        if (!Directory.Exists(appFolderBinPath))
                        {
                            Directory.CreateDirectory(appFolderBinPath);
                        }

                        // Copy to bin folder under public app folder
                        File.Copy(
                            Path.Combine(packageToolsPath, packageToolFile),
                            Path.Combine(appFolderBinPath, packageToolFile),
                            true);
                    }
                }
            }
        }