mirror of
https://github.com/arangodb/kube-arangodb.git
synced 2024-12-14 11:57:37 +00:00
[Feature] ArangoMember Overrides (#1398)
This commit is contained in:
parent
0aa65c6ec9
commit
5bdd1687cb
24 changed files with 506 additions and 52 deletions
|
@ -18,6 +18,7 @@
|
|||
- (Feature) Add basic metrics for ArangoDeploymentReplication CR
|
||||
- (Bugfix) Use ArangoMember as owner reference for syncmaster secrets instead of Deployment
|
||||
- (Improvement) Remove PodSchedulingFailure condition instead of setting to false, restart pod if it could not be scheduled
|
||||
- (Feature) Add ArangoMember overrides
|
||||
|
||||
## [1.2.32](https://github.com/arangodb/kube-arangodb/tree/1.2.32) (2023-08-07)
|
||||
- (Feature) Backup lifetime - remove Backup once its lifetime has been reached
|
||||
|
|
65
docs/api/ArangoMember.V1.md
Normal file
65
docs/api/ArangoMember.V1.md
Normal file
|
@ -0,0 +1,65 @@
|
|||
# API Reference for ArangoMember V1
|
||||
|
||||
## Spec
|
||||
|
||||
### .spec.deploymentUID: string
|
||||
|
||||
DeploymentUID define Deployment UID.
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_spec.go#L34)
|
||||
|
||||
### .spec.group: int
|
||||
|
||||
Group define Member Groups.
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_spec.go#L29)
|
||||
|
||||
### .spec.id: string
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_spec.go#L31)
|
||||
|
||||
### .spec.overrides.resources: core.ResourceRequirements
|
||||
|
||||
Resources holds resource requests & limits. Overrides template provided on the group level.
|
||||
|
||||
Links:
|
||||
* [Documentation of core.ResourceRequirements](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#resourcerequirements-v1-core)
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_spec_overrides.go#L38)
|
||||
|
||||
### .spec.overrides.volumeClaimTemplate: core.PersistentVolumeClaim
|
||||
|
||||
VolumeClaimTemplate specifies a template for volume claims. Overrides template provided on the group level.
|
||||
|
||||
Links:
|
||||
* [Documentation of core.PersistentVolumeClaim](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#persistentvolumeclaim-v1-core)
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_spec_overrides.go#L33)
|
||||
|
||||
### .spec.template.checksum: string
|
||||
|
||||
Checksum keep the Pod Spec Checksum (with ignored fields).
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_pod_template.go#L60)
|
||||
|
||||
### .spec.template.endpoint: string
|
||||
|
||||
Deprecated: Endpoint is not saved into the template
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_pod_template.go#L63)
|
||||
|
||||
### .spec.template.podSpec: core.PodTemplateSpec
|
||||
|
||||
PodSpec specifies the Pod Spec used for this Member.
|
||||
|
||||
Links:
|
||||
* [Documentation of core.PodTemplateSpec](https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#podtemplatespec-v1-core)
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_pod_template.go#L54)
|
||||
|
||||
### .spec.template.podSpecChecksum: string
|
||||
|
||||
PodSpecChecksum keep the Pod Spec Checksum (without ignored fields).
|
||||
|
||||
[Code Reference](/pkg/apis/deployment/v1/arango_member_pod_template.go#L57)
|
||||
|
1
go.mod
1
go.mod
|
@ -28,6 +28,7 @@ require (
|
|||
github.com/arangodb/go-driver v1.4.1
|
||||
github.com/arangodb/go-driver/v2 v2.0.0-20211021031401-d92dcd5a4c83
|
||||
github.com/arangodb/go-upgrade-rules v0.0.0-20180809110947-031b4774ff21
|
||||
github.com/arangodb/rebalancer v0.1.1
|
||||
github.com/cenkalti/backoff v2.2.1+incompatible
|
||||
github.com/dchest/uniuri v0.0.0-20160212164326-8902c56451e9
|
||||
github.com/gin-gonic/gin v1.9.1
|
||||
|
|
2
go.sum
2
go.sum
|
@ -82,6 +82,8 @@ github.com/arangodb/go-upgrade-rules v0.0.0-20180809110947-031b4774ff21 h1:+W7D5
|
|||
github.com/arangodb/go-upgrade-rules v0.0.0-20180809110947-031b4774ff21/go.mod h1:RkPIG6JJ2pcJUoymc18NxAJGraZd+iAEVnOTDjZey/w=
|
||||
github.com/arangodb/go-velocypack v0.0.0-20200318135517-5af53c29c67e h1:Xg+hGrY2LcQBbxd0ZFdbGSyRKTYMZCfBbw/pMJFOk1g=
|
||||
github.com/arangodb/go-velocypack v0.0.0-20200318135517-5af53c29c67e/go.mod h1:mq7Shfa/CaixoDxiyAAc5jZ6CVBAyPaNQCGS7mkj4Ho=
|
||||
github.com/arangodb/rebalancer v0.1.1 h1:8MikmxlhywKnw/wiDqctD8FFwBZhAAF1E3mIqh8nzCA=
|
||||
github.com/arangodb/rebalancer v0.1.1/go.mod h1:wLvglmYNuoTUYbLQq/UESIMVkINmSX9eZWC5QB9kNyk=
|
||||
github.com/armon/circbuf v0.0.0-20150827004946-bbbad097214e/go.mod h1:3U/XgcO3hCbHZ8TKRvWD2dDTCfh9M9ya+I9JpbB7O8o=
|
||||
github.com/armon/go-metrics v0.0.0-20180917152333-f0300d1749da/go.mod h1:Q73ZrmVTwzkszR9V5SSuryQ31EELlFMUz1kKyl939pY=
|
||||
github.com/armon/go-radix v0.0.0-20180808171621-7fddfc383310/go.mod h1:ufUuZ+zHj4x4TnLV4JWEpy2hxWSpsRywHrMgIH9cCH8=
|
||||
|
|
|
@ -147,6 +147,13 @@ func Test_GenerateAPIDocs(t *testing.T) {
|
|||
},
|
||||
},
|
||||
fmt.Sprintf("%s/pkg/apis/deployment/v1", root))
|
||||
|
||||
generateDocs(t, map[string]map[string]interface{}{
|
||||
"ArangoMember.V1": {
|
||||
"Spec": api.ArangoMember{}.Spec,
|
||||
},
|
||||
},
|
||||
fmt.Sprintf("%s/pkg/apis/deployment/v1", root))
|
||||
}
|
||||
|
||||
func generateDocs(t *testing.T, objects map[string]map[string]interface{}, paths ...string) {
|
||||
|
@ -320,7 +327,7 @@ func iterateOverObjectDirect(t *testing.T, docs map[string]*ast.Field, name stri
|
|||
|
||||
doc, ok := docs[docName]
|
||||
if !ok && !f.Anonymous {
|
||||
require.True(t, ok, docName)
|
||||
require.True(t, ok, docName, f.Name)
|
||||
}
|
||||
|
||||
if !f.Anonymous {
|
||||
|
|
|
@ -48,11 +48,18 @@ func GetArangoMemberPodTemplate(pod *core.PodTemplateSpec, podSpecChecksum strin
|
|||
}
|
||||
|
||||
type ArangoMemberPodTemplate struct {
|
||||
PodSpec *core.PodTemplateSpec `json:"podSpec,omitempty"`
|
||||
PodSpecChecksum string `json:"podSpecChecksum,omitempty"`
|
||||
Checksum string `json:"checksum,omitempty"`
|
||||
// PodSpec specifies the Pod Spec used for this Member.
|
||||
// +doc/type: core.PodTemplateSpec
|
||||
// +doc/link: Documentation of core.PodTemplateSpec|https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#podtemplatespec-v1-core
|
||||
PodSpec *core.PodTemplateSpec `json:"podSpec,omitempty"`
|
||||
|
||||
// deprecated
|
||||
// PodSpecChecksum keep the Pod Spec Checksum (without ignored fields).
|
||||
PodSpecChecksum string `json:"podSpecChecksum,omitempty"`
|
||||
|
||||
// Checksum keep the Pod Spec Checksum (with ignored fields).
|
||||
Checksum string `json:"checksum,omitempty"`
|
||||
|
||||
// Deprecated: Endpoint is not saved into the template
|
||||
Endpoint *string `json:"endpoint,omitempty"`
|
||||
}
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
//
|
||||
// DISCLAIMER
|
||||
//
|
||||
// Copyright 2016-2022 ArangoDB GmbH, Cologne, Germany
|
||||
// Copyright 2016-2023 ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
|
@ -25,9 +25,17 @@ import (
|
|||
)
|
||||
|
||||
type ArangoMemberSpec struct {
|
||||
Group ServerGroup `json:"group,omitempty"`
|
||||
ID string `json:"id,omitempty"`
|
||||
DeploymentUID types.UID `json:"deploymentUID,omitempty"`
|
||||
// Group define Member Groups.
|
||||
Group ServerGroup `json:"group,omitempty"`
|
||||
|
||||
ID string `json:"id,omitempty"`
|
||||
|
||||
// DeploymentUID define Deployment UID.
|
||||
DeploymentUID types.UID `json:"deploymentUID,omitempty"`
|
||||
|
||||
// Overrides define Member Overrides (Override values from ServerGroup).
|
||||
Overrides *ArangoMemberSpecOverrides `json:"overrides,omitempty"`
|
||||
|
||||
// Template keeps template which is gonna be applied on the Pod.
|
||||
Template *ArangoMemberPodTemplate `json:"template,omitempty"`
|
||||
}
|
||||
|
|
125
pkg/apis/deployment/v1/arango_member_spec_overrides.go
Normal file
125
pkg/apis/deployment/v1/arango_member_spec_overrides.go
Normal file
|
@ -0,0 +1,125 @@
|
|||
//
|
||||
// DISCLAIMER
|
||||
//
|
||||
// Copyright 2023 ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
// Copyright holder is ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
|
||||
package v1
|
||||
|
||||
import (
|
||||
core "k8s.io/api/core/v1"
|
||||
|
||||
"github.com/arangodb/kube-arangodb/pkg/util"
|
||||
)
|
||||
|
||||
type ArangoMemberSpecOverrides struct {
|
||||
// VolumeClaimTemplate specifies a template for volume claims. Overrides template provided on the group level.
|
||||
// +doc/type: core.PersistentVolumeClaim
|
||||
// +doc/link: Documentation of core.PersistentVolumeClaim|https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#persistentvolumeclaim-v1-core
|
||||
VolumeClaimTemplate *core.PersistentVolumeClaim `json:"volumeClaimTemplate,omitempty"`
|
||||
|
||||
// Resources holds resource requests & limits. Overrides template provided on the group level.
|
||||
// +doc/type: core.ResourceRequirements
|
||||
// +doc/link: Documentation of core.ResourceRequirements|https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#resourcerequirements-v1-core
|
||||
Resources core.ResourceRequirements `json:"resources,omitempty"`
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) HasVolumeClaimTemplate(g *ServerGroupSpec) bool {
|
||||
if g != nil {
|
||||
if g.HasVolumeClaimTemplate() {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
if a != nil {
|
||||
return a.VolumeClaimTemplate != nil
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) GetVolumeClaimTemplate(g *ServerGroupSpec) *core.PersistentVolumeClaim {
|
||||
if a != nil {
|
||||
if a.VolumeClaimTemplate != nil {
|
||||
return a.VolumeClaimTemplate.DeepCopy()
|
||||
}
|
||||
}
|
||||
|
||||
if g != nil {
|
||||
if g.VolumeClaimTemplate != nil {
|
||||
return g.VolumeClaimTemplate.DeepCopy()
|
||||
}
|
||||
}
|
||||
|
||||
return &core.PersistentVolumeClaim{}
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) GetResources(g *ServerGroupSpec) core.ResourceRequirements {
|
||||
rl := core.ResourceList{}
|
||||
rr := core.ResourceList{}
|
||||
|
||||
if g != nil {
|
||||
if l := g.Resources.Limits; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rl[k] = v
|
||||
}
|
||||
}
|
||||
if l := g.Resources.Requests; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rr[k] = v
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if a != nil {
|
||||
if l := a.Resources.Limits; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rl[k] = v
|
||||
}
|
||||
}
|
||||
if l := a.Resources.Requests; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rr[k] = v
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ret := core.ResourceRequirements{}
|
||||
|
||||
if len(rl) > 0 {
|
||||
ret.Limits = rl
|
||||
}
|
||||
if len(rr) > 0 {
|
||||
ret.Requests = rr
|
||||
}
|
||||
|
||||
return ret
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) GetStorageClassName(g *ServerGroupSpec) string {
|
||||
if a != nil {
|
||||
if z := a.VolumeClaimTemplate; z != nil {
|
||||
return util.TypeOrDefault[string](z.Spec.StorageClassName)
|
||||
}
|
||||
}
|
||||
|
||||
if g != nil {
|
||||
return g.GetStorageClassName()
|
||||
}
|
||||
|
||||
return ""
|
||||
}
|
27
pkg/apis/deployment/v1/zz_generated.deepcopy.go
generated
27
pkg/apis/deployment/v1/zz_generated.deepcopy.go
generated
|
@ -534,6 +534,11 @@ func (in *ArangoMemberPodTemplate) DeepCopy() *ArangoMemberPodTemplate {
|
|||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *ArangoMemberSpec) DeepCopyInto(out *ArangoMemberSpec) {
|
||||
*out = *in
|
||||
if in.Overrides != nil {
|
||||
in, out := &in.Overrides, &out.Overrides
|
||||
*out = new(ArangoMemberSpecOverrides)
|
||||
(*in).DeepCopyInto(*out)
|
||||
}
|
||||
if in.Template != nil {
|
||||
in, out := &in.Template, &out.Template
|
||||
*out = new(ArangoMemberPodTemplate)
|
||||
|
@ -552,6 +557,28 @@ func (in *ArangoMemberSpec) DeepCopy() *ArangoMemberSpec {
|
|||
return out
|
||||
}
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *ArangoMemberSpecOverrides) DeepCopyInto(out *ArangoMemberSpecOverrides) {
|
||||
*out = *in
|
||||
if in.VolumeClaimTemplate != nil {
|
||||
in, out := &in.VolumeClaimTemplate, &out.VolumeClaimTemplate
|
||||
*out = new(corev1.PersistentVolumeClaim)
|
||||
(*in).DeepCopyInto(*out)
|
||||
}
|
||||
in.Resources.DeepCopyInto(&out.Resources)
|
||||
return
|
||||
}
|
||||
|
||||
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ArangoMemberSpecOverrides.
|
||||
func (in *ArangoMemberSpecOverrides) DeepCopy() *ArangoMemberSpecOverrides {
|
||||
if in == nil {
|
||||
return nil
|
||||
}
|
||||
out := new(ArangoMemberSpecOverrides)
|
||||
in.DeepCopyInto(out)
|
||||
return out
|
||||
}
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *ArangoMemberStatus) DeepCopyInto(out *ArangoMemberStatus) {
|
||||
*out = *in
|
||||
|
|
|
@ -48,11 +48,18 @@ func GetArangoMemberPodTemplate(pod *core.PodTemplateSpec, podSpecChecksum strin
|
|||
}
|
||||
|
||||
type ArangoMemberPodTemplate struct {
|
||||
PodSpec *core.PodTemplateSpec `json:"podSpec,omitempty"`
|
||||
PodSpecChecksum string `json:"podSpecChecksum,omitempty"`
|
||||
Checksum string `json:"checksum,omitempty"`
|
||||
// PodSpec specifies the Pod Spec used for this Member.
|
||||
// +doc/type: core.PodTemplateSpec
|
||||
// +doc/link: Documentation of core.PodTemplateSpec|https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#podtemplatespec-v1-core
|
||||
PodSpec *core.PodTemplateSpec `json:"podSpec,omitempty"`
|
||||
|
||||
// deprecated
|
||||
// PodSpecChecksum keep the Pod Spec Checksum (without ignored fields).
|
||||
PodSpecChecksum string `json:"podSpecChecksum,omitempty"`
|
||||
|
||||
// Checksum keep the Pod Spec Checksum (with ignored fields).
|
||||
Checksum string `json:"checksum,omitempty"`
|
||||
|
||||
// Deprecated: Endpoint is not saved into the template
|
||||
Endpoint *string `json:"endpoint,omitempty"`
|
||||
}
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
//
|
||||
// DISCLAIMER
|
||||
//
|
||||
// Copyright 2016-2022 ArangoDB GmbH, Cologne, Germany
|
||||
// Copyright 2016-2023 ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
|
@ -25,9 +25,17 @@ import (
|
|||
)
|
||||
|
||||
type ArangoMemberSpec struct {
|
||||
Group ServerGroup `json:"group,omitempty"`
|
||||
ID string `json:"id,omitempty"`
|
||||
DeploymentUID types.UID `json:"deploymentUID,omitempty"`
|
||||
// Group define Member Groups.
|
||||
Group ServerGroup `json:"group,omitempty"`
|
||||
|
||||
ID string `json:"id,omitempty"`
|
||||
|
||||
// DeploymentUID define Deployment UID.
|
||||
DeploymentUID types.UID `json:"deploymentUID,omitempty"`
|
||||
|
||||
// Overrides define Member Overrides (Override values from ServerGroup).
|
||||
Overrides *ArangoMemberSpecOverrides `json:"overrides,omitempty"`
|
||||
|
||||
// Template keeps template which is gonna be applied on the Pod.
|
||||
Template *ArangoMemberPodTemplate `json:"template,omitempty"`
|
||||
}
|
||||
|
|
125
pkg/apis/deployment/v2alpha1/arango_member_spec_overrides.go
Normal file
125
pkg/apis/deployment/v2alpha1/arango_member_spec_overrides.go
Normal file
|
@ -0,0 +1,125 @@
|
|||
//
|
||||
// DISCLAIMER
|
||||
//
|
||||
// Copyright 2023 ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
// You may obtain a copy of the License at
|
||||
//
|
||||
// http://www.apache.org/licenses/LICENSE-2.0
|
||||
//
|
||||
// Unless required by applicable law or agreed to in writing, software
|
||||
// distributed under the License is distributed on an "AS IS" BASIS,
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
//
|
||||
// Copyright holder is ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
|
||||
package v2alpha1
|
||||
|
||||
import (
|
||||
core "k8s.io/api/core/v1"
|
||||
|
||||
"github.com/arangodb/kube-arangodb/pkg/util"
|
||||
)
|
||||
|
||||
type ArangoMemberSpecOverrides struct {
|
||||
// VolumeClaimTemplate specifies a template for volume claims. Overrides template provided on the group level.
|
||||
// +doc/type: core.PersistentVolumeClaim
|
||||
// +doc/link: Documentation of core.PersistentVolumeClaim|https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#persistentvolumeclaim-v1-core
|
||||
VolumeClaimTemplate *core.PersistentVolumeClaim `json:"volumeClaimTemplate,omitempty"`
|
||||
|
||||
// Resources holds resource requests & limits. Overrides template provided on the group level.
|
||||
// +doc/type: core.ResourceRequirements
|
||||
// +doc/link: Documentation of core.ResourceRequirements|https://kubernetes.io/docs/reference/generated/kubernetes-api/v1.26/#resourcerequirements-v1-core
|
||||
Resources core.ResourceRequirements `json:"resources,omitempty"`
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) HasVolumeClaimTemplate(g *ServerGroupSpec) bool {
|
||||
if g != nil {
|
||||
if g.HasVolumeClaimTemplate() {
|
||||
return true
|
||||
}
|
||||
}
|
||||
|
||||
if a != nil {
|
||||
return a.VolumeClaimTemplate != nil
|
||||
}
|
||||
|
||||
return false
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) GetVolumeClaimTemplate(g *ServerGroupSpec) *core.PersistentVolumeClaim {
|
||||
if a != nil {
|
||||
if a.VolumeClaimTemplate != nil {
|
||||
return a.VolumeClaimTemplate.DeepCopy()
|
||||
}
|
||||
}
|
||||
|
||||
if g != nil {
|
||||
if g.VolumeClaimTemplate != nil {
|
||||
return g.VolumeClaimTemplate.DeepCopy()
|
||||
}
|
||||
}
|
||||
|
||||
return &core.PersistentVolumeClaim{}
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) GetResources(g *ServerGroupSpec) core.ResourceRequirements {
|
||||
rl := core.ResourceList{}
|
||||
rr := core.ResourceList{}
|
||||
|
||||
if g != nil {
|
||||
if l := g.Resources.Limits; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rl[k] = v
|
||||
}
|
||||
}
|
||||
if l := g.Resources.Requests; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rr[k] = v
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if a != nil {
|
||||
if l := a.Resources.Limits; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rl[k] = v
|
||||
}
|
||||
}
|
||||
if l := a.Resources.Requests; len(l) > 0 {
|
||||
for k, v := range l {
|
||||
rr[k] = v
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ret := core.ResourceRequirements{}
|
||||
|
||||
if len(rl) > 0 {
|
||||
ret.Limits = rl
|
||||
}
|
||||
if len(rr) > 0 {
|
||||
ret.Requests = rr
|
||||
}
|
||||
|
||||
return ret
|
||||
}
|
||||
|
||||
func (a *ArangoMemberSpecOverrides) GetStorageClassName(g *ServerGroupSpec) string {
|
||||
if a != nil {
|
||||
if z := a.VolumeClaimTemplate; z != nil {
|
||||
return util.TypeOrDefault[string](z.Spec.StorageClassName)
|
||||
}
|
||||
}
|
||||
|
||||
if g != nil {
|
||||
return g.GetStorageClassName()
|
||||
}
|
||||
|
||||
return ""
|
||||
}
|
|
@ -534,6 +534,11 @@ func (in *ArangoMemberPodTemplate) DeepCopy() *ArangoMemberPodTemplate {
|
|||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *ArangoMemberSpec) DeepCopyInto(out *ArangoMemberSpec) {
|
||||
*out = *in
|
||||
if in.Overrides != nil {
|
||||
in, out := &in.Overrides, &out.Overrides
|
||||
*out = new(ArangoMemberSpecOverrides)
|
||||
(*in).DeepCopyInto(*out)
|
||||
}
|
||||
if in.Template != nil {
|
||||
in, out := &in.Template, &out.Template
|
||||
*out = new(ArangoMemberPodTemplate)
|
||||
|
@ -552,6 +557,28 @@ func (in *ArangoMemberSpec) DeepCopy() *ArangoMemberSpec {
|
|||
return out
|
||||
}
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *ArangoMemberSpecOverrides) DeepCopyInto(out *ArangoMemberSpecOverrides) {
|
||||
*out = *in
|
||||
if in.VolumeClaimTemplate != nil {
|
||||
in, out := &in.VolumeClaimTemplate, &out.VolumeClaimTemplate
|
||||
*out = new(v1.PersistentVolumeClaim)
|
||||
(*in).DeepCopyInto(*out)
|
||||
}
|
||||
in.Resources.DeepCopyInto(&out.Resources)
|
||||
return
|
||||
}
|
||||
|
||||
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new ArangoMemberSpecOverrides.
|
||||
func (in *ArangoMemberSpecOverrides) DeepCopy() *ArangoMemberSpecOverrides {
|
||||
if in == nil {
|
||||
return nil
|
||||
}
|
||||
out := new(ArangoMemberSpecOverrides)
|
||||
in.DeepCopyInto(out)
|
||||
return out
|
||||
}
|
||||
|
||||
// DeepCopyInto is an autogenerated deepcopy function, copying the receiver, writing into out. in must be non-nil.
|
||||
func (in *ArangoMemberStatus) DeepCopyInto(out *ArangoMemberStatus) {
|
||||
*out = *in
|
||||
|
|
|
@ -118,11 +118,6 @@ func (a *actionArangoMemberUpdatePodSpec) Start(ctx context.Context) (bool, erro
|
|||
return false, err
|
||||
}
|
||||
|
||||
if z := m.Endpoint; z != nil {
|
||||
q := *z
|
||||
template.Endpoint = &q
|
||||
}
|
||||
|
||||
if err := inspector.WithArangoMemberUpdate(ctx, cache, name, func(member *api.ArangoMember) (bool, error) {
|
||||
if !member.Spec.Template.Equals(template) {
|
||||
member.Spec.Template = template.DeepCopy()
|
||||
|
|
|
@ -89,11 +89,13 @@ func (a *actionPVCResize) Start(ctx context.Context) (bool, error) {
|
|||
return true, nil
|
||||
}
|
||||
|
||||
am := cache.ArangoMember().V1().GetSimpleOptional(m.ArangoMemberName(a.actionCtx.GetName(), group))
|
||||
|
||||
var res core.ResourceList
|
||||
if groupSpec.HasVolumeClaimTemplate() {
|
||||
res = groupSpec.GetVolumeClaimTemplate().Spec.Resources.Requests
|
||||
if am.Spec.Overrides.HasVolumeClaimTemplate(&groupSpec) {
|
||||
res = am.Spec.Overrides.GetVolumeClaimTemplate(&groupSpec).Spec.Resources.Requests
|
||||
} else {
|
||||
res = groupSpec.Resources.Requests
|
||||
res = am.Spec.Overrides.GetResources(&groupSpec).Requests
|
||||
}
|
||||
|
||||
if requestedSize, ok := res[core.ResourceStorage]; ok {
|
||||
|
|
|
@ -108,15 +108,17 @@ func (r *Reconciler) isStorageClassChanged(_ context.Context, apiObject k8sutil.
|
|||
return false, "", nil
|
||||
}
|
||||
|
||||
groupSpec := spec.GetServerGroupSpec(group)
|
||||
storageClassName := groupSpec.GetStorageClassName()
|
||||
if storageClassName == "" {
|
||||
// A storage class is not set.
|
||||
cache, ok := context.ACS().ClusterCache(member.ClusterID)
|
||||
if !ok {
|
||||
return false, "", nil
|
||||
}
|
||||
|
||||
cache, ok := context.ACS().ClusterCache(member.ClusterID)
|
||||
if !ok {
|
||||
am := cache.ArangoMember().V1().GetSimpleOptional(member.ArangoMemberName(context.GetName(), group))
|
||||
|
||||
groupSpec := spec.GetServerGroupSpec(group)
|
||||
storageClassName := am.Spec.Overrides.GetStorageClassName(&groupSpec)
|
||||
if storageClassName == "" {
|
||||
// A storage class is not set.
|
||||
return false, "", nil
|
||||
}
|
||||
|
||||
|
@ -184,6 +186,8 @@ func (r *Reconciler) isVolumeSizeChanged(_ context.Context, _ k8sutil.APIObject,
|
|||
return false, "", nil
|
||||
}
|
||||
|
||||
am := cache.ArangoMember().V1().GetSimpleOptional(member.ArangoMemberName(context.GetName(), group))
|
||||
|
||||
pvc, ok := cache.PersistentVolumeClaim().V1().GetSimple(member.PersistentVolumeClaim.GetName())
|
||||
if !ok {
|
||||
r.log.
|
||||
|
@ -195,7 +199,7 @@ func (r *Reconciler) isVolumeSizeChanged(_ context.Context, _ k8sutil.APIObject,
|
|||
}
|
||||
|
||||
groupSpec := spec.GetServerGroupSpec(group)
|
||||
ok, volumeSize, requestedSize := shouldVolumeResize(groupSpec, pvc)
|
||||
ok, volumeSize, requestedSize := shouldVolumeResize(groupSpec, am, pvc)
|
||||
if !ok {
|
||||
return false, "", nil
|
||||
}
|
||||
|
@ -227,13 +231,14 @@ func (r *Reconciler) isVolumeSizeChanged(_ context.Context, _ k8sutil.APIObject,
|
|||
// shouldVolumeResize returns false when a volume should not resize.
|
||||
// Currently, it is only possible to shrink a volume size.
|
||||
// When return true then the actual and required volume size are returned.
|
||||
func shouldVolumeResize(groupSpec api.ServerGroupSpec,
|
||||
func shouldVolumeResize(groupSpec api.ServerGroupSpec, am *api.ArangoMember,
|
||||
pvc *core.PersistentVolumeClaim) (bool, resource.Quantity, resource.Quantity) {
|
||||
var res core.ResourceList
|
||||
if groupSpec.HasVolumeClaimTemplate() {
|
||||
res = groupSpec.GetVolumeClaimTemplate().Spec.Resources.Requests
|
||||
|
||||
if am.Spec.Overrides.HasVolumeClaimTemplate(&groupSpec) {
|
||||
res = am.Spec.Overrides.GetVolumeClaimTemplate(&groupSpec).Spec.Resources.Requests
|
||||
} else {
|
||||
res = groupSpec.Resources.Requests
|
||||
res = am.Spec.Overrides.GetResources(&groupSpec).Requests
|
||||
}
|
||||
|
||||
if requestedSize, ok := res[core.ResourceStorage]; ok {
|
||||
|
|
|
@ -110,7 +110,7 @@ func (r *Reconciler) syncMemberStatus(ctx context.Context, apiObject k8sutil.API
|
|||
|
||||
amember, ok := cache.ArangoMember().V1().GetSimple(name)
|
||||
if !ok {
|
||||
r.log.Error("Unable to get cache")
|
||||
r.log.Error("Unable to get member")
|
||||
continue
|
||||
}
|
||||
|
||||
|
|
|
@ -84,12 +84,21 @@ func (r *Reconciler) createRotateServerStorageResizePlanInternal(spec api.Deploy
|
|||
// Only make changes when phase is created
|
||||
continue
|
||||
}
|
||||
|
||||
if member.Member.PersistentVolumeClaim.GetName() == "" {
|
||||
// Plan is irrelevant without PVC
|
||||
continue
|
||||
}
|
||||
groupSpec := spec.GetServerGroupSpec(member.Group)
|
||||
|
||||
cache, ok := context.ACS().ClusterCache(member.Member.ClusterID)
|
||||
if !ok {
|
||||
// Do not work without cache
|
||||
continue
|
||||
}
|
||||
|
||||
am := cache.ArangoMember().V1().GetSimpleOptional(member.Member.ArangoMemberName(context.GetName(), member.Group))
|
||||
|
||||
if groupSpec.VolumeResizeMode.Get() != mode {
|
||||
continue
|
||||
}
|
||||
|
@ -110,10 +119,10 @@ func (r *Reconciler) createRotateServerStorageResizePlanInternal(spec api.Deploy
|
|||
}
|
||||
|
||||
var res core.ResourceList
|
||||
if groupSpec.HasVolumeClaimTemplate() {
|
||||
res = groupSpec.GetVolumeClaimTemplate().Spec.Resources.Requests
|
||||
if am.Spec.Overrides.HasVolumeClaimTemplate(&groupSpec) {
|
||||
res = am.Spec.Overrides.GetVolumeClaimTemplate(&groupSpec).Spec.Resources.Requests
|
||||
} else {
|
||||
res = groupSpec.Resources.Requests
|
||||
res = am.Spec.Overrides.GetResources(&groupSpec).Requests
|
||||
}
|
||||
if requestedSize, ok := res[core.ResourceStorage]; ok {
|
||||
if volumeSize, ok := pvc.Spec.Resources.Requests[core.ResourceStorage]; ok {
|
||||
|
|
|
@ -56,6 +56,7 @@ import (
|
|||
"github.com/arangodb/kube-arangodb/pkg/util"
|
||||
"github.com/arangodb/kube-arangodb/pkg/util/arangod/conn"
|
||||
"github.com/arangodb/kube-arangodb/pkg/util/errors"
|
||||
"github.com/arangodb/kube-arangodb/pkg/util/errors/panics"
|
||||
"github.com/arangodb/kube-arangodb/pkg/util/k8sutil"
|
||||
inspectorInterface "github.com/arangodb/kube-arangodb/pkg/util/k8sutil/inspector"
|
||||
arangomemberv1 "github.com/arangodb/kube-arangodb/pkg/util/k8sutil/inspector/arangomember/v1"
|
||||
|
@ -701,7 +702,10 @@ type LastLogRecord struct {
|
|||
}
|
||||
|
||||
func (l *LastLogRecord) Run(e *zerolog.Event, level zerolog.Level, msg string) {
|
||||
l.t.Log(msg)
|
||||
for _, s := range panics.GetStack(0) {
|
||||
l.t.Logf("Stack: %s", s.String())
|
||||
}
|
||||
l.t.Logf(msg)
|
||||
l.msg = msg
|
||||
}
|
||||
|
||||
|
@ -717,6 +721,7 @@ type testCase struct {
|
|||
|
||||
kclient.FakeDataInput
|
||||
Extender func(t *testing.T, r *Reconciler, c *testCase)
|
||||
Data func(t *testing.T, in kclient.FakeDataInput, c *testCase) kclient.FakeDataInput
|
||||
}
|
||||
|
||||
func (t testCase) Inspector(test *testing.T) inspectorInterface.Inspector {
|
||||
|
@ -1235,6 +1240,10 @@ func TestCreatePlan(t *testing.T) {
|
|||
ctx, cancel := context.WithCancel(context.Background())
|
||||
defer cancel()
|
||||
|
||||
if testCase.Data != nil {
|
||||
testCase.FakeDataInput = testCase.Data(t, testCase.FakeDataInput, &testCase)
|
||||
}
|
||||
|
||||
i := testCase.Inspector(t)
|
||||
|
||||
testCase.context.Inspector = i
|
||||
|
@ -1263,6 +1272,10 @@ func TestCreatePlan(t *testing.T) {
|
|||
|
||||
err, _ := r.CreatePlan(ctx)
|
||||
|
||||
if event := testCase.context.RecordedEvent; event != nil {
|
||||
t.Logf("Event recorded: %s : %s : %s", event.Type, event.Reason, event.Message)
|
||||
}
|
||||
|
||||
// Assert
|
||||
if testCase.ExpectedEvent != nil {
|
||||
require.NotNil(t, testCase.context.RecordedEvent)
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
//
|
||||
// DISCLAIMER
|
||||
//
|
||||
// Copyright 2016-2022 ArangoDB GmbH, Cologne, Germany
|
||||
// Copyright 2016-2023 ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
|
@ -81,6 +81,14 @@ func (p *arangoMembersInspectorV1) GetSimple(name string) (*api.ArangoMember, bo
|
|||
return arangoMember, true
|
||||
}
|
||||
|
||||
func (p *arangoMembersInspectorV1) GetSimpleOptional(name string) *api.ArangoMember {
|
||||
a, ok := p.GetSimple(name)
|
||||
if !ok {
|
||||
return &api.ArangoMember{}
|
||||
}
|
||||
return a
|
||||
}
|
||||
|
||||
func (p *arangoMembersInspectorV1) Iterate(action ins.Action, filters ...ins.Filter) error {
|
||||
for _, arangoMember := range p.arangoMembers {
|
||||
if err := p.iterateArangoMember(arangoMember, action, filters...); err != nil {
|
||||
|
|
|
@ -76,6 +76,7 @@ type ArangoDContainer struct {
|
|||
groupSpec api.ServerGroupSpec
|
||||
spec api.DeploymentSpec
|
||||
group api.ServerGroup
|
||||
arangoMember api.ArangoMember
|
||||
imageInfo api.ImageInfo
|
||||
cachedStatus interfaces.Inspector
|
||||
input pod.Input
|
||||
|
@ -206,9 +207,11 @@ func (a *ArangoDContainer) GetEnvs() ([]core.EnvVar, []core.EnvFromSource) {
|
|||
|
||||
envs.Add(true, k8sutil.GetLifecycleEnv()...)
|
||||
|
||||
if a.groupSpec.Resources.Limits != nil {
|
||||
resources := a.member.arangoMember.Spec.Overrides.GetResources(&a.groupSpec)
|
||||
|
||||
if resources.Limits != nil {
|
||||
if a.groupSpec.GetOverrideDetectedTotalMemory() {
|
||||
if limits, ok := a.groupSpec.Resources.Limits[core.ResourceMemory]; ok {
|
||||
if limits, ok := resources.Limits[core.ResourceMemory]; ok {
|
||||
envs.Add(true, core.EnvVar{
|
||||
Name: ArangoDBOverrideDetectedTotalMemoryEnv,
|
||||
Value: fmt.Sprintf("%d", limits.Value()),
|
||||
|
@ -217,7 +220,7 @@ func (a *ArangoDContainer) GetEnvs() ([]core.EnvVar, []core.EnvFromSource) {
|
|||
}
|
||||
|
||||
if a.groupSpec.GetOverrideDetectedNumberOfCores() {
|
||||
if limits, ok := a.groupSpec.Resources.Limits[core.ResourceCPU]; ok {
|
||||
if limits, ok := resources.Limits[core.ResourceCPU]; ok {
|
||||
envs.Add(true, core.EnvVar{
|
||||
Name: ArangoDBOverrideDetectedNumberOfCoresEnv,
|
||||
Value: fmt.Sprintf("%d", limits.Value()),
|
||||
|
@ -278,7 +281,7 @@ func (a *ArangoDContainer) GetEnvs() ([]core.EnvVar, []core.EnvFromSource) {
|
|||
}
|
||||
|
||||
func (a *ArangoDContainer) GetResourceRequirements() core.ResourceRequirements {
|
||||
return k8sutil.ExtractPodResourceRequirement(a.groupSpec.Resources)
|
||||
return k8sutil.ExtractPodResourceRequirement(a.arangoMember.Spec.Overrides.GetResources(&a.groupSpec))
|
||||
}
|
||||
|
||||
func (a *ArangoDContainer) GetLifecycle() (*core.Lifecycle, error) {
|
||||
|
@ -529,6 +532,7 @@ func (m *MemberArangoDPod) GetContainerCreator() interfaces.ContainerCreator {
|
|||
resources: m.resources,
|
||||
imageInfo: m.imageInfo,
|
||||
groupSpec: m.groupSpec,
|
||||
arangoMember: m.arangoMember,
|
||||
cachedStatus: m.cachedStatus,
|
||||
input: m.AsInput(),
|
||||
status: m.status,
|
||||
|
|
|
@ -55,6 +55,7 @@ type ArangoSyncContainer struct {
|
|||
imageInfo api.ImageInfo
|
||||
apiObject meta.Object
|
||||
memberStatus api.MemberStatus
|
||||
arangoMember api.ArangoMember
|
||||
tlsKeyfileSecretName string
|
||||
clientAuthCASecretName string
|
||||
masterJWTSecretName string
|
||||
|
@ -147,7 +148,7 @@ func (a *ArangoSyncContainer) GetProbes() (*core.Probe, *core.Probe, *core.Probe
|
|||
}
|
||||
|
||||
func (a *ArangoSyncContainer) GetResourceRequirements() core.ResourceRequirements {
|
||||
return k8sutil.ExtractPodResourceRequirement(a.groupSpec.Resources)
|
||||
return k8sutil.ExtractPodResourceRequirement(a.arangoMember.Spec.Overrides.GetResources(&a.groupSpec))
|
||||
}
|
||||
|
||||
func (a *ArangoSyncContainer) GetLifecycle() (*core.Lifecycle, error) {
|
||||
|
@ -319,6 +320,7 @@ func (m *MemberSyncPod) GetContainerCreator() interfaces.ContainerCreator {
|
|||
imageInfo: m.imageInfo,
|
||||
apiObject: m.apiObject,
|
||||
memberStatus: m.memberStatus,
|
||||
arangoMember: m.arangoMember,
|
||||
tlsKeyfileSecretName: m.tlsKeyfileSecretName,
|
||||
clientAuthCASecretName: m.clientAuthCASecretName,
|
||||
masterJWTSecretName: m.masterJWTSecretName,
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
//
|
||||
// DISCLAIMER
|
||||
//
|
||||
// Copyright 2016-2022 ArangoDB GmbH, Cologne, Germany
|
||||
// Copyright 2016-2023 ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
|
@ -61,10 +61,15 @@ func (r *Resources) EnsurePVCs(ctx context.Context, cachedStatus inspectorInterf
|
|||
continue
|
||||
}
|
||||
|
||||
storageClassName := spec.GetStorageClassName()
|
||||
am, exists := cachedStatus.ArangoMember().V1().GetSimple(m.ArangoMemberName(deploymentName, group))
|
||||
if !exists {
|
||||
continue
|
||||
}
|
||||
|
||||
storageClassName := am.Spec.Overrides.GetStorageClassName(&spec)
|
||||
role := group.AsRole()
|
||||
resources := spec.Resources
|
||||
vct := spec.VolumeClaimTemplate
|
||||
resources := am.Spec.Overrides.GetResources(&spec)
|
||||
vct := am.Spec.Overrides.GetVolumeClaimTemplate(&spec)
|
||||
finalizers := r.createPVCFinalizers()
|
||||
err := globals.GetGlobalTimeouts().Kubernetes().RunWithTimeout(ctx, func(ctxChild context.Context) error {
|
||||
return k8sutil.CreatePersistentVolumeClaim(ctxChild, cachedStatus.PersistentVolumeClaimsModInterface().V1(),
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
//
|
||||
// DISCLAIMER
|
||||
//
|
||||
// Copyright 2016-2022 ArangoDB GmbH, Cologne, Germany
|
||||
// Copyright 2016-2023 ArangoDB GmbH, Cologne, Germany
|
||||
//
|
||||
// Licensed under the Apache License, Version 2.0 (the "License");
|
||||
// you may not use this file except in compliance with the License.
|
||||
|
@ -29,6 +29,7 @@ type Inspector interface {
|
|||
gvk.GVK
|
||||
|
||||
GetSimple(name string) (*api.ArangoMember, bool)
|
||||
GetSimpleOptional(name string) *api.ArangoMember
|
||||
Iterate(action Action, filters ...Filter) error
|
||||
Read() ReadInterface
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue