You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: designs/extensible-cli-and-scaffolding-plugins.md
+34-15Lines changed: 34 additions & 15 deletions
Display the source diff
Display the rich diff
Original file line number
Diff line number
Diff line change
@@ -1,6 +1,7 @@
1
1
# Extensible CLI and Scaffolding Plugins
2
2
3
3
## Overview
4
+
4
5
I would like for Kubebuilder to become more extensible, such that it could be imported and used as a library in other projects. Specifically, I'm looking for a way to use Kubebuilder's existing CLI and scaffolding for Go projects, but to also be able to augment the Kubebuilder project structure with other custom project types so that I can support the Kubebuilder workflow with non-Go operators (e.g. operator-sdk's Ansible and Helm-based operators).
5
6
6
7
The idea is for Kubebuilder to define one or more plugin interfaces that can be used to drive what the `init`, `create api` and `create webhooks` subcommands do and to add a new `cli` package that other projects can use to integrate out-of-tree plugins with the Kubebuilder CLI in their own projects.
@@ -12,25 +13,29 @@ The idea is for Kubebuilder to define one or more plugin interfaces that can be
Each plugin would minimally be required to implement the `Plugin` interface.
21
25
22
26
```go
23
27
typePlugininterface {
24
28
// Version returns the project version that this plugin implements.
25
29
// For example, Kubebuilder's Go v2 plugin implementation would return 2.
26
-
Version() uint
30
+
Version() string
27
31
// Name returns a name defining the plugin type.
28
32
// For example, Kubebuilder's plugins would return "go".
29
33
Name() string
30
34
}
31
35
```
32
36
33
37
### Optional
38
+
34
39
Next, a plugin could optionally implement further interfaces to declare its support for specific Kubebuilder subcommands. For example:
35
40
*`InitPlugin` - to initialize new projects
36
41
*`CreateAPIPlugin` - to create APIs (and possibly controllers) for existing projects
@@ -39,24 +44,37 @@ Next, a plugin could optionally implement further interfaces to declare its supp
39
44
Each of these interfaces would follow the same pattern (see the `InitPlugin` interface example below).
40
45
41
46
```go
42
-
typeInitPlugininterface {
47
+
typeInitPluginGetterinterface {
43
48
Plugin
49
+
// GetInitPlugin returns the underlying InitPlugin interface.
50
+
GetInitPlugin() InitPlugin
51
+
}
44
52
45
-
// InitDescription returns a description of what this plugin initializes
46
-
// for a new project. It is used to display help.
47
-
InitDescription() string
53
+
typeInitPlugininterface {
54
+
GenericSubcommand
55
+
}
56
+
```
48
57
49
-
// InitHelp returns one or more examples of the command-line usage
50
-
// of this plugin's project initialization support. It is used to display help.
51
-
InitExample() string
58
+
Each specialized plugin interface can leverage a generic subcommand interface, which prevents duplication of methods while permitting type checking and interface flexibility. A plugin context can be used to preserve default help text in case a plugin does not implement its own.
52
59
53
-
// BindInitFlags binds the plugin's init flags to the CLI. This allows each
54
-
// plugin to define its own command line flags for the `kubebuilder init`
55
-
// subcommand.
56
-
BindInitFlags(fs *pflag.FlagSet)
60
+
```go
61
+
typeGenericSubcommandinterface {
62
+
// UpdateContext updates a PluginContext with command-specific help text, like description and examples.
63
+
// Can be a no-op if default help text is desired.
64
+
UpdateContext(*PluginContext)
65
+
// BindFlags binds the plugin's flags to the CLI. This allows each plugin to define its own
66
+
// command line flags for the kubebuilder subcommand.
67
+
BindFlags(fs *pflag.FlagSet)
68
+
// Run runs the subcommand.
69
+
Run() error
70
+
}
57
71
58
-
// Init initializes a project.
59
-
Init() error
72
+
typePluginContextstruct {
73
+
// Description is a description of what this subcommand does. It is used to display help.
74
+
Descriptionstring
75
+
// Examples are one or more examples of the command-line usage
76
+
// of this plugin's project subcommand support. It is used to display help.
77
+
Examplesstring
60
78
}
61
79
```
62
80
@@ -125,6 +143,7 @@ func main() {
125
143
## Comments & Questions
126
144
127
145
### Cobra Commands
146
+
128
147
As discussed earlier as part of [#1148](https://github.com/kubernetes-sigs/kubebuilder/pull/1148), one goal is to eliminate the use of `cobra.Command` in the exported API of Kubebuilder since that is considered an internal implementation detail.
129
148
130
149
However, at some point, projects that make use of this extensibility will likely want to integrate their own subcommands. In this proposal, `cli.WithExtraCommands()`_DOES_ expose `cobra.Command` to allow callers to pass their own subcommands to the CLI.
0 commit comments