Skip to content

Commit

Permalink
feat: add nodeSelector to InstanceOverridesSpec (#450)
Browse files Browse the repository at this point in the history
* Feat: Add node selector to instance overrides

* apply nodeselector

* Add unit test for node selector

* Update pod_builder_test.go

* fix lint errors

* update

* update lint config

---------

Co-authored-by: Nour <[email protected]>
  • Loading branch information
vimystic and nourspace authored Feb 13, 2025
1 parent 2cf0dbf commit 4194f19
Show file tree
Hide file tree
Showing 9 changed files with 47 additions and 15 deletions.
19 changes: 8 additions & 11 deletions .golangci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -26,28 +26,25 @@ linters-settings:
desc: "Although Ginkgo is used in kubebuilder, use testify instead. Ginkgo is bloated providing little value."
- pkg: github.com/onsi/ginkgo
desc: "Although Ginkgo is used in kubebuilder, use testify instead. Ginkgo is bloated providing little value."
govet:
check-shadowing: true
govet: {}
misspell:
locale: US
ignore-words:
- "statuser"
nakedret:
# make an issue if func has more lines of code than this setting and it has naked returns; default is 30
max-func-lines: 0 # completely disallow naked returns
max-func-lines: 0 # Completely disallow naked returns
nolintlint:
allow-leading-space: true # don't require machine-readable nolint directives (i.e. with no leading space)
allow-unused: false # report any unused nolint directives
require-explanation: false # don't require an explanation for nolint directives
require-specific: false # don't require nolint directives to be specific about which linter is being skipped
allow-unused: false # Report any unused nolint directives
require-explanation: false # Don't require an explanation for nolint directives
require-specific: false # Don't require nolint directives to be specific

linters:
disable-all: true
enable:
- bodyclose
- depguard
- errcheck
- exportloopref
- copyloopvar # Replaces exportloopref (Go 1.22+)
- goimports
- goprintffuncname
- gosimple
Expand All @@ -58,7 +55,7 @@ linters:
- noctx
- nolintlint
- staticcheck
- stylecheck # replacement for golint
- stylecheck # Replacement for golint
- unconvert
- unused
- whitespace
- whitespace
5 changes: 5 additions & 0 deletions api/v1/cosmosfullnode_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -798,6 +798,11 @@ type InstanceOverridesSpec struct {
// Sets an individual instance's external address.
// +optional
ExternalAddress *string `json:"externalAddress"`

// NodeSelector is a selector which must be true for the pod to fit on a node.
// Selector which must match a node's labels for the pod to be scheduled on that node.
// +optional
NodeSelector map[string]string `json:"nodeSelector,omitempty"`
}

type DisableStrategy string
Expand Down
7 changes: 7 additions & 0 deletions api/v1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

7 changes: 7 additions & 0 deletions config/crd/bases/cosmos.strange.love_cosmosfullnodes.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -408,6 +408,13 @@ spec:
image:
description: Overrides an individual instance's Image.
type: string
nodeSelector:
additionalProperties:
type: string
description: |-
NodeSelector is a selector which must be true for the pod to fit on a node.
Selector which must match a node's labels for the pod to be scheduled on that node.
type: object
volumeClaimTemplate:
description: Overrides an individual instance's PVC.
properties:
Expand Down
1 change: 0 additions & 1 deletion internal/cosmos/status_collector.go
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,6 @@ func (coll StatusCollector) Collect(ctx context.Context, pods []corev1.Pod) Stat
statuses := make(StatusCollection, len(pods))

for i := range pods {
i := i
eg.Go(func() error {
pod := pods[i]
statuses[i].TS = now
Expand Down
4 changes: 3 additions & 1 deletion internal/fullnode/pod_builder.go
Original file line number Diff line number Diff line change
Expand Up @@ -196,7 +196,6 @@ func (b PodBuilder) Build() (*corev1.Pod, error) {
}
var vrs *cosmosv1.ChainVersion
for _, v := range b.crd.Spec.ChainSpec.Versions {
v := v
if instanceHeight < v.UpgradeHeight {
break
}
Expand All @@ -214,6 +213,9 @@ func (b PodBuilder) Build() (*corev1.Pod, error) {
if o.Image != "" {
setChainContainerImage(pod, o.Image)
}
if o.NodeSelector != nil {
pod.Spec.NodeSelector = o.NodeSelector
}
}

kube.NormalizeMetadata(&pod.ObjectMeta)
Expand Down
17 changes: 17 additions & 0 deletions internal/fullnode/pod_builder_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -102,6 +102,23 @@ func TestPodBuilder(t *testing.T) {
require.Equal(t, pod, pod2)
})

t.Run("instanceOverrides - nodeSelector applied", func(t *testing.T) {
crd := defaultCRD()
crd.Spec.InstanceOverrides = map[string]cosmosv1.InstanceOverridesSpec{
"osmosis-5": {
NodeSelector: map[string]string{"kubernetes.io/hostname": "worker-1"},
},
}

builder := NewPodBuilder(&crd)
pod, err := builder.WithOrdinal(5).Build()
require.NoError(t, err)

// Verify that nodeSelector was applied from InstanceOverrides
require.NotNil(t, pod.Spec.NodeSelector)
require.Equal(t, "worker-1", pod.Spec.NodeSelector["kubernetes.io/hostname"])
})

t.Run("happy path - ports", func(t *testing.T) {
crd := defaultCRD()
pod, err := NewPodBuilder(&crd).Build()
Expand Down
1 change: 0 additions & 1 deletion internal/fullnode/pvc_disk_usage.go
Original file line number Diff line number Diff line change
Expand Up @@ -61,7 +61,6 @@ func (c DiskUsageCollector) CollectDiskUsage(ctx context.Context, crd *cosmosv1.
)

for i := range pods.Items {
i := i
eg.Go(func() error {
pod := pods.Items[i]
cctx, cancel := context.WithTimeout(ctx, 10*time.Second)
Expand Down
1 change: 0 additions & 1 deletion internal/volsnapshot/vol_snapshot_control.go
Original file line number Diff line number Diff line change
Expand Up @@ -162,7 +162,6 @@ func (control VolumeSnapshotControl) DeleteOldSnapshots(ctx context.Context, log

var merr error
for _, vs := range toDelete {
vs := vs
log.Info("Deleting volume snapshot", "volumeSnapshotName", vs.Name, "limit", limit)
if err := control.client.Delete(ctx, &vs); kube.IgnoreNotFound(err) != nil {
merr = errors.Join(merr, fmt.Errorf("delete %s: %w", vs.Name, err))
Expand Down

0 comments on commit 4194f19

Please sign in to comment.