Commit d56c180
committed
Merge pull request #55871 from atlassian/unstructured-converter-no-mutation
Automatic merge from submit-queue. If you want to cherry-pick this change to another branch, please follow the instructions <a href="https://github.com/kubernetes/community/blob/master/contributors/devel/cherry-picks.md">here</a>.
Fix potential unexpected object mutation that can lead to data races
**What this PR does / why we need it**:
In #51526 I introduced an optimization - do a deep copy instead of to and from JSON roundtrip to convert anything that implements `runtime.Unstructured`. I just discovered that the method that is used there `UnstructuredContent()` in both `Unstructured` and `UnstructuredList` may mutate the original object.
https://github.com/kubernetes/kubernetes/blob/200875039812d1559555727da74596dc925cfa77/staging/src/k8s.io/apimachinery/pkg/apis/meta/v1/unstructured/unstructured.go#L87-L92
https://github.com/kubernetes/kubernetes/blob/7c10cbc642b47a8f11a74d5178ebbe76a9588cb6/staging/src/k8s.io/apimachinery/pkg/apis/meta/v1/unstructured/unstructured_list.go#L58-L75
This is problematic because previously (before #51526) there was no mutation and because this is unexpected and may lead to data races - it is bad behaviour to mutate original object when you just want a copy of it.
This PR fixes the issue.
Without the fix the tests I've added are failing because when comparison is done original object is not the same:
```
converter_test.go:154: Object changed, diff:
object.Object[items]:
a: []interface {}{}
b: <nil>
converter_test.go:154: Object changed, diff:
object.Object[items]:
a: []interface {}{map[string]interface {}{"kind":"Pod"}}
b: <nil>
```
However the underlying issue is not fixed here - `UnstructuredContent()` is brittle and dangerous. Method name does not imply that it mutates data when you call it. And godoc does not mention that either:
https://github.com/kubernetes/kubernetes/blob/509df603b18d356777176953e5d160b6f3d0bba9/staging/src/k8s.io/apimachinery/pkg/runtime/interfaces.go#L233-L249
Something needs to be done about it IMO.
Also `UnstructuredContent()` implementation in `UnstructuredList` does not implement the behaviour required by godoc in `runtime.Unstructured`.
**Release note**:
```release-note
NONE
```
/kind bug
/sig api-machinery
/assign @sttts
Kubernetes-commit: 2cbb07a4394ef4cfc1666e114674a047023ed1782 files changed
+40
-8
lines changed| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
411 | 411 | | |
412 | 412 | | |
413 | 413 | | |
414 | | - | |
| 414 | + | |
| 415 | + | |
415 | 416 | | |
416 | 417 | | |
417 | 418 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
135 | 135 | | |
136 | 136 | | |
137 | 137 | | |
138 | | - | |
| 138 | + | |
139 | 139 | | |
140 | 140 | | |
141 | 141 | | |
| |||
169 | 169 | | |
170 | 170 | | |
171 | 171 | | |
| 172 | + | |
| 173 | + | |
| 174 | + | |
| 175 | + | |
| 176 | + | |
| 177 | + | |
| 178 | + | |
| 179 | + | |
| 180 | + | |
| 181 | + | |
| 182 | + | |
| 183 | + | |
| 184 | + | |
| 185 | + | |
| 186 | + | |
| 187 | + | |
| 188 | + | |
| 189 | + | |
| 190 | + | |
| 191 | + | |
| 192 | + | |
| 193 | + | |
| 194 | + | |
| 195 | + | |
| 196 | + | |
| 197 | + | |
| 198 | + | |
| 199 | + | |
| 200 | + | |
| 201 | + | |
| 202 | + | |
| 203 | + | |
172 | 204 | | |
173 | 205 | | |
174 | 206 | | |
| |||
260 | 292 | | |
261 | 293 | | |
262 | 294 | | |
263 | | - | |
| 295 | + | |
264 | 296 | | |
265 | 297 | | |
266 | 298 | | |
| |||
465 | 497 | | |
466 | 498 | | |
467 | 499 | | |
468 | | - | |
469 | | - | |
470 | | - | |
471 | | - | |
472 | | - | |
| 500 | + | |
| 501 | + | |
| 502 | + | |
| 503 | + | |
473 | 504 | | |
474 | 505 | | |
475 | 506 | | |
| |||
0 commit comments