Skip to content

Commit f86d87e

Browse files
committed
WIP
1 parent 2ebb072 commit f86d87e

File tree

1 file changed

+133
-72
lines changed

1 file changed

+133
-72
lines changed

keps/sig-cluster-lifecycle/wgs/20200108-instance-specific-componentconfig.md

Lines changed: 133 additions & 72 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,19 @@ participating-sigs:
99
- sig-architecture
1010
- wg-component-standard
1111
reviewers:
12-
- TBD
12+
- sttts
13+
- stealthybox
14+
- liggitt
15+
- rosti
16+
- neolit123
17+
- obitech
1318
approvers:
14-
- TBD
19+
- sttts
20+
- stealthybox
21+
- liggitt
1522
editor: TBD
1623
creation-date: 2020-01-08
17-
last-updated: 2020-01-10
24+
last-updated: 2020-06-02
1825
status: provisional
1926
---
2027

@@ -89,6 +96,12 @@ some values are required to be unique to each instance. To date, we have held
8996
off migrating these parameters to existing ComponentConfig APIs, because we lack
9097
a decision on how to consistently handle them.
9198

99+
This KEP proposes that components use a separate, instance-specific Kind,
100+
to clearly identify and separate parameters that are instance-specific from
101+
parameters that are sharable. It also proposes some mitigations in the event
102+
that the initial categorization is incorrect, e.g. we discover an
103+
instance-specific use-case for a sharable field.
104+
92105
The primary goal of this KEP is to make and codify a decision, so that we can
93106
move forward with ComponentConfig implementation.
94107

