Skip to content

Commit 71c41d0

Browse files
authored
feat: add volume-snapshot-suffix optional argument to snapshot command (cloudnative-pg#2492)
This patch add `volume-snapshot-suffix` optional argument to snapshot command Closes: cloudnative-pg#2492 Signed-off-by: Armando Ruocco <armando.ruocco@enterprisedb.com>
1 parent ee797f5 commit 71c41d0

File tree

6 files changed

+109
-61
lines changed

6 files changed

+109
-61
lines changed

.github/workflows/continuous-delivery.yml

+2-2
Original file line numberDiff line numberDiff line change
@@ -21,8 +21,8 @@ on:
2121
feature_type:
2222
description: >
2323
Feature Type (disruptive, performance, upgrade, smoke, basic, service-connectivity, self-healing,
24-
backup-restore, operator, observability, replication, plugin, postgres-configuration, pod-scheduling,
25-
cluster-metadata, recovery, importing-databases, storage, security, maintenance)
24+
backup-restore, snapshot, operator, observability, replication, plugin, postgres-configuration,
25+
pod-scheduling, cluster-metadata, recovery, importing-databases, storage, security, maintenance)
2626
required: false
2727
log_level:
2828
description: 'Log level for operator (error, warning, info(default), debug, trace)'

contribute/e2e_testing_environment/README.md

+1
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,7 @@ exported, it will select all medium test cases from the feature type provided.
130130
| `service-connectivity` |
131131
| `self-healing` |
132132
| `backup-restore` |
133+
| `snapshot` |
133134
| `operator` |
134135
| `observability` |
135136
| `replication` |

internal/cmd/plugin/snapshot/cmd.go

+21-2
Original file line numberDiff line numberDiff line change
@@ -67,8 +67,9 @@ The other replicas will continue working.`,
6767
clusterName := args[0]
6868

6969
snapshotClassName, _ := cmd.Flags().GetString("volume-snapshot-class-name")
70+
snapshotNameSuffix, _ := cmd.Flags().GetString("volume-snapshot-suffix")
7071

71-
snapshotCmd, err := newSnapshotCommand(cmd.Context(), clusterName, snapshotClassName)
72+
snapshotCmd, err := newSnapshotCommand(cmd.Context(), clusterName, snapshotClassName, snapshotNameSuffix)
7273
if err != nil {
7374
return err
7475
}
@@ -84,6 +85,13 @@ The other replicas will continue working.`,
8485
`The VolumeSnapshotClass name to be used for the snapshot
8586
(defaults to empty, which will make use of the default VolumeSnapshotClass)`)
8687

88+
cmd.Flags().StringP("volume-snapshot-suffix",
89+
"x",
90+
"",
91+
"Specifies the suffix of the created volume snapshot. Optional. "+
92+
"Defaults to the snapshot time expressed as unix timestamp",
93+
)
94+
8795
return cmd
8896
}
8997

@@ -94,16 +102,23 @@ type snapshotCommand struct {
94102
pvcs []corev1.PersistentVolumeClaim
95103
snapshotClassName string
96104
snapshotTime time.Time
105+
snapshotSuffix string
97106
}
98107

99108
// newSnapshotCommand creates the snapshot command
100-
func newSnapshotCommand(ctx context.Context, clusterName, snapshotClassName string) (*snapshotCommand, error) {
109+
func newSnapshotCommand(
110+
ctx context.Context,
111+
clusterName string,
112+
snapshotClassName string,
113+
snapshotSuffix string,
114+
) (*snapshotCommand, error) {
101115
var cluster apiv1.Cluster
102116

103117
cmd := &snapshotCommand{
104118
ctx: ctx,
105119
cluster: &cluster,
106120
snapshotClassName: snapshotClassName,
121+
snapshotSuffix: snapshotSuffix,
107122
}
108123

109124
// Get the Cluster object
@@ -324,5 +339,9 @@ func (cmd *snapshotCommand) waitSnapshot(name string) error {
324339

325340
// getSnapshotName gets the snapshot name for a certain PVC
326341
func (cmd *snapshotCommand) getSnapshotName(pvcName string) string {
342+
if cmd.snapshotSuffix != "" {
343+
return fmt.Sprintf("%s-%v", pvcName, cmd.snapshotSuffix)
344+
}
345+
327346
return fmt.Sprintf("%s-%v", pvcName, cmd.snapshotTime.Unix())
328347
}

tests/e2e/volume_snapshot_test.go

+72-46
Original file line numberDiff line numberDiff line change
@@ -29,56 +29,82 @@ import (
2929

3030
// Test case for validating volume snapshots
3131
// with different storage providers in different k8s environments
32-
var _ = Describe("Verify volume snapshot", Label(tests.LabelBackupRestore, tests.LabelStorage), func() {
33-
const (
34-
sampleFile = fixturesDir + "/volume_snapshot/cluster_volume_snapshot.yaml.template"
35-
clusterName = "volume-snapshot"
36-
level = tests.Medium
37-
)
38-
BeforeEach(func() {
39-
if testLevelEnv.Depth < int(level) {
40-
Skip("Test depth is lower than the amount requested for this test")
41-
}
42-
// This need to be removed later
43-
if IsLocal() {
44-
Skip("This test is only run on AKS, EKS and GKE clusters for now")
45-
}
46-
})
47-
// Initializing a global namespace variable to be used in each test case
48-
var namespace, namespacePrefix string
49-
// Gathering the default volumeSnapshot class for the current environment
50-
volumeSnapshotClassName := os.Getenv("E2E_DEFAULT_VOLUMESNAPSHOT_CLASS")
32+
var _ = Describe("Verify Volume Snapshot",
33+
Label(tests.LabelBackupRestore, tests.LabelStorage, tests.LabelSnapshot), func() {
34+
const (
35+
sampleFile = fixturesDir + "/volume_snapshot/cluster_volume_snapshot.yaml.template"
36+
clusterName = "volume-snapshot"
37+
level = tests.Medium
38+
)
39+
BeforeEach(func() {
40+
if testLevelEnv.Depth < int(level) {
41+
Skip("Test depth is lower than the amount requested for this test")
42+
}
43+
// This need to be removed later
44+
if IsLocal() {
45+
Skip("This test is only run on AKS, EKS and GKE clusters for now")
46+
}
47+
})
48+
// Initializing a global namespace variable to be used in each test case
49+
var namespace, namespacePrefix string
50+
// Gathering the default volumeSnapshot class for the current environment
51+
volumeSnapshotClassName := os.Getenv("E2E_DEFAULT_VOLUMESNAPSHOT_CLASS")
5152

52-
Context("Can create a Volume Snapshot", Ordered, func() {
53-
BeforeAll(func() {
54-
var err error
55-
// Initializing namespace variable to be used in test case
56-
namespacePrefix = "volume-snapshot"
57-
namespace, err = env.CreateUniqueNamespace(namespacePrefix)
58-
Expect(err).ToNot(HaveOccurred())
59-
DeferCleanup(func() error {
60-
if CurrentSpecReport().Failed() {
61-
env.DumpNamespaceObjects(namespace, "out/"+CurrentSpecReport().LeafNodeText+".log")
62-
}
63-
return env.DeleteNamespace(namespace)
53+
Context("Can create a Volume Snapshot", Ordered, func() {
54+
BeforeAll(func() {
55+
var err error
56+
// Initializing namespace variable to be used in test case
57+
namespacePrefix = "volume-snapshot"
58+
namespace, err = env.CreateUniqueNamespace(namespacePrefix)
59+
Expect(err).ToNot(HaveOccurred())
60+
DeferCleanup(func() error {
61+
if CurrentSpecReport().Failed() {
62+
env.DumpNamespaceObjects(namespace, "out/"+CurrentSpecReport().LeafNodeText+".log")
63+
}
64+
return env.DeleteNamespace(namespace)
65+
})
66+
// Creating a cluster with three nodes
67+
AssertCreateCluster(namespace, clusterName, sampleFile, env)
6468
})
65-
// Creating a cluster with three nodes
66-
AssertCreateCluster(namespace, clusterName, sampleFile, env)
67-
})
6869

69-
It("Using the kubectl cnpg plugin", func() {
70-
err := utils.CreateVolumeSnapshotBackup(volumeSnapshotClassName, namespace, clusterName)
71-
Expect(err).ToNot(HaveOccurred())
70+
It("using the kubectl cnpg plugin", func() {
71+
err := utils.CreateVolumeSnapshotBackup(
72+
volumeSnapshotClassName,
73+
namespace,
74+
clusterName,
75+
"",
76+
)
77+
Expect(err).ToNot(HaveOccurred())
78+
79+
out, _, err := utils.Run(fmt.Sprintf("kubectl get volumesnapshot -n %v", namespace))
80+
Expect(err).ToNot(HaveOccurred())
81+
GinkgoWriter.Println("output of current volumesnapshot \n")
82+
GinkgoWriter.Println(out)
7283

73-
out, _, err := utils.Run(fmt.Sprintf("kubectl get volumesnapshot -n %v", namespace))
74-
Expect(err).ToNot(HaveOccurred())
75-
GinkgoWriter.Print("output of current volumesnapshot")
76-
GinkgoWriter.Print(out)
84+
out, _, err = utils.Run(fmt.Sprintf("kubectl get volumesnapshotcontent -n %v", namespace))
85+
Expect(err).ToNot(HaveOccurred())
86+
GinkgoWriter.Println("output of current volumesnapshotcontent \n")
87+
GinkgoWriter.Println(out)
88+
})
89+
90+
It("using the kubectl cnpg plugin with a custom suffix", func() {
91+
err := utils.CreateVolumeSnapshotBackup(
92+
volumeSnapshotClassName,
93+
namespace,
94+
clusterName,
95+
"test",
96+
)
97+
Expect(err).ToNot(HaveOccurred())
7798

78-
out, _, err = utils.Run(fmt.Sprintf("kubectl get volumesnapshotcontent -n %v", namespace))
79-
Expect(err).ToNot(HaveOccurred())
80-
GinkgoWriter.Print("output of current volumesnapshotcontent")
81-
GinkgoWriter.Print(out)
99+
out, _, err := utils.Run(fmt.Sprintf("kubectl get volumesnapshot -n %v", namespace))
100+
Expect(err).ToNot(HaveOccurred())
101+
GinkgoWriter.Println("output of current volumesnapshot \n")
102+
GinkgoWriter.Println(out)
103+
104+
out, _, err = utils.Run(fmt.Sprintf("kubectl get volumesnapshotcontent -n %v", namespace))
105+
Expect(err).ToNot(HaveOccurred())
106+
GinkgoWriter.Println("output of current volumesnapshotcontent \n")
107+
GinkgoWriter.Println(out)
108+
})
82109
})
83110
})
84-
})

tests/labels.go

+3
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,9 @@ const (
5050
// LabelBackupRestore is a label for only selecting backup and restore tests
5151
LabelBackupRestore = "backup-restore"
5252

53+
// LabelSnapshot is a label for selecting snapshot tests
54+
LabelSnapshot = "snapshot"
55+
5356
// LabelOperator is a label for only selecting operator tests
5457
LabelOperator = "operator"
5558

tests/utils/backup.go

+10-11
Original file line numberDiff line numberDiff line change
@@ -497,18 +497,17 @@ func GetConditionsInClusterStatus(
497497
func CreateVolumeSnapshotBackup(
498498
volumeSnapshotClass,
499499
namespace,
500-
clusterName string,
500+
clusterName,
501+
snapshotSuffix string,
501502
) error {
502-
var err error
503-
if volumeSnapshotClass == "" {
504-
_, _, err = Run(fmt.Sprintf("kubectl cnpg snapshot %v -n %v",
505-
clusterName, namespace))
506-
} else {
507-
_, _, err = Run(fmt.Sprintf("kubectl cnpg snapshot %v -c %v -n %v",
508-
clusterName, volumeSnapshotClass, namespace))
503+
command := fmt.Sprintf("kubectl cnpg snapshot %v -n %v", clusterName, namespace)
504+
if volumeSnapshotClass != "" {
505+
command = fmt.Sprintf("%v -c %v", command, volumeSnapshotClass)
509506
}
510-
if err != nil {
511-
return err
507+
if snapshotSuffix != "" {
508+
command = fmt.Sprintf("%v -x %v", command, snapshotSuffix)
512509
}
513-
return nil
510+
511+
_, _, err := Run(command)
512+
return err
514513
}

0 commit comments

Comments
 (0)