Flattened architecture. Does not compile

This commit is contained in:
Jguer 2017-08-02 18:24:03 +01:00
parent 5ad1772bba
commit b4f4a42d50
19 changed files with 1174 additions and 1329 deletions

View file

@ -1,64 +0,0 @@
package main
import (
"fmt"
"os"
aur "github.com/jguer/yay/aur"
"github.com/jguer/yay/config"
pac "github.com/jguer/yay/pacman"
)
// Install handles package installs
func install(pkgs []string, flags []string) error {
aurs, repos, _ := pac.PackageSlices(pkgs)
if len(repos) != 0 {
err := config.PassToPacman("-S", repos, flags)
if err != nil {
fmt.Println("Error installing repo packages.")
}
}
if len(aurs) != 0 {
err := aur.Install(aurs, flags)
if err != nil {
fmt.Println("Error installing aur packages.")
}
}
return nil
}
// CleanDependencies removels all dangling dependencies in system
func cleanDependencies(pkgs []string) error {
hanging, err := pac.HangingPackages()
if err != nil {
return err
}
if len(hanging) != 0 {
if !config.ContinueTask("Confirm Removal?", "nN") {
return nil
}
err = pac.CleanRemove(hanging)
}
return err
}
// GetPkgbuild gets the pkgbuild of the package 'pkg' trying the ABS first and then the AUR trying the ABS first and then the AUR.
func getPkgbuild(pkg string) (err error) {
wd, err := os.Getwd()
if err != nil {
return
}
wd = wd + "/"
err = pac.GetPkgbuild(pkg, wd)
if err == nil {
return
}
err = aur.GetPkgbuild(pkg, wd)
return
}

View file

@ -1,256 +0,0 @@
package aur
import (
"bufio"
"fmt"
"net/http"
"os"
"sort"
"strings"
alpm "github.com/jguer/go-alpm"
vcs "github.com/jguer/yay/aur/vcs"
"github.com/jguer/yay/config"
"github.com/jguer/yay/pacman"
rpc "github.com/mikkeloscar/aur"
)
// BaseURL givers the AUR default address.
const BaseURL string = "https://aur.archlinux.org"
var specialDBsauce = false
// NarrowSearch searches AUR and narrows based on subarguments
func NarrowSearch(pkgS []string, sortS bool) (Query, error) {
if len(pkgS) == 0 {
return nil, nil
}
r, err := rpc.Search(pkgS[0])
if err != nil {
return nil, err
}
if len(pkgS) == 1 {
if sortS {
sort.Sort(Query(r))
}
return r, err
}
var aq Query
var n int
for _, res := range r {
match := true
for _, pkgN := range pkgS[1:] {
if !(strings.Contains(res.Name, pkgN) || strings.Contains(strings.ToLower(res.Description), pkgN)) {
match = false
break
}
}
if match {
n++
aq = append(aq, res)
}
}
if sortS {
sort.Sort(aq)
}
return aq, err
}
// Install sends system commands to make and install a package from pkgName
func Install(pkgName []string, flags []string) (err error) {
q, err := rpc.Info(pkgName)
if err != nil {
return
}
if len(q) != len(pkgName) {
fmt.Printf("Some package from list\n%+v\ndoes not exist", pkgName)
}
var finalrm []string
for _, i := range q {
mrm, err := PkgInstall(&i, flags)
if err != nil {
fmt.Println("Error installing", i.Name, ":", err)
}
finalrm = append(finalrm, mrm...)
}
if len(finalrm) != 0 {
err = RemoveMakeDeps(finalrm)
}
return err
}
// CreateDevelDB forces yay to create a DB of the existing development packages
func CreateDevelDB() error {
foreign, err := pacman.ForeignPackages()
if err != nil {
return err
}
keys := make([]string, len(foreign))
i := 0
for k := range foreign {
keys[i] = k
i++
}
config.YayConf.NoConfirm = true
specialDBsauce = true
err = Install(keys, nil)
return err
}
func develUpgrade(foreign map[string]alpm.Package, flags []string) error {
fmt.Println(" Checking development packages...")
develUpdates := vcs.CheckUpdates(foreign)
if len(develUpdates) != 0 {
for _, q := range develUpdates {
fmt.Printf("\x1b[1m\x1b[32m==>\x1b[33;1m %s\x1b[0m\n", q)
}
// Install updated packages
if !config.ContinueTask("Proceed with upgrade?", "nN") {
return nil
}
err := Install(develUpdates, flags)
if err != nil {
fmt.Println(err)
}
}
return nil
}
// Upgrade tries to update every foreign package installed in the system
// func Upgrade(flags []string) error {
// fmt.Println("\x1b[1;36;1m::\x1b[0m\x1b[1m Starting AUR upgrade...\x1b[0m")
// foreign, err := pacman.ForeignPackages()
// if err != nil {
// return err
// }
// keys := make([]string, len(foreign))
// i := 0
// for k := range foreign {
// keys[i] = k
// i++
// }
// if config.YayConf.Devel {
// err := develUpgrade(foreign, flags)
// if err != nil {
// fmt.Println(err)
// }
// }
// var q Query
// var j int
// for i = len(keys); i != 0; i = j {
// j = i - config.YayConf.RequestSplitN
// if j < 0 {
// j = 0
// }
// qtemp, err := rpc.Info(keys[j:i])
// q = append(q, qtemp...)
// if err != nil {
// return err
// }
// }
// var buffer bytes.Buffer
// buffer.WriteString("\n")
// outdated := q[:0]
// for i, res := range q {
// fmt.Printf("\r Checking %d/%d packages...", i+1, len(q))
// if _, ok := foreign[res.Name]; ok {
// // Leaving this here for now, warn about downgrades later
// if (config.YayConf.TimeUpdate && (int64(res.LastModified) > foreign[res.Name].BuildDate().Unix())) ||
// alpm.VerCmp(foreign[res.Name].Version(), res.Version) < 0 {
// buffer.WriteString(fmt.Sprintf("\x1b[1m\x1b[32m==>\x1b[33;1m %s: \x1b[0m%s \x1b[33;1m-> \x1b[0m%s\n",
// res.Name, foreign[res.Name].Version(), res.Version))
// outdated = append(outdated, res)
// }
// }
// }
// fmt.Println(buffer.String())
// //If there are no outdated packages, don't prompt
// if len(outdated) == 0 {
// fmt.Println("there is nothing to do")
// return nil
// }
// // Install updated packages
// if !config.ContinueTask("Proceed with upgrade?", "nN") {
// return nil
// }
// var finalmdeps []string
// for _, pkgi := range outdated {
// mdeps, err := PkgInstall(&pkgi, flags)
// finalmdeps = append(finalmdeps, mdeps...)
// if err != nil {
// fmt.Println(err)
// }
// }
// err = pacman.CleanRemove(finalmdeps)
// if err != nil {
// fmt.Println(err)
// }
// return nil
// }
// GetPkgbuild downloads pkgbuild from the AUR.
func GetPkgbuild(pkgN string, dir string) (err error) {
aq, err := rpc.Info([]string{pkgN})
if err != nil {
return err
}
if len(aq) == 0 {
return fmt.Errorf("no results")
}
fmt.Printf("\x1b[1;32m==>\x1b[1;33m %s \x1b[1;32mfound in AUR.\x1b[0m\n", pkgN)
config.DownloadAndUnpack(BaseURL+aq[0].URLPath, dir, false)
return
}
//CreateAURList creates a new completion file
func CreateAURList(out *os.File) (err error) {
resp, err := http.Get("https://aur.archlinux.org/packages.gz")
if err != nil {
return err
}
defer resp.Body.Close()
scanner := bufio.NewScanner(resp.Body)
scanner.Scan()
for scanner.Scan() {
fmt.Print(scanner.Text())
out.WriteString(scanner.Text())
if config.YayConf.Shell == "fish" {
fmt.Print("\tAUR\n")
out.WriteString("\tAUR\n")
} else {
fmt.Print("\n")
out.WriteString("\n")
}
}
return nil
}

View file

@ -1,44 +0,0 @@
package aur
import (
"fmt"
"github.com/jguer/yay/config"
rpc "github.com/mikkeloscar/aur"
)
// Query is a collection of Results
type Query []rpc.Pkg
func (q Query) Len() int {
return len(q)
}
func (q Query) Less(i, j int) bool {
if config.YayConf.SortMode == config.BottomUp {
return q[i].NumVotes < q[j].NumVotes
}
return q[i].NumVotes > q[j].NumVotes
}
func (q Query) Swap(i, j int) {
q[i], q[j] = q[j], q[i]
}
// MissingPackage warns if the Query was unable to find a package
func (q Query) MissingPackage(pkgS []string) {
for _, depName := range pkgS {
found := false
for _, dep := range q {
if dep.Name == depName {
found = true
break
}
}
if !found {
fmt.Println("\x1b[31mUnable to find", depName, "in AUR\x1b[0m")
}
}
return
}

View file