@@ -137,7 +150,7 @@ See also issue [#61647](https://github.com/kubernetes/kubernetes/issues/61647).
137150
### Non-Goals
138151

139152
- Provide a standard way to continue specifying configuration on the
140-
command-line. TODO: maybe?? might be important for some cases... pods w/ templates.
153+
command-line.
141154
- Redesign APIs/refactor the existing set of parameters. This is about providing
142155
a clear migration path for all classes of parameters.
143156
- Eliminate instance-specific config parameters altogether. This is a special
@@ -147,81 +160,45 @@ See also issue [#61647](https://github.com/kubernetes/kubernetes/issues/61647).
147160

148161
## Proposal
149162

150-
This KEP has two major parts. First, a simple solution to cleanly separate
151-
instance-specific parameters from shareable parameters so that the latter may
152-
continue to be shared via a single ConfigMap. Second, provide examples of how
153-
to configure instance-specific parameters in the new model for kubelet and
154-
kube-proxy, which are the two components currently capable of sharing parameters
155-
from the same ConfigMap.
163+
Taking the Kubelet as an example, there are three categories of fields
164+
(identified by @liggitt):
165+
1. clearly instance-specific (e.g. `--node-ip`, `--provider-id`,
166+
`--hostname-override`)
167+
2. possibly instance-specific (e.g. `--bind-address`, `--root-dir`)
168+
3. highly unlikely to be instance-specific (e.g. cloud provider, node lease
169+
duration)
156170

157-
### Separate config object for instance-specific config
171+
Today, the "sharable" configuration Kinds may contain (2) or (3); in Kubelet
172+
we have been careful to keep (1) out of the configuration schema (as mentioned
173+
above).
158174

159-
The proposal is this: Add a new Kind for instance-specific config, and put
160-
instance-specific parameters in that object.
175+
This KEP proposes that components use a separate, instance-specific Kind,
176+
to clearly identify and separate parameters that are instance-specific from
177+
parameters that are sharable. It also proposes that components have a way
178+
to define the same field in both instance-specific and sharable Kinds, and
179+
define a merge such that the instance-specific field overrides the sharable
180+
field. This gives us some flexibility if we miscategorize fields, or discover
181+
an instance-specific use-case for a sharable field.
161182

162-
This is relatively simple and isolates the parameters so that they can be
163-
dealt with separately. ComponentConfig files containing only sharable parameters
164-
can continue to be shared via a single ConfigMap. Files containing only
165-
instance-specific parameters can be provided to components via other means,
166-
such as the node startup scripts or an init container that inserts values from
167-
the Pod's Downward API.
183+
### Separate Kind for instance-specific config
168184

169-
### Why not just keep using flags for instance-specific parameters?
185+
First, add a new instance-specific ComponentConfig Kind in each component's
186+
config API. This gives us a clear structure to separate instance-specific and
187+
sharable fields. This KEP proposes a new flag, `--instance-config`, for this
188+
new Kind.
170189

171-
Flags have various problems, outlined in the [Versioned Component Configuration Files](https://docs.google.com/document/d/1FdaEJUEh091qf5B98HM6_8MS764iXrxxigNIdwHYW9c)
172-
doc.
190+
ComponentConfig files containing only sharable parameters can continue to be
191+
shared via a single ConfigMap. Files containing only instance-specific
192+
parameters can be provided to components via other means, such as the node
193+
startup scripts or an init container that inserts values from the Pod's Downward
194+
API.
173195

174-
Leaving some parameters as flags while the rest are exposed via ComponentConfig
175-
results in an inconsistent API surface, and an inconsistent API versioning
176-
policy. Why fix only part of the problem when we can fix the whole thing?
196+
### Case-by-case merge if fields are miscategorized
177197

178-
### Why not just auto-detect?
198+
Second, allow instance-specific configs to override shared config when the same
199+
field is specified in both.
179200

180-
One alternative that has been proposed in the past is to find a way to
181-
auto-detect values of instance-specific parameters and simply eliminate them
182-
from the configuration workflow. This is a great idea in theory, because it
183-
solves the problem by removing work for users, but it may be difficult in
184-
practice. For example, on a machine with multiple network cards, which IP should
185-
the kubelet use?
186-
187-
Implementing the two-object approach does not prevent us from finding ways to
188-
auto-detect instance specific config in the future. It is worth noting that the
189-
_possibility_ of someday being able to auto-detect these has led to some
190-
hesitation to make a firm decision today. We have delayed for too long already,
191-
and a firm decision is needed to move forward.
192-
193-
### Risks and Mitigations
194-
195-
This creates an additional bucket for config parameters. We must be vigilant
196-
that only parameters that are truly instance-specific are added to the
197-
instance-specific Kind. We can provide warnings to developers via comments
198-
and tests to deter adding parameters to the instance-specific Kind that should
199-
instead be in the sharable Kind.
200-
201-
For users deploying Pod templates, this solution can make the template more
202-
verbose. In the future, we can explore more elegant ways of generating files
203-
with instance-specific parameters correctly substituted. This proposal argues
204-
that the extra verbosity is worth the benefit of a consistent, versioned API for
205-
configuring core components.
206-
207-
## Design Details
208-
209-
ComponentConfig APIs are currently defined as a separate API group for each
210-
component, usually containing a single top-level Kind for configuring that
211-
component. The naming convention for the API group is `{component}.config.k8s.io`,
212-
and the convention for the Kind is `{Component}Configuration`. This KEP proposes
213-
that the naming convention for the new Kind be `{Component}InstanceConfiguration`.
214-
215-
The canonical flag for providing a ComponentConfig file to a component is
216-
`--config`. This KEP proposes that the canonical flag for providing an
217-
instance-specific config file be `--instance-config`, and that the
218-
instance-specific object not initially be permitted as part of a yaml stream
219-
in the `--config` file (and vice-versa). This is for the sake of a simple
220-
implementation and can be enabled in the future, if we decide it is useful.
221-
222-
As with sharable ComponentConfig parameters, command line flags for
223-
instance-specific parameters should continue to function and take precedence
224-
over values from the config file so that backwards compatibility is maintained.
201+
Additional implementation details are included in the Design Details section.
225202

226203
### Kube-proxy Example
227204

@@ -305,7 +282,7 @@ spec:
305282
- bash -c
306283
args:
307284
- cat << EOF > /etc/config/kube-proxy-instance.yaml
308-
kind: KubeProxyInstanceConfiguration
285+
kind: InstanceConfiguration
309286
apiVersion: kubeproxy.config.k8s.io/v1alpha1
310287
hostnameOverride: ${NODE_NAME}
311288
EOF
@@ -360,6 +337,90 @@ the values supplied to `--config` when consuming a remote configuration. Thus,
360337
the instance-specific parameters would not interfere with sharable parameters
361338
in this approach.
362339

340+
### Alternative: Define a general merge semantic for ComponentConfig
341+
342+
Prior discussions included the idea to define a general merge option instead,
343+
which would have pushed the field categorization decision to the user by
344+
allowing them to specify arbitrary patches on top of the config (for example,
345+
with repeated invocations of a `--config` flag). This is the most flexible
346+
solution, but also the most open-ended, and provides the least structural
347+
guidance to users.
348+
349+
While this KEP recognizes the utility of components that can merge configuration
350+
and is open to future development in this direction, it proposes that we focus
351+
on a clear, near-term solution for this ComponentConfig use case, rather than
352+
attempt to define and standardize a way of merging or generating config outside
353+
of kube-apiserver, where many competing solutions, such as jsonnet, kustomize,
354+
etc, already exist, and significant debate is likely required. The priority of
355+
this KEP is to unblock ComponentConfig so that components can move to versioned
356+
APIs. Improvements can be made in future API versions.
357+
358+
359+
### Why not just keep using flags for instance-specific parameters?
360+
361+
Flags have various problems, outlined in the
362+
[Versioned Component Configuration Files](https://docs.google.com/document/d/1FdaEJUEh091qf5B98HM6_8MS764iXrxxigNIdwHYW9c)
363+
doc.
364+
365+
Leaving some parameters as flags while the rest are exposed via ComponentConfig
366+
results in an inconsistent API surface, and an inconsistent API versioning
367+
policy. Why fix only part of the problem when we can fix the whole thing?
368+
369+
### Why not just auto-detect?
370+
371+
One alternative that has been proposed in the past is to find a way to
372+
auto-detect values of instance-specific parameters and simply eliminate them
373+
from the configuration workflow. This is a great idea in theory, because it
374+
solves the problem by removing work for users, but it may be difficult in
375+
practice. For example, on a machine with multiple network cards, which IP should
376+
the kubelet use?
377+
378+
Implementing the two-object approach does not prevent us from finding ways to
379+
auto-detect instance specific config in the future. It is worth noting that the
380+
_possibility_ of someday being able to auto-detect these has led to some
381+
hesitation to make a firm decision today. We have delayed for too long already,
382+
and a firm decision is needed to move forward.
383+
384+
### Risks and Mitigations
385+
386+
One risk is that fields get miscategorized. We mitigate this risk by providing a
387+
way to define the field in both places, where instance-specific overrides
388+
sharable, as described in the proposal and below design details.
389+
390+
For users deploying Pod templates, this solution can make the template more
391+
verbose. In the future, we can explore more elegant ways of generating files
392+
with instance-specific parameters correctly substituted. This proposal argues
393+
that the extra verbosity is worth the benefit of a consistent, versioned API for
394+
configuring core components.
395+
396+
## Design Details
397+
398+
TODO:
399+
- which side gets used at runtime?
400+
- new naming convention
401+
- code examples for the merge
402+
- sketch out the proposed case-by-case merge and see if it would actually be
403+
more complicated.
404+
405+
ComponentConfig APIs are currently defined as a separate API group for each
406+
component, usually containing a single top-level Kind for configuring that
407+
component. The naming convention for the API group is `{component}.config.k8s.io`,
408+
and the convention for the Kind is `{Component}Configuration`. This KEP proposes
409+
that the naming convention for the new Kind be `{Component}InstanceConfiguration`.
410+
411+
The canonical flag for providing a ComponentConfig file to a component is
412+
`--config`. This KEP proposes that the canonical flag for providing an
413+
instance-specific config file be `--instance-config`, and that the
414+
instance-specific object not initially be permitted as part of a yaml stream
415+
in the `--config` file (and vice-versa). This is for the sake of a simple
416+
implementation and can be enabled in the future, if we decide it is useful.
417+
418+
As with sharable ComponentConfig parameters, command line flags for
419+
instance-specific parameters should continue to function and take precedence
420+
over values from the config file so that backwards compatibility is maintained.
421+
422+
423+
363424
### Test Plan
364425

365426
ComponentConfig APIs are typically tested similarly to API server APIs, for

0 commit comments

Comments
 (0)