| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118 |
- using Invercargill;
- using Invercargill.DataStructures;
- namespace Usm {
- public class Resolver {
- private Dictionary<Repository, RepositoryListing> listings = new Dictionary<Repository, RepositoryListing>();
- private Set<AbstractPackage> supplied = new HashSet<AbstractPackage>();
- private Enumerable<AbstractPackage> available_packages() {
- return
- supplied.concat(listings
- .select_many<Pair<Repository, RepositoryListingEntry>>(l => l.value.entries.select_pairs<Repository, RepositoryListingEntry>(e => l.key, e => e))
- .select<AbstractPackage>(p => new AbstractPackage.from_repository(p.value1, p.value2)));
- }
- public void load_listing(Repository repo, RepositoryListing listing) {
- listings.set(repo, listing);
- }
- public void supply_package(string path) throws Error {
- supplied.add(new AbstractPackage.from_package(path));
- }
- public void load_cache(Paths paths) throws Error {
- var state = new SystemState(paths);
- foreach (var package in state.get_cached_packages()) {
- supply_package(package.package_path);
- }
- }
- public AbstractPackage? find_package(string search) {
- return available_packages()
- .first_or_default(p => p.manifest.name == search);
- }
- public AbstractPackage? find_resource(ResourceRef resource) {
- return available_packages()
- .first_or_default(p => p.manifest.provides.any(r => resource.satisfied_by(r.key)));
- }
- public void solve_dependencies_for(PackageSet package_set) {
- var queue = new Fifo<AbstractPackage>();
- package_set.iterate(i => queue.push(i));
- foreach (var item in queue) {
- var dependencies = item.manifest.dependencies.build
- .concat(item.manifest.dependencies.manage)
- .concat(item.manifest.dependencies.runtime);
- foreach (var dep in dependencies) {
- if(package_set.provides(dep) || dep.is_satisfied()) {
- continue;
- }
- var provider = find_resource(dep);
- if(provider == null) {
- error(@"Could not solve dependency $dep");
- }
- package_set.add(provider);
- queue.push(provider);
- }
- }
- }
- }
- public class PackageSet : HashSet<AbstractPackage> {
- public void add_from_file(string path) throws Error {
- add(new AbstractPackage.from_package(path));
- }
- public void add_from_repo(Repository repository, RepositoryListingEntry entry) throws Error {
- add(new AbstractPackage.from_repository(repository, entry));
- }
- public bool is_satisfied() {
- return all(check_satisfied);
- }
- private bool check_satisfied(AbstractPackage package) {
- return package.manifest.dependencies.build.all(d => provides(d) || d.is_satisfied()) &&
- package.manifest.dependencies.manage.all(d => provides(d) || d.is_satisfied()) &&
- package.manifest.dependencies.runtime.all(d => provides(d) || d.is_satisfied());
- }
- public bool provides(ResourceRef resource) {
- return any(p => p.manifest.provides.any(r => resource.satisfied_by(r.key)));
- }
- }
- public class AbstractPackage {
- public Manifest manifest { get; set; }
- public Repository? repository { get; set; }
- public RepositoryListingEntry? repository_entry { get; set; }
- public string? package_path { get; set; }
- public CachedPackage? cached_package { get; set; }
- public AbstractPackage.from_package(string path) throws Error {
- package_path = path;
- manifest = new Manifest.from_file(path);
- }
- public AbstractPackage.from_repository(Repository repository, RepositoryListingEntry entry) {
- this.repository = repository;
- this.repository_entry = entry;
- this.manifest = entry.manifest;
- }
- }
- }
|