-
Notifications
You must be signed in to change notification settings - Fork 1.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
🐛 Fix multiline Ready condition in clusterctl describe for v1beta2 #11781
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change | ||||
---|---|---|---|---|---|---|
|
@@ -294,6 +294,154 @@ func Test_TreePrefix(t *testing.T) { | |||||
} | ||||||
} | ||||||
|
||||||
func Test_V1Beta2TreePrefix(t *testing.T) { | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. might be
Suggested change
(this is what we are testing) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Same again as for the above comments, I copied it from the v1beta1 test |
||||||
tests := []struct { | ||||||
name string | ||||||
objectTree *tree.ObjectTree | ||||||
expectPrefix []string | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Should this be
Suggested change
or expectedTable given that it is more than the simple prefix There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Just copied from the v1beta1 test above :) can change it, but I should change it in both cases then |
||||||
}{ | ||||||
{ | ||||||
name: "Conditions should get the right prefix with multiline message", | ||||||
objectTree: func() *tree.ObjectTree { | ||||||
root := fakeObject("root", | ||||||
withV1Beta2Condition(metav1.Condition{ | ||||||
Type: "Available", | ||||||
Status: metav1.ConditionFalse, | ||||||
Reason: "NotAvailable", | ||||||
Message: "1\n2", | ||||||
}), | ||||||
) | ||||||
obectjTree := tree.NewObjectTree(root, tree.ObjectTreeOptions{ | ||||||
V1Beta2: true, | ||||||
}) | ||||||
|
||||||
o1 := fakeObject("child1", | ||||||
withV1Beta2Condition(falseV1Beta2Condition("Available", "1\n2")), | ||||||
) | ||||||
|
||||||
o2 := fakeObject("child2", | ||||||
withV1Beta2Condition(falseV1Beta2Condition("Available", "1\n2")), | ||||||
) | ||||||
obectjTree.Add(root, o1) | ||||||
obectjTree.Add(root, o2) | ||||||
return obectjTree | ||||||
}(), | ||||||
expectPrefix: []string{ | ||||||
"Object/root", | ||||||
"│ 2", | ||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I'm a little bit confused by seeing only the second line of the message (2) and not the first line (1). There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. It is just like the other/v1beta1 tests, we just check the prefix. We cannot ensure the age, thus we should only verify the prefix here. |
||||||
"├─Object/child1", | ||||||
"│ 2", | ||||||
"└─Object/child2", | ||||||
Comment on lines
+330
to
+334
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Without the fix (where
|
||||||
}, | ||||||
}, | ||||||
{ | ||||||
name: "Conditions should get the right prefix with multiline message and a child", | ||||||
objectTree: func() *tree.ObjectTree { | ||||||
root := fakeObject("root", | ||||||
withV1Beta2Condition(metav1.Condition{ | ||||||
Type: "Available", | ||||||
Status: metav1.ConditionTrue, | ||||||
Reason: "Available", | ||||||
}), | ||||||
) | ||||||
obectjTree := tree.NewObjectTree(root, tree.ObjectTreeOptions{ | ||||||
V1Beta2: true, | ||||||
}) | ||||||
|
||||||
o1 := fakeObject("child1", | ||||||
withV1Beta2Condition(trueV1Beta2Condition()), | ||||||
) | ||||||
|
||||||
o2 := fakeObject("child2", | ||||||
withV1Beta2Condition(falseV1Beta2Condition("Available", "1\n2")), | ||||||
) | ||||||
o2_1 := fakeObject("child2.1") | ||||||
obectjTree.Add(root, o1) | ||||||
obectjTree.Add(root, o2) | ||||||
obectjTree.Add(o2, o2_1) | ||||||
return obectjTree | ||||||
}(), | ||||||
expectPrefix: []string{ | ||||||
"Object/root", | ||||||
"├─Object/child1", | ||||||
"└─Object/child2", | ||||||
" │ 2", | ||||||
" └─Object/child2.1", | ||||||
Comment on lines
+365
to
+369
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Without the fix
|
||||||
}, | ||||||
}, | ||||||
{ | ||||||
name: "Conditions should get the right prefix with childs", | ||||||
objectTree: func() *tree.ObjectTree { | ||||||
root := fakeObject("root", | ||||||
withV1Beta2Condition(metav1.Condition{ | ||||||
Type: "Available", | ||||||
Status: metav1.ConditionTrue, | ||||||
Reason: "Available", | ||||||
}), | ||||||
) | ||||||
obectjTree := tree.NewObjectTree(root, tree.ObjectTreeOptions{ | ||||||
V1Beta2: true, | ||||||
}) | ||||||
|
||||||
o1 := fakeObject("child1", | ||||||
withV1Beta2Condition(trueV1Beta2Condition()), | ||||||
) | ||||||
|
||||||
o2 := fakeObject("child2", | ||||||
withV1Beta2Condition(falseV1Beta2Condition("Available", "1\n2")), | ||||||
) | ||||||
o2_1 := fakeObject("child2.1", | ||||||
withV1Beta2Condition(falseV1Beta2Condition("Available", "1\n2")), | ||||||
) | ||||||
o3 := fakeObject("child3", | ||||||
withV1Beta2Condition(falseV1Beta2Condition("Available", "1\n2")), | ||||||
) | ||||||
o3_1 := fakeObject("child3.1", | ||||||
withV1Beta2Condition(falseV1Beta2Condition("Available", "1\n2")), | ||||||
) | ||||||
obectjTree.Add(root, o1) | ||||||
obectjTree.Add(root, o2) | ||||||
obectjTree.Add(o2, o2_1) | ||||||
obectjTree.Add(root, o3) | ||||||
obectjTree.Add(o3, o3_1) | ||||||
return obectjTree | ||||||
}(), | ||||||
expectPrefix: []string{ | ||||||
"Object/root", | ||||||
"├─Object/child1", | ||||||
"├─Object/child2", | ||||||
"│ │ 2", | ||||||
"│ └─Object/child2.1", | ||||||
"│ 2", | ||||||
"└─Object/child3", | ||||||
" │ 2", | ||||||
" └─Object/child3.1", | ||||||
" 2", | ||||||
Comment on lines
+410
to
+419
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Without the fix
|
||||||
}, | ||||||
}, | ||||||
} | ||||||
for _, tt := range tests { | ||||||
t.Run(tt.name, func(t *testing.T) { | ||||||
g := NewWithT(t) | ||||||
var output bytes.Buffer | ||||||
|
||||||
// Creates the output table | ||||||
tbl := tablewriter.NewWriter(&output) | ||||||
|
||||||
formatTableTreeV1Beta2(tbl) | ||||||
|
||||||
// Add row for the root object, the cluster, and recursively for all the nodes representing the cluster status. | ||||||
addObjectRowV1Beta2("", tbl, tt.objectTree, tt.objectTree.GetRoot()) | ||||||
tbl.Render() | ||||||
|
||||||
// remove empty lines from the output. We need this because v1beta2 adds lines at the beginning and end. | ||||||
outputString := strings.TrimSpace(output.String()) | ||||||
|
||||||
g.Expect(outputString).Should(MatchTable(tt.expectPrefix)) | ||||||
}) | ||||||
} | ||||||
} | ||||||
|
||||||
type objectOption func(object ctrlclient.Object) | ||||||
|
||||||
func fakeObject(name string, options ...objectOption) ctrlclient.Object { | ||||||
|
@@ -331,6 +479,32 @@ func withCondition(c *clusterv1.Condition) func(ctrlclient.Object) { | |||||
} | ||||||
} | ||||||
|
||||||
func withV1Beta2Condition(c metav1.Condition) func(ctrlclient.Object) { | ||||||
return func(m ctrlclient.Object) { | ||||||
cluster := m.(*clusterv1.Cluster) | ||||||
conds := cluster.GetV1Beta2Conditions() | ||||||
conds = append(conds, c) | ||||||
cluster.SetV1Beta2Conditions(conds) | ||||||
} | ||||||
} | ||||||
|
||||||
func trueV1Beta2Condition() metav1.Condition { | ||||||
return metav1.Condition{ | ||||||
Type: "Available", | ||||||
Status: metav1.ConditionTrue, | ||||||
Reason: "Available", | ||||||
} | ||||||
} | ||||||
|
||||||
func falseV1Beta2Condition(t, m string) metav1.Condition { | ||||||
return metav1.Condition{ | ||||||
Type: t, | ||||||
Status: metav1.ConditionFalse, | ||||||
Reason: "Not" + t, | ||||||
Message: m, | ||||||
} | ||||||
} | ||||||
|
||||||
func withDeletionTimestamp(object ctrlclient.Object) { | ||||||
now := metav1.Now() | ||||||
object.SetDeletionTimestamp(&now) | ||||||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm a little bit confused by having a filler at the end of the prefix given that what comes next goes in a different column (and so it automatically goes in the right position, no need to indent)
Same below for the additional spaces
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is a copy from the code for the conditions
cluster-api/cmd/clusterctl/cmd/describe_cluster.go
Lines 438 to 439 in eac73ac
This is necessary as the objects condition might have a multiline message and should be handled exactly as conditions via
--show-conditions
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe it makes sense to reference
addOtherConditionsV1Beta2()
andgetChildPrefix()
in a comment