Example #1
0
        /// <summary>
        /// Gets the list of packages to install along with there dependencies
        /// </summary>
        /// <param name="repository">The package repository</param>
        /// <param name="seederConfiguration">The seeder configuration</param>
        /// <returns>The list of packages</returns>
        private static async Task <IEnumerable <PackageIdentity> > GetPackagesToInstall(
            IPackageRepository repository,
            SeederConfiguration seederConfiguration)
        {
            // TODO: extract to helper method along with Configuration extensions
            var supportedFramework = NuGetFramework.ParseFrameworkName(
                PackageRepositoryExtensions.CurrentRuntime,
                DefaultFrameworkNameProvider.Instance);

            var packageTasks =
                seederConfiguration.RequiredPackages.Select(
                    async packageName =>
            {
                var package = await repository.GetAsync(packageName);
                if (package == null)
                {
                    throw new PackageNotFoundException(packageName);
                }

                return(package);
            });

            var packagesToInstall = (await Task.WhenAll(packageTasks)).ToDictionary(p => p.Identity.Id);
            var queue             = new Queue <IPackageSearchMetadata>(packagesToInstall.Values);

            while (queue.Count > 0)
            {
                var package       = queue.Dequeue();
                var dependencySet =
                    NuGetFrameworkUtility.GetNearest(package.DependencySets, supportedFramework);
                if (dependencySet == null || !NuGetFrameworkUtility.IsCompatibleWithFallbackCheck(
                        supportedFramework,
                        dependencySet.TargetFramework))
                {
                    continue;
                }

                foreach (var dependency in dependencySet.Packages)
                {
                    IPackageSearchMetadata packageToInstall;
                    if (!packagesToInstall.TryGetValue(dependency.Id, out packageToInstall))
                    {
                        packageToInstall = await repository.GetAsync(dependency.Id);

                        if (packageToInstall == null)
                        {
                            throw new PackageNotFoundException(dependency.Id);
                        }

                        packagesToInstall.Add(dependency.Id, packageToInstall);
                        if (queue.All(p => p.Identity.Id != packageToInstall.Identity.Id))
                        {
                            queue.Enqueue(packageToInstall);
                        }
                    }
                }
            }

            return(packagesToInstall.Values.Select(p => p.Identity));
        }
Example #2
0
        /// <summary>
        /// Reads the configuration
        /// </summary>
        /// <param name="args">The program command line arguments</param>
        /// <returns>The configuration</returns>
        private static Configuration ReadConfiguration(string[] args)
        {
            var configuration = new Configuration();

            configuration.ConfigFile = args != null && args.Length > 0 ? args[0] : "seeder.hocon";
            if (configuration.ConfigFile == null || !File.Exists(configuration.ConfigFile))
            {
                Console.WriteLine("Configuration file was not found");
                return(null);
            }

            configuration.Config = ConfigurationFactory.ParseString(File.ReadAllText(configuration.ConfigFile));
            configuration.Nuget  = configuration.Config.GetString("KlusterKite.NodeManager.PackageRepository");
            if (string.IsNullOrWhiteSpace(configuration.Nuget))
            {
                Console.WriteLine("Nuget is not properly defined");
                return(null);
            }

            configuration.NugetCheckPeriod =
                configuration.Config.GetTimeSpan("NugetCheckPeriod", TimeSpan.FromMinutes(1));
            configuration.Runtime = configuration.Config.GetString("Runtime");

            configuration.Configurations = new List <SeederConfiguration>();
            foreach (var subConfig in configuration.Config.GetStringList("SeederConfigurations"))
            {
                var seederConfig = configuration.Config.GetConfig(subConfig);
                if (seederConfig == null)
                {
                    Console.WriteLine($"SeederConfiguration {subConfig} was not found in the config");
                    return(null);
                }

                var seederConfiguration = new SeederConfiguration(subConfig, seederConfig);
                if (seederConfiguration.RequiredPackages == null || seederConfiguration.RequiredPackages.Count == 0)
                {
                    Console.WriteLine($"SeederConfiguration {subConfig} misses the RequiredPackages property");
                    return(null);
                }

                if (seederConfiguration.Seeders == null || seederConfiguration.Seeders.Count == 0)
                {
                    Console.WriteLine($"SeederConfiguration {subConfig} misses the Seeders property");
                    return(null);
                }

                configuration.Configurations.Add(seederConfiguration);
            }

            if (configuration.Configurations.Count == 0)
            {
                Console.WriteLine("SeederConfiguration is empty");
                return(null);
            }

            return(configuration);
        }
Example #3
0
        /// <summary>
        /// Runs seeder configuration
        /// </summary>
        /// <param name="configuration">The global configuration</param>
        /// <param name="seederConfiguration">The seeder configuration</param>
        private static void RunSeederConfiguration(Configuration configuration, SeederConfiguration seederConfiguration)
        {
            var executionDir = Path.Combine(Path.GetTempPath(), Guid.NewGuid().ToString("N"));

            Directory.CreateDirectory(executionDir);

            try
            {
                while (true)
                {
                    try
                    {
                        var repository = new RemotePackageRepository(configuration.Nuget);
                        var packages   = GetPackagesToInstall(repository, seederConfiguration).GetAwaiter()
                                         .GetResult();

                        repository.CreateServiceAsync(
                            packages,
                            configuration.Runtime,
                            PackageRepositoryExtensions.CurrentRuntime,
                            executionDir,
                            "KlusterKite.NodeManager.Seeder",
                            Console.WriteLine).GetAwaiter().GetResult();

                        Console.WriteLine("Packages installed");
                    }
                    catch (PackageNotFoundException packageNotFoundException)
                    {
                        Console.WriteLine($"Package {packageNotFoundException.Message} was not found");
                        Thread.Sleep(configuration.NugetCheckPeriod);
                        continue;
                    }
                    catch (AggregateException exception)
                    {
                        var e = exception.InnerExceptions?.FirstOrDefault() ?? exception;
                        Console.WriteLine(e.Message);
                        Console.WriteLine(e.StackTrace);
                        Thread.Sleep(configuration.NugetCheckPeriod);
                        continue;
                    }
                    catch (Exception exception)
                    {
                        Console.WriteLine(exception.Message);
                        Console.WriteLine(exception.StackTrace);
                        Thread.Sleep(configuration.NugetCheckPeriod);
                        continue;
                    }

                    try
                    {
                        File.Copy(configuration.ConfigFile, Path.Combine(executionDir, "seeder.hocon"), true);

                        // todo: move to CreateServiceAsync
                        // ConfigurationUtils.FixAssemblyVersions(Path.Combine(executionDir, "KlusterKite.NodeManager.Seeder.exe.config"));
                        Console.WriteLine($"Seeder prepared in {executionDir}");
#if APPDOMAIN
                        var process = new Process
                        {
                            StartInfo =
                            {
                                UseShellExecute  = false,
                                WorkingDirectory = executionDir,
                                FileName         = "KlusterKite.NodeManager.Seeder.exe",
                                Arguments        = seederConfiguration.Name
                            }
                        };
#elif CORECLR
                        var process = new Process
                        {
                            StartInfo =
                            {
                                UseShellExecute  = false,
                                WorkingDirectory = executionDir,
                                FileName         = "dotnet",
                                Arguments        = $"KlusterKite.NodeManager.Seeder.dll {seederConfiguration.Name}"
                            }
                        };
#endif
                        process.Start();
                        process.WaitForExit();
                        process.Dispose();
                        Console.WriteLine("Seeder stopped");
                        break;
                    }
                    catch (Exception e)
                    {
                        Console.WriteLine(e.Message);
                        Console.WriteLine(e.StackTrace);
                        Console.ReadLine();
                        break;
                    }
                }
            }
            finally
            {
                try
                {
                    Directory.Delete(executionDir, true);
                }
                catch
                {
                    Console.WriteLine("Failed to remove execution directory");
                }
            }
        }