mirror of
https://github.com/mudler/luet.git
synced 2025-09-07 10:10:17 +00:00
Drop Best from solver and add cases for solver with expansion
This commit is contained in:
@@ -16,12 +16,13 @@
|
|||||||
package pkg
|
package pkg
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"bytes"
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
"sort"
|
"sort"
|
||||||
|
|
||||||
//. "github.com/mudler/luet/pkg/logger"
|
// . "github.com/mudler/luet/pkg/logger"
|
||||||
|
|
||||||
"github.com/crillab/gophersat/bf"
|
"github.com/crillab/gophersat/bf"
|
||||||
version "github.com/hashicorp/go-version"
|
version "github.com/hashicorp/go-version"
|
||||||
|
@@ -16,13 +16,11 @@
|
|||||||
package solver
|
package solver
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"sort"
|
|
||||||
|
|
||||||
//. "github.com/mudler/luet/pkg/logger"
|
//. "github.com/mudler/luet/pkg/logger"
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
|
|
||||||
"github.com/crillab/gophersat/bf"
|
"github.com/crillab/gophersat/bf"
|
||||||
version "github.com/hashicorp/go-version"
|
|
||||||
pkg "github.com/mudler/luet/pkg/package"
|
pkg "github.com/mudler/luet/pkg/package"
|
||||||
)
|
)
|
||||||
|
|
||||||
@@ -33,7 +31,6 @@ type PackageSolver interface {
|
|||||||
Uninstall(candidate pkg.Package) ([]pkg.Package, error)
|
Uninstall(candidate pkg.Package) ([]pkg.Package, error)
|
||||||
ConflictsWithInstalled(p pkg.Package) (bool, error)
|
ConflictsWithInstalled(p pkg.Package) (bool, error)
|
||||||
ConflictsWith(p pkg.Package, ls []pkg.Package) (bool, error)
|
ConflictsWith(p pkg.Package, ls []pkg.Package) (bool, error)
|
||||||
Best([]pkg.Package) pkg.Package
|
|
||||||
World() []pkg.Package
|
World() []pkg.Package
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -81,31 +78,6 @@ func NewSolver(installed pkg.PackageDatabase, definitiondb pkg.PackageDatabase,
|
|||||||
return &Solver{InstalledDatabase: installed, DefinitionDatabase: definitiondb, SolverDatabase: solverdb}
|
return &Solver{InstalledDatabase: installed, DefinitionDatabase: definitiondb, SolverDatabase: solverdb}
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: []pkg.Package should have its own type with this kind of methods in (+Unique, sort, etc.)
|
|
||||||
func (s *Solver) Best(set []pkg.Package) pkg.Package {
|
|
||||||
var versionsMap map[string]pkg.Package = make(map[string]pkg.Package)
|
|
||||||
if len(set) == 0 {
|
|
||||||
panic("Best needs a list with elements")
|
|
||||||
}
|
|
||||||
|
|
||||||
versionsRaw := []string{}
|
|
||||||
for _, p := range set {
|
|
||||||
versionsRaw = append(versionsRaw, p.GetVersion())
|
|
||||||
versionsMap[p.GetVersion()] = p
|
|
||||||
}
|
|
||||||
|
|
||||||
versions := make([]*version.Version, len(versionsRaw))
|
|
||||||
for i, raw := range versionsRaw {
|
|
||||||
v, _ := version.NewVersion(raw)
|
|
||||||
versions[i] = v
|
|
||||||
}
|
|
||||||
|
|
||||||
// After this, the versions are properly sorted
|
|
||||||
sort.Sort(version.Collection(versions))
|
|
||||||
|
|
||||||
return versionsMap[versions[len(versions)-1].Original()]
|
|
||||||
}
|
|
||||||
|
|
||||||
// SetWorld is a setter for the list of all known packages to the solver
|
// SetWorld is a setter for the list of all known packages to the solver
|
||||||
|
|
||||||
func (s *Solver) SetDefinitionDatabase(db pkg.PackageDatabase) {
|
func (s *Solver) SetDefinitionDatabase(db pkg.PackageDatabase) {
|
||||||
@@ -113,27 +85,12 @@ func (s *Solver) SetDefinitionDatabase(db pkg.PackageDatabase) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
func (s *Solver) World() []pkg.Package {
|
func (s *Solver) World() []pkg.Package {
|
||||||
var all []pkg.Package
|
return s.DefinitionDatabase.World()
|
||||||
// FIXME: This should all be locked in the db - for now forbid the solver to be run in threads.
|
|
||||||
for _, k := range s.DefinitionDatabase.GetPackages() {
|
|
||||||
pack, err := s.DefinitionDatabase.GetPackage(k)
|
|
||||||
if err == nil {
|
|
||||||
all = append(all, pack)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return all
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Solver) Installed() []pkg.Package {
|
func (s *Solver) Installed() []pkg.Package {
|
||||||
var all []pkg.Package
|
|
||||||
// FIXME: This should all be locked in the db - for now forbid the solver to be run in threads.
|
return s.InstalledDatabase.World()
|
||||||
for _, k := range s.InstalledDatabase.GetPackages() {
|
|
||||||
pack, err := s.InstalledDatabase.GetPackage(k)
|
|
||||||
if err == nil {
|
|
||||||
all = append(all, pack)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return all
|
|
||||||
}
|
}
|
||||||
|
|
||||||
func (s *Solver) noRulesWorld() bool {
|
func (s *Solver) noRulesWorld() bool {
|
||||||
|
@@ -219,6 +219,58 @@ var _ = Describe("Solver", func() {
|
|||||||
Expect(err).ToNot(HaveOccurred())
|
Expect(err).ToNot(HaveOccurred())
|
||||||
})
|
})
|
||||||
|
|
||||||
|
It("Solves deps with expansion", func() {
|
||||||
|
|
||||||
|
E := pkg.NewPackage("E", "", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
||||||
|
C := pkg.NewPackage("C", "", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
||||||
|
D := pkg.NewPackage("D", "", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
||||||
|
B := pkg.NewPackage("B", "1.1", []*pkg.DefaultPackage{D}, []*pkg.DefaultPackage{})
|
||||||
|
A := pkg.NewPackage("A", "", []*pkg.DefaultPackage{&pkg.DefaultPackage{Name: "B", Version: ">1.0"}}, []*pkg.DefaultPackage{})
|
||||||
|
|
||||||
|
for _, p := range []pkg.Package{A, B, C, D, E} {
|
||||||
|
_, err := dbDefinitions.CreatePackage(p)
|
||||||
|
Expect(err).ToNot(HaveOccurred())
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, p := range []pkg.Package{} {
|
||||||
|
_, err := dbInstalled.CreatePackage(p)
|
||||||
|
Expect(err).ToNot(HaveOccurred())
|
||||||
|
}
|
||||||
|
s = NewSolver(dbInstalled, dbDefinitions, db)
|
||||||
|
|
||||||
|
solution, err := s.Install([]pkg.Package{A})
|
||||||
|
Expect(solution).To(ContainElement(PackageAssert{Package: A, Value: true}))
|
||||||
|
Expect(solution).To(ContainElement(PackageAssert{Package: B, Value: true}))
|
||||||
|
Expect(solution).To(ContainElement(PackageAssert{Package: D, Value: true}))
|
||||||
|
Expect(len(solution)).To(Equal(3))
|
||||||
|
Expect(err).ToNot(HaveOccurred())
|
||||||
|
})
|
||||||
|
It("Solves deps with moreexpansion", func() {
|
||||||
|
|
||||||
|
E := pkg.NewPackage("E", "", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
||||||
|
C := pkg.NewPackage("C", "", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
||||||
|
D := pkg.NewPackage("D", "1.4", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
||||||
|
B := pkg.NewPackage("B", "1.1", []*pkg.DefaultPackage{&pkg.DefaultPackage{Name: "D", Version: ">1.0"}}, []*pkg.DefaultPackage{})
|
||||||
|
A := pkg.NewPackage("A", "", []*pkg.DefaultPackage{&pkg.DefaultPackage{Name: "B", Version: ">1.0"}}, []*pkg.DefaultPackage{})
|
||||||
|
|
||||||
|
for _, p := range []pkg.Package{A, B, C, D, E} {
|
||||||
|
_, err := dbDefinitions.CreatePackage(p)
|
||||||
|
Expect(err).ToNot(HaveOccurred())
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, p := range []pkg.Package{} {
|
||||||
|
_, err := dbInstalled.CreatePackage(p)
|
||||||
|
Expect(err).ToNot(HaveOccurred())
|
||||||
|
}
|
||||||
|
s = NewSolver(dbInstalled, dbDefinitions, db)
|
||||||
|
|
||||||
|
solution, err := s.Install([]pkg.Package{A})
|
||||||
|
Expect(solution).To(ContainElement(PackageAssert{Package: A, Value: true}))
|
||||||
|
Expect(solution).To(ContainElement(PackageAssert{Package: B, Value: true}))
|
||||||
|
Expect(solution).To(ContainElement(PackageAssert{Package: D, Value: true}))
|
||||||
|
Expect(len(solution)).To(Equal(3))
|
||||||
|
Expect(err).ToNot(HaveOccurred())
|
||||||
|
})
|
||||||
It("Uninstalls simple package correctly", func() {
|
It("Uninstalls simple package correctly", func() {
|
||||||
|
|
||||||
C := pkg.NewPackage("C", "", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
C := pkg.NewPackage("C", "", []*pkg.DefaultPackage{}, []*pkg.DefaultPackage{})
|
||||||
@@ -542,7 +594,7 @@ var _ = Describe("Solver", func() {
|
|||||||
Expect(lst).To(ContainElement(a03))
|
Expect(lst).To(ContainElement(a03))
|
||||||
Expect(lst).ToNot(ContainElement(old))
|
Expect(lst).ToNot(ContainElement(old))
|
||||||
Expect(len(lst)).To(Equal(5))
|
Expect(len(lst)).To(Equal(5))
|
||||||
p := s.Best(lst)
|
p := pkg.Best(lst)
|
||||||
Expect(p).To(Equal(a03))
|
Expect(p).To(Equal(a03))
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
|
@@ -68,7 +68,6 @@ func (r *CompilerRecipe) Load(path string) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return errors.Wrap(err, "Error reading yaml "+currentpath)
|
return errors.Wrap(err, "Error reading yaml "+currentpath)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Path is set only internally when tree is loaded from disk
|
// Path is set only internally when tree is loaded from disk
|
||||||
pack.SetPath(filepath.Dir(currentpath))
|
pack.SetPath(filepath.Dir(currentpath))
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user