@ -1,255 +0,0 @@
package aur
import (
"fmt"
"os"
"os/exec"
vcs "github.com/jguer/yay/aur/vcs"
"github.com/jguer/yay/config"
"github.com/jguer/yay/pacman"
rpc "github.com/mikkeloscar/aur"
gopkg "github.com/mikkeloscar/gopkgbuild"
)
// PkgDependencies returns package dependencies not installed belonging to AUR
// 0 is Repo, 1 is Foreign.
func PkgDependencies(a *rpc.Pkg) (runDeps [2][]string, makeDeps [2][]string, err error) {
var q Query
if len(a.Depends) == 0 && len(a.MakeDepends) == 0 {
q, err = rpc.Info([]string{a.Name})
if len(q) == 0 || err != nil {
err = fmt.Errorf("Unable to search dependencies, %s", err)
return
}
} else {
q = append(q, *a)
}
depSearch := pacman.BuildDependencies(a.Depends)
if len(a.Depends) != 0 {
runDeps[0], runDeps[1] = depSearch(q[0].Depends, true, false)
if len(runDeps[0]) != 0 || len(runDeps[1]) != 0 {
fmt.Println("\x1b[1;32m=>\x1b[1;33m Run Dependencies: \x1b[0m")
printDeps(runDeps[0], runDeps[1])
}
}
if len(a.MakeDepends) != 0 {
makeDeps[0], makeDeps[1] = depSearch(q[0].MakeDepends, false, false)
if len(makeDeps[0]) != 0 || len(makeDeps[1]) != 0 {
fmt.Println("\x1b[1;32m=>\x1b[1;33m Make Dependencies: \x1b[0m")
printDeps(makeDeps[0], makeDeps[1])
}
}
depSearch(a.MakeDepends, false, true)
err = nil
return
}
func printDeps(repoDeps []string, aurDeps []string) {
if len(repoDeps) != 0 {
fmt.Print("\x1b[1;32m==> Repository dependencies: \x1b[0m")
for _, repoD := range repoDeps {
fmt.Print("\x1b[33m", repoD, " \x1b[0m")
}
fmt.Print("\n")
}
if len(aurDeps) != 0 {
fmt.Print("\x1b[1;32m==> AUR dependencies: \x1b[0m")
for _, aurD := range aurDeps {
fmt.Print("\x1b[33m", aurD, " \x1b[0m")
}
fmt.Print("\n")
}
}
func setupPackageSpace(a *rpc.Pkg) (pkgbuild *gopkg.PKGBUILD, err error) {
dir := config.YayConf.BuildDir + a.PackageBase + "/"
if _, err = os.Stat(dir); !os.IsNotExist(err) {
if !config.ContinueTask("Directory exists. Clean Build?", "yY") {
_ = os.RemoveAll(config.YayConf.BuildDir + a.PackageBase)
}
}
if err = config.DownloadAndUnpack(BaseURL+a.URLPath, config.YayConf.BuildDir, false); err != nil {
return
}
if !config.ContinueTask("Edit PKGBUILD?", "yY") {
editcmd := exec.Command(config.Editor(), dir+"PKGBUILD")
editcmd.Stdin, editcmd.Stdout, editcmd.Stderr = os.Stdin, os.Stdout, os.Stderr
editcmd.Run()
}
pkgbuild, err = gopkg.ParseSRCINFO(dir + ".SRCINFO")
if err == nil {
for _, pkgsource := range pkgbuild.Source {
owner, repo := vcs.ParseSource(pkgsource)
if owner != "" && repo != "" {
err = vcs.BranchInfo(a.Name, owner, repo)
if err != nil {
fmt.Println(err)
}
}
}
}
err = os.Chdir(dir)
if err != nil {
return
}
return
}
// PkgInstall handles install from Info Result.
func PkgInstall(a *rpc.Pkg, flags []string) (finalmdeps []string, err error) {
fmt.Printf("\x1b[1;32m==> Installing\x1b[33m %s\x1b[0m\n", a.Name)
if a.Maintainer == "" {
fmt.Println("\x1b[1;31;40m==> Warning:\x1b[0;;40m This package is orphaned.\x1b[0m")
}
_, err = setupPackageSpace(a)
if err != nil {
return
}
if specialDBsauce {
return
}
runDeps, makeDeps, err := PkgDependencies(a)
if err != nil {
return
}
repoDeps := append(runDeps[0], makeDeps[0]...)
aurDeps := append(runDeps[1], makeDeps[1]...)
finalmdeps = append(finalmdeps, makeDeps[0]...)
finalmdeps = append(finalmdeps, makeDeps[1]...)
if len(aurDeps) != 0 || len(repoDeps) != 0 {
if !config.ContinueTask("Continue?", "nN") {
return finalmdeps, fmt.Errorf("user did not like the dependencies")
}
}
aurQ, _ := rpc.Info(aurDeps)
if len(aurQ) != len(aurDeps) {
(Query)(aurQ).MissingPackage(aurDeps)
if !config.ContinueTask("Continue?", "nN") {
return finalmdeps, fmt.Errorf("unable to install dependencies")
}
}
var depArgs []string
if config.YayConf.NoConfirm {
depArgs = []string{"--asdeps", "--noconfirm"}
} else {
depArgs = []string{"--asdeps"}
}
// Repo dependencies
if len(repoDeps) != 0 {
errR := config.PassToPacman("-S", repoDeps, depArgs)
if errR != nil {
return finalmdeps, errR
}
}
// Handle AUR dependencies
for _, dep := range aurQ {
finalmdepsR, errA := PkgInstall(&dep, depArgs)
finalmdeps = append(finalmdeps, finalmdepsR...)
if errA != nil {
pacman.CleanRemove(repoDeps)
pacman.CleanRemove(aurDeps)
return finalmdeps, errA
}
}
args := []string{"-sri"}
args = append(args, flags...)
makepkgcmd := exec.Command(config.YayConf.MakepkgBin, args...)
makepkgcmd.Stdin, makepkgcmd.Stdout, makepkgcmd.Stderr = os.Stdin, os.Stdout, os.Stderr
err = makepkgcmd.Run()
if err == nil {
_ = vcs.SaveBranchInfo()
}
return
}
// PrintInfo prints package info like pacman -Si.
func PrintInfo(a *rpc.Pkg) {
fmt.Println("\x1b[1;37mRepository :\x1b[0m", "aur")
fmt.Println("\x1b[1;37mName :\x1b[0m", a.Name)
fmt.Println("\x1b[1;37mVersion :\x1b[0m", a.Version)
fmt.Println("\x1b[1;37mDescription :\x1b[0m", a.Description)
if a.URL != "" {
fmt.Println("\x1b[1;37mURL :\x1b[0m", a.URL)
} else {
fmt.Println("\x1b[1;37mURL :\x1b[0m", "None")
}
fmt.Println("\x1b[1;37mLicenses :\x1b[0m", a.License)
// if len(a.Provides) != 0 {
// fmt.Println("\x1b[1;37mProvides :\x1b[0m", a.Provides)
// } else {
// fmt.Println("\x1b[1;37mProvides :\x1b[0m", "None")
// }
if len(a.Depends) != 0 {
fmt.Println("\x1b[1;37mDepends On :\x1b[0m", a.Depends)
} else {
fmt.Println("\x1b[1;37mDepends On :\x1b[0m", "None")
}
if len(a.MakeDepends) != 0 {
fmt.Println("\x1b[1;37mMake depends On :\x1b[0m", a.MakeDepends)
} else {
fmt.Println("\x1b[1;37mMake depends On :\x1b[0m", "None")
}
if len(a.OptDepends) != 0 {
fmt.Println("\x1b[1;37mOptional Deps :\x1b[0m", a.OptDepends)
} else {
fmt.Println("\x1b[1;37mOptional Deps :\x1b[0m", "None")
}
if len(a.Conflicts) != 0 {
fmt.Println("\x1b[1;37mConflicts With :\x1b[0m", a.Conflicts)
} else {
fmt.Println("\x1b[1;37mConflicts With :\x1b[0m", "None")
}
if a.Maintainer != "" {
fmt.Println("\x1b[1;37mMaintainer :\x1b[0m", a.Maintainer)
} else {
fmt.Println("\x1b[1;37mMaintainer :\x1b[0m", "None")
}
fmt.Println("\x1b[1;37mVotes :\x1b[0m", a.NumVotes)
fmt.Println("\x1b[1;37mPopularity :\x1b[0m", a.Popularity)
if a.OutOfDate != 0 {
fmt.Println("\x1b[1;37mOut-of-date :\x1b[0m", "Yes")
}
}
// RemoveMakeDeps receives a make dependency list and removes those
// that are no longer necessary.
func RemoveMakeDeps(depS []string) (err error) {
hanging := pacman.SliceHangingPackages(depS)
if len(hanging) != 0 {
if !config.ContinueTask("Confirm Removal?", "nN") {
return nil
}
err = pacman.CleanRemove(hanging)
}
return
}

60
clean.go Normal file
View file

@ -0,0 +1,60 @@
package main
// GetPkgbuild gets the pkgbuild of the package 'pkg' trying the ABS first and then the AUR trying the ABS first and then the AUR.
// RemoveMakeDeps receives a make dependency list and removes those
// that are no longer necessary.
func removeMakeDeps(depS []string) (err error) {
hanging := sliceHangingPackages(depS)
if len(hanging) != 0 {
if !continueTask("Confirm Removal?", "nN") {
return nil
}
err = cleanRemove(hanging)
}
return
}
// RemovePackage removes package from VCS information
func removeVCSPackage(pkgs []string) {
for _, pkgName := range pkgs {
for i, e := range savedInfo {
if e.Package == pkgName {
savedInfo[i] = savedInfo[len(savedInfo)-1]
savedInfo = savedInfo[:len(savedInfo)-1]
}
}
}
_ = saveVCSInfo()
return
}
// CleanDependencies removels all dangling dependencies in system
func cleanDependencies(pkgs []string) error {
hanging, err := hangingPackages()
if err != nil {
return err
}
if len(hanging) != 0 {
if !continueTask("Confirm Removal?", "nN") {
return nil
}
err = cleanRemove(hanging)
}
return err
}
// CleanRemove sends a full removal command to pacman with the pkgName slice
func cleanRemove(pkgName []string) (err error) {
if len(pkgName) == 0 {
return nil
}
err = passToPacman("-Rsnc", pkgName, []string{"--noconfirm"})
return err
}

127
cmd.go
View file

