From 06d085a2a675faf5bf619abd156ad9ba198b306e Mon Sep 17 00:00:00 2001 From: knqyf263 Date: Thu, 16 May 2024 08:24:20 +0400 Subject: [PATCH] feat: check if the same version installed Signed-off-by: knqyf263 --- pkg/plugin/index.go | 1 + pkg/plugin/manager.go | 26 ++++-- pkg/plugin/manager_test.go | 59 +++++++----- pkg/plugin/manager_unix_test.go | 88 ++++++++++++++---- pkg/plugin/testdata/plugin/index.yaml | 2 +- .../08/6aefb548a1150b765d1e163a5e542fc80bd660 | Bin 0 -> 147 bytes .../0a/e1413e3807e024dbc7de4129d12bdcae7dea61 | 3 + .../2e/cea228bf881042eb74d3b691c5c6abfb2f7ee4 | Bin 91 -> 0 bytes .../3b/147ae5ffafba7c1d833b4f4bc8ac6a22a8c9bf | Bin 343 -> 0 bytes .../92/9b4718db99b64a38b4e8c3ec8e673976821c08 | Bin 0 -> 344 bytes .../96/e190ae5bcaa3900e568608faf00f16c3ff2714 | 2 - .../a0/82cf7b16998b8f048e7d2bf8207d9525688a9f | Bin 0 -> 90 bytes .../b0/b5089c438d32daafa5a10acb7836280f31fd1b | Bin 165 -> 0 bytes .../b8/fad1dc57e9b544da159fd2da39f82d4dcce34a | Bin 165 -> 0 bytes .../d7/8abde66b1d35bdac65402f0e2cddf3a96cd377 | Bin 0 -> 380 bytes .../dc/135ebfc7f680300c981029184a492bbdfa6db3 | Bin 0 -> 91 bytes .../dd/c882ca64495a0498b3303be6a4ae58213f0485 | Bin 91 -> 0 bytes .../testdata/test_plugin.git/packed-refs | 6 +- .../test_plugin.git/refs/heads/.gitkeep | 0 .../test_plugin.git/refs/tags/.gitkeep | 0 pkg/plugin/testdata/test_plugin/plugin.yaml | 2 +- 21 files changed, 130 insertions(+), 59 deletions(-) create mode 100644 pkg/plugin/testdata/test_plugin.git/objects/08/6aefb548a1150b765d1e163a5e542fc80bd660 create mode 100644 pkg/plugin/testdata/test_plugin.git/objects/0a/e1413e3807e024dbc7de4129d12bdcae7dea61 delete mode 100644 pkg/plugin/testdata/test_plugin.git/objects/2e/cea228bf881042eb74d3b691c5c6abfb2f7ee4 delete mode 100644 pkg/plugin/testdata/test_plugin.git/objects/3b/147ae5ffafba7c1d833b4f4bc8ac6a22a8c9bf create mode 100644 pkg/plugin/testdata/test_plugin.git/objects/92/9b4718db99b64a38b4e8c3ec8e673976821c08 delete mode 100644 pkg/plugin/testdata/test_plugin.git/objects/96/e190ae5bcaa3900e568608faf00f16c3ff2714 create mode 100644 pkg/plugin/testdata/test_plugin.git/objects/a0/82cf7b16998b8f048e7d2bf8207d9525688a9f delete mode 100644 pkg/plugin/testdata/test_plugin.git/objects/b0/b5089c438d32daafa5a10acb7836280f31fd1b delete mode 100644 pkg/plugin/testdata/test_plugin.git/objects/b8/fad1dc57e9b544da159fd2da39f82d4dcce34a create mode 100644 pkg/plugin/testdata/test_plugin.git/objects/d7/8abde66b1d35bdac65402f0e2cddf3a96cd377 create mode 100644 pkg/plugin/testdata/test_plugin.git/objects/dc/135ebfc7f680300c981029184a492bbdfa6db3 delete mode 100644 pkg/plugin/testdata/test_plugin.git/objects/dd/c882ca64495a0498b3303be6a4ae58213f0485 delete mode 100644 pkg/plugin/testdata/test_plugin.git/refs/heads/.gitkeep delete mode 100644 pkg/plugin/testdata/test_plugin.git/refs/tags/.gitkeep diff --git a/pkg/plugin/index.go b/pkg/plugin/index.go index c825c16e67af..980d4ef1e41f 100644 --- a/pkg/plugin/index.go +++ b/pkg/plugin/index.go @@ -24,6 +24,7 @@ type Index struct { Version int `yaml:"version"` Plugins []struct { Name string `yaml:"name"` + Version string `yaml:"version"` Maintainer string `yaml:"maintainer"` Summary string `yaml:"summary"` Repository string `yaml:"repository"` diff --git a/pkg/plugin/manager.go b/pkg/plugin/manager.go index 8f1cd28c80f9..741d245d6b62 100644 --- a/pkg/plugin/manager.go +++ b/pkg/plugin/manager.go @@ -31,14 +31,20 @@ var ( type ManagerOption func(indexer *Manager) func WithWriter(w io.Writer) ManagerOption { - return func(indexer *Manager) { - indexer.w = w + return func(manager *Manager) { + manager.w = w + } +} + +func WithLogger(logger *log.Logger) ManagerOption { + return func(manager *Manager) { + manager.logger = logger } } func WithIndexURL(indexURL string) ManagerOption { - return func(indexer *Manager) { - indexer.indexURL = indexURL + return func(manager *Manager) { + manager.indexURL = indexURL } } @@ -90,11 +96,11 @@ func Search(ctx context.Context, keyword string) error { return defaultManager( // Install installs a plugin func (m *Manager) Install(ctx context.Context, arg string, opts Options) (Plugin, error) { - input := m.parseArg(arg) + input := m.parseArg(ctx, arg) input.name = m.tryIndex(ctx, input.name) // If the plugin is already installed, it skips installing the plugin. - if p, installed := m.isInstalled(ctx, input.name); installed { + if p, installed := m.isInstalled(ctx, input.name, input.version); installed { m.logger.InfoContext(ctx, "The plugin is already installed", log.String("name", p.Name)) return p, nil } @@ -343,14 +349,14 @@ func (m *Manager) loadMetadata(dir string) (Plugin, error) { return plugin, nil } -func (m *Manager) isInstalled(ctx context.Context, url string) (Plugin, bool) { +func (m *Manager) isInstalled(ctx context.Context, url, version string) (Plugin, bool) { installedPlugins, err := m.LoadAll(ctx) if err != nil { return Plugin{}, false } for _, plugin := range installedPlugins { - if plugin.Repository == url { + if plugin.Repository == url && (version == "" || plugin.Version == version) { return plugin, true } } @@ -371,12 +377,12 @@ func (i *Input) String() string { return i.name } -func (m *Manager) parseArg(arg string) Input { +func (m *Manager) parseArg(ctx context.Context, arg string) Input { before, after, found := strings.Cut(arg, "@v") if !found { return Input{name: arg} } else if _, err := semver.Parse(after); err != nil { - m.logger.Debug("Unable to identify the plugin version", log.String("name", arg), log.Err(err)) + m.logger.DebugContext(ctx, "Unable to identify the plugin version", log.String("name", arg), log.Err(err)) return Input{name: arg} } // cf. https://github.com/hashicorp/go-getter/blob/268c11cae8cf0d9374783e06572679796abe9ce9/README.md#git-git diff --git a/pkg/plugin/manager_test.go b/pkg/plugin/manager_test.go index c831f77ed6f8..134d1d160763 100644 --- a/pkg/plugin/manager_test.go +++ b/pkg/plugin/manager_test.go @@ -5,6 +5,7 @@ package plugin_test import ( "bytes" "context" + "fmt" "github.com/aquasecurity/trivy/pkg/clock" ftypes "github.com/aquasecurity/trivy/pkg/fanal/types" v1 "github.com/google/go-containerregistry/pkg/v1" @@ -22,6 +23,34 @@ import ( "github.com/aquasecurity/trivy/pkg/plugin" ) +func setupInstalledPlugin(t *testing.T, homeDir string, p plugin.Plugin) { + pluginDir := filepath.Join(homeDir, ".trivy", "plugins", p.Name) + + // Create the test plugin directory + err := os.MkdirAll(pluginDir, os.ModePerm) + require.NoError(t, err) + + // write the plugin name + pluginMetadata := fmt.Sprintf(`name: "%s" +repository: "%s" +version: "%s" +usage: test +description: test +platforms: + - selector: + os: linux + arch: amd64 + uri: ./test.sh + bin: ./test.sh +installed: + platform: + os: linux + arch: amd64`, p.Name, p.Repository, p.Version) + + err = os.WriteFile(filepath.Join(pluginDir, "plugin.yaml"), []byte(pluginMetadata), os.ModePerm) + require.NoError(t, err) +} + func TestManager_Run(t *testing.T) { if runtime.GOOS == "windows" { // the test.sh script can't be run on windows so skipping @@ -318,38 +347,24 @@ func TestManager_Upgrade(t *testing.T) { t.Skip("Test satisfied adequately by Linux tests") } pluginName := "test_plugin" + pluginVersion := "0.0.5" tempDir := t.TempDir() - pluginDir := filepath.Join(tempDir, ".trivy", "plugins", pluginName) - t.Setenv("XDG_DATA_HOME", tempDir) - - // Create the test plugin directory - err := os.MkdirAll(pluginDir, os.ModePerm) - require.NoError(t, err) - - // write the plugin name - pluginMetadata := `name: "test_plugin" -repository: testdata/test_plugin -version: "0.0.5" -usage: test -description: A simple test plugin -installed: - platform: - os: linux - arch: amd64` - - err = os.WriteFile(filepath.Join(pluginDir, "plugin.yaml"), []byte(pluginMetadata), os.ModePerm) - require.NoError(t, err) + setupInstalledPlugin(t, tempDir, plugin.Plugin{ + Name: pluginName, + Version: pluginVersion, + Repository: "testdata/test_plugin", + }) ctx := context.Background() m := plugin.NewManager() // verify initial version - verifyVersion(t, ctx, m, pluginName, "0.0.5") + verifyVersion(t, ctx, m, pluginName, pluginVersion) // Upgrade the existing plugin - err = m.Upgrade(ctx, nil) + err := m.Upgrade(ctx, nil) require.NoError(t, err) // verify plugin updated diff --git a/pkg/plugin/manager_unix_test.go b/pkg/plugin/manager_unix_test.go index f9f8cfecd008..52f4b0d4e2c3 100644 --- a/pkg/plugin/manager_unix_test.go +++ b/pkg/plugin/manager_unix_test.go @@ -4,19 +4,24 @@ package plugin_test import ( "archive/zip" + "bytes" "context" + "fmt" "net/http" "net/http/httptest" "os" "path/filepath" "testing" + "time" - v1 "github.com/google/go-containerregistry/pkg/v1" + "github.com/google/go-containerregistry/pkg/v1" "github.com/sosedoff/gitkit" // Not work on Windows "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" + "github.com/aquasecurity/trivy/pkg/clock" ftypes "github.com/aquasecurity/trivy/pkg/fanal/types" + "github.com/aquasecurity/trivy/pkg/log" "github.com/aquasecurity/trivy/pkg/plugin" "github.com/aquasecurity/trivy/pkg/utils/fsutils" ) @@ -37,13 +42,20 @@ func setupGitServer() (*httptest.Server, error) { } func TestManager_Install(t *testing.T) { - ts, err := setupGitServer() + gs, err := setupGitServer() require.NoError(t, err) - defer ts.Close() + t.Cleanup(gs.Close) + + ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { + zr := zip.NewWriter(w) + require.NoError(t, zr.AddFS(os.DirFS("testdata/test_plugin"))) + require.NoError(t, zr.Close()) + })) + t.Cleanup(ts.Close) wantPlugin := plugin.Plugin{ Name: "test_plugin", - Repository: "github.com/aquasecurity/trivy-plugin-test", + Repository: "testdata/test_plugin", Version: "0.2.0", Summary: "test", Description: "test", @@ -67,41 +79,75 @@ func TestManager_Install(t *testing.T) { wantPluginWithVersion := wantPlugin wantPluginWithVersion.Version = "0.1.0" + wantLogs := `2021-08-25T12:20:30Z INFO Installing the plugin... src="%s" +2021-08-25T12:20:30Z INFO Plugin successfully installed name="test_plugin" version="%s" +` + tests := []struct { name string pluginName string + installed *plugin.Plugin want plugin.Plugin wantFile string + wantLogs string wantErr string }{ { - name: "http", - want: wantPlugin, - wantFile: ".trivy/plugins/test_plugin/test.sh", + name: "http", + pluginName: ts.URL + "/test_plugin.zip", + want: wantPlugin, + wantFile: ".trivy/plugins/test_plugin/test.sh", + wantLogs: fmt.Sprintf(wantLogs, ts.URL+"/test_plugin.zip", "0.2.0"), }, { name: "local path", pluginName: "testdata/test_plugin", want: wantPlugin, wantFile: ".trivy/plugins/test_plugin/test.sh", + wantLogs: fmt.Sprintf(wantLogs, "testdata/test_plugin", "0.2.0"), }, { name: "git", - pluginName: "git::" + ts.URL + "/test_plugin.git", + pluginName: "git::" + gs.URL + "/test_plugin.git", want: wantPlugin, wantFile: ".trivy/plugins/test_plugin/test.sh", + wantLogs: fmt.Sprintf(wantLogs, "git::"+gs.URL+"/test_plugin.git", "0.2.0"), }, { name: "with version", - pluginName: "git::" + ts.URL + "/test_plugin.git@v0.1.0", + pluginName: "git::" + gs.URL + "/test_plugin.git@v0.1.0", want: wantPluginWithVersion, wantFile: ".trivy/plugins/test_plugin/test.sh", + wantLogs: fmt.Sprintf(wantLogs, "git::"+gs.URL+"/test_plugin.git", "0.1.0"), }, { name: "via index", - pluginName: "test", + pluginName: "test_plugin", want: wantPlugin, wantFile: ".trivy/plugins/test_plugin/test.sh", + wantLogs: fmt.Sprintf(wantLogs, "testdata/test_plugin", "0.2.0"), + }, + { + name: "installed", + pluginName: "test_plugin", + installed: &plugin.Plugin{ + Name: "test_plugin", + Repository: "testdata/test_plugin", + Version: "0.2.0", + }, + want: wantPlugin, + wantLogs: "2021-08-25T12:20:30Z INFO The plugin is already installed name=\"test_plugin\"\n", + }, + { + name: "different version installed", + pluginName: "test_plugin@v0.2.0", + installed: &plugin.Plugin{ + Name: "test_plugin", + Repository: "testdata/test_plugin", + Version: "0.1.0", + }, + want: wantPlugin, + wantLogs: fmt.Sprintf(wantLogs, "testdata/test_plugin", "0.2.0"), }, { name: "plugin not found", @@ -124,17 +170,16 @@ func TestManager_Install(t *testing.T) { // For plugin index fsutils.SetCacheDir("testdata") - if tt.pluginName == "" { - ts := httptest.NewServer(http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) { - zr := zip.NewWriter(w) - require.NoError(t, zr.AddFS(os.DirFS("testdata/test_plugin"))) - require.NoError(t, zr.Close()) - })) - t.Cleanup(ts.Close) - tt.pluginName = ts.URL + "/test_plugin.zip" + if tt.installed != nil { + setupInstalledPlugin(t, dst, *tt.installed) } - got, err := plugin.NewManager().Install(context.Background(), tt.pluginName, plugin.Options{ + var gotLogs bytes.Buffer + logger := log.New(log.NewHandler(&gotLogs, nil)) + + ctx := clock.With(context.Background(), time.Date(2021, 8, 25, 12, 20, 30, 5, time.UTC)) + + got, err := plugin.NewManager(plugin.WithLogger(logger)).Install(ctx, tt.pluginName, plugin.Options{ Platform: ftypes.Platform{ Platform: &v1.Platform{ Architecture: "amd64", @@ -149,7 +194,10 @@ func TestManager_Install(t *testing.T) { assert.NoError(t, err) assert.EqualExportedValues(t, tt.want, got) - assert.FileExists(t, filepath.Join(dst, tt.wantFile)) + if tt.wantFile != "" { + assert.FileExists(t, filepath.Join(dst, tt.wantFile)) + } + assert.Equal(t, tt.wantLogs, gotLogs.String()) }) } } diff --git a/pkg/plugin/testdata/plugin/index.yaml b/pkg/plugin/testdata/plugin/index.yaml index 17fbb1987939..b37b86e176a0 100644 --- a/pkg/plugin/testdata/plugin/index.yaml +++ b/pkg/plugin/testdata/plugin/index.yaml @@ -9,7 +9,7 @@ plugins: maintainer: aquasecurity summary: A bar plugin repository: github.com/aquasecurity/trivy-plugin-bar - - name: test + - name: test_plugin maintainer: aquasecurity summary: A test plugin repository: testdata/test_plugin \ No newline at end of file diff --git a/pkg/plugin/testdata/test_plugin.git/objects/08/6aefb548a1150b765d1e163a5e542fc80bd660 b/pkg/plugin/testdata/test_plugin.git/objects/08/6aefb548a1150b765d1e163a5e542fc80bd660 new file mode 100644 index 0000000000000000000000000000000000000000..e7d696256b86d9c3323ac0740015d918dae20479 GIT binary patch literal 147 zcmV;E0Brww0Zooe4#F@DL|Nw)R`-O05K?m)}bpc2I(oI`pUXp0py9{vdRpd=i8&5in`$3aPP4!^isNtVPhcckT1 zw3u%pIWY=g4?>ofdcUbQK@3>-<@wQ=mdyaV^>Xe`No+v(7qo2Mnz`2htT&%uLTVfd BMbrQQ literal 0 HcmV?d00001 diff --git a/pkg/plugin/testdata/test_plugin.git/objects/0a/e1413e3807e024dbc7de4129d12bdcae7dea61 b/pkg/plugin/testdata/test_plugin.git/objects/0a/e1413e3807e024dbc7de4129d12bdcae7dea61 new file mode 100644 index 000000000000..b16c882bc30f --- /dev/null +++ b/pkg/plugin/testdata/test_plugin.git/objects/0a/e1413e3807e024dbc7de4129d12bdcae7dea61 @@ -0,0 +1,3 @@ +xM�� +�0 ���S��[7a}ɺ� +�#iE�޵(��s�,>-0��!b C!)�����A1�$�$~h� ��� �����AI ��ZI,�\:�r*{,��A�8��'��o�M����hd���^�ݩ� �����[������Bi \ No newline at end of file diff --git a/pkg/plugin/testdata/test_plugin.git/objects/2e/cea228bf881042eb74d3b691c5c6abfb2f7ee4 b/pkg/plugin/testdata/test_plugin.git/objects/2e/cea228bf881042eb74d3b691c5c6abfb2f7ee4 deleted file mode 100644 index 49854ac328a7897c2f95617f3d3106c06323fe54..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 91 zcmV-h0HptT0V^p=O;s>AVK6i>Ff%bxD99;I&&<=SOw7$;*szsjj&rZkt@TS6a-FU) x)8IG!D-Bd;ZfdGfl3HA%SDeA%$!hw*{rS|TCxh9}X~@jyIJ-Hz1^|ja9q?cnEi3>4 diff --git a/pkg/plugin/testdata/test_plugin.git/objects/3b/147ae5ffafba7c1d833b4f4bc8ac6a22a8c9bf b/pkg/plugin/testdata/test_plugin.git/objects/3b/147ae5ffafba7c1d833b4f4bc8ac6a22a8c9bf deleted file mode 100644 index 90ef65cdcbb0f3ea5eb0221c0917783cada503ae..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 343 zcmV-d0jU0X0hN$TZ-X!pgnRa{@I7j3V;~^4RUuHI1S=#EQf`g|&WlnAdH(uBqTYJx zNGr{L((FpZ%c58}P#)lirp_|BTyjm5I8$X=R~V9YZ9xbki%exQ%M?w*BuBEQ0Cs3r zWevAq)g_ly0-t}~n<&_N*XL#N3h@9d14TwUf;}W71X|j@YqEa_#kbh61$^ve+Kxxz zbn3#X=TIYxC-#j47-QO5yhiPOh z0CqGqFWXwNlGKeTH;mN(%nzU}j#9Z0_@LJj-jpS2l}}Df4y7 psQ{$xIxeVt%;uJtJNka@oP_ZL?seGI`l}3ZM19;x;0LO$j3F)Mq{ILK diff --git a/pkg/plugin/testdata/test_plugin.git/objects/92/9b4718db99b64a38b4e8c3ec8e673976821c08 b/pkg/plugin/testdata/test_plugin.git/objects/92/9b4718db99b64a38b4e8c3ec8e673976821c08 new file mode 100644 index 0000000000000000000000000000000000000000..ba6cfbad6f8c1f126ac73ae05fca5053271761db GIT binary patch literal 344 zcmV-e0jK_W0hN$TZ-PJ+g}a_#F?&;;VL&ixo1#!4h4BFt!wyCm1r!nLgI{0Jbk|K! za+7nv4oJIIf`-f{TcYpNR- zg|2Ht*D|Q;`78a-0rWAod{mffuVpuy(>t3HTH3)^?qoi8yu4?8lsR@wKDEr`m+hg> zCh3y#RMAWh;A#C)In)UyZ*h$Vh}{!fC={rVJ`}c*p?BA;Zk>8Pn-SVZGhBq4g{h}Y z0QPjLYn4r;g>g!Pfhs$*twD<0Jhs~?3#!%munJUDR7&Z1sa4fa$*pXH+%j(SIX#Ex q^)&`?vz$+hQ8sE�ϗ��/�5YR���jZ~l���~����c[Q8CB`��{���ף�'��5��n�[g~Qn�7`�3V�&�'����I�K��xJ���ibfQ�ɍn�:6?�ϯ��si���n��fie�� ɷDX�M�wU7���kl\W����x��*d8+"���,�D ����}|����e�Iv����˅�6�-bV(�kPC����L�{Y�|�xm�mbz�y�i���-���ཎ( �U���d���B�� \ No newline at end of file diff --git a/pkg/plugin/testdata/test_plugin.git/objects/a0/82cf7b16998b8f048e7d2bf8207d9525688a9f b/pkg/plugin/testdata/test_plugin.git/objects/a0/82cf7b16998b8f048e7d2bf8207d9525688a9f new file mode 100644 index 0000000000000000000000000000000000000000..981abada0a9bb47d7e259c251f028edc84038ebf GIT binary patch literal 90 zcmV-g0HyzU0V^p=O;s>AVK6i>Ff%bxD99;I&&<=SOw7$;;K+Kv)nlP3cUi2Qm{nYe w{t51D2|#7$rltxdsl_FF#Tg8qtfmj#pHE$SGMMe0hRl49vzw!906R(?UD|Xgng9R* literal 0 HcmV?d00001 diff --git a/pkg/plugin/testdata/test_plugin.git/objects/b0/b5089c438d32daafa5a10acb7836280f31fd1b b/pkg/plugin/testdata/test_plugin.git/objects/b0/b5089c438d32daafa5a10acb7836280f31fd1b deleted file mode 100644 index ff074f718b4f923acd2a68e754fc9aea7f0f5f0c..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 165 zcmV;W09yZe0Y#2W4#F@DL|Nw)R`*S-3bDv#P?`p6DL-PTqPHgrNO(8To*Az$uCOfg zC1`II3~Y(-$(1LDL1ddEA;)|wcp~p*l_vU0zltVnN=7~>&Ul>T*D*G?IBX`2p@z+J zk@Fy^c&}SVUvHL7#>D-kljJl%V)mp2zzAfWHMO*lmAx9VQV5U&Cg8 z<@3O(I44_1U$2IA!kGI>C(+9M49SsT03(pGM%U7&+5{3{(Ujg_KpL&Nfi`6~49pk|h7h8}{`G-G z-F4F=UFqCUI#*Xmb!}UX(8lb;IFu!nh!LgT96Ow|oM~jS(k)1?89{ErZDKo&Nv=UJ zhw?H)PIzv)m=!taxnoJna;s#DmWq{*OS$VXf)!#wK8>etfalA@RTGE8Pk-H4)5@w@ zsIL72v5Rd+DP|PjAqyce(doUh{O_RY&0}TY$5~#m2?dPfEsVpBSS9H(c;f)3ScEBR zwyRl(Y5Zt*dqqXJ|NZM6)hUjW^UTb$j`laY^Xsj7K3yJbt`Ev+=5Gyv!~M61NJN>P z{CtsjNWCTej5KJDzAL-QO)y;xr`1blwx;4H*SN|25Q`+R0i5aKyC~wsJId24wf_`- z!lWguq3HLPcR!APt$neJ&25DXS(c2h} acGpAn8NAmK2>)MY0JIAVK6i>Ff%bxD99;I&&<=SOw7$;;Ckq2XTknJ<@WJ=j+z&> x@2snRl?YU3ZfdGfl3HA%SDeA%$!hw*{rS|TCxh9}X~@jyIJ-Hz1^}iS9{935F311? literal 0 HcmV?d00001 diff --git a/pkg/plugin/testdata/test_plugin.git/objects/dd/c882ca64495a0498b3303be6a4ae58213f0485 b/pkg/plugin/testdata/test_plugin.git/objects/dd/c882ca64495a0498b3303be6a4ae58213f0485 deleted file mode 100644 index 12c485b8eebc9109746f60712543f49600b49890..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 91 zcmV-h0HptT0V^p=O;s>AVK6i>Ff%bxD99;I&&<=SOw7$;*zxP)o$!}iU2ciazjVv; xhpz9L$6i2X=BB0!C8@poQBMNj