diff --git a/cmd.go b/cmd.go index 304bb69d..6b233d12 100644 --- a/cmd.go +++ b/cmd.go @@ -102,6 +102,7 @@ Permanent configuration options: --cleanafter Remove package sources after successful install --nocleanafter Do not remove package sources after successful build + --keepsrc Keep pkg/ and src/ after building packages --bottomup Shows AUR's packages first and then repository's --topdown Shows repository's packages first and then AUR's --singlelineresults List each search result on its own line diff --git a/completions/bash b/completions/bash index f29c68b5..23743edb 100644 --- a/completions/bash +++ b/completions/bash @@ -72,7 +72,7 @@ _yay() { makepkg pacman git gpg gpgflags config requestsplitn sudoloop nosudoloop redownload noredownload redownloadall rebuild rebuildall rebuildtree norebuild sortby singlelineresults doublelineresults answerclean answerdiff answeredit answerupgrade noanswerclean noanswerdiff - noansweredit noanswerupgrade cleanmenu diffmenu editmenu cleanafter nocleanafter + noansweredit noanswerupgrade cleanmenu diffmenu editmenu cleanafter nocleanafter keepsrc nocleanmenu nodiffmenu provides noprovides pgpfetch nopgpfetch useask nouseask combinedupgrade nocombinedupgrade aur repo makepkgconf nomakepkgconf askremovemake askyesremovemake removemake noremovemake completioninterval aururl aurrpcurl diff --git a/completions/fish b/completions/fish index 58f5d55f..eb89d0b1 100644 --- a/completions/fish +++ b/completions/fish @@ -231,6 +231,7 @@ complete -c $progname -n "not $noopt" -l devel -d 'Check -git/-svn/-hg developme complete -c $progname -n "not $noopt" -l nodevel -d 'Disable development version checking' -f complete -c $progname -n "not $noopt" -l cleanafter -d 'Clean package sources after successful build' -f complete -c $progname -n "not $noopt" -l nocleanafter -d 'Disable package sources cleaning' -f +complete -c $progname -n "not $noopt" -l keepsrc -d 'Keep pkg/ and src/ after building packages' -f complete -c $progname -n "not $noopt" -l timeupdate -d 'Check package modification date and version' -f complete -c $progname -n "not $noopt" -l notimeupdate -d 'Check only package version change' -f complete -c $progname -n "not $noopt" -l redownload -d 'Redownload PKGBUILD of package even if up-to-date' -f diff --git a/completions/zsh b/completions/zsh index 77621a5a..e1f1ec43 100644 --- a/completions/zsh +++ b/completions/zsh @@ -86,6 +86,7 @@ _pacman_opts_common=( '--nodevel[Disable development version checking]' '--cleanafter[Clean package sources after successful build]' '--nocleanafter[Disable package sources cleaning after successful build]' + '--keepsrc[Keep pkg/ and src/ after building packages]' '--timeupdate[Check packages modification date and version]' '--notimeupdate[Check only package version change]' '--redownload[Always download pkgbuilds of targets]' diff --git a/doc/yay.8 b/doc/yay.8 index b368f2db..88486584 100644 --- a/doc/yay.8 +++ b/doc/yay.8 @@ -384,6 +384,10 @@ instead of having to reclone the entire repo. .B \-\-nocleanafter Do not remove package sources after successful Install. +.TP +.B \-\-keepsrc +Keep pkg/ and src/ after building packages + .TP .B \-\-timeupdate During sysupgrade also compare the build time of installed packages against diff --git a/local_install_test.go b/local_install_test.go index 9cf70549..c9d2fa5e 100644 --- a/local_install_test.go +++ b/local_install_test.go @@ -56,16 +56,16 @@ func TestIntegrationLocalInstall(t *testing.T) { } wantShow := []string{ - "makepkg --verifysource --skippgpcheck -Ccf", + "makepkg --verifysource --skippgpcheck -f -Cc", "pacman -S --config /etc/pacman.conf -- community/dotnet-sdk-6.0 community/dotnet-runtime-6.0", "pacman -D -q --asdeps --config /etc/pacman.conf -- dotnet-runtime-6.0 dotnet-sdk-6.0", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/jellyfin-server-10.8.4-1-x86_64.pkg.tar.zst /testdir/jellyfin-web-10.8.4-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- jellyfin-server jellyfin-web", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/jellyfin-10.8.4-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- jellyfin", @@ -324,14 +324,14 @@ func TestIntegrationLocalInstallNeeded(t *testing.T) { } wantShow := []string{ - "makepkg --verifysource --skippgpcheck -Ccf", + "makepkg --verifysource --skippgpcheck -f -Cc", "pacman -S --config /etc/pacman.conf -- community/dotnet-sdk-6.0 community/dotnet-runtime-6.0", "pacman -D -q --asdeps --config /etc/pacman.conf -- dotnet-runtime-6.0 dotnet-sdk-6.0", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", } @@ -492,16 +492,16 @@ func TestIntegrationLocalInstallGenerateSRCINFO(t *testing.T) { } wantShow := []string{ - "makepkg --verifysource --skippgpcheck -Ccf", + "makepkg --verifysource --skippgpcheck -f -Cc", "pacman -S --config /etc/pacman.conf -- community/dotnet-sdk-6.0 community/dotnet-runtime-6.0", "pacman -D -q --asdeps --config /etc/pacman.conf -- dotnet-runtime-6.0 dotnet-sdk-6.0", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/jellyfin-server-10.8.4-1-x86_64.pkg.tar.zst /testdir/jellyfin-web-10.8.4-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- jellyfin-server jellyfin-web", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/jellyfin-10.8.4-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- jellyfin", @@ -783,12 +783,12 @@ func TestIntegrationLocalInstallWithDepsProvides(t *testing.T) { } wantShow := []string{ - "makepkg --verifysource --skippgpcheck -Ccf", - "makepkg --nobuild -fC --ignorearch", + "makepkg --verifysource --skippgpcheck -f -Cc", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/ceph-libs-bin-17.2.6-2-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- ceph-libs-bin", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/ceph-bin-17.2.6-2-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- ceph-bin", @@ -910,13 +910,13 @@ func TestIntegrationLocalInstallTwoSrcInfosWithDeps(t *testing.T) { } wantShow := []string{ - "makepkg --verifysource --skippgpcheck -Ccf", - "makepkg --verifysource --skippgpcheck -Ccf", - "makepkg --nobuild -fC --ignorearch", + "makepkg --verifysource --skippgpcheck -f -Cc", + "makepkg --verifysource --skippgpcheck -f -Cc", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir1/libzip-git-1.9.2.r166.gd2c47d0f-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- libzip-git", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir2/gourou-0.8.1-4-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- gourou", diff --git a/pkg/settings/args.go b/pkg/settings/args.go index 92fcac56..ddcf84ab 100644 --- a/pkg/settings/args.go +++ b/pkg/settings/args.go @@ -53,6 +53,8 @@ func (c *Configuration) handleOption(option, value string) bool { c.CleanAfter = true case "noafterclean", "nocleanafter": c.CleanAfter = false + case "keepsrc": + c.KeepSrc = true case "debug": c.Debug = true return false diff --git a/pkg/settings/config.go b/pkg/settings/config.go index 23a1e7e0..e342e0ed 100644 --- a/pkg/settings/config.go +++ b/pkg/settings/config.go @@ -56,6 +56,7 @@ type Configuration struct { TimeUpdate bool `json:"timeupdate"` Devel bool `json:"devel"` CleanAfter bool `json:"cleanAfter"` + KeepSrc bool `json:"keepSrc"` Provides bool `json:"provides"` PGPFetch bool `json:"pgpfetch"` CleanMenu bool `json:"cleanmenu"` @@ -193,6 +194,7 @@ func DefaultConfig(version string) *Configuration { AURURL: "https://aur.archlinux.org", BuildDir: os.ExpandEnv("$HOME/.cache/yay"), CleanAfter: false, + KeepSrc: false, Editor: "", EditorFlags: "", Devel: false, diff --git a/pkg/settings/exe/cmd_builder.go b/pkg/settings/exe/cmd_builder.go index 624b7b03..f11201ba 100644 --- a/pkg/settings/exe/cmd_builder.go +++ b/pkg/settings/exe/cmd_builder.go @@ -39,6 +39,7 @@ type ICmdBuilder interface { BuildMakepkgCmd(ctx context.Context, dir string, extraArgs ...string) *exec.Cmd BuildPacmanCmd(ctx context.Context, args *parser.Arguments, mode parser.TargetMode, noConfirm bool) *exec.Cmd AddMakepkgFlag(string) + GetKeepSrc() bool SudoLoop() } @@ -56,6 +57,7 @@ type CmdBuilder struct { PacmanBin string PacmanConfigPath string PacmanDBPath string + KeepSrc bool Runner Runner Log *text.Logger } @@ -75,6 +77,7 @@ func NewCmdBuilder(cfg *settings.Configuration, runner Runner, logger *text.Logg PacmanBin: cfg.PacmanBin, PacmanConfigPath: cfg.PacmanConf, PacmanDBPath: dbPath, + KeepSrc: cfg.KeepSrc, Runner: runner, Log: logger, } @@ -296,3 +299,7 @@ func (c *CmdBuilder) Show(cmd *exec.Cmd) error { func (c *CmdBuilder) Capture(cmd *exec.Cmd) (stdout, stderr string, err error) { return c.Runner.Capture(cmd) } + +func (c *CmdBuilder) GetKeepSrc() bool { + return c.KeepSrc +} diff --git a/pkg/settings/exe/mock.go b/pkg/settings/exe/mock.go index cbf32382..31a1f896 100644 --- a/pkg/settings/exe/mock.go +++ b/pkg/settings/exe/mock.go @@ -25,6 +25,7 @@ type MockBuilder struct { BuildMakepkgCmdCalls []Call BuildMakepkgCmdFn func(ctx context.Context, dir string, extraArgs ...string) *exec.Cmd BuildPacmanCmdFn func(ctx context.Context, args *parser.Arguments, mode parser.TargetMode, noConfirm bool) *exec.Cmd + GetKeepSrcFn func() bool } type MockRunner struct { @@ -95,6 +96,10 @@ func (m *MockBuilder) Show(cmd *exec.Cmd) error { return m.Runner.Show(cmd) } +func (m *MockBuilder) GetKeepSrc() bool { + return false +} + func (m *MockRunner) Capture(cmd *exec.Cmd) (stdout, stderr string, err error) { m.CaptureCallsMu.Lock() m.CaptureCalls = append(m.CaptureCalls, Call{ diff --git a/pkg/settings/parser/parser.go b/pkg/settings/parser/parser.go index 6e7166b1..885bf9c1 100644 --- a/pkg/settings/parser/parser.go +++ b/pkg/settings/parser/parser.go @@ -378,6 +378,7 @@ func isArg(arg string) bool { case "save": case "afterclean", "cleanafter": case "noafterclean", "nocleanafter": + case "keepsrc": case "devel": case "nodevel": case "timeupdate": diff --git a/pkg/sync/build/installer.go b/pkg/sync/build/installer.go index 66988cd3..59b2599d 100644 --- a/pkg/sync/build/installer.go +++ b/pkg/sync/build/installer.go @@ -277,7 +277,11 @@ func (installer *Installer) buildPkg(ctx context.Context, dir, base string, installIncompatible, needed, isTarget bool, ) (map[string]string, error) { - args := []string{"--nobuild", "-fC"} + args := []string{"--nobuild", "-f"} + + if !installer.exeCmd.GetKeepSrc() { + args = append(args, "-C") + } if installIncompatible { args = append(args, "--ignorearch") @@ -296,19 +300,23 @@ func (installer *Installer) buildPkg(ctx context.Context, switch { case needed && installer.pkgsAreAlreadyInstalled(pkgdests, pkgVersion) || installer.downloadOnly: - args = []string{"-c", "--nobuild", "--noextract", "--ignorearch"} + args = []string{"--nobuild", "--noextract", "--ignorearch"} pkgdests = map[string]string{} installer.log.Warnln(gotext.Get("%s is up to date -- skipping", text.Cyan(base+"-"+pkgVersion))) case installer.skipAlreadyBuiltPkg(isTarget, pkgdests): - args = []string{"-c", "--nobuild", "--noextract", "--ignorearch"} + args = []string{"--nobuild", "--noextract", "--ignorearch"} installer.log.Warnln(gotext.Get("%s already made -- skipping build", text.Cyan(base+"-"+pkgVersion))) default: - args = []string{"-cf", "--noconfirm", "--noextract", "--noprepare", "--holdver"} + args = []string{"-f", "--noconfirm", "--noextract", "--noprepare", "--holdver"} if installIncompatible { args = append(args, "--ignorearch") } } + if !installer.exeCmd.GetKeepSrc() { + args = append(args, "-c") + } + errMake := installer.exeCmd.Show( installer.exeCmd.BuildMakepkgCmd(ctx, dir, args...)) diff --git a/pkg/sync/build/installer_test.go b/pkg/sync/build/installer_test.go index a16d433d..434e4874 100644 --- a/pkg/sync/build/installer_test.go +++ b/pkg/sync/build/installer_test.go @@ -56,8 +56,8 @@ func TestInstaller_InstallNeeded(t *testing.T) { isInstalled: false, isBuilt: false, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --needed --config -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config -- yay", }, @@ -68,7 +68,7 @@ func TestInstaller_InstallNeeded(t *testing.T) { isInstalled: false, isBuilt: true, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --needed --config -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config -- yay", @@ -80,7 +80,7 @@ func TestInstaller_InstallNeeded(t *testing.T) { isInstalled: true, isBuilt: false, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", }, wantCapture: []string{"makepkg --packagelist"}, @@ -212,8 +212,8 @@ func TestInstaller_InstallMixedSourcesAndLayers(t *testing.T) { wantShow: []string{ "pacman -S --config /etc/pacman.conf -- core/linux", "pacman -D -q --asdeps --config /etc/pacman.conf -- linux", - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- yay", }, @@ -241,8 +241,8 @@ func TestInstaller_InstallMixedSourcesAndLayers(t *testing.T) { wantShow: []string{ "pacman -S --config /etc/pacman.conf -- core/linux", "pacman -D -q --asdeps --config /etc/pacman.conf -- linux", - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- yay", }, @@ -293,10 +293,10 @@ func TestInstaller_InstallMixedSourcesAndLayers(t *testing.T) { { desc: "same layer -- aur", wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config /etc/pacman.conf -- pacman -U --config /etc/pacman.conf -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- yay", }, @@ -323,12 +323,12 @@ func TestInstaller_InstallMixedSourcesAndLayers(t *testing.T) { { desc: "different layer -- aur", wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config /etc/pacman.conf -- pacman -U --config /etc/pacman.conf -- /testdir/jellyfin-server-10.8.8-1-x86_64.pkg.tar.zst", "pacman -D -q --asdeps --config /etc/pacman.conf -- jellyfin-server", - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config /etc/pacman.conf -- pacman -U --config /etc/pacman.conf -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- yay", }, @@ -374,13 +374,13 @@ func TestInstaller_InstallMixedSourcesAndLayers(t *testing.T) { } showOverride := func(cmd *exec.Cmd) error { - if strings.Contains(cmd.String(), "makepkg -cf --noconfirm") && cmd.Dir == tmpDir { + if strings.Contains(cmd.String(), "makepkg -f --noconfirm") && cmd.Dir == tmpDir { f, err := os.OpenFile(pkgTar, os.O_RDONLY|os.O_CREATE, 0o666) require.NoError(td, err) require.NoError(td, f.Close()) } - if strings.Contains(cmd.String(), "makepkg -cf --noconfirm") && cmd.Dir == tmpDirJfin { + if strings.Contains(cmd.String(), "makepkg -f --noconfirm") && cmd.Dir == tmpDirJfin { f, err := os.OpenFile(jfinPkgTar, os.O_RDONLY|os.O_CREATE, 0o666) require.NoError(td, err) require.NoError(td, f.Close()) @@ -570,7 +570,7 @@ func TestInstaller_CompileFailed(t *testing.T) { } showOverride := func(cmd *exec.Cmd) error { - if tc.failBuild && strings.Contains(cmd.String(), "makepkg -cf --noconfirm") && cmd.Dir == tmpDir { + if tc.failBuild && strings.Contains(cmd.String(), "makepkg -f --noconfirm") && cmd.Dir == tmpDir { return errors.New("makepkg failed") } return nil @@ -694,13 +694,13 @@ func TestInstaller_InstallSplitPackage(t *testing.T) { wantShow: []string{ "pacman -S --config /etc/pacman.conf -- community/dotnet-runtime-6.0 community/aspnet-runtime community/dotnet-sdk-6.0", "pacman -D -q --asdeps --config /etc/pacman.conf -- dotnet-runtime-6.0 aspnet-runtime dotnet-sdk-6.0", - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/jellyfin-web-10.8.4-1-x86_64.pkg.tar.zst /testdir/jellyfin-server-10.8.4-1-x86_64.pkg.tar.zst", "pacman -D -q --asdeps --config /etc/pacman.conf -- jellyfin-server jellyfin-web", - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/jellyfin-10.8.4-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config /etc/pacman.conf -- jellyfin", @@ -818,7 +818,7 @@ func TestInstaller_InstallDownloadOnly(t *testing.T) { isInstalled: false, isBuilt: false, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", }, wantCapture: []string{"makepkg --packagelist"}, @@ -828,7 +828,7 @@ func TestInstaller_InstallDownloadOnly(t *testing.T) { isInstalled: false, isBuilt: true, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", }, wantCapture: []string{"makepkg --packagelist"}, @@ -838,7 +838,7 @@ func TestInstaller_InstallDownloadOnly(t *testing.T) { isInstalled: true, isBuilt: false, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", }, wantCapture: []string{"makepkg --packagelist"}, @@ -1075,7 +1075,7 @@ func TestInstaller_InstallRebuild(t *testing.T) { isBuilt: true, isInstalled: false, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config -- yay", @@ -1099,8 +1099,8 @@ func TestInstaller_InstallRebuild(t *testing.T) { isBuilt: true, isInstalled: false, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config -- yay", }, @@ -1123,8 +1123,8 @@ func TestInstaller_InstallRebuild(t *testing.T) { isInstalled: true, isBuilt: true, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asexplicit --config -- yay", }, @@ -1147,8 +1147,8 @@ func TestInstaller_InstallRebuild(t *testing.T) { isInstalled: true, isBuilt: true, wantShow: []string{ - "makepkg --nobuild -fC --ignorearch", - "makepkg -cf --noconfirm --noextract --noprepare --holdver --ignorearch", + "makepkg --nobuild -f -C --ignorearch", + "makepkg -f -c --noconfirm --noextract --noprepare --holdver --ignorearch", "pacman -U --config -- /testdir/yay-91.0.0-1-x86_64.pkg.tar.zst", "pacman -D -q --asdeps --config -- yay", }, @@ -1337,3 +1337,107 @@ func TestInstaller_InstallUpgrade(t *testing.T) { }) } } + +func TestInstaller_KeepSrc(t *testing.T) { + t.Parallel() + + makepkgBin := t.TempDir() + "/makepkg" + pacmanBin := t.TempDir() + "/pacman" + f, err := os.OpenFile(makepkgBin, os.O_RDONLY|os.O_CREATE, 0o755) + require.NoError(t, err) + require.NoError(t, f.Close()) + + f, err = os.OpenFile(pacmanBin, os.O_RDONLY|os.O_CREATE, 0o755) + require.NoError(t, err) + require.NoError(t, f.Close()) + + type testCase struct { + desc string + wantShow []string + targets []map[string]*dep.InstallInfo + } + + tmpDir := t.TempDir() + + testCases := []testCase{ + { + desc: "--keepsrc", + wantShow: []string{ + "makepkg --nobuild -f --ignorearch", + "makepkg --nobuild --noextract --ignorearch", + "pacman -U --config -- /testdir/yay-92.0.0-1-x86_64.pkg.tar.zst", + "pacman -D -q --asexplicit --config -- yay", + }, + targets: []map[string]*dep.InstallInfo{ + { + "yay": { + Source: dep.AUR, + Reason: dep.Explicit, + Version: "92.0.0-1", + SrcinfoPath: ptrString(tmpDir + "/.SRCINFO"), + AURBase: ptrString("yay"), + }, + }, + }, + }, + } + + for _, tc := range testCases { + tc := tc + t.Run(tc.desc, func(td *testing.T) { + tmpDir := td.TempDir() + pkgTar := tmpDir + "/yay-92.0.0-1-x86_64.pkg.tar.zst" + + captureOverride := func(cmd *exec.Cmd) (stdout string, stderr string, err error) { + return pkgTar, "", nil + } + + // create a mock file + f, err := os.OpenFile(pkgTar, os.O_RDONLY|os.O_CREATE, 0o666) + require.NoError(td, err) + require.NoError(td, f.Close()) + + mockDB := &mock.DBExecutor{} + mockRunner := &exe.MockRunner{CaptureFn: captureOverride} + cmdBuilder := &exe.CmdBuilder{ + MakepkgBin: makepkgBin, + SudoBin: "su", + PacmanBin: pacmanBin, + KeepSrc: true, + Runner: mockRunner, + SudoLoopEnabled: false, + } + + installer := NewInstaller(mockDB, cmdBuilder, &vcs.Mock{}, parser.ModeAny, + parser.RebuildModeNo, false, newTestLogger()) + + cmdArgs := parser.MakeArguments() + cmdArgs.AddTarget("yay") + + pkgBuildDirs := map[string]string{ + "yay": tmpDir, + } + + errI := installer.Install(context.Background(), cmdArgs, tc.targets, pkgBuildDirs, []string{}, false) + require.NoError(td, errI) + + require.Len(td, mockRunner.ShowCalls, len(tc.wantShow)) + + for i, call := range mockRunner.ShowCalls { + show := call.Args[0].(*exec.Cmd).String() + show = strings.ReplaceAll(show, tmpDir, "/testdir") // replace the temp dir with a static path + show = strings.ReplaceAll(show, makepkgBin, "makepkg") + show = strings.ReplaceAll(show, pacmanBin, "pacman") + + // options are in a different order on different systems and on CI root user is used + assert.Subset(td, strings.Split(show, " "), strings.Split(tc.wantShow[i], " "), show) + + // Only assert makepkg commands don't have clean arguments + if strings.HasPrefix(show, "makepkg") { + assert.NotContains(td, show, "-c") + assert.NotContains(td, show, "-C") + } + } + }) + } +} diff --git a/pkg/sync/workdir/aur_source.go b/pkg/sync/workdir/aur_source.go index b517095b..6777369b 100644 --- a/pkg/sync/workdir/aur_source.go +++ b/pkg/sync/workdir/aur_source.go @@ -32,7 +32,11 @@ func (e *ErrDownloadSource) Unwrap() error { func downloadPKGBUILDSource(ctx context.Context, cmdBuilder exe.ICmdBuilder, pkgBuildDir string, installIncompatible bool, ) error { - args := []string{"--verifysource", "--skippgpcheck", "-Ccf"} + args := []string{"--verifysource", "--skippgpcheck", "-f"} + + if !cmdBuilder.GetKeepSrc() { + args = append(args, "-Cc") + } if installIncompatible { args = append(args, "--ignorearch") diff --git a/pkg/sync/workdir/aur_source_test.go b/pkg/sync/workdir/aur_source_test.go index 266ddac8..dd141f97 100644 --- a/pkg/sync/workdir/aur_source_test.go +++ b/pkg/sync/workdir/aur_source_test.go @@ -33,6 +33,10 @@ func (z *TestMakepkgBuilder) BuildMakepkgCmd(ctx context.Context, dir string, ex assert.Contains(z.test, cmd.String(), z.want) } + if z.GetKeepSrc() { + assert.NotContains(z.test, cmd.String(), "-Cc") + } + if z.wantDir != "" { assert.Equal(z.test, z.wantDir, cmd.Dir) } @@ -46,20 +50,54 @@ func (z *TestMakepkgBuilder) Show(cmd *exec.Cmd) error { return z.showError } +func (z *TestMakepkgBuilder) GetKeepSrc() bool { + return z.parentBuilder.KeepSrc +} + // GIVEN 1 package // WHEN downloadPKGBUILDSource is called // THEN 1 call should be made to makepkg with the specified parameters and dir func Test_downloadPKGBUILDSource(t *testing.T) { t.Parallel() - cmdBuilder := &TestMakepkgBuilder{ - parentBuilder: &exe.CmdBuilder{MakepkgConfPath: "/etc/not.conf", MakepkgFlags: []string{"--nocheck"}, MakepkgBin: "makepkg"}, - test: t, - want: "makepkg --nocheck --config /etc/not.conf --verifysource --skippgpcheck -Ccf", - wantDir: "/tmp/yay-bin", + + type testCase struct { + desc string + keepSrc bool + want string + } + + testCases := []testCase{ + { + desc: "keepsrc", + keepSrc: true, + want: "makepkg --nocheck --config /etc/not.conf --verifysource --skippgpcheck -f", + }, + { + desc: "nokeepsrc", + keepSrc: false, + want: "makepkg --nocheck --config /etc/not.conf --verifysource --skippgpcheck -f -Cc", + }, + } + + for _, tc := range testCases { + tc := tc + t.Run(tc.desc, func(td *testing.T) { + cmdBuilder := &TestMakepkgBuilder{ + parentBuilder: &exe.CmdBuilder{ + MakepkgConfPath: "/etc/not.conf", + MakepkgFlags: []string{"--nocheck"}, + MakepkgBin: "makepkg", + KeepSrc: tc.keepSrc, + }, + test: t, + want: tc.want, + wantDir: "/tmp/yay-bin", + } + err := downloadPKGBUILDSource(context.Background(), cmdBuilder, filepath.Join("/tmp", "yay-bin"), false) + assert.NoError(t, err) + assert.Equal(t, 1, int(cmdBuilder.passes)) + }) } - err := downloadPKGBUILDSource(context.Background(), cmdBuilder, filepath.Join("/tmp", "yay-bin"), false) - assert.NoError(t, err) - assert.Equal(t, 1, int(cmdBuilder.passes)) } // GIVEN 1 package @@ -70,7 +108,7 @@ func Test_downloadPKGBUILDSourceError(t *testing.T) { cmdBuilder := &TestMakepkgBuilder{ parentBuilder: &exe.CmdBuilder{MakepkgConfPath: "/etc/not.conf", MakepkgFlags: []string{"--nocheck"}, MakepkgBin: "makepkg"}, test: t, - want: "makepkg --nocheck --config /etc/not.conf --verifysource --skippgpcheck -Ccf", + want: "makepkg --nocheck --config /etc/not.conf --verifysource --skippgpcheck -f -Cc", wantDir: "/tmp/yay-bin", showError: &exec.ExitError{}, } diff --git a/sync_test.go b/sync_test.go index 973b16e4..488176c5 100644 --- a/sync_test.go +++ b/sync_test.go @@ -552,11 +552,11 @@ pkgname = python-vosk } wantShow := []string{ "pacman -S -y --config /etc/pacman.conf --", - "makepkg --verifysource --skippgpcheck -Ccf", "makepkg --nobuild -fC --ignorearch", + "makepkg --verifysource --skippgpcheck -f -Cc", "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/vosk-api-0.3.45-1-x86_64.pkg.tar.zst", - "makepkg --nobuild -fC --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", - "makepkg --nobuild -fC --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", + "makepkg --nobuild -f -C --ignorearch", "makepkg -c --nobuild --noextract --ignorearch", "pacman -U --config /etc/pacman.conf -- /testdir/vosk-api-0.3.45-1-x86_64.pkg.tar.zst /testdir/python-vosk-0.3.45-1-x86_64.pkg.tar.zst", "pacman -D -q --asdeps --config /etc/pacman.conf -- vosk-api", "pacman -D -q --asexplicit --config /etc/pacman.conf -- python-vosk",