@ -2,6 +2,7 @@ package main
import (
"bufio"
"encoding/json"
"fmt"
"io"
"os"
@ -9,9 +10,6 @@ import (
"strings"
"time"
"github.com/jguer/yay/aur"
vcs "github.com/jguer/yay/aur/vcs"
"github.com/jguer/yay/config"
pac "github.com/jguer/yay/pacman"
)
@ -42,7 +40,61 @@ func usage() {
`)
}
var version = "2.116"
func init() {
defaultSettings(&config)
var err error
configfile := os.Getenv("HOME") + "/.config/yay/config.json"
if _, err = os.Stat(configfile); os.IsNotExist(err) {
_ = os.MkdirAll(os.Getenv("HOME")+"/.config/yay", 0755)
// Save the default config if nothing is found
config.saveConfig()
} else {
file, err := os.Open(configfile)
if err != nil {
fmt.Println("Error reading config:", err)
} else {
decoder := json.NewDecoder(file)
err = decoder.Decode(&config)
if err != nil {
fmt.Println("Loading default Settings\nError reading config:", err)
defaultSettings(&config)
}
}
}
AlpmConf, err = readAlpmConfig(config.PacmanConf)
if err != nil {
fmt.Println("Unable to read Pacman conf", err)
os.Exit(1)
}
AlpmHandle, err = AlpmConf.CreateHandle()
if err != nil {
fmt.Println("Unable to CreateHandle", err)
os.Exit(1)
}
updated = false
configfile = os.Getenv("HOME") + "/.config/yay/yay_vcs.json"
if _, err := os.Stat(configfile); os.IsNotExist(err) {
_ = os.MkdirAll(os.Getenv("HOME")+"/.config/yay", 0755)
return
}
file, err := os.Open(configfile)
if err != nil {
fmt.Println("error:", err)
return
}
decoder := json.NewDecoder(file)
err = decoder.Decode(&savedInfo)
if err != nil {
fmt.Println("error:", err)
}
}
func parser() (op string, options []string, packages []string, changedConfig bool, err error) {
if len(os.Args) < 2 {
@ -65,41 +117,41 @@ func parser() (op string, options []string, packages []string, changedConfig boo
changedConfig = true
switch arg {
case "--printconfig":
fmt.Printf("%+v", config.YayConf)
fmt.Printf("%+v", config)
os.Exit(0)
case "--gendb":
err = aur.CreateDevelDB()
err = createDevelDB()
if err != nil {
fmt.Println(err)
}
err = vcs.SaveBranchInfo()
err = saveVCSInfo()
if err != nil {
fmt.Println(err)
}
os.Exit(0)
case "--devel":
config.YayConf.Devel = true
config.Devel = true
case "--nodevel":
config.YayConf.Devel = false
config.Devel = false
case "--timeupdate":
config.YayConf.TimeUpdate = true
config.TimeUpdate = true
case "--notimeupdate":
config.YayConf.TimeUpdate = false
config.TimeUpdate = false
case "--topdown":
config.YayConf.SortMode = config.TopDown
config.SortMode = TopDown
case "--complete":
config.YayConf.Shell = "sh"
config.Shell = "sh"
_ = complete()
os.Exit(0)
case "--fcomplete":
config.YayConf.Shell = "fish"
config.Shell = "fish"
_ = complete()
os.Exit(0)
case "--help":
usage()
os.Exit(0)
case "--noconfirm":
config.YayConf.NoConfirm = true
config.NoConfirm = true
fallthrough
default:
options = append(options, arg)
@ -132,9 +184,9 @@ func main() {
err = localStatistics(version)
case "-Ss", "-Ssq", "-Sqs":
if op == "-Ss" {
config.YayConf.SearchMode = config.Detailed
config.SearchMode = Detailed
} else {
config.YayConf.SearchMode = config.Minimal
config.SearchMode = Minimal
}
if pkgs != nil {
@ -143,14 +195,14 @@ func main() {
case "-S":
err = install(pkgs, options)
case "-Sy":
err = config.PassToPacman("-Sy", nil, nil)
err = passToPacman("-Sy", nil, nil)
if err != nil {
break
}
err = install(pkgs, options)
case "-Syu", "-Suy", "-Su":
if strings.Contains(op, "y") {
err = config.PassToPacman("-Sy", nil, nil)
err = passToPacman("-Sy", nil, nil)
if err != nil {
break
}
@ -159,36 +211,35 @@ func main() {
case "-Si":
err = syncInfo(pkgs, options)
case "yogurt":
config.YayConf.SearchMode = config.NumberMenu
config.SearchMode = NumberMenu
if pkgs != nil {
err = numberMenu(pkgs, options)
}
default:
if op[0] == 'R' {
vcs.RemovePackage(pkgs)
removeVCSPackage(pkgs)
}
err = config.PassToPacman(op, pkgs, options)
err = passToPacman(op, pkgs, options)
}
var erra error
if vcs.Updated {
erra = vcs.SaveBranchInfo()
if updated {
erra = saveVCSInfo()
if erra != nil {
fmt.Println(err)
}
}
if changedConfig {
erra = config.SaveConfig()
erra = config.saveConfig()
if erra != nil {
fmt.Println(err)
}
}
erra = config.AlpmHandle.Release()
erra = AlpmHandle.Release()
if erra != nil {
fmt.Println(err)
}
@ -203,12 +254,12 @@ func main() {
func numberMenu(pkgS []string, flags []string) (err error) {
var num int
aq, err := aur.NarrowSearch(pkgS, true)
aq, err := narrowSearch(pkgS, true)
if err != nil {
fmt.Println("Error during AUR search:", err)
}
numaq := len(aq)
pq, numpq, err := pac.Search(pkgS)
pq, numpq, err := searchRepo(pkgS)
if err != nil {
return
}
@ -217,12 +268,12 @@ func numberMenu(pkgS []string, flags []string) (err error) {
return fmt.Errorf("no packages match search")
}
if config.YayConf.SortMode == config.BottomUp {
printAURSearch(aq, numpq)
if config.SortMode == BottomUp {
aq.printSearch(numpq)
pq.PrintSearch()
} else {
pq.PrintSearch()
printAURSearch(aq, numpq)
pq.printSearch()
aq.printSearch(numpq)
}
fmt.Printf("\x1b[32m%s\x1b[0m\nNumbers: ", "Type numbers to install. Separate each number with a space.")
@ -247,13 +298,13 @@ func numberMenu(pkgS []string, flags []string) (err error) {
if num > numaq+numpq-1 || num < 0 {
continue
} else if num > numpq-1 {
if config.YayConf.SortMode == config.BottomUp {
if config.SortMode == BottomUp {
aurInstall = append(aurInstall, aq[numaq+numpq-num-1].Name)
} else {
aurInstall = append(aurInstall, aq[num-numpq].Name)
}
} else {
if config.YayConf.SortMode == config.BottomUp {
if config.SortMode == BottomUp {
repoInstall = append(repoInstall, pq[numpq-num-1].Name())
} else {
repoInstall = append(repoInstall, pq[num].Name())
@ -266,7 +317,7 @@ func numberMenu(pkgS []string, flags []string) (err error) {
}
if len(aurInstall) != 0 {
err = aur.Install(aurInstall, flags)
err = Install(aurInstall, flags)
}
return err
@ -274,7 +325,7 @@ func numberMenu(pkgS []string, flags []string) (err error) {
// Complete provides completion info for shells
func complete() (err error) {
path := os.Getenv("HOME") + "/.cache/yay/aur_" + config.YayConf.Shell + ".cache"
path := os.Getenv("HOME") + "/.cache/yay/aur_" + config.Shell + ".cache"
if info, err := os.Stat(path); os.IsNotExist(err) || time.Since(info.ModTime()).Hours() > 48 {
os.MkdirAll(os.Getenv("HOME")+"/.cache/yay/", 0755)
@ -284,7 +335,7 @@ func complete() (err error) {
return err
}
if aur.CreateAURList(out) != nil {
if createAURList(out) != nil {
defer os.Remove(path)
}
err = pac.CreatePackageList(out)

60
completions.go Normal file
View file

@ -0,0 +1,60 @@
package main
import (
"bufio"
"fmt"
"net/http"
"os"
)
//CreateAURList creates a new completion file
func createAURList(out *os.File) (err error) {
resp, err := http.Get("https://aur.archlinux.org/packages.gz")
if err != nil {
return err
}
defer resp.Body.Close()
scanner := bufio.NewScanner(resp.Body)
scanner.Scan()
for scanner.Scan() {
fmt.Print(scanner.Text())
out.WriteString(scanner.Text())
if config.Shell == "fish" {
fmt.Print("\tAUR\n")
out.WriteString("\tAUR\n")
} else {
fmt.Print("\n")
out.WriteString("\n")
}
}
return nil
}
//CreatePackageList appends Repo packages to completion cache
func CreatePackageList(out *os.File) (err error) {
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return
}
_ = dbList.ForEach(func(db alpm.Db) error {
_ = db.PkgCache().ForEach(func(pkg alpm.Package) error {
fmt.Print(pkg.Name())
out.WriteString(pkg.Name())
if config.Shell == "fish" {
fmt.Print("\t" + pkg.DB().Name() + "\n")
out.WriteString("\t" + pkg.DB().Name() + "\n")
} else {
fmt.Print("\n")
out.WriteString("\n")
}
return nil
})
return nil
})
return nil
}

View file

@ -1,10 +1,8 @@
package config
package main
import (
"encoding/json"
"fmt"
"io"
"net/http"
"os"
"os/exec"
"strings"
@ -42,9 +40,22 @@ type Configuration struct {
TimeUpdate bool `json:"timeupdate"`
}
var version = "2.116"
// BaseURL givers the AUR default address.
const BaseURL string = "https://aur.archlinux.org"
var specialDBsauce = false
var savedInfo infos
var configfile string
// Updated returns if database has been updated
var updated bool
// YayConf holds the current config values for yay.
var YayConf Configuration
var config Configuration
// AlpmConf holds the current config values for pacman.
var AlpmConf alpm.PacmanConfig
@ -52,43 +63,6 @@ var AlpmConf alpm.PacmanConfig
// AlpmHandle is the alpm handle used by yay.
var AlpmHandle *alpm.Handle
func init() {
defaultSettings(&YayConf)
var err error
configfile := os.Getenv("HOME") + "/.config/yay/config.json"
if _, err = os.Stat(configfile); os.IsNotExist(err) {
_ = os.MkdirAll(os.Getenv("HOME")+"/.config/yay", 0755)
// Save the default config if nothing is found
SaveConfig()
} else {
file, err := os.Open(configfile)
if err != nil {
fmt.Println("Error reading config:", err)
} else {
decoder := json.NewDecoder(file)
err = decoder.Decode(&YayConf)
if err != nil {
fmt.Println("Loading default Settings\nError reading config:", err)
defaultSettings(&YayConf)
}
}
}
AlpmConf, err = readAlpmConfig(YayConf.PacmanConf)
if err != nil {
fmt.Println("Unable to read Pacman conf", err)
os.Exit(1)
}
AlpmHandle, err = AlpmConf.CreateHandle()
if err != nil {
fmt.Println("Unable to CreateHandle", err)
os.Exit(1)
}
}
func readAlpmConfig(pacmanconf string) (conf alpm.PacmanConfig, err error) {
file, err := os.Open(pacmanconf)
if err != nil {
@ -102,10 +76,10 @@ func readAlpmConfig(pacmanconf string) (conf alpm.PacmanConfig, err error) {
}
// SaveConfig writes yay config to file.
func SaveConfig() error {
YayConf.NoConfirm = false
func (config *Configuration) saveConfig() error {
config.NoConfirm = false
configfile := os.Getenv("HOME") + "/.config/yay/config.json"
marshalledinfo, _ := json.MarshalIndent(YayConf, "", "\t")
marshalledinfo, _ := json.MarshalIndent(config, "", "\t")
in, err := os.OpenFile(configfile, os.O_RDWR|os.O_CREATE, 0755)
if err != nil {
return err
@ -134,7 +108,7 @@ func defaultSettings(config *Configuration) {
}
// Editor returns the preferred system editor.
func Editor() string {
func editor() string {
switch {
case YayConf.Editor != "":
editor, err := exec.LookPath(YayConf.Editor)
@ -183,7 +157,7 @@ func Editor() string {
// ContinueTask prompts if user wants to continue task.
//If NoConfirm is set the action will continue without user input.
func ContinueTask(s string, def string) (cont bool) {
func continueTask(s string, def string) (cont bool) {
if YayConf.NoConfirm {
return true
}
@ -210,60 +184,8 @@ func ContinueTask(s string, def string) (cont bool) {
return true
}
func downloadFile(path string, url string) (err error) {
// Create the file
out, err := os.Create(path)
if err != nil {
return err
}
defer out.Close()
// Get the data
resp, err := http.Get(url)
if err != nil {
return err
}
defer resp.Body.Close()
// Writer the body to file
_, err = io.Copy(out, resp.Body)
return err
}
// DownloadAndUnpack downloads url tgz and extracts to path.
func DownloadAndUnpack(url string, path string, trim bool) (err error) {
err = os.MkdirAll(path, 0755)
if err != nil {
return
}
tokens := strings.Split(url, "/")
fileName := tokens[len(tokens)-1]
tarLocation := path + fileName
defer os.Remove(tarLocation)
err = downloadFile(tarLocation, url)
if err != nil {
return
}
if trim {
err = exec.Command("/bin/sh", "-c",
YayConf.TarBin+" --strip-components 2 --include='*/"+fileName[:len(fileName)-7]+"/trunk/' -xf "+tarLocation+" -C "+path).Run()
os.Rename(path+"trunk", path+fileName[:len(fileName)-7]) // kurwa
} else {
err = exec.Command(YayConf.TarBin, "-xf", tarLocation, "-C", path).Run()
}
if err != nil {
return
}
return
}
// PassToPacman outsorces execution to pacman binary without modifications.
func PassToPacman(op string, pkgs []string, flags []string) error {
func passToPacman(op string, pkgs []string, flags []string) error {
var cmd *exec.Cmd
var args []string
@ -287,16 +209,3 @@ func PassToPacman(op string, pkgs []string, flags []string) error {
err := cmd.Run()
return err
}
// Human returns results in Human readable format.
func Human(size int64) string {
floatsize := float32(size)
units := [...]string{"", "Ki", "Mi", "Gi", "Ti", "Pi", "Ei", "Zi", "Yi"}
for _, unit := range units {
if floatsize < 1024 {
return fmt.Sprintf("%.1f %sB", floatsize, unit)
}
floatsize /= 1024
}
return fmt.Sprintf("%d%s", size, "B")
}

76
depencies.go Normal file
View file

@ -0,0 +1,76 @@
package main
// BuildDependencies finds packages, on the second run
// compares with a baselist and avoids searching those
func BuildDependencies(baselist []string) func(toCheck []string, isBaseList bool, last bool) (repo []string, notFound []string) {
localDb, err := AlpmHandle.LocalDb()
if err != nil {
panic(err)
}
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
panic(err)
}
f := func(c rune) bool {
return c == '>' || c == '<' || c == '=' || c == ' '
}
return func(toCheck []string, isBaseList bool, close bool) (repo []string, notFound []string) {
if close {
return
}
Loop:
for _, dep := range toCheck {
if !isBaseList {
for _, base := range baselist {
if base == dep {
continue Loop
}
}
}
if _, erp := localDb.PkgCache().FindSatisfier(dep); erp == nil {
continue
} else if pkg, erp := dbList.FindSatisfier(dep); erp == nil {
repo = append(repo, pkg.Name())
} else {
field := strings.FieldsFunc(dep, f)
notFound = append(notFound, field[0])
}
}
return
}
}
// DepSatisfier receives a string slice, returns a slice of packages found in
// repos and one of packages not found in repos. Leaves out installed packages.
func DepSatisfier(toCheck []string) (repo []string, notFound []string, err error) {
localDb, err := AlpmHandle.LocalDb()
if err != nil {
return
}
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return
}
f := func(c rune) bool {
return c == '>' || c == '<' || c == '=' || c == ' '
}
for _, dep := range toCheck {
if _, erp := localDb.PkgCache().FindSatisfier(dep); erp == nil {
continue
} else if pkg, erp := dbList.FindSatisfier(dep); erp == nil {
repo = append(repo, pkg.Name())
} else {
field := strings.FieldsFunc(dep, f)
notFound = append(notFound, field[0])
}
}
err = nil
return
}

122
download.go Normal file
View file

@ -0,0 +1,122 @@
package main
import (
"fmt"
"io"
"net/http"
"os"
"os/exec"
"strings"
rpc "github.com/mikkeloscar/aur"
)
func downloadFile(path string, url string) (err error) {
// Create the file
out, err := os.Create(path)
if err != nil {
return err
}
defer out.Close()
// Get the data
resp, err := http.Get(url)
if err != nil {
return err
}
defer resp.Body.Close()
// Writer the body to file
_, err = io.Copy(out, resp.Body)
return err
}
// DownloadAndUnpack downloads url tgz and extracts to path.
func downloadAndUnpack(url string, path string, trim bool) (err error) {
err = os.MkdirAll(path, 0755)
if err != nil {
return
}
tokens := strings.Split(url, "/")
fileName := tokens[len(tokens)-1]
tarLocation := path + fileName
defer os.Remove(tarLocation)
err = downloadFile(tarLocation, url)
if err != nil {
return
}
if trim {
err = exec.Command("/bin/sh", "-c",
YayConf.TarBin+" --strip-components 2 --include='*/"+fileName[:len(fileName)-7]+"/trunk/' -xf "+tarLocation+" -C "+path).Run()
os.Rename(path+"trunk", path+fileName[:len(fileName)-7]) // kurwa
} else {
err = exec.Command(YayConf.TarBin, "-xf", tarLocation, "-C", path).Run()
}
if err != nil {
return
}
return
}
func getPkgbuild(pkg string) (err error) {
wd, err := os.Getwd()
if err != nil {
return
}
wd = wd + "/"
err = getPkgbuildfromABS(pkg, wd)
if err == nil {
return
}
err = GetPkgbuildfromAUR(pkg, wd)
return
}
// GetPkgbuild downloads pkgbuild from the ABS.
func getPkgbuildfromABS(pkgN string, path string) (err error) {
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return
}
for _, db := range dbList.Slice() {
pkg, err := db.PkgByName(pkgN)
if err == nil {
var url string
if db.Name() == "core" || db.Name() == "extra" {
url = "https://projects.archlinux.org/svntogit/packages.git/snapshot/packages/" + pkg.Name() + ".tar.gz"
} else if db.Name() == "community" {
url = "https://projects.archlinux.org/svntogit/community.git/snapshot/community-packages/" + pkg.Name() + ".tar.gz"
} else {
return fmt.Errorf("Not in standard repositories")
}
fmt.Printf("\x1b[1;32m==>\x1b[1;33m %s \x1b[1;32mfound in ABS.\x1b[0m\n", pkgN)
errD := DownloadAndUnpack(url, path, true)
return errD
}
}
return fmt.Errorf("package not found")
}
// GetPkgbuild downloads pkgbuild from the AUR.
func getPkgbuildfromAUR(pkgN string, dir string) (err error) {
aq, err := rpc.Info([]string{pkgN})
if err != nil {
return err
}
if len(aq) == 0 {
return fmt.Errorf("no results")
}
fmt.Printf("\x1b[1;32m==>\x1b[1;33m %s \x1b[1;32mfound in AUR.\x1b[0m\n", pkgN)
DownloadAndUnpack(BaseURL+aq[0].URLPath, dir, false)
return
}

175
install.go Normal file
View file

@ -0,0 +1,175 @@
package main
import (
"fmt"
"os"
"os/exec"
"github.com/jguer/yay/pacman"
rpc "github.com/mikkeloscar/aur"
)
// Install handles package installs
func install(pkgs []string, flags []string) error {
aurs, repos, _ := pac.PackageSlices(pkgs)
if len(repos) != 0 {
err := PassToPacman("-S", repos, flags)
if err != nil {
fmt.Println("Error installing repo packages.")
}
}
if len(aurs) != 0 {
err := Install(aurs, flags)
if err != nil {
fmt.Println("Error installing aur packages.")
}
}
return nil
}
// Install sends system commands to make and install a package from pkgName
func Install(pkgName []string, flags []string) (err error) {
q, err := rpc.Info(pkgName)
if err != nil {
return
}
if len(q) != len(pkgName) {
fmt.Printf("Some package from list\n%+v\ndoes not exist", pkgName)
}
var finalrm []string
for _, i := range q {
mrm, err := PkgInstall(&i, flags)
if err != nil {
fmt.Println("Error installing", i.Name, ":", err)
}
finalrm = append(finalrm, mrm...)
}
if len(finalrm) != 0 {
err = removeMakeDeps(finalrm)
}
return err
}
func setupPackageSpace(a *rpc.Pkg) (pkgbuild *gopkg.PKGBUILD, err error) {
dir := config.BuildDir + a.PackageBase + "/"
if _, err = os.Stat(dir); !os.IsNotExist(err) {
if !ContinueTask("Directory exists. Clean Build?", "yY") {
_ = os.RemoveAll(config.BuildDir + a.PackageBase)
}
}
if err = DownloadAndUnpack(BaseURL+a.URLPath, config.BuildDir, false); err != nil {
return
}
if !ContinueTask("Edit PKGBUILD?", "yY") {
editcmd := exec.Command(Editor(), dir+"PKGBUILD")
editcmd.Stdin, editcmd.Stdout, editcmd.Stderr = os.Stdin, os.Stdout, os.Stderr
editcmd.Run()
}
pkgbuild, err = gopkg.ParseSRCINFO(dir + ".SRCINFO")
if err == nil {
for _, pkgsource := range pkgbuild.Source {
owner, repo := vcs.ParseSource(pkgsource)
if owner != "" && repo != "" {
err = vcs.BranchInfo(a.Name, owner, repo)
if err != nil {
fmt.Println(err)
}
}
}
}
err = os.Chdir(dir)
if err != nil {
return
}
return
}
// PkgInstall handles install from Info Result.
func PkgInstall(a *rpc.Pkg, flags []string) (finalmdeps []string, err error) {
fmt.Printf("\x1b[1;32m==> Installing\x1b[33m %s\x1b[0m\n", a.Name)
if a.Maintainer == "" {
fmt.Println("\x1b[1;31;40m==> Warning:\x1b[0;;40m This package is orphaned.\x1b[0m")
}
_, err = setupPackageSpace(a)
if err != nil {
return
}
if specialDBsauce {
return
}
runDeps, makeDeps, err := PkgDependencies(a)
if err != nil {
return
}
repoDeps := append(runDeps[0], makeDeps[0]...)
aurDeps := append(runDeps[1], makeDeps[1]...)
finalmdeps = append(finalmdeps, makeDeps[0]...)
finalmdeps = append(finalmdeps, makeDeps[1]...)
if len(aurDeps) != 0 || len(repoDeps) != 0 {
if !ContinueTask("Continue?", "nN") {
return finalmdeps, fmt.Errorf("user did not like the dependencies")
}
}
aurQ, _ := rpc.Info(aurDeps)
if len(aurQ) != len(aurDeps) {
(Query)(aurQ).MissingPackage(aurDeps)
if !ContinueTask("Continue?", "nN") {
return finalmdeps, fmt.Errorf("unable to install dependencies")
}
}
var depArgs []string
if config.NoConfirm {
depArgs = []string{"--asdeps", "--noconfirm"}
} else {
depArgs = []string{"--asdeps"}
}
// Repo dependencies
if len(repoDeps) != 0 {
errR := PassToPacman("-S", repoDeps, depArgs)
if errR != nil {
return finalmdeps, errR
}
}
// Handle AUR dependencies
for _, dep := range aurQ {
finalmdepsR, errA := PkgInstall(&dep, depArgs)
finalmdeps = append(finalmdeps, finalmdepsR...)
if errA != nil {
pacman.CleanRemove(repoDeps)
pacman.CleanRemove(aurDeps)
return finalmdeps, errA
}
}
args := []string{"-sri"}
args = append(args, flags...)
makepkgcmd := exec.Command(config.MakepkgBin, args...)
makepkgcmd.Stdin, makepkgcmd.Stdout, makepkgcmd.Stderr = os.Stdin, os.Stdout, os.Stderr
err = makepkgcmd.Run()
if err == nil {
_ = vcs.SaveBranchInfo()
}
return
}

View file

@ -1,39 +0,0 @@
package install
import "fmt"
// Install sends system commands to make and install a package from pkgName
func Install(pkgName []string, flags []string) (err error) {
q, err := rpc.Info(pkgName)
if err != nil {
return
}
if len(q) != len(pkgName) {
fmt.Printf("Some package from list\n%+v\ndoes not exist", pkgName)
}
var finalrm []string
for _, i := range q {
mrm, err := PkgInstall(&i, flags)
if err != nil {
fmt.Println("Error installing", i.Name, ":", err)
}
finalrm = append(finalrm, mrm...)
}
if len(finalrm) != 0 {
err = RemoveMakeDeps(finalrm)
}
return err
}
// PkgInstall handles install from Info Result.
func PkgInstall(a []*rpc.Pkg, flags []string) (finalmdeps []string, err error) {
for _, pkg := range a {
if pkg.Maintainer == "" {
fmt.Println("\x1b[1;31;40m==> Warning:\x1b[0;;40m This package is orphaned.\x1b[0m")
}
}
}

View file

@ -1,428 +1 @@
package pacman
import (
"fmt"
"os"
"strings"
"github.com/jguer/go-alpm"
"github.com/jguer/yay/config"
)
// Query holds the results of a repository search.
type Query []alpm.Package
// Search handles repo searches. Creates a RepoSearch struct.
func Search(pkgInputN []string) (s Query, n int, err error) {
dbList, err := config.AlpmHandle.SyncDbs()
if err != nil {
return
}
// BottomUp functions
initL := func(len int) int {
if config.YayConf.SortMode == config.TopDown {
return 0
} else {
return len - 1
}
}
compL := func(len int, i int) bool {
if config.YayConf.SortMode == config.TopDown {
return i < len
} else {
return i > -1
}
}
finalL := func(i int) int {
if config.YayConf.SortMode == config.TopDown {
return i + 1
} else {
return i - 1
}
}
dbS := dbList.Slice()
lenDbs := len(dbS)
for f := initL(lenDbs); compL(lenDbs, f); f = finalL(f) {
pkgS := dbS[f].PkgCache().Slice()
lenPkgs := len(pkgS)
for i := initL(lenPkgs); compL(lenPkgs, i); i = finalL(i) {
match := true
for _, pkgN := range pkgInputN {
if !(strings.Contains(pkgS[i].Name(), pkgN) || strings.Contains(strings.ToLower(pkgS[i].Description()), pkgN)) {
match = false
break
}
}
if match {
n++
s = append(s, pkgS[i])
}
}
}
return
}
//PrintSearch receives a RepoSearch type and outputs pretty text.
func (s Query) PrintSearch() {
for i, res := range s {
var toprint string
if config.YayConf.SearchMode == config.NumberMenu {
if config.YayConf.SortMode == config.BottomUp {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", len(s)-i-1)
} else {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", i)
}
} else if config.YayConf.SearchMode == config.Minimal {
fmt.Println(res.Name())
continue
}
toprint += fmt.Sprintf("\x1b[1m%s/\x1b[33m%s \x1b[36m%s \x1b[0m",
res.DB().Name(), res.Name(), res.Version())
if len(res.Groups().Slice()) != 0 {
toprint += fmt.Sprint(res.Groups().Slice(), " ")
}
localDb, err := config.AlpmHandle.LocalDb()
if err == nil {
if _, err = localDb.PkgByName(res.Name()); err == nil {
toprint += fmt.Sprintf("\x1b[32;40mInstalled\x1b[0m")
}
}
toprint += "\n " + res.Description()
fmt.Println(toprint)
}
}
// PackageSlices separates an input slice into aur and repo slices
func PackageSlices(toCheck []string) (aur []string, repo []string, err error) {
dbList, err := config.AlpmHandle.SyncDbs()
if err != nil {
return
}
for _, pkg := range toCheck {
found := false
_ = dbList.ForEach(func(db alpm.Db) error {
if found {
return nil
}
_, err = db.PkgByName(pkg)
if err == nil {
found = true
repo = append(repo, pkg)
}
return nil
})
if !found {
if _, errdb := dbList.PkgCachebyGroup(pkg); errdb == nil {
repo = append(repo, pkg)
} else {
aur = append(aur, pkg)
}
}
}
err = nil
return
}
// BuildDependencies finds packages, on the second run
// compares with a baselist and avoids searching those
func BuildDependencies(baselist []string) func(toCheck []string, isBaseList bool, last bool) (repo []string, notFound []string) {
localDb, err := config.AlpmHandle.LocalDb()
if err != nil {
panic(err)
}
dbList, err := config.AlpmHandle.SyncDbs()
if err != nil {
panic(err)
}
f := func(c rune) bool {
return c == '>' || c == '<' || c == '=' || c == ' '
}
return func(toCheck []string, isBaseList bool, close bool) (repo []string, notFound []string) {
if close {
return
}
Loop:
for _, dep := range toCheck {
if !isBaseList {
for _, base := range baselist {
if base == dep {
continue Loop
}
}
}
if _, erp := localDb.PkgCache().FindSatisfier(dep); erp == nil {
continue
} else if pkg, erp := dbList.FindSatisfier(dep); erp == nil {
repo = append(repo, pkg.Name())
} else {
field := strings.FieldsFunc(dep, f)
notFound = append(notFound, field[0])
}
}
return
}
}
// DepSatisfier receives a string slice, returns a slice of packages found in
// repos and one of packages not found in repos. Leaves out installed packages.
func DepSatisfier(toCheck []string) (repo []string, notFound []string, err error) {
localDb, err := config.AlpmHandle.LocalDb()
if err != nil {
return
}
dbList, err := config.AlpmHandle.SyncDbs()
if err != nil {
return
}
f := func(c rune) bool {
return c == '>' || c == '<' || c == '=' || c == ' '
}
for _, dep := range toCheck {
if _, erp := localDb.PkgCache().FindSatisfier(dep); erp == nil {
continue
} else if pkg, erp := dbList.FindSatisfier(dep); erp == nil {
repo = append(repo, pkg.Name())
} else {
field := strings.FieldsFunc(dep, f)
notFound = append(notFound, field[0])
}
}
err = nil
return
}
// PkgNameSlice returns a slice of package names
// func (s Query) PkgNameSlice() (pkgNames []string) {
// for _, e := range s {
// pkgNames = append(pkgNames, e.Name())
// }
// return
// }
// CleanRemove sends a full removal command to pacman with the pkgName slice
func CleanRemove(pkgName []string) (err error) {
if len(pkgName) == 0 {
return nil
}
err = config.PassToPacman("-Rsnc", pkgName, []string{"--noconfirm"})
return err
}
// ForeignPackages returns a map of foreign packages, with their version and date as values.
func ForeignPackages() (foreign map[string]alpm.Package, err error) {
localDb, err := config.AlpmHandle.LocalDb()
if err != nil {
return
}
dbList, err := config.AlpmHandle.SyncDbs()
if err != nil {
return
}
foreign = make(map[string]alpm.Package)
f := func(k alpm.Package) error {
found := false
_ = dbList.ForEach(func(d alpm.Db) error {
if found {
return nil
}
_, err = d.PkgByName(k.Name())
if err == nil {
found = true
}
return nil
})
if !found {
foreign[k.Name()] = k
}
return nil
}
err = localDb.PkgCache().ForEach(f)
return
}
// Statistics returns statistics about packages installed in system
func Statistics() (info struct {
Totaln int
Expln int
TotalSize int64
}, err error) {
var tS int64 // TotalSize
var nPkg int
var ePkg int
localDb, err := config.AlpmHandle.LocalDb()
if err != nil {
return
}
for _, pkg := range localDb.PkgCache().Slice() {
tS += pkg.ISize()
nPkg++
if pkg.Reason() == 0 {
ePkg++
}
}
info = struct {
Totaln int
Expln int
TotalSize int64
}{
nPkg, ePkg, tS,
}
return
}
// BiggestPackages prints the name of the ten biggest packages in the system.
func BiggestPackages() {
localDb, err := config.AlpmHandle.LocalDb()
if err != nil {
return
}
pkgCache := localDb.PkgCache()
pkgS := pkgCache.SortBySize().Slice()
if len(pkgS) < 10 {
return
}
for i := 0; i < 10; i++ {
fmt.Printf("%s: \x1B[0;33m%s\x1B[0m\n", pkgS[i].Name(), config.Human(pkgS[i].ISize()))
}
// Could implement size here as well, but we just want the general idea
}
// HangingPackages returns a list of packages installed as deps
// and unneeded by the system
func HangingPackages() (hanging []string, err error) {
localDb, err := config.AlpmHandle.LocalDb()
if err != nil {
return
}
f := func(pkg alpm.Package) error {
if pkg.Reason() != alpm.PkgReasonDepend {
return nil
}
requiredby := pkg.ComputeRequiredBy()
if len(requiredby) == 0 {
hanging = append(hanging, pkg.Name())
fmt.Printf("%s: \x1B[0;33m%s\x1B[0m\n", pkg.Name(), config.Human(pkg.ISize()))
}
return nil
}
err = localDb.PkgCache().ForEach(f)
return
}
// SliceHangingPackages returns a list of packages installed as deps
// and unneeded by the system from a provided list of package names.
func SliceHangingPackages(pkgS []string) (hanging []string) {
localDb, err := config.AlpmHandle.LocalDb()
if err != nil {
return
}
big:
for _, pkgName := range pkgS {
for _, hangN := range hanging {
if hangN == pkgName {
continue big
}
}
pkg, err := localDb.PkgByName(pkgName)
if err == nil {
if pkg.Reason() != alpm.PkgReasonDepend {
continue
}
requiredby := pkg.ComputeRequiredBy()
if len(requiredby) == 0 {
hanging = append(hanging, pkgName)
fmt.Printf("%s: \x1B[0;33m%s\x1B[0m\n", pkg.Name(), config.Human(pkg.ISize()))
}
}
}
return
}
// GetPkgbuild downloads pkgbuild from the ABS.
func GetPkgbuild(pkgN string, path string) (err error) {
dbList, err := config.AlpmHandle.SyncDbs()
if err != nil {
return
}
for _, db := range dbList.Slice() {
pkg, err := db.PkgByName(pkgN)
if err == nil {
var url string
if db.Name() == "core" || db.Name() == "extra" {
url = "https://projects.archlinux.org/svntogit/packages.git/snapshot/packages/" + pkg.Name() + ".tar.gz"
} else if db.Name() == "community" {
url = "https://projects.archlinux.org/svntogit/community.git/snapshot/community-packages/" + pkg.Name() + ".tar.gz"
} else {
return fmt.Errorf("Not in standard repositories")
}
fmt.Printf("\x1b[1;32m==>\x1b[1;33m %s \x1b[1;32mfound in ABS.\x1b[0m\n", pkgN)
errD := config.DownloadAndUnpack(url, path, true)
return errD
}
}
return fmt.Errorf("package not found")
}
//CreatePackageList appends Repo packages to completion cache
func CreatePackageList(out *os.File) (err error) {
dbList, err := config.AlpmHandle.SyncDbs()
if err != nil {
return
}
_ = dbList.ForEach(func(db alpm.Db) error {
_ = db.PkgCache().ForEach(func(pkg alpm.Package) error {
fmt.Print(pkg.Name())
out.WriteString(pkg.Name())
if config.YayConf.Shell == "fish" {
fmt.Print("\t" + pkg.DB().Name() + "\n")
out.WriteString("\t" + pkg.DB().Name() + "\n")
} else {
fmt.Print("\n")
out.WriteString("\n")
}
return nil
})
return nil
})
return nil
}

View file

@ -1,4 +1,4 @@
package pacman
package main
import (
"os"

183
print.go Normal file
View file

@ -0,0 +1,183 @@
package main
import (
"fmt"
rpc "github.com/mikkeloscar/aur"
)
// Human returns results in Human readable format.
func human(size int64) string {
floatsize := float32(size)
units := [...]string{"", "Ki", "Mi", "Gi", "Ti", "Pi", "Ei", "Zi", "Yi"}
for _, unit := range units {
if floatsize < 1024 {
return fmt.Sprintf("%.1f %sB", floatsize, unit)
}
floatsize /= 1024
}
return fmt.Sprintf("%d%s", size, "B")
}
// PrintSearch handles printing search results in a given format
func (q aurQuery) printSearch(start int) {
localDb, _ := config.AlpmHandle.LocalDb()
for i, res := range q {
var toprint string
if config.YayConf.SearchMode == config.NumberMenu {
if config.YayConf.SortMode == config.BottomUp {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", len(q)+start-i-1)
} else {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", start+i)
}
} else if config.YayConf.SearchMode == config.Minimal {
fmt.Println(res.Name)
continue
}
toprint += fmt.Sprintf("\x1b[1m%s/\x1b[33m%s \x1b[36m%s \x1b[0m(%d) ", "aur", res.Name, res.Version, res.NumVotes)
if res.Maintainer == "" {
toprint += fmt.Sprintf("\x1b[31;40m(Orphaned)\x1b[0m ")
}
if res.OutOfDate != 0 {
toprint += fmt.Sprintf("\x1b[31;40m(Out-of-date)\x1b[0m ")
}
if _, err := localDb.PkgByName(res.Name); err == nil {
toprint += fmt.Sprintf("\x1b[32;40mInstalled\x1b[0m")
}
toprint += "\n " + res.Description
fmt.Println(toprint)
}
return
}
//PrintSearch receives a RepoSearch type and outputs pretty text.
func (s repoQuery) printSearch() {
for i, res := range s {
var toprint string
if config.SearchMode == NumberMenu {
if config.SortMode == BottomUp {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", len(s)-i-1)
} else {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", i)
}
} else if config.SearchMode == Minimal {
fmt.Println(res.Name())
continue
}
toprint += fmt.Sprintf("\x1b[1m%s/\x1b[33m%s \x1b[36m%s \x1b[0m",
res.DB().Name(), res.Name(), res.Version())
if len(res.Groups().Slice()) != 0 {
toprint += fmt.Sprint(res.Groups().Slice(), " ")
}
localDb, err := AlpmHandle.LocalDb()
if err == nil {
if _, err = localDb.PkgByName(res.Name()); err == nil {
toprint += fmt.Sprintf("\x1b[32;40mInstalled\x1b[0m")
}
}
toprint += "\n " + res.Description()
fmt.Println(toprint)
}
}
func printDeps(repoDeps []string, aurDeps []string) {
if len(repoDeps) != 0 {
fmt.Print("\x1b[1;32m==> Repository dependencies: \x1b[0m")
for _, repoD := range repoDeps {
fmt.Print("\x1b[33m", repoD, " \x1b[0m")
}
fmt.Print("\n")
}
if len(aurDeps) != 0 {
fmt.Print("\x1b[1;32m==> AUR dependencies: \x1b[0m")
for _, aurD := range aurDeps {
fmt.Print("\x1b[33m", aurD, " \x1b[0m")
}
fmt.Print("\n")
}
}
// PrintInfo prints package info like pacman -Si.
func PrintInfo(a *rpc.Pkg) {
fmt.Println("\x1b[1;37mRepository :\x1b[0m", "aur")
fmt.Println("\x1b[1;37mName :\x1b[0m", a.Name)
fmt.Println("\x1b[1;37mVersion :\x1b[0m", a.Version)
fmt.Println("\x1b[1;37mDescription :\x1b[0m", a.Description)
if a.URL != "" {
fmt.Println("\x1b[1;37mURL :\x1b[0m", a.URL)
} else {
fmt.Println("\x1b[1;37mURL :\x1b[0m", "None")
}
fmt.Println("\x1b[1;37mLicenses :\x1b[0m", a.License)
// if len(a.Provides) != 0 {
// fmt.Println("\x1b[1;37mProvides :\x1b[0m", a.Provides)
// } else {
// fmt.Println("\x1b[1;37mProvides :\x1b[0m", "None")
// }
if len(a.Depends) != 0 {
fmt.Println("\x1b[1;37mDepends On :\x1b[0m", a.Depends)
} else {
fmt.Println("\x1b[1;37mDepends On :\x1b[0m", "None")
}
if len(a.MakeDepends) != 0 {
fmt.Println("\x1b[1;37mMake depends On :\x1b[0m", a.MakeDepends)
} else {
fmt.Println("\x1b[1;37mMake depends On :\x1b[0m", "None")
}
if len(a.OptDepends) != 0 {
fmt.Println("\x1b[1;37mOptional Deps :\x1b[0m", a.OptDepends)
} else {
fmt.Println("\x1b[1;37mOptional Deps :\x1b[0m", "None")
}
if len(a.Conflicts) != 0 {
fmt.Println("\x1b[1;37mConflicts With :\x1b[0m", a.Conflicts)
} else {
fmt.Println("\x1b[1;37mConflicts With :\x1b[0m", "None")
}
if a.Maintainer != "" {
fmt.Println("\x1b[1;37mMaintainer :\x1b[0m", a.Maintainer)
} else {
fmt.Println("\x1b[1;37mMaintainer :\x1b[0m", "None")
}
fmt.Println("\x1b[1;37mVotes :\x1b[0m", a.NumVotes)
fmt.Println("\x1b[1;37mPopularity :\x1b[0m", a.Popularity)
if a.OutOfDate != 0 {
fmt.Println("\x1b[1;37mOut-of-date :\x1b[0m", "Yes")
}
}
// BiggestPackages prints the name of the ten biggest packages in the system.
func biggestPackages() {
localDb, err := AlpmHandle.LocalDb()
if err != nil {
return
}
pkgCache := localDb.PkgCache()
pkgS := pkgCache.SortBySize().Slice()
if len(pkgS) < 10 {
return
}
for i := 0; i < 10; i++ {
fmt.Printf("%s: \x1B[0;33m%s\x1B[0m\n", pkgS[i].Name(), Human(pkgS[i].ISize()))
}
// Could implement size here as well, but we just want the general idea
}

369
query.go
View file

@ -2,51 +2,99 @@ package main
import (
"fmt"
"sort"
"strings"
"github.com/jguer/yay/aur"
"github.com/jguer/yay/config"
alpm "github.com/jguer/go-alpm"
pac "github.com/jguer/yay/pacman"
rpc "github.com/mikkeloscar/aur"
)
// PrintSearch handles printing search results in a given format
func printAURSearch(q aur.Query, start int) {
localDb, _ := config.AlpmHandle.LocalDb()
// Query is a collection of Results
type aurQuery []rpc.Pkg
for i, res := range q {
var toprint string
if config.YayConf.SearchMode == config.NumberMenu {
if config.YayConf.SortMode == config.BottomUp {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", len(q)+start-i-1)
} else {
toprint += fmt.Sprintf("\x1b[33m%d\x1b[0m ", start+i)
// Query holds the results of a repository search.
type repoQuery []alpm.Package
func (q aurQuery) Len() int {
return len(q)
}
func (q aurQuery) Less(i, j int) bool {
if config.SortMode == BottomUp {
return q[i].NumVotes < q[j].NumVotes
}
return q[i].NumVotes > q[j].NumVotes
}
func (q aurQuery) Swap(i, j int) {
q[i], q[j] = q[j], q[i]
}
// MissingPackage warns if the Query was unable to find a package
func (q aurQuery) missingPackage(pkgS []string) {
for _, depName := range pkgS {
found := false
for _, dep := range q {
if dep.Name == depName {
found = true
break
}
} else if config.YayConf.SearchMode == config.Minimal {
fmt.Println(res.Name)
continue
}
toprint += fmt.Sprintf("\x1b[1m%s/\x1b[33m%s \x1b[36m%s \x1b[0m(%d) ", "aur", res.Name, res.Version, res.NumVotes)
if res.Maintainer == "" {
toprint += fmt.Sprintf("\x1b[31;40m(Orphaned)\x1b[0m ")
}
if res.OutOfDate != 0 {
toprint += fmt.Sprintf("\x1b[31;40m(Out-of-date)\x1b[0m ")
if !found {
fmt.Println("\x1b[31mUnable to find", depName, "in AUR\x1b[0m")
}
}
return
}
if _, err := localDb.PkgByName(res.Name); err == nil {
toprint += fmt.Sprintf("\x1b[32;40mInstalled\x1b[0m")
}
toprint += "\n " + res.Description
fmt.Println(toprint)
// NarrowSearch searches AUR and narrows based on subarguments
func narrowSearch(pkgS []string, sortS bool) (aurQuery, error) {
if len(pkgS) == 0 {
return nil, nil
}
return
r, err := rpc.Search(pkgS[0])
if err != nil {
return nil, err
}
if len(pkgS) == 1 {
if sortS {
sort.Sort(Query(r))
}
return r, err
}
var aq aurQuery
var n int
for _, res := range r {
match := true
for _, pkgN := range pkgS[1:] {
if !(strings.Contains(res.Name, pkgN) || strings.Contains(strings.ToLower(res.Description), pkgN)) {
match = false
break
}
}
if match {
n++
aq = append(aq, res)
}
}
if sortS {
sort.Sort(aq)
}
return aq, err
}
// SyncSearch presents a query to the local repos and to the AUR.
func syncSearch(pkgS []string) (err error) {
aq, err := aur.NarrowSearch(pkgS, true)
aq, err := narrowSearch(pkgS, true)
if err != nil {
return err
}
@ -55,12 +103,12 @@ func syncSearch(pkgS []string) (err error) {
return err
}
if config.YayConf.SortMode == config.BottomUp {
printAURSearch(aq, 0)
if config.SortMode == BottomUp {
aq.printAURSearch(0)
pq.PrintSearch()
} else {
pq.PrintSearch()
printAURSearch(aq, 0)
aq.printAURSearch(0)
}
return nil
@ -79,12 +127,12 @@ func syncInfo(pkgS []string, flags []string) (err error) {
fmt.Println(err)
}
for _, aurP := range q {
aur.PrintInfo(&aurP)
PrintInfo(&aurP)
}
}
if len(repoS) != 0 {
err = config.PassToPacman("-Si", repoS, flags)
err = PassToPacman("-Si", repoS, flags)
}
return
@ -107,7 +155,7 @@ func localStatistics(version string) error {
fmt.Printf("\x1B[1;32mTotal installed packages: \x1B[0;33m%d\x1B[0m\n", info.Totaln)
fmt.Printf("\x1B[1;32mTotal foreign installed packages: \x1B[0;33m%d\x1B[0m\n", len(foreignS))
fmt.Printf("\x1B[1;32mExplicitly installed packages: \x1B[0;33m%d\x1B[0m\n", info.Expln)
fmt.Printf("\x1B[1;32mTotal Size occupied by packages: \x1B[0;33m%s\x1B[0m\n", config.Human(info.TotalSize))
fmt.Printf("\x1B[1;32mTotal Size occupied by packages: \x1B[0;33m%s\x1B[0m\n", Human(info.TotalSize))
fmt.Println("\x1B[1;34m===========================================\x1B[0m")
fmt.Println("\x1B[1;32mTen biggest packages\x1B[0m")
pac.BiggestPackages()
@ -120,10 +168,10 @@ func localStatistics(version string) error {
i++
}
var q aur.Query
var q aurQuery
var j int
for i = len(keys); i != 0; i = j {
j = i - config.YayConf.RequestSplitN
j = i - config.RequestSplitN
if j < 0 {
j = 0
}
@ -167,3 +215,252 @@ func localStatistics(version string) error {
return nil
}
// Search handles repo searches. Creates a RepoSearch struct.
func queryRepo(pkgInputN []string) (s repoQuery, n int, err error) {
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return
}
// BottomUp functions
initL := func(len int) int {
if config.SortMode == TopDown {
return 0
}
return len - 1
}
compL := func(len int, i int) bool {
if config.SortMode == TopDown {
return i < len
}
return i > -1
}
finalL := func(i int) int {
if config.SortMode == TopDown {
return i + 1
}
return i - 1
}
dbS := dbList.Slice()
lenDbs := len(dbS)
for f := initL(lenDbs); compL(lenDbs, f); f = finalL(f) {
pkgS := dbS[f].PkgCache().Slice()
lenPkgs := len(pkgS)
for i := initL(lenPkgs); compL(lenPkgs, i); i = finalL(i) {
match := true
for _, pkgN := range pkgInputN {
if !(strings.Contains(pkgS[i].Name(), pkgN) || strings.Contains(strings.ToLower(pkgS[i].Description()), pkgN)) {
match = false
break
}
}
if match {
n++
s = append(s, pkgS[i])
}
}
}
return
}
// PkgDependencies returns package dependencies not installed belonging to AUR
// 0 is Repo, 1 is Foreign.
func pkgDependencies(a *rpc.Pkg) (runDeps [2][]string, makeDeps [2][]string, err error) {
var q aurQuery
if len(a.Depends) == 0 && len(a.MakeDepends) == 0 {
q, err = rpc.Info([]string{a.Name})
if len(q) == 0 || err != nil {
err = fmt.Errorf("Unable to search dependencies, %s", err)
return
}
} else {
q = append(q, *a)
}
depSearch := pacman.BuildDependencies(a.Depends)
if len(a.Depends) != 0 {
runDeps[0], runDeps[1] = depSearch(q[0].Depends, true, false)
if len(runDeps[0]) != 0 || len(runDeps[1]) != 0 {
fmt.Println("\x1b[1;32m=>\x1b[1;33m Run Dependencies: \x1b[0m")
printDeps(runDeps[0], runDeps[1])
}
}
if len(a.MakeDepends) != 0 {
makeDeps[0], makeDeps[1] = depSearch(q[0].MakeDepends, false, false)
if len(makeDeps[0]) != 0 || len(makeDeps[1]) != 0 {
fmt.Println("\x1b[1;32m=>\x1b[1;33m Make Dependencies: \x1b[0m")
printDeps(makeDeps[0], makeDeps[1])
}
}
depSearch(a.MakeDepends, false, true)
err = nil
return
}
// PackageSlices separates an input slice into aur and repo slices
func packageSlices(toCheck []string) (aur []string, repo []string, err error) {
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return
}
for _, pkg := range toCheck {
found := false
_ = dbList.ForEach(func(db alpm.Db) error {
if found {
return nil
}
_, err = db.PkgByName(pkg)
if err == nil {
found = true
repo = append(repo, pkg)
}
return nil
})
if !found {
if _, errdb := dbList.PkgCachebyGroup(pkg); errdb == nil {
repo = append(repo, pkg)
} else {
aur = append(aur, pkg)
}
}
}
err = nil
return
}
// ForeignPackages returns a map of foreign packages, with their version and date as values.
func foreignPackages() (foreign map[string]alpm.Package, err error) {
localDb, err := AlpmHandle.LocalDb()
if err != nil {
return
}
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return
}
foreign = make(map[string]alpm.Package)
f := func(k alpm.Package) error {
found := false
_ = dbList.ForEach(func(d alpm.Db) error {
if found {
return nil
}
_, err = d.PkgByName(k.Name())
if err == nil {
found = true
}
return nil
})
if !found {
foreign[k.Name()] = k
}
return nil
}
err = localDb.PkgCache().ForEach(f)
return
}
// HangingPackages returns a list of packages installed as deps
// and unneeded by the system
func hangingPackages() (hanging []string, err error) {
localDb, err := AlpmHandle.LocalDb()
if err != nil {
return
}
f := func(pkg alpm.Package) error {
if pkg.Reason() != alpm.PkgReasonDepend {
return nil
}
requiredby := pkg.ComputeRequiredBy()
if len(requiredby) == 0 {
hanging = append(hanging, pkg.Name())
fmt.Printf("%s: \x1B[0;33m%s\x1B[0m\n", pkg.Name(), Human(pkg.ISize()))
}
return nil
}
err = localDb.PkgCache().ForEach(f)
return
}
// Statistics returns statistics about packages installed in system
func statistics() (info struct {
Totaln int
Expln int
TotalSize int64
}, err error) {
var tS int64 // TotalSize
var nPkg int
var ePkg int
localDb, err := AlpmHandle.LocalDb()
if err != nil {
return
}
for _, pkg := range localDb.PkgCache().Slice() {
tS += pkg.ISize()
nPkg++
if pkg.Reason() == 0 {
ePkg++
}
}
info = struct {
Totaln int
Expln int
TotalSize int64
}{
nPkg, ePkg, tS,
}
return
}
// SliceHangingPackages returns a list of packages installed as deps
// and unneeded by the system from a provided list of package names.
func sliceHangingPackages(pkgS []string) (hanging []string) {
localDb, err := AlpmHandle.LocalDb()
if err != nil {
return
}
big:
for _, pkgName := range pkgS {
for _, hangN := range hanging {
if hangN == pkgName {
continue big
}
}
pkg, err := localDb.PkgByName(pkgName)
if err == nil {
if pkg.Reason() != alpm.PkgReasonDepend {
continue
}
requiredby := pkg.ComputeRequiredBy()
if len(requiredby) == 0 {
hanging = append(hanging, pkgName)
fmt.Printf("%s: \x1B[0;33m%s\x1B[0m\n", pkg.Name(), Human(pkg.ISize()))
}
}
}
return
}

View file

@ -10,8 +10,6 @@ import (
"unicode"
alpm "github.com/jguer/go-alpm"
"github.com/jguer/yay/aur"
"github.com/jguer/yay/config"
rpc "github.com/mikkeloscar/aur"
pkgb "github.com/mikkeloscar/gopkgbuild"
)
@ -62,11 +60,11 @@ func (u upSlice) Less(i, j int) bool {
// FilterPackages filters packages based on source and type.
func FilterPackages() (local []alpm.Package, remote []alpm.Package,
localNames []string, remoteNames []string, err error) {
localDb, err := config.AlpmHandle.LocalDb()
localDb, err := AlpmHandle.LocalDb()
if err != nil {
return
}
dbList, err := config.AlpmHandle.SyncDbs()
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return
}
@ -194,7 +192,7 @@ func upAUR(remote []alpm.Package, remoteNames []string) (toUpgrade upSlice, err
for i := len(remote); i != 0; i = j {
//Split requests so AUR RPC doesn't get mad at us.
j = i - config.YayConf.RequestSplitN
j = i - config.RequestSplitN
if j < 0 {
j = 0
}
@ -218,7 +216,7 @@ func upAUR(remote []alpm.Package, remoteNames []string) (toUpgrade upSlice, err
if x > max {
break
} else if qtemp[x].Name == local[i].Name() {
if (config.YayConf.TimeUpdate && (int64(qtemp[x].LastModified) > local[i].BuildDate().Unix())) ||
if (config.TimeUpdate && (int64(qtemp[x].LastModified) > local[i].BuildDate().Unix())) ||
(alpm.VerCmp(local[i].Version(), qtemp[x].Version) < 0) {
packageC <- upgrade{qtemp[x].Name, "aur", local[i].Version(), qtemp[x].Version}
}
@ -248,7 +246,7 @@ func upAUR(remote []alpm.Package, remoteNames []string) (toUpgrade upSlice, err
// repo gathers local packages and checks if they have new versions.
// Output: Upgrade type package list.
func upRepo(local []alpm.Package) (upSlice, error) {
dbList, err := config.AlpmHandle.SyncDbs()
dbList, err := AlpmHandle.SyncDbs()
if err != nil {
return nil, err
}
@ -259,14 +257,14 @@ primeloop:
newPkg := pkg.NewVersion(dbList)
if newPkg != nil {
for _, ignorePkg := range config.AlpmConf.IgnorePkg {
for _, ignorePkg := range AlpmConf.IgnorePkg {
if pkg.Name() == ignorePkg {
fmt.Printf("\x1b[33mwarning:\x1b[0m %s (ignored pkg) ignoring upgrade (%s -> %s)\n", pkg.Name(), pkg.Version(), newPkg.Version())
continue primeloop
}
}
for _, ignoreGroup := range config.AlpmConf.IgnoreGroup {
for _, ignoreGroup := range AlpmConf.IgnoreGroup {
for _, group := range pkg.Groups().Slice() {
if group == ignoreGroup {
fmt.Printf("\x1b[33mwarning:\x1b[0m %s (ignored group) ignoring upgrade (%s -> %s)\n", pkg.Name(), pkg.Version(), newPkg.Version())
@ -336,7 +334,7 @@ func upgradePkgs(flags []string) error {
repoNames = append(repoNames, k.Name)
}
err := config.PassToPacman("-S", repoNames, flags)
err := PassToPacman("-S", repoNames, flags)
if err != nil {
fmt.Println("Error upgrading repo packages.")
}
@ -353,7 +351,28 @@ func upgradePkgs(flags []string) error {
}
aurNames = append(aurNames, k.Name)
}
aur.Install(aurNames, flags)
Install(aurNames, flags)
}
return nil
}
func develUpgrade(foreign map[string]alpm.Package, flags []string) error {
fmt.Println(" Checking development packages...")
develUpdates := vcs.CheckUpdates(foreign)
if len(develUpdates) != 0 {
for _, q := range develUpdates {
fmt.Printf("\x1b[1m\x1b[32m==>\x1b[33;1m %s\x1b[0m\n", q)
}
// Install updated packages
if !ContinueTask("Proceed with upgrade?", "nN") {
return nil
}
err := Install(develUpdates, flags)
if err != nil {
fmt.Println(err)
}
}
return nil
}

View file

@ -1,4 +1,4 @@
package github
package main
import (
"encoding/json"
@ -8,6 +8,7 @@ import (
"strings"
alpm "github.com/jguer/go-alpm"
"github.com/jguer/yay/pacman"
)
// branch contains the information of a repository branch
@ -30,35 +31,28 @@ type Info struct {
type infos []Info
var savedInfo infos
var configfile string
// Updated returns if database has been updated
var Updated bool
func init() {
Updated = false
configfile = os.Getenv("HOME") + "/.config/yay/yay_vcs.json"
if _, err := os.Stat(configfile); os.IsNotExist(err) {
_ = os.MkdirAll(os.Getenv("HOME")+"/.config/yay", 0755)
return
}
file, err := os.Open(configfile)
// CreateDevelDB forces yay to create a DB of the existing development packages
func createDevelDB() error {
foreign, err := pacman.ForeignPackages()
if err != nil {
fmt.Println("error:", err)
return
return err
}
decoder := json.NewDecoder(file)
err = decoder.Decode(&savedInfo)
if err != nil {
fmt.Println("error:", err)
keys := make([]string, len(foreign))
i := 0
for k := range foreign {
keys[i] = k
i++
}
config.NoConfirm = true
specialDBsauce = true
err = Install(keys, nil)
return err
}
// ParseSource returns owner and repo from source
func ParseSource(source string) (owner string, repo string) {
func parseSource(source string) (owner string, repo string) {
if !(strings.Contains(source, "git://") ||
strings.Contains(source, ".git") ||
strings.Contains(source, "git+https://")) {
@ -97,16 +91,15 @@ func (info *Info) needsUpdate() bool {
if e.Name == "master" {
if e.Commit.SHA != info.SHA {
return true
} else {
return false
}
return false
}
}
return false
}
// CheckUpdates returns list of outdated packages
func CheckUpdates(foreign map[string]alpm.Package) (toUpdate []string) {
func checkUpdates(foreign map[string]alpm.Package) (toUpdate []string) {
for _, e := range savedInfo {
if e.needsUpdate() {
if _, ok := foreign[e.Package]; ok {
@ -128,23 +121,8 @@ func inStore(pkgName string) *Info {
return nil
}
// RemovePackage removes package from VCS information
func RemovePackage(pkgs []string) {
for _, pkgName := range pkgs {
for i, e := range savedInfo {
if e.Package == pkgName {
savedInfo[i] = savedInfo[len(savedInfo)-1]
savedInfo = savedInfo[:len(savedInfo)-1]
}
}
}
_ = SaveBranchInfo()
return
}
// BranchInfo updates saved information
func BranchInfo(pkgName string, owner string, repo string) (err error) {
func branchInfo(pkgName string, owner string, repo string) (err error) {
Updated = true
var newRepo branches
url := "https://api.github.com/repos/" + owner + "/" + repo + "/branches"
@ -173,8 +151,8 @@ func BranchInfo(pkgName string, owner string, repo string) (err error) {
return
}
func SaveBranchInfo() error {
marshalledinfo, err := json.Marshal(savedInfo)
func saveVCSInfo() error {
marshalledinfo, err := json.MarshalIndent(savedInfo)
if err != nil || string(marshalledinfo) == "null" {
return err
}

View file

@ -1,4 +1,4 @@
package github
package main
import (
"testing"