示例#1
0
        private async Task StageDefinition(Definition definition)
        {
            foreach (var dependency in definition.Dependencies ?? new Dictionary <Name, VersionRange>())
            {
                var repo = definition.Repositories?.FirstOrDefault(r => r.Name == dependency.Key);

                var adapter = new AdapterBuilder(dependency.Key, repo).Adapter();

                var versions = await adapter.GetVersions();

                var versionMatch = versions.LastOrDefault(version => dependency.Value.IsSatisfied(version));
                if (versionMatch == null)
                {
                    throw new Exception("No matching version found");
                }

                Directory.CreateDirectory(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging", dependency.Key.Vendor, dependency.Key.Project));

                await adapter.Download(versionMatch);

                var dependencyDefinition = Definition.Load(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging", dependency.Key.Vendor, dependency.Key.Project, Program.DefinitionFile));

                // TODO: What should be validated?
                if (dependencyDefinition.Name != dependency.Key)
                {
                    throw new Exception("Downloaded package does not match requested.");
                }
                if (dependencyDefinition.Version != versionMatch)
                {
                    throw new Exception("Downloaded package does not match requested.");
                }

                await StageDefinition(dependencyDefinition);
            }
        }
示例#2
0
        public async Task Apply()
        {
            if (Directory.Exists(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging")))
            {
                Directory.Delete(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging"), true);
            }

            foreach (var definition in this.Definitions)
            {
                var path = Path.Combine(Environment.CurrentDirectory, Program.PluginPath, definition.Name.Vendor, definition.Name.Project, Program.DefinitionFile);

                if (File.Exists(path))
                {
                    var loadedDefinition = Definition.Load(path);

                    if (loadedDefinition.Name == definition.Name && loadedDefinition.Version == definition.Version)
                    {
                        continue;
                    }
                }

                // Missing or outdated

                var dir = Path.Combine(Environment.CurrentDirectory, Program.PluginPath, definition.Name.Vendor, definition.Name.Project);
                if (Directory.Exists(dir))
                {
                    Directory.Delete(dir, true);
                }

                Directory.CreateDirectory(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging", definition.Name.Vendor, definition.Name.Project));

                Repository repo    = null;              // masterDefinition.Repositories?.FirstOrDefault(r => r.Name == definition.Name); // TODO
                var        adapter = new AdapterBuilder(definition.Name, repo).Adapter();
                await adapter.Download(definition.Version);

                var dependencyDefinition = Definition.Load(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging", definition.Name.Vendor, definition.Name.Project, Program.DefinitionFile));

                if (dependencyDefinition.Name != definition.Name)
                {
                    throw new Exception("Downloaded package does not match requested.");
                }
                if (dependencyDefinition.Version != definition.Version)
                {
                    throw new Exception("Downloaded package does not match requested.");
                }

                var src       = Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging", definition.Name.Vendor, definition.Name.Project);
                var dst       = Path.Combine(Environment.CurrentDirectory, Program.PluginPath, definition.Name.Vendor, definition.Name.Project);
                var configSrc = Path.Combine(src, "config");
                var configDst = Path.Combine(Environment.CurrentDirectory, "config", definition.Name.Vendor, definition.Name.Project);

                new DirectoryInfo(src).Copy(dst);

                if (Directory.Exists(configSrc))
                {
                    Directory.CreateDirectory(configDst);

                    foreach (var yml in Directory.EnumerateFiles(configSrc, "*.yml", SearchOption.TopDirectoryOnly))
                    {
                        File.Copy(yml, configDst, false);
                    }
                }
            }

            if (Directory.Exists(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging")))
            {
                Directory.Delete(Path.Combine(Environment.CurrentDirectory, Program.PluginPath, ".staging"), true);
            }
        }
示例#3
0
        public async Task Apply(Plugin baseDefinition = null)
        {
            if (baseDefinition != null)
            {
                var results = await StageDefinition(baseDefinition);

                var top = results.Item1;
                var all = top.Concat(results.Item2).Distinct().ToList();

                foreach (var plugin in top.Where(d => d.Dependencies != null))
                {
                    foreach (var dependency in plugin.Dependencies)
                    {
                        var dependencyPlugin = all.FirstOrDefault(p => p.Name == dependency.Key);
                        if (dependencyPlugin == null)
                        {
                            throw new Exception($"Unable to find dependency {dependency.Key}@{dependency.Value} required by {plugin.Name}@{plugin.Version}");                                                   // TODO: DependencyException
                        }
                        if (!dependency.Value.IsSatisfied(dependencyPlugin.Version))
                        {
                            throw new Exception($"{plugin.Name}@{plugin.Version} requires {dependencyPlugin.Name}@{dependency.Value} but {dependencyPlugin.Name}@{dependencyPlugin.Version} was found");
                        }

                        if (plugin.DependencyNodes == null)
                        {
                            plugin.DependencyNodes = new List <Plugin>();
                        }
                        plugin.DependencyNodes.Add(dependencyPlugin);
                    }
                }

                this.Plugins = top;
            }

            this.Plugins = Sort(this.Plugins);             // TODO: Don't store nested dependencies but still load them

            foreach (var definition in this.Plugins)
            {
                var path = Path.Combine(Environment.CurrentDirectory, ConfigurationManager.PluginPath, definition.Name.Vendor, definition.Name.Project, ConfigurationManager.DefinitionFile);

                if (File.Exists(path))
                {
                    var loadedDefinition = Plugin.Load(path);

                    // TODO: IEquality
                    if (loadedDefinition.Name.ToString() == definition.Name.ToString() &&
                        loadedDefinition.Version.ToString() == definition.Version.ToString() &&
                        baseDefinition?.Repositories?.FirstOrDefault(r => r.Name == definition.Name && r.Type == "local") == null)
                    {
                        continue;
                    }
                }

                // TODO: Remove extra plugin folders/files

                // Missing or outdated

                var dir = Path.Combine(Environment.CurrentDirectory, ConfigurationManager.PluginPath, definition.Name.Vendor, definition.Name.Project);
                if (Directory.Exists(dir))
                {
                    DeleteDirectory(dir);
                }
                Directory.CreateDirectory(dir);

                var repo    = baseDefinition?.Repositories?.FirstOrDefault(r => r.Name == definition.Name);
                var adapter = new AdapterBuilder(definition.Name, repo).Adapter();
                await adapter.Download(new Version(definition.Version.ToString()));

                var dependencyDefinition = Plugin.Load(Path.Combine(dir, ConfigurationManager.DefinitionFile));

                if (dependencyDefinition.Name != definition.Name)
                {
                    throw new Exception("Downloaded package does not match requested.");
                }
                if (dependencyDefinition.Version.ToString() != definition.Version.ToString())
                {
                    throw new Exception("Downloaded package does not match requested.");
                }

                var configSrc = Path.Combine(dir, ConfigurationManager.ConfigurationPath);
                var configDst = Path.Combine(Environment.CurrentDirectory, ConfigurationManager.ConfigurationPath, definition.Name.Vendor, definition.Name.Project);

                if (!Directory.Exists(configSrc))
                {
                    continue;
                }
                if (!Directory.Exists(configDst))
                {
                    Directory.CreateDirectory(configDst);
                }

                // TODO: More files?
                // TODO: Ask user to replace
                foreach (var yml in Directory.EnumerateFiles(configSrc, "*.yml", SearchOption.TopDirectoryOnly))
                {
                    try
                    {
                        File.Copy(yml, Path.Combine(configDst, Path.GetFileName(yml)), false);
                    }
                    catch (Exception ex)
                    {
                        Console.WriteLine(ex.Message);
                    }
                }
            }
        }