Skip to content
This repository was archived by the owner on Apr 4, 2023. It is now read-only.

Commit d7293b7

Browse files
Merge pull request #263 from wallrj/262-cassandra-version-status
Automatic merge from submit-queue. Report the actual Cassandra Version * Add a Pilot.Status.Cassandra.Version field. * Add a nodetool.Version method which queries Cassandra version via JMX / Jolokia. * A CassandraVersion type that wraps semver.Version in order to add a special case for versions without a patch number. * Update the Pilot.Status.Cassandra.Version field during calls to Pilot.Sync. * An E2E test for version reporting. Fixes: #262 **Release note**: ```release-note NONE ```
2 parents fb2505c + 09b69d6 commit d7293b7

File tree

19 files changed

+565
-38
lines changed

19 files changed

+565
-38
lines changed

hack/e2e.sh

Lines changed: 15 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,9 @@ source "${SCRIPT_DIR}/libe2e.sh"
3838
: ${CHART_VALUES:="${SCRIPT_DIR}/testdata/values.yaml"}
3939
: ${CHART_VALUES_CASSANDRA:="${SCRIPT_DIR}/testdata/values_cassandra.yaml"}
4040

41+
# Save the cluster logs when the script exits (success or failure)
42+
trap "dump_debug_logs ${PWD}/_artifacts/dump_debug_logs" EXIT
43+
4144
helm delete --purge "${RELEASE_NAME}" || true
4245

4346
function debug_navigator_start() {
@@ -182,7 +185,7 @@ if [[ "test_elasticsearchcluster" = "${TEST_PREFIX}"* ]]; then
182185
ES_TEST_NS="test-elasticsearchcluster-${TEST_ID}"
183186
test_elasticsearchcluster "${ES_TEST_NS}"
184187
if [ "${FAILURE_COUNT}" -gt "0" ]; then
185-
fail_and_exit "${ES_TEST_NS}"
188+
exit 1
186189
fi
187190
kube_delete_namespace_and_wait "${ES_TEST_NS}"
188191
fi
@@ -223,6 +226,16 @@ function test_cassandracluster() {
223226
fail_test "Cassandra pilots did not elect a leader"
224227
fi
225228

229+
if ! retry TIMEOUT=300 \
230+
stdout_equals "${CASS_VERSION}" \
231+
kubectl --namespace "${namespace}" \
232+
get pilots \
233+
--output 'jsonpath={.items[0].status.cassandra.version}'
234+
then
235+
kubectl --namespace "${namespace}" get pilots -o yaml
236+
fail_test "Pilots failed to report the expected version"
237+
fi
238+
226239
# Wait 5 minutes for cassandra to start and listen for CQL queries.
227240
if ! retry TIMEOUT=300 cql_connect \
228241
"${namespace}" \
@@ -358,9 +371,8 @@ if [[ "test_cassandracluster" = "${TEST_PREFIX}"* ]]; then
358371
done
359372

360373
test_cassandracluster "${CASS_TEST_NS}"
361-
dump_debug_logs "${CASS_TEST_NS}"
362374
if [ "${FAILURE_COUNT}" -gt "0" ]; then
363-
fail_and_exit "${CASS_TEST_NS}"
375+
exit 1
364376
fi
365377
kube_delete_namespace_and_wait "${CASS_TEST_NS}"
366378
fi

hack/libe2e.sh

Lines changed: 7 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -168,25 +168,18 @@ function stdout_gt() {
168168
}
169169

170170
function dump_debug_logs() {
171-
local namespace="${1}"
172-
local output_dir="$(pwd)/_artifacts/${namespace}"
173-
171+
local output_dir="${1}"
174172
echo "Dumping cluster state to ${output_dir}"
175173
mkdir -p "${output_dir}"
176174
kubectl cluster-info dump \
177-
--namespaces "${namespace}" \
175+
--all-namespaces \
178176
--output-directory "${output_dir}" || true
179-
}
180-
181-
function fail_and_exit() {
182-
local namespace="${1}"
183-
184-
kubectl api-versions
185-
kubectl get apiservice -o yaml
186177

187-
dump_debug_logs "${namespace}"
188-
189-
exit 1
178+
# Some other resources which aren't included in cluster-info dump
179+
for kind in apiservice cassandraclusters elasticsearchclusters pilots; do
180+
kubectl get "${kind}" --all-namespaces --output json > "${output_dir}/${kind}.json" || true
181+
done
182+
kubectl api-versions > "${output_dir}/api-versions.txt" || true
190183
}
191184

192185
function cql_connect() {
Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
apiVersion: "navigator.jetstack.io/v1alpha1"
22
kind: "CassandraCluster"
33
metadata:
4-
name: ${CASS_NAME}
4+
name: "${CASS_NAME}"
55
spec:
66
version: "${CASS_VERSION}"
77
cqlPort: ${CASS_CQL_PORT}
@@ -17,11 +17,7 @@ spec:
1717
size: "5Gi"
1818
storageClass: "default"
1919
nodeSelector:
20-
image:
21-
repository: "cassandra"
22-
tag: "3"
23-
pullPolicy: "IfNotPresent"
2420
pilotImage:
25-
repository: ${NAVIGATOR_IMAGE_REPOSITORY}/navigator-pilot-cassandra
26-
tag: ${NAVIGATOR_IMAGE_TAG}
27-
pullPolicy: ${NAVIGATOR_IMAGE_PULLPOLICY}
21+
repository: "${NAVIGATOR_IMAGE_REPOSITORY}/navigator-pilot-cassandra"
22+
tag: "${NAVIGATOR_IMAGE_TAG}"
23+
pullPolicy: "${NAVIGATOR_IMAGE_PULLPOLICY}"

pkg/apis/navigator/types.go

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ import (
55
"k8s.io/api/core/v1"
66
"k8s.io/apimachinery/pkg/api/resource"
77
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
8+
9+
"github.com/jetstack/navigator/pkg/cassandra/version"
810
)
911

1012
// In this file we define the outer containing types for the ElasticsearchCluster
@@ -28,7 +30,7 @@ type CassandraClusterSpec struct {
2830
NavigatorClusterConfig
2931

3032
NodePools []CassandraClusterNodePool
31-
Version semver.Version
33+
Version version.Version
3234
Image *ImageSpec
3335
CqlPort int32
3436
}
@@ -196,6 +198,8 @@ type PilotStatus struct {
196198
Conditions []PilotCondition
197199
// Contains status information specific to Elasticsearch Pilots
198200
Elasticsearch *ElasticsearchPilotStatus
201+
// Contains status information specific to Cassandra Pilots
202+
Cassandra *CassandraPilotStatus
199203
}
200204

201205
type ElasticsearchPilotStatus struct {
@@ -206,6 +210,10 @@ type ElasticsearchPilotStatus struct {
206210
Version semver.Version
207211
}
208212

213+
type CassandraPilotStatus struct {
214+
Version *version.Version
215+
}
216+
209217
// PilotCondition contains condition information for a Pilot.
210218
type PilotCondition struct {
211219
// Type of the condition, currently ('Ready').

pkg/apis/navigator/v1alpha1/types.go

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,8 @@ import (
55
"k8s.io/api/core/v1"
66
"k8s.io/apimachinery/pkg/api/resource"
77
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
8+
9+
"github.com/jetstack/navigator/pkg/cassandra/version"
810
)
911

1012
const (
@@ -38,7 +40,7 @@ type CassandraClusterSpec struct {
3840
CqlPort int32 `json:"cqlPort"`
3941

4042
// The version of the database to be used for nodes in the cluster.
41-
Version semver.Version `json:"version"`
43+
Version version.Version `json:"version"`
4244
}
4345

4446
// CassandraClusterNodePool describes a node pool within a CassandraCluster.
@@ -288,6 +290,8 @@ type PilotStatus struct {
288290
Conditions []PilotCondition `json:"conditions"`
289291
// Contains status information specific to Elasticsearch Pilots
290292
Elasticsearch *ElasticsearchPilotStatus `json:"elasticsearch,omitempty"`
293+
// Contains status information specific to Cassandra Pilots
294+
Cassandra *CassandraPilotStatus `json:"cassandra,omitempty"`
291295
}
292296

293297
type ElasticsearchPilotStatus struct {
@@ -299,6 +303,12 @@ type ElasticsearchPilotStatus struct {
299303
Version semver.Version `json:"version,omitempty"`
300304
}
301305

306+
type CassandraPilotStatus struct {
307+
// Version as reported by the Cassandra process.
308+
// `nil` indicates that the version is not yet known / not yet reported.
309+
Version *version.Version `json:"version,omitempty"`
310+
}
311+
302312
// PilotCondition contains condition information for a Pilot.
303313
type PilotCondition struct {
304314
// Type of the condition, currently ('Ready').

pkg/apis/navigator/v1alpha1/zz_generated.conversion.go

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ package v1alpha1
2222

2323
import (
2424
navigator "github.com/jetstack/navigator/pkg/apis/navigator"
25+
version "github.com/jetstack/navigator/pkg/cassandra/version"
2526
v1 "k8s.io/api/core/v1"
2627
conversion "k8s.io/apimachinery/pkg/conversion"
2728
runtime "k8s.io/apimachinery/pkg/runtime"
@@ -48,6 +49,8 @@ func RegisterConversions(scheme *runtime.Scheme) error {
4849
Convert_navigator_CassandraClusterSpec_To_v1alpha1_CassandraClusterSpec,
4950
Convert_v1alpha1_CassandraClusterStatus_To_navigator_CassandraClusterStatus,
5051
Convert_navigator_CassandraClusterStatus_To_v1alpha1_CassandraClusterStatus,
52+
Convert_v1alpha1_CassandraPilotStatus_To_navigator_CassandraPilotStatus,
53+
Convert_navigator_CassandraPilotStatus_To_v1alpha1_CassandraPilotStatus,
5154
Convert_v1alpha1_ElasticsearchCluster_To_navigator_ElasticsearchCluster,
5255
Convert_navigator_ElasticsearchCluster_To_v1alpha1_ElasticsearchCluster,
5356
Convert_v1alpha1_ElasticsearchClusterList_To_navigator_ElasticsearchClusterList,
@@ -265,6 +268,26 @@ func Convert_navigator_CassandraClusterStatus_To_v1alpha1_CassandraClusterStatus
265268
return autoConvert_navigator_CassandraClusterStatus_To_v1alpha1_CassandraClusterStatus(in, out, s)
266269
}
267270

271+
func autoConvert_v1alpha1_CassandraPilotStatus_To_navigator_CassandraPilotStatus(in *CassandraPilotStatus, out *navigator.CassandraPilotStatus, s conversion.Scope) error {
272+
out.Version = (*version.Version)(unsafe.Pointer(in.Version))
273+
return nil
274+
}
275+
276+
// Convert_v1alpha1_CassandraPilotStatus_To_navigator_CassandraPilotStatus is an autogenerated conversion function.
277+
func Convert_v1alpha1_CassandraPilotStatus_To_navigator_CassandraPilotStatus(in *CassandraPilotStatus, out *navigator.CassandraPilotStatus, s conversion.Scope) error {
278+
return autoConvert_v1alpha1_CassandraPilotStatus_To_navigator_CassandraPilotStatus(in, out, s)
279+
}
280+
281+
func autoConvert_navigator_CassandraPilotStatus_To_v1alpha1_CassandraPilotStatus(in *navigator.CassandraPilotStatus, out *CassandraPilotStatus, s conversion.Scope) error {
282+
out.Version = (*version.Version)(unsafe.Pointer(in.Version))
283+
return nil
284+
}
285+
286+
// Convert_navigator_CassandraPilotStatus_To_v1alpha1_CassandraPilotStatus is an autogenerated conversion function.
287+
func Convert_navigator_CassandraPilotStatus_To_v1alpha1_CassandraPilotStatus(in *navigator.CassandraPilotStatus, out *CassandraPilotStatus, s conversion.Scope) error {
288+
return autoConvert_navigator_CassandraPilotStatus_To_v1alpha1_CassandraPilotStatus(in, out, s)
289+
}
290+
268291
func autoConvert_v1alpha1_ElasticsearchCluster_To_navigator_ElasticsearchCluster(in *ElasticsearchCluster, out *navigator.ElasticsearchCluster, s conversion.Scope) error {
269292
out.ObjectMeta = in.ObjectMeta
270293
if err := Convert_v1alpha1_ElasticsearchClusterSpec_To_navigator_ElasticsearchClusterSpec(&in.Spec, &out.Spec, s); err != nil {
@@ -695,6 +718,7 @@ func autoConvert_v1alpha1_PilotStatus_To_navigator_PilotStatus(in *PilotStatus,
695718
out.LastCompletedPhase = navigator.PilotPhase(in.LastCompletedPhase)
696719
out.Conditions = *(*[]navigator.PilotCondition)(unsafe.Pointer(&in.Conditions))
697720
out.Elasticsearch = (*navigator.ElasticsearchPilotStatus)(unsafe.Pointer(in.Elasticsearch))
721+
out.Cassandra = (*navigator.CassandraPilotStatus)(unsafe.Pointer(in.Cassandra))
698722
return nil
699723
}
700724

@@ -707,6 +731,7 @@ func autoConvert_navigator_PilotStatus_To_v1alpha1_PilotStatus(in *navigator.Pil
707731
out.LastCompletedPhase = PilotPhase(in.LastCompletedPhase)
708732
out.Conditions = *(*[]PilotCondition)(unsafe.Pointer(&in.Conditions))
709733
out.Elasticsearch = (*ElasticsearchPilotStatus)(unsafe.Pointer(in.Elasticsearch))
734+
out.Cassandra = (*CassandraPilotStatus)(unsafe.Pointer(in.Cassandra))
710735
return nil
711736
}
712737

pkg/apis/navigator/v1alpha1/zz_generated.deepcopy.go

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ limitations under the License.
2121
package v1alpha1
2222

2323
import (
24+
version "github.com/jetstack/navigator/pkg/cassandra/version"
2425
runtime "k8s.io/apimachinery/pkg/runtime"
2526
)
2627

@@ -184,6 +185,31 @@ func (in *CassandraClusterStatus) DeepCopy() *CassandraClusterStatus {
184185
return out
185186
}
186187

188+
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
189+
func (in *CassandraPilotStatus) DeepCopyInto(out *CassandraPilotStatus) {
190+
*out = *in
191+
if in.Version != nil {
192+
in, out := &in.Version, &out.Version
193+
if *in == nil {
194+
*out = nil
195+
} else {
196+
*out = new(version.Version)
197+
**out = **in
198+
}
199+
}
200+
return
201+
}
202+
203+
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CassandraPilotStatus.
204+
func (in *CassandraPilotStatus) DeepCopy() *CassandraPilotStatus {
205+
if in == nil {
206+
return nil
207+
}
208+
out := new(CassandraPilotStatus)
209+
in.DeepCopyInto(out)
210+
return out
211+
}
212+
187213
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
188214
func (in *ElasticsearchCluster) DeepCopyInto(out *ElasticsearchCluster) {
189215
*out = *in
@@ -602,6 +628,15 @@ func (in *PilotStatus) DeepCopyInto(out *PilotStatus) {
602628
(*in).DeepCopyInto(*out)
603629
}
604630
}
631+
if in.Cassandra != nil {
632+
in, out := &in.Cassandra, &out.Cassandra
633+
if *in == nil {
634+
*out = nil
635+
} else {
636+
*out = new(CassandraPilotStatus)
637+
(*in).DeepCopyInto(*out)
638+
}
639+
}
605640
return
606641
}
607642

pkg/apis/navigator/validation/cassandra.go

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -66,11 +66,5 @@ func ValidateCassandraClusterSpec(spec *navigator.CassandraClusterSpec, fldPath
6666
ValidateImageSpec(spec.Image, fldPath.Child("image"))...,
6767
)
6868
}
69-
if spec.Version.Equal(emptySemver) {
70-
allErrs = append(
71-
allErrs,
72-
field.Required(fldPath.Child("version"), "must be a semver version"),
73-
)
74-
}
7569
return allErrs
7670
}

pkg/apis/navigator/validation/cassandra_test.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import (
77

88
"github.com/jetstack/navigator/pkg/apis/navigator"
99
"github.com/jetstack/navigator/pkg/apis/navigator/validation"
10+
"github.com/jetstack/navigator/pkg/cassandra/version"
1011
)
1112

1213
var (
@@ -16,7 +17,7 @@ var (
1617
Namespace: "bar",
1718
},
1819
Spec: navigator.CassandraClusterSpec{
19-
Version: validSemver,
20+
Version: *version.New("5.6.2"),
2021
Image: &validImageSpec,
2122
NavigatorClusterConfig: validNavigatorClusterConfig,
2223
},

pkg/apis/navigator/zz_generated.deepcopy.go

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ limitations under the License.
2121
package navigator
2222

2323
import (
24+
version "github.com/jetstack/navigator/pkg/cassandra/version"
2425
runtime "k8s.io/apimachinery/pkg/runtime"
2526
)
2627

@@ -184,6 +185,31 @@ func (in *CassandraClusterStatus) DeepCopy() *CassandraClusterStatus {
184185
return out
185186
}
186187

188+
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
189+
func (in *CassandraPilotStatus) DeepCopyInto(out *CassandraPilotStatus) {
190+
*out = *in
191+
if in.Version != nil {
192+
in, out := &in.Version, &out.Version
193+
if *in == nil {
194+
*out = nil
195+
} else {
196+
*out = new(version.Version)
197+
**out = **in
198+
}
199+
}
200+
return
201+
}
202+
203+
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CassandraPilotStatus.
204+
func (in *CassandraPilotStatus) DeepCopy() *CassandraPilotStatus {
205+
if in == nil {
206+
return nil
207+
}
208+
out := new(CassandraPilotStatus)
209+
in.DeepCopyInto(out)
210+
return out
211+
}
212+
187213
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
188214
func (in *ElasticsearchCluster) DeepCopyInto(out *ElasticsearchCluster) {
189215
*out = *in
@@ -602,6 +628,15 @@ func (in *PilotStatus) DeepCopyInto(out *PilotStatus) {
602628
(*in).DeepCopyInto(*out)
603629
}
604630
}
631+
if in.Cassandra != nil {
632+
in, out := &in.Cassandra, &out.Cassandra
633+
if *in == nil {
634+
*out = nil
635+
} else {
636+
*out = new(CassandraPilotStatus)
637+
(*in).DeepCopyInto(*out)
638+
}
639+
}
605640
return
606641
}
607642

0 commit comments

Comments
 (0)