Skip to content

Commit efb5f6d

Browse files
authored
Merge pull request #148 from arangodb/feature/replication-status
Replication shard status in ArangoDeploymentReplication status
2 parents bb9b064 + cdd74f4 commit efb5f6d

File tree

10 files changed

+321
-19
lines changed

10 files changed

+321
-19
lines changed

main.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -160,7 +160,7 @@ func cmdMainRun(cmd *cobra.Command, args []string) {
160160
mux := http.NewServeMux()
161161
mux.HandleFunc("/health", livenessProbe.LivenessHandler)
162162
mux.HandleFunc("/ready/deployment", deploymentProbe.ReadyHandler)
163-
mux.HandleFunc("/ready/deployment-replications", deploymentReplicationProbe.ReadyHandler)
163+
mux.HandleFunc("/ready/deployment-replication", deploymentReplicationProbe.ReadyHandler)
164164
mux.HandleFunc("/ready/storage", storageProbe.ReadyHandler)
165165
mux.Handle("/metrics", prometheus.Handler())
166166
listenAddr := net.JoinHostPort(serverOptions.host, strconv.Itoa(serverOptions.port))
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
//
2+
// DISCLAIMER
3+
//
4+
// Copyright 2018 ArangoDB GmbH, Cologne, Germany
5+
//
6+
// Licensed under the Apache License, Version 2.0 (the "License");
7+
// you may not use this file except in compliance with the License.
8+
// You may obtain a copy of the License at
9+
//
10+
// http://www.apache.org/licenses/LICENSE-2.0
11+
//
12+
// Unless required by applicable law or agreed to in writing, software
13+
// distributed under the License is distributed on an "AS IS" BASIS,
14+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
// See the License for the specific language governing permissions and
16+
// limitations under the License.
17+
//
18+
// Copyright holder is ArangoDB GmbH, Cologne, Germany
19+
//
20+
// Author Ewout Prangsma
21+
//
22+
23+
package v1alpha
24+
25+
// CollectionStatus contains the status of a single collection.
26+
type CollectionStatus struct {
27+
// Name of the collection
28+
Name string `json:"name"`
29+
// Replication status per shard.
30+
// The list is ordered by shard index (0..noShards-1)
31+
Shards []ShardStatus `json:"shards,omitempty"`
32+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
//
2+
// DISCLAIMER
3+
//
4+
// Copyright 2018 ArangoDB GmbH, Cologne, Germany
5+
//
6+
// Licensed under the Apache License, Version 2.0 (the "License");
7+
// you may not use this file except in compliance with the License.
8+
// You may obtain a copy of the License at
9+
//
10+
// http://www.apache.org/licenses/LICENSE-2.0
11+
//
12+
// Unless required by applicable law or agreed to in writing, software
13+
// distributed under the License is distributed on an "AS IS" BASIS,
14+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
// See the License for the specific language governing permissions and
16+
// limitations under the License.
17+
//
18+
// Copyright holder is ArangoDB GmbH, Cologne, Germany
19+
//
20+
// Author Ewout Prangsma
21+
//
22+
23+
package v1alpha
24+
25+
// DatabaseStatus contains the status of a single database.
26+
type DatabaseStatus struct {
27+
// Name of the database
28+
Name string `json:"name"`
29+
// Collections holds the replication status of each collection in the database.
30+
// List is ordered by name of the collection.
31+
Collections []CollectionStatus `json:"collections,omitempty"`
32+
}
Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,30 @@
1+
//
2+
// DISCLAIMER
3+
//
4+
// Copyright 2018 ArangoDB GmbH, Cologne, Germany
5+
//
6+
// Licensed under the Apache License, Version 2.0 (the "License");
7+
// you may not use this file except in compliance with the License.
8+
// You may obtain a copy of the License at
9+
//
10+
// http://www.apache.org/licenses/LICENSE-2.0
11+
//
12+
// Unless required by applicable law or agreed to in writing, software
13+
// distributed under the License is distributed on an "AS IS" BASIS,
14+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
// See the License for the specific language governing permissions and
16+
// limitations under the License.
17+
//
18+
// Copyright holder is ArangoDB GmbH, Cologne, Germany
19+
//
20+
// Author Ewout Prangsma
21+
//
22+
23+
package v1alpha
24+
25+
// EndpointStatus contains the status of either the source or destination endpoint.
26+
type EndpointStatus struct {
27+
// Databases holds the replication status of all databases from the point of view of this endpoint.
28+
// List is ordered by name of the database.
29+
Databases []DatabaseStatus `json:"databases,omitempty"`
30+
}

pkg/apis/replication/v1alpha/replication_phase.go

Lines changed: 0 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -28,9 +28,6 @@ type DeploymentReplicationPhase string
2828
const (
2929
// DeploymentReplicationPhaseNone indicates that the phase is not set yet
3030
DeploymentReplicationPhaseNone DeploymentReplicationPhase = ""
31-
// DeploymentReplicationPhaseRunning indicates that the deployment replication is under control of the
32-
// ArangoDeploymentReplication operator.
33-
DeploymentReplicationPhaseRunning DeploymentReplicationPhase = "Running"
3431
// DeploymentReplicationPhaseFailed indicates that a deployment replication is in a failed state
3532
// from which automatic recovery is impossible. Inspect `Reason` for more info.
3633
DeploymentReplicationPhaseFailed DeploymentReplicationPhase = "Failed"

pkg/apis/replication/v1alpha/replication_status.go

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,10 +26,19 @@ package v1alpha
2626
// an ArangoDeploymentReplication.
2727
type DeploymentReplicationStatus struct {
2828
// Phase holds the current lifetime phase of the deployment replication
29-
Phase DeploymentReplicationPhase `json:"phase"`
29+
Phase DeploymentReplicationPhase `json:"phase,omitempty"`
3030
// Reason contains a human readable reason for reaching the current phase (can be empty)
3131
Reason string `json:"reason,omitempty"` // Reason for current phase
3232

3333
// Conditions specific to the entire deployment replication
3434
Conditions ConditionList `json:"conditions,omitempty"`
35+
36+
// Source contains the detailed status of the source endpoint
37+
Source EndpointStatus `json:"source"`
38+
// Destination contains the detailed status of the destination endpoint
39+
Destination EndpointStatus `json:"destination"`
40+
41+
// CancelFailures records the number of times that the configuration was canceled
42+
// which resulted in an error.
43+
CancelFailures int `json:"cancel-failures,omitempty"`
3544
}
Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
//
2+
// DISCLAIMER
3+
//
4+
// Copyright 2018 ArangoDB GmbH, Cologne, Germany
5+
//
6+
// Licensed under the Apache License, Version 2.0 (the "License");
7+
// you may not use this file except in compliance with the License.
8+
// You may obtain a copy of the License at
9+
//
10+
// http://www.apache.org/licenses/LICENSE-2.0
11+
//
12+
// Unless required by applicable law or agreed to in writing, software
13+
// distributed under the License is distributed on an "AS IS" BASIS,
14+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15+
// See the License for the specific language governing permissions and
16+
// limitations under the License.
17+
//
18+
// Copyright holder is ArangoDB GmbH, Cologne, Germany
19+
//
20+
// Author Ewout Prangsma
21+
//
22+
23+
package v1alpha
24+
25+
// ShardStatus contains the status of a single shard.
26+
type ShardStatus struct {
27+
Status string `json:"status"`
28+
}

pkg/apis/replication/v1alpha/zz_generated.deepcopy.go

Lines changed: 85 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,27 @@ func (in *ArangoDeploymentReplicationList) DeepCopyObject() runtime.Object {
8989
return nil
9090
}
9191

92+
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
93+
func (in *CollectionStatus) DeepCopyInto(out *CollectionStatus) {
94+
*out = *in
95+
if in.Shards != nil {
96+
in, out := &in.Shards, &out.Shards
97+
*out = make([]ShardStatus, len(*in))
98+
copy(*out, *in)
99+
}
100+
return
101+
}
102+
103+
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new CollectionStatus.
104+
func (in *CollectionStatus) DeepCopy() *CollectionStatus {
105+
if in == nil {
106+
return nil
107+
}
108+
out := new(CollectionStatus)
109+
in.DeepCopyInto(out)
110+
return out
111+
}
112+
92113
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
93114
func (in *Condition) DeepCopyInto(out *Condition) {
94115
*out = *in
@@ -107,6 +128,29 @@ func (in *Condition) DeepCopy() *Condition {
107128
return out
108129
}
109130

131+
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
132+
func (in *DatabaseStatus) DeepCopyInto(out *DatabaseStatus) {
133+
*out = *in
134+
if in.Collections != nil {
135+
in, out := &in.Collections, &out.Collections
136+
*out = make([]CollectionStatus, len(*in))
137+
for i := range *in {
138+
(*in)[i].DeepCopyInto(&(*out)[i])
139+
}
140+
}
141+
return
142+
}
143+
144+
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new DatabaseStatus.
145+
func (in *DatabaseStatus) DeepCopy() *DatabaseStatus {
146+
if in == nil {
147+
return nil
148+
}
149+
out := new(DatabaseStatus)
150+
in.DeepCopyInto(out)
151+
return out
152+
}
153+
110154
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
111155
func (in *DeploymentReplicationSpec) DeepCopyInto(out *DeploymentReplicationSpec) {
112156
*out = *in
@@ -135,6 +179,8 @@ func (in *DeploymentReplicationStatus) DeepCopyInto(out *DeploymentReplicationSt
135179
(*in)[i].DeepCopyInto(&(*out)[i])
136180
}
137181
}
182+
in.Source.DeepCopyInto(&out.Source)
183+
in.Destination.DeepCopyInto(&out.Destination)
138184
return
139185
}
140186

@@ -214,6 +260,29 @@ func (in *EndpointSpec) DeepCopy() *EndpointSpec {
214260
return out
215261
}
216262

263+
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
264+
func (in *EndpointStatus) DeepCopyInto(out *EndpointStatus) {
265+
*out = *in
266+
if in.Databases != nil {
267+
in, out := &in.Databases, &out.Databases
268+
*out = make([]DatabaseStatus, len(*in))
269+
for i := range *in {
270+
(*in)[i].DeepCopyInto(&(*out)[i])
271+
}
272+
}
273+
return
274+
}
275+
276+
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new EndpointStatus.
277+
func (in *EndpointStatus) DeepCopy() *EndpointStatus {
278+
if in == nil {
279+
return nil
280+
}
281+
out := new(EndpointStatus)
282+
in.DeepCopyInto(out)
283+
return out
284+
}
285+
217286
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
218287
func (in *EndpointTLSSpec) DeepCopyInto(out *EndpointTLSSpec) {
219288
*out = *in
@@ -238,3 +307,19 @@ func (in *EndpointTLSSpec) DeepCopy() *EndpointTLSSpec {
238307
in.DeepCopyInto(out)
239308
return out
240309
}
310+
311+
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
312+
func (in *ShardStatus) DeepCopyInto(out *ShardStatus) {
313+
*out = *in
314+
return
315+
}
316+
317+
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ShardStatus.
318+
func (in *ShardStatus) DeepCopy() *ShardStatus {
319+
if in == nil {
320+
return nil
321+
}
322+
out := new(ShardStatus)
323+
in.DeepCopyInto(out)
324+
return out
325+
}

pkg/replication/finalizers.go

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,10 @@ import (
3737
"github.com/arangodb/kube-arangodb/pkg/util/k8sutil"
3838
)
3939

40+
const (
41+
maxCancelFailures = 5 // After this amount of failed cancel-synchronization attempts, the operator switch to abort-sychronization.
42+
)
43+
4044
// addFinalizers adds a stop-sync finalizer to the api object when needed.
4145
func (dr *DeploymentReplication) addFinalizers() error {
4246
apiObject := dr.apiObject
@@ -92,7 +96,7 @@ func (dr *DeploymentReplication) inspectFinalizerDeplReplStopSync(ctx context.Co
9296
}
9397

9498
// Inspect deployment deletion state in source
95-
abort := false
99+
abort := dr.status.CancelFailures > maxCancelFailures
96100
depls := dr.deps.CRCli.DatabaseV1alpha().ArangoDeployments(p.GetNamespace())
97101
if name := p.Spec.Source.GetDeploymentName(); name != "" {
98102
depl, err := depls.Get(name, metav1.GetOptions{})
@@ -150,6 +154,10 @@ func (dr *DeploymentReplication) inspectFinalizerDeplReplStopSync(ctx context.Co
150154
_, err = destClient.Master().CancelSynchronization(ctx, req)
151155
if err != nil && !client.IsPreconditionFailed(err) {
152156
log.Warn().Err(err).Bool("abort", abort).Msg("Failed to stop synchronization")
157+
dr.status.CancelFailures++
158+
if err := dr.updateCRStatus(); err != nil {
159+
log.Warn().Err(err).Msg("Failed to update status to reflect cancel-failures increment")
160+
}
153161
return maskAny(err)
154162
}
155163
return nil

0 commit comments

Comments
 (0)