Browse code

d/cluster/convert: expose Addr() on plugins

The swarmPlugin type does not implement the Swarm plugin.AddrPlugin
interface because it embeds an interface value which does not include
that method in its method set. (You can type-assert an interface value
to another interface which the concrete type implements, but a struct
embedding an interface value is not itself an interface value.) Wrap the
plugin with a different adapter type which exposes the Addr() method if
the concrete plugin implements it.

Signed-off-by: Cory Snider <csnider@mirantis.com>

Cory Snider authored on 2025/05/13 09:05:00
Showing 1 changed files
... ...
@@ -24,19 +24,37 @@ func (p swarmPlugin) Client() plugin.Client {
24 24
 	return p.CompatPlugin.Client()
25 25
 }
26 26
 
27
+type addrPlugin struct {
28
+	plugingetter.CompatPlugin
29
+	plugingetter.PluginAddr
30
+}
31
+
32
+var _ plugin.AddrPlugin = (*addrPlugin)(nil)
33
+
34
+func (p addrPlugin) Client() plugin.Client {
35
+	return p.CompatPlugin.Client()
36
+}
37
+
38
+func adaptPluginForSwarm(p plugingetter.CompatPlugin) plugin.Plugin {
39
+	if pa, ok := p.(plugingetter.PluginAddr); ok {
40
+		return addrPlugin{p, pa}
41
+	}
42
+	return swarmPlugin{p}
43
+}
44
+
27 45
 func (g pluginGetter) Get(name string, capability string) (plugin.Plugin, error) {
28 46
 	p, err := g.pg.Get(name, capability, plugingetter.Lookup)
29 47
 	if err != nil {
30 48
 		return nil, err
31 49
 	}
32
-	return swarmPlugin{p}, nil
50
+	return adaptPluginForSwarm(p), nil
33 51
 }
34 52
 
35 53
 func (g pluginGetter) GetAllManagedPluginsByCap(capability string) []plugin.Plugin {
36 54
 	pp := g.pg.GetAllManagedPluginsByCap(capability)
37 55
 	ret := make([]plugin.Plugin, len(pp))
38 56
 	for i, p := range pp {
39
-		ret[i] = swarmPlugin{p}
57
+		ret[i] = adaptPluginForSwarm(p)
40 58
 	}
41 59
 	return ret
42 60
 }