From 1c644325cfbdd9251782615d722a98c1be843ef1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Mon, 22 Jun 2020 11:52:05 +0200 Subject: [PATCH 1/8] chore: Add support for internal plugins --- go.sum | 3 +++ pkg/kn/config/config.go | 2 +- pkg/kn/plugin/manager.go | 40 +++++++++++++++++++++++++++++++++++++--- 3 files changed, 41 insertions(+), 4 deletions(-) diff --git a/go.sum b/go.sum index 90f765ecd5..41691c4aea 100644 --- a/go.sum +++ b/go.sum @@ -360,6 +360,7 @@ github.com/evanphx/json-patch v4.5.0+incompatible/go.mod h1:50XU6AFN0ol/bzJsmQLi github.com/exponent-io/jsonpath v0.0.0-20151013193312-d6023ce2651d/go.mod h1:ZZMPRZwes7CROmyNKgQzC3XPs6L/G2EJLHddWejkmf4= github.com/fatih/camelcase v1.0.0/go.mod h1:yN2Sb0lFhZJUdVvtELVWefmrXpuZESvPmqwoZc+/fpc= github.com/fatih/color v1.7.0/go.mod h1:Zm6kSWBoL9eyXnKyktHP6abPY2pDugNf5KwzbycvMj4= +github.com/fatih/color v1.9.0 h1:8xPHl4/q1VyqGIPif1F+1V3Y3lSmrq01EabUW3CoW5s= github.com/fatih/color v1.9.0/go.mod h1:eQcE1qtQxscV5RaZvpXrrb8Drkc3/DdQ+uUYCNjL+zU= github.com/flynn/go-shlex v0.0.0-20150515145356-3f9db97f8568/go.mod h1:xEzjJPgXI435gkrCt3MPfRiAkVrwSbHsst4LCFVfpJc= github.com/fortytw2/leaktest v1.2.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g= @@ -809,6 +810,7 @@ github.com/mattbaird/jsonpatch v0.0.0-20171005235357-81af80346b1a/go.mod h1:M1qo github.com/mattn/go-colorable v0.0.9/go.mod h1:9vuHe8Xs5qXnSaW/c/ABM9alt+Vo+STaOChaDxuIBZU= github.com/mattn/go-colorable v0.1.1/go.mod h1:FuOcm+DKB9mbwrcAfNl7/TZVBZ6rcnceauSikq3lYCQ= github.com/mattn/go-colorable v0.1.2/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= +github.com/mattn/go-colorable v0.1.4 h1:snbPLB8fVfU9iwbbo30TPtbLRzwWu6aJS6Xh4eaaviA= github.com/mattn/go-colorable v0.1.4/go.mod h1:U0ppj6V5qS13XJ6of8GYAs25YV2eR4EVcfRqFIhoBtE= github.com/mattn/go-colorable v0.1.6/go.mod h1:u6P/XSegPjTcexA+o6vUJrdnUu04hMope9wVRipJSqc= github.com/mattn/go-ieproxy v0.0.0-20190610004146-91bb50d98149/go.mod h1:31jz6HNzdxOmlERGGEc4v/dMssOfmp2p5bT/okiKFFc= @@ -818,6 +820,7 @@ github.com/mattn/go-isatty v0.0.3/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNx github.com/mattn/go-isatty v0.0.4/go.mod h1:M+lRXTBqGeGNdLjl/ufCoiOlB5xdOkqRJdNxMWT7Zi4= github.com/mattn/go-isatty v0.0.5/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= github.com/mattn/go-isatty v0.0.8/go.mod h1:Iq45c/XA43vh69/j3iqttzPXn0bhXyGjM0Hdxcsrc5s= +github.com/mattn/go-isatty v0.0.11 h1:FxPOTFNqGkuDUGi3H/qkUbQO4ZiBa2brKq5r0l8TGeM= github.com/mattn/go-isatty v0.0.11/go.mod h1:PhnuNfih5lzO57/f3n+odYbM4JtupLOxQOAqxQCu2WE= github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU= github.com/mattn/go-runewidth v0.0.2/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU= diff --git a/pkg/kn/config/config.go b/pkg/kn/config/config.go index 48088e25cf..22e1fe3980 100644 --- a/pkg/kn/config/config.go +++ b/pkg/kn/config/config.go @@ -129,7 +129,7 @@ func BootstrapConfig() error { viper.SetConfigFile(GlobalConfig.ConfigFile()) viper.AutomaticEnv() // read in environment variables that match - // Defaults are taken from the parsed flags, which in turn have bootstrapDefaults + // Defaults are taken from the parsed flags, which in turn have bootstrap defaults // TODO: Re-enable when legacy handling for plugin config has been removed // For now default handling is happening directly in the getter of GlobalConfig // viper.SetDefault(keyPluginsDirectory, bootstrapDefaults.pluginsDir) diff --git a/pkg/kn/plugin/manager.go b/pkg/kn/plugin/manager.go index a136c33fc5..b00fc47962 100644 --- a/pkg/kn/plugin/manager.go +++ b/pkg/kn/plugin/manager.go @@ -30,6 +30,9 @@ import ( "github.com/spf13/cobra" ) +// Allow plugins to register to this slice for inlining +var InternalPlugins PluginList + // Interface describing a plugin type Plugin interface { // Get the name of the plugin (the file name without extensions) @@ -99,13 +102,19 @@ func (manager *Manager) FindPlugin(parts []string) (Plugin, error) { return nil, nil } + // Try to find internal plugin fist + plugin := lookupInternalPlugin(parts) + if plugin != nil { + return plugin, nil + } + // Try to find plugin in pluginsDir pluginDir, err := homedir.Expand(manager.pluginsDir) if err != nil { return nil, err } - return findMostSpecificPlugin(pluginDir, parts, manager.lookupInPath) + return findMostSpecificPluginInPath(pluginDir, parts, manager.lookupInPath) } // ListPlugins lists all plugins that can be found in the plugin directory or in the path (if configured) @@ -116,7 +125,8 @@ func (manager *Manager) ListPlugins() (PluginList, error) { // ListPluginsForCommandGroup lists all plugins that can be found in the plugin directory or in the path (if configured), // and which fits to a command group func (manager *Manager) ListPluginsForCommandGroup(commandGroupParts []string) (PluginList, error) { - var plugins []Plugin + // Initialize with list of internal plugins + var plugins = append([]Plugin{}, InternalPlugins...) dirs, err := manager.pluginLookupDirectories() if err != nil { @@ -343,7 +353,7 @@ func stripWindowsExecExtensions(name string) string { // Return the path and the parts building the most specific plugin in the given directory // If lookupInPath is true, then also the OS PATH is checked. // An error returned if any IO operation fails -func findMostSpecificPlugin(dir string, parts []string, lookupInPath bool) (Plugin, error) { +func findMostSpecificPluginInPath(dir string, parts []string, lookupInPath bool) (Plugin, error) { for i := len(parts); i > 0; i-- { // Construct plugin name to lookup @@ -429,3 +439,27 @@ func findInDirOrPath(name string, dir string, lookupInPath bool) (string, error) // Not found return "", nil } + +// lookupInternalPlugin looks up internally registered plugins. Return nil if none is found. +func lookupInternalPlugin(parts []string) Plugin { + for _, plugin := range InternalPlugins { + if equalsSlice(plugin.CommandParts(), parts) { + return plugin + } + } + return nil +} + +// equalsSlice return true if two string slices contain the same elements +func equalsSlice(a, b []string) bool { + if len(a) != len(b) || len(a) == 0 { + return false + } + + for i := range a { + if a[i] != b[i] { + return false + } + } + return true +} From 8213d290490a50d11f24dc5eb5d40aebb4f11458 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Tue, 23 Jun 2020 08:32:39 +0200 Subject: [PATCH 2/8] added test for internal plugin lookup --- pkg/kn/plugin/manager.go | 10 +++++-- pkg/kn/plugin/manager_test.go | 52 +++++++++++++++++++++++++++++++++-- 2 files changed, 57 insertions(+), 5 deletions(-) diff --git a/pkg/kn/plugin/manager.go b/pkg/kn/plugin/manager.go index b00fc47962..455acfca59 100644 --- a/pkg/kn/plugin/manager.go +++ b/pkg/kn/plugin/manager.go @@ -441,10 +441,14 @@ func findInDirOrPath(name string, dir string, lookupInPath bool) (string, error) } // lookupInternalPlugin looks up internally registered plugins. Return nil if none is found. +// Start with longest argument path first to find the most specific match func lookupInternalPlugin(parts []string) Plugin { - for _, plugin := range InternalPlugins { - if equalsSlice(plugin.CommandParts(), parts) { - return plugin + for i := len(parts); i > 0; i-- { + checkParts := parts[0:i] + for _, plugin := range InternalPlugins { + if equalsSlice(plugin.CommandParts(), checkParts) { + return plugin + } } } return nil diff --git a/pkg/kn/plugin/manager_test.go b/pkg/kn/plugin/manager_test.go index 66c319b26d..6a8ec111c7 100644 --- a/pkg/kn/plugin/manager_test.go +++ b/pkg/kn/plugin/manager_test.go @@ -21,6 +21,7 @@ import ( "path/filepath" "regexp" "runtime" + "strings" "testing" "github.com/spf13/cobra" @@ -39,6 +40,18 @@ type testContext struct { pluginManager *Manager } +type testPlugin struct { + parts []string +} + +func (t testPlugin) Name() string { return strings.Join(t.parts, " ") } +func (t testPlugin) Execute(args []string) error { return nil} +func (t testPlugin) Description() (string, error) { return "desc: " + t.Name(), nil } +func (t testPlugin) CommandParts() []string { return t.parts } +func (t testPlugin) Path() string { return "" } + +var _ Plugin = testPlugin{} + func TestEmptyFind(t *testing.T) { ctx := setup(t) defer cleanup(t, ctx) @@ -65,7 +78,7 @@ func TestLookupInPluginsDir(t *testing.T) { assert.Equal(t, out, "OK \n") } -func TestLookupWithNotFoundResult(t *testing.T) { +func TestFindWithNotFoundResult(t *testing.T) { ctx := setup(t) defer cleanup(t, ctx) @@ -74,7 +87,7 @@ func TestLookupWithNotFoundResult(t *testing.T) { assert.NilError(t, err, "no error expected") } -func TestPluginInPath(t *testing.T) { +func TestFindPluginInPath(t *testing.T) { ctx := setup(t) defer cleanup(t, ctx) @@ -90,6 +103,9 @@ func TestPluginInPath(t *testing.T) { plugin, err := ctx.pluginManager.FindPlugin(pluginCommands) assert.NilError(t, err) assert.Assert(t, plugin != nil) + desc, err := plugin.Description() + assert.NilError(t, err) + assert.Assert(t, desc != "") assert.Equal(t, plugin.Path(), filepath.Join(tmpPathDir, "kn-path-test")) assert.DeepEqual(t, plugin.CommandParts(), pluginCommands) @@ -100,6 +116,38 @@ func TestPluginInPath(t *testing.T) { assert.Assert(t, plugin == nil) } +func TestFindPluginInternally(t *testing.T) { + ctx := setup(t) + defer cleanup(t, ctx) + + // Initialize registered plugins + plugins := PluginList{ + testPlugin{[]string{"a", "b"}}, + testPlugin{[]string{"a"}}, + } + oldPlugins := InternalPlugins + defer func() { + InternalPlugins = oldPlugins + }() + InternalPlugins = plugins + + data := []struct { + parts []string + name string + } { + { []string{ "a", "b"}, "a b" }, + { []string{ "a"}, "a" }, + { []string{ "a", "c"}, "a" }, + } + for _, d := range data { + plugin, err := ctx.pluginManager.FindPlugin(d.parts) + assert.NilError(t, err) + assert.Assert(t, plugin != nil) + assert.Equal(t, plugin.Name(), d.name) + assert.DeepEqual(t, plugin.CommandParts(), strings.Split(d.name, " ")) + } +} + func TestPluginExecute(t *testing.T) { ctx := setup(t) defer cleanup(t, ctx) From 3c2f887387f8b0c18613ab4d558044569cbd25bf Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Tue, 23 Jun 2020 08:33:37 +0200 Subject: [PATCH 3/8] add changelog entry --- CHANGELOG.adoc | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG.adoc b/CHANGELOG.adoc index 1e77fb0787..2c50157649 100644 --- a/CHANGELOG.adoc +++ b/CHANGELOG.adoc @@ -73,6 +73,10 @@ | Add sugar controller to E2E tests | https://github.com/knative/client/pull/920[#920] +| 🎁 +| Add support for internal plugins +| https://github.com/knative/client/pull/880[#880] + | 🎁 | Add "url" output format to return service url in service describe | https://github.com/knative/client/pull/916[#916] From a6f63331c38f200e4cb7aca3e68e834d5c72c405 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Tue, 23 Jun 2020 08:57:56 +0200 Subject: [PATCH 4/8] fix formatting --- pkg/kn/plugin/manager_test.go | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/pkg/kn/plugin/manager_test.go b/pkg/kn/plugin/manager_test.go index 6a8ec111c7..2ee79750ca 100644 --- a/pkg/kn/plugin/manager_test.go +++ b/pkg/kn/plugin/manager_test.go @@ -44,11 +44,11 @@ type testPlugin struct { parts []string } -func (t testPlugin) Name() string { return strings.Join(t.parts, " ") } -func (t testPlugin) Execute(args []string) error { return nil} +func (t testPlugin) Name() string { return strings.Join(t.parts, " ") } +func (t testPlugin) Execute(args []string) error { return nil } func (t testPlugin) Description() (string, error) { return "desc: " + t.Name(), nil } -func (t testPlugin) CommandParts() []string { return t.parts } -func (t testPlugin) Path() string { return "" } +func (t testPlugin) CommandParts() []string { return t.parts } +func (t testPlugin) Path() string { return "" } var _ Plugin = testPlugin{} @@ -133,11 +133,11 @@ func TestFindPluginInternally(t *testing.T) { data := []struct { parts []string - name string - } { - { []string{ "a", "b"}, "a b" }, - { []string{ "a"}, "a" }, - { []string{ "a", "c"}, "a" }, + name string + }{ + {[]string{"a", "b"}, "a b"}, + {[]string{"a"}, "a"}, + {[]string{"a", "c"}, "a"}, } for _, d := range data { plugin, err := ctx.pluginManager.FindPlugin(d.parts) From fec6e283499099591a0d494a228d0014a7abed93 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Thu, 16 Jul 2020 11:27:53 +0200 Subject: [PATCH 5/8] update to latest changes on main --- pkg/kn/plugin/manager.go | 40 ++++++++++++++++++++++++++++++---------- 1 file changed, 30 insertions(+), 10 deletions(-) diff --git a/pkg/kn/plugin/manager.go b/pkg/kn/plugin/manager.go index 455acfca59..add852b068 100644 --- a/pkg/kn/plugin/manager.go +++ b/pkg/kn/plugin/manager.go @@ -125,8 +125,9 @@ func (manager *Manager) ListPlugins() (PluginList, error) { // ListPluginsForCommandGroup lists all plugins that can be found in the plugin directory or in the path (if configured), // and which fits to a command group func (manager *Manager) ListPluginsForCommandGroup(commandGroupParts []string) (PluginList, error) { + // Initialize with list of internal plugins - var plugins = append([]Plugin{}, InternalPlugins...) + var plugins = append([]Plugin{}, filterPluginsByCommandGroup(InternalPlugins, commandGroupParts)...) dirs, err := manager.pluginLookupDirectories() if err != nil { @@ -135,6 +136,9 @@ func (manager *Manager) ListPluginsForCommandGroup(commandGroupParts []string) ( // Examine all files in possible plugin directories hasSeen := make(map[string]bool) + for _, pl := range plugins { + hasSeen[pl.Name()] = true + } for _, dir := range dirs { files, err := ioutil.ReadDir(dir) @@ -154,7 +158,7 @@ func (manager *Manager) ListPluginsForCommandGroup(commandGroupParts []string) ( } // Check if plugin matches a command group - if !isPartOfCommandGroup(commandGroupParts, f.Name()) { + if !isPluginFileNamePartOfCommandGroup(commandGroupParts, f.Name()) { continue } @@ -175,18 +179,34 @@ func (manager *Manager) ListPluginsForCommandGroup(commandGroupParts []string) ( return plugins, nil } -func isPartOfCommandGroup(commandGroupParts []string, name string) bool { +func filterPluginsByCommandGroup(plugins PluginList, commandGroupParts []string) PluginList { + ret := PluginList{} + for _, pl := range plugins { + if isPartOfCommandGroup(commandGroupParts, pl.CommandParts()) { + ret = append(ret, pl) + } + } + return ret +} + +func isPartOfCommandGroup(commandGroupParts []string, commandParts []string) bool { + if len(commandParts) != len(commandGroupParts)+1 { + return false + } + for i := range commandGroupParts { + if commandParts[i] != commandGroupParts[i] { + return false + } + } + return true +} + +func isPluginFileNamePartOfCommandGroup(commandGroupParts []string, pluginFileName string) bool { if commandGroupParts == nil { return true } - commandParts := extractPluginCommandFromFileName(name) - - // commandParts must be one more element then the parts of the command group - // it belongs to. E.g. for the command "service", "log" (2 elements) the containing - // group only has one element ("service"). This condition is here for - // shortcut and ensure that we don't run in an out-of-bound array error - // in the loop below. + commandParts := extractPluginCommandFromFileName(pluginFileName) if len(commandParts) != len(commandGroupParts)+1 { return false } From 8a3522c5527168989c054c6b459c6e8e36c27504 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Mon, 24 Aug 2020 09:41:16 +0200 Subject: [PATCH 6/8] Added more tests + some docs --- docs/plugins/README.md | 36 +++++++++++++++ pkg/kn/plugin/manager.go | 2 +- pkg/kn/plugin/manager_test.go | 85 ++++++++++++++++++++++++++++------- 3 files changed, 106 insertions(+), 17 deletions(-) diff --git a/docs/plugins/README.md b/docs/plugins/README.md index 4f0d1ab4a2..ccdcfd0d12 100644 --- a/docs/plugins/README.md +++ b/docs/plugins/README.md @@ -21,3 +21,39 @@ Please refer to the documentation and examples for more information on how to write your own plugins. - [kn plugin](../cmd/kn_plugin.md) - Plugin command group + + +## Plugin Inlining + +It is possible to inline plugins that are written in golang. +The following steps are required: + +* In your plugin project, create a implementation of the `Plugin` interface and add it to the global `plugin.InternalPlugins` slice in your `init()` method, like in this example: + +```go +package plugin + +import ( + "knative.dev/client/pkg/kn/plugin" +) + +func init() { + plugin.InternalPlugins = append(plugin.InternalPlugins, &myPlugin{}) +} +``` + +* In your fork of the kn client, add a file `plugin_register.go` to the root package directory which imports your plugin's implementation package: + +```go +package root + +import ( + _ "github.com/rhuss/myplugin/plugin" +) + +// RegisterInlinePlugins is an empty function which however forces the +// compiler to run all init() methods of the registered imports +func RegisterInlinePlugins() {} +``` + +* Update you `go.mod` file with the new dependency and build your custom distribution of `kn` diff --git a/pkg/kn/plugin/manager.go b/pkg/kn/plugin/manager.go index add852b068..a4f09cf409 100644 --- a/pkg/kn/plugin/manager.go +++ b/pkg/kn/plugin/manager.go @@ -163,7 +163,7 @@ func (manager *Manager) ListPluginsForCommandGroup(commandGroupParts []string) ( } // Ignore all plugins that are shadowed - if _, ok := hasSeen[name]; !ok { + if seen, ok := hasSeen[name]; !ok || !seen { plugins = append(plugins, &plugin{ path: filepath.Join(dir, f.Name()), name: stripWindowsExecExtensions(f.Name()), diff --git a/pkg/kn/plugin/manager_test.go b/pkg/kn/plugin/manager_test.go index 2ee79750ca..db7e22d817 100644 --- a/pkg/kn/plugin/manager_test.go +++ b/pkg/kn/plugin/manager_test.go @@ -44,7 +44,7 @@ type testPlugin struct { parts []string } -func (t testPlugin) Name() string { return strings.Join(t.parts, " ") } +func (t testPlugin) Name() string { return "kn-" + strings.Join(t.parts, "-") } func (t testPlugin) Execute(args []string) error { return nil } func (t testPlugin) Description() (string, error) { return "desc: " + t.Name(), nil } func (t testPlugin) CommandParts() []string { return t.parts } @@ -121,30 +121,23 @@ func TestFindPluginInternally(t *testing.T) { defer cleanup(t, ctx) // Initialize registered plugins - plugins := PluginList{ + defer (prepareInternalPlugins( testPlugin{[]string{"a", "b"}}, - testPlugin{[]string{"a"}}, - } - oldPlugins := InternalPlugins - defer func() { - InternalPlugins = oldPlugins - }() - InternalPlugins = plugins + testPlugin{[]string{"a"}}))() data := []struct { parts []string name string }{ - {[]string{"a", "b"}, "a b"}, - {[]string{"a"}, "a"}, - {[]string{"a", "c"}, "a"}, + {[]string{"a", "b"}, "kn-a-b"}, + {[]string{"a"}, "kn-a"}, + {[]string{"a", "c"}, "kn-a"}, } for _, d := range data { plugin, err := ctx.pluginManager.FindPlugin(d.parts) assert.NilError(t, err) assert.Assert(t, plugin != nil) assert.Equal(t, plugin.Name(), d.name) - assert.DeepEqual(t, plugin.CommandParts(), strings.Split(d.name, " ")) } } @@ -160,20 +153,80 @@ func TestPluginExecute(t *testing.T) { assert.Equal(t, out, "OK arg1 arg2\n") } +func TestPluginMixed(t *testing.T) { + ctx := setup(t) + defer cleanup(t, ctx) + + createTestPlugin(t, "kn-external", ctx) + createTestPlugin(t, "kn-shadow", ctx) + + // Initialize registered plugins + defer (prepareInternalPlugins( + testPlugin{[]string{"internal"}}, + testPlugin{[]string{"shadow"}}, + ))() + + data := []struct { + path []string + name string + isInternal bool + }{ + {[]string{ "external" },"kn-external", false}, + {[]string{ "internal" }, "kn-internal", true}, + {[]string{ "shadow" }, "kn-shadow", true}, + } + for _, d := range data { + plugin, err := ctx.pluginManager.FindPlugin(d.path) + assert.NilError(t, err) + assert.Assert(t, plugin != nil) + assert.Equal(t, plugin.Name(), d.name) + _, ok := plugin.(testPlugin) + assert.Equal(t, d.isInternal, ok) + } +} + +func prepareInternalPlugins(plugins ...Plugin) func() { + oldPlugins := InternalPlugins + InternalPlugins = plugins + return func() { + InternalPlugins = oldPlugins + } +} + func TestPluginListForCommandGroup(t *testing.T) { ctx := setup(t) defer cleanup(t, ctx) - createTestPlugin(t, "kn-service-log_2", ctx) + createTestPlugin(t, "kn-service-external", ctx) + createTestPlugin(t, "kn-foo-bar", ctx) + createTestPlugin(t, "kn-service-shadow", ctx) + + // Internal plugin should be filtered out if not belong to the service group + defer (prepareInternalPlugins( + testPlugin{[]string{"service", "internal"}}, + testPlugin{[]string{"service", "shadow"}}, + testPlugin{[]string{"bla", "blub"}}, + testPlugin{[]string{"bla", "blub", "longer"}}))() pluginList, err := ctx.pluginManager.ListPluginsForCommandGroup([]string{"service"}) assert.NilError(t, err) - assert.Assert(t, pluginList.Len() == 1) - assert.Equal(t, pluginList[0].Name(), "kn-service-log_2") + assert.Assert(t, pluginList.Len() == 3) + assert.Assert(t, containsPluginWithName(pluginList, "kn-service-internal")) + assert.Assert(t, containsPluginWithName(pluginList, "kn-service-external")) + assert.Assert(t, containsPluginWithName(pluginList, "kn-service-shadow")) pluginList, err = ctx.pluginManager.ListPluginsForCommandGroup([]string{}) assert.NilError(t, err) assert.Assert(t, pluginList.Len() == 0) } +func containsPluginWithName(plugins PluginList, name string) bool { + for _, pl := range plugins { + if pl.Name() == name { + return true + } + } + return false +} + func TestPluginHelpMessage(t *testing.T) { ctx := setup(t) defer cleanup(t, ctx) From 157968f42c6a090053f9654293486d667b4c185e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Mon, 24 Aug 2020 09:44:58 +0200 Subject: [PATCH 7/8] formatting fix --- pkg/kn/plugin/manager_test.go | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/pkg/kn/plugin/manager_test.go b/pkg/kn/plugin/manager_test.go index db7e22d817..72e8c43e13 100644 --- a/pkg/kn/plugin/manager_test.go +++ b/pkg/kn/plugin/manager_test.go @@ -157,7 +157,7 @@ func TestPluginMixed(t *testing.T) { ctx := setup(t) defer cleanup(t, ctx) - createTestPlugin(t, "kn-external", ctx) + createTestPlugin(t, "kn-external", ctx) createTestPlugin(t, "kn-shadow", ctx) // Initialize registered plugins @@ -167,13 +167,13 @@ func TestPluginMixed(t *testing.T) { ))() data := []struct { - path []string - name string - isInternal bool + path []string + name string + isInternal bool }{ - {[]string{ "external" },"kn-external", false}, - {[]string{ "internal" }, "kn-internal", true}, - {[]string{ "shadow" }, "kn-shadow", true}, + {[]string{"external"}, "kn-external", false}, + {[]string{"internal"}, "kn-internal", true}, + {[]string{"shadow"}, "kn-shadow", true}, } for _, d := range data { plugin, err := ctx.pluginManager.FindPlugin(d.path) @@ -188,7 +188,7 @@ func TestPluginMixed(t *testing.T) { func prepareInternalPlugins(plugins ...Plugin) func() { oldPlugins := InternalPlugins InternalPlugins = plugins - return func() { + return func() { InternalPlugins = oldPlugins } } From 71c242b4b22261bc1a0d28c5f7050980a2bc4ed9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Roland=20Hu=C3=9F?= Date: Tue, 25 Aug 2020 10:39:27 +0200 Subject: [PATCH 8/8] moved to proper injection label for setting up the broker in integration test --- lib/test/broker.go | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/test/broker.go b/lib/test/broker.go index 8fdd5bd4f2..3784f17678 100644 --- a/lib/test/broker.go +++ b/lib/test/broker.go @@ -24,7 +24,7 @@ import ( // LabelNamespaceForDefaultBroker adds label 'knative-eventing-injection=enabled' to the configured namespace func LabelNamespaceForDefaultBroker(r *KnRunResultCollector) error { - cmd := []string{"label", "namespace", r.KnTest().Kn().Namespace(), v1beta1.DeprecatedInjectionAnnotation + "=enabled"} + cmd := []string{"label", "namespace", r.KnTest().Kn().Namespace(), v1beta1.InjectionAnnotation + "=enabled"} _, err := Kubectl{}.Run(cmd...) if err != nil { @@ -43,7 +43,7 @@ func LabelNamespaceForDefaultBroker(r *KnRunResultCollector) error { // UnlabelNamespaceForDefaultBroker removes label 'knative-eventing-injection=enabled' from the configured namespace func UnlabelNamespaceForDefaultBroker(r *KnRunResultCollector) { - cmd := []string{"label", "namespace", r.KnTest().Kn().Namespace(), v1beta1.DeprecatedInjectionAnnotation + "-"} + cmd := []string{"label", "namespace", r.KnTest().Kn().Namespace(), v1beta1.InjectionAnnotation + "-"} _, err := Kubectl{}.Run(cmd...) if err != nil { r.T().Fatalf("error executing '%s': %s", strings.Join(cmd, " "), err.Error())