Skip to content

Commit b4a4b53

Browse files
committed
test: add inline volume e2e test
fix test fix test failure
1 parent d307c85 commit b4a4b53

File tree

5 files changed

+182
-28
lines changed

5 files changed

+182
-28
lines changed

test/e2e/dynamic_provisioning_test.go

Lines changed: 88 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ limitations under the License.
1717
package e2e
1818

1919
import (
20+
"context"
2021
"fmt"
2122
"log"
2223
"os"
@@ -277,18 +278,37 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Dynamic Provisioning", func() {
277278
test.Run(cs, ns)
278279
})
279280

280-
ginkgo.It("should create a NFSv3 volume on demand with mount options [nfs]", func() {
281-
if isAzureStackCloud {
282-
ginkgo.Skip("test case is not available for Azure Stack")
283-
}
281+
ginkgo.It("should create a volume on demand (Bring Your Own Key)", func() {
282+
// get storage account secret name
283+
err := os.Chdir("../..")
284+
gomega.Expect(err).NotTo(gomega.HaveOccurred())
285+
defer func() {
286+
err := os.Chdir("test/e2e")
287+
gomega.Expect(err).NotTo(gomega.HaveOccurred())
288+
}()
289+
290+
getSecretNameScript := "test/utils/get_storage_account_secret_name.sh"
291+
log.Printf("run script: %s\n", getSecretNameScript)
292+
293+
cmd := exec.Command("bash", getSecretNameScript)
294+
output, err := cmd.CombinedOutput()
295+
log.Printf("got output: %v, error: %v\n", string(output), err)
296+
gomega.Expect(err).NotTo(gomega.HaveOccurred())
297+
298+
secretName := strings.TrimSuffix(string(output), "\n")
299+
log.Printf("got storage account secret name: %v\n", secretName)
300+
bringKeyStorageClassParameters["csi.storage.k8s.io/provisioner-secret-name"] = secretName
301+
bringKeyStorageClassParameters["csi.storage.k8s.io/node-stage-secret-name"] = secretName
302+
284303
pods := []testsuites.PodDetails{
285304
{
286305
Cmd: "echo 'hello world' > /mnt/test-1/data && grep 'hello world' /mnt/test-1/data",
287306
Volumes: []testsuites.VolumeDetails{
288307
{
289308
ClaimSize: "10Gi",
290309
MountOptions: []string{
291-
"nconnect=16",
310+
"-o allow_other",
311+
"--file-cache-timeout-in-seconds=120",
292312
},
293313
VolumeMount: testsuites.VolumeMountDetails{
294314
NameGenerate: "test-volume-",
@@ -299,17 +319,37 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Dynamic Provisioning", func() {
299319
},
300320
}
301321
test := testsuites.DynamicallyProvisionedCmdVolumeTest{
302-
CSIDriver: testDriver,
303-
Pods: pods,
304-
StorageClassParameters: map[string]string{
305-
"skuName": "Premium_LRS",
306-
"protocol": "nfs",
322+
CSIDriver: testDriver,
323+
Pods: pods,
324+
StorageClassParameters: bringKeyStorageClassParameters,
325+
}
326+
test.Run(cs, ns)
327+
})
328+
329+
ginkgo.It("should create a volume on demand and resize it [blob.csi.azure.com]", func() {
330+
pods := []testsuites.PodDetails{
331+
{
332+
Cmd: "echo 'hello world' > /mnt/test-1/data && grep 'hello world' /mnt/test-1/data",
333+
Volumes: []testsuites.VolumeDetails{
334+
{
335+
ClaimSize: "10Gi",
336+
VolumeMount: testsuites.VolumeMountDetails{
337+
NameGenerate: "test-volume-",
338+
MountPathGenerate: "/mnt/test-",
339+
},
340+
},
341+
},
307342
},
308343
}
344+
test := testsuites.DynamicallyProvisionedResizeVolumeTest{
345+
CSIDriver: testDriver,
346+
Pods: pods,
347+
StorageClassParameters: map[string]string{"skuName": "Standard_LRS"},
348+
}
309349
test.Run(cs, ns)
310350
})
311351

312-
ginkgo.It("should create a volume on demand (Bring Your Own Key)", func() {
352+
ginkgo.It("should create an CSI inline volume [blob.csi.azure.com]", func() {
313353
// get storage account secret name
314354
err := os.Chdir("../..")
315355
gomega.Expect(err).NotTo(gomega.HaveOccurred())
@@ -328,15 +368,27 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Dynamic Provisioning", func() {
328368

329369
secretName := strings.TrimSuffix(string(output), "\n")
330370
log.Printf("got storage account secret name: %v\n", secretName)
331-
bringKeyStorageClassParameters["csi.storage.k8s.io/provisioner-secret-name"] = secretName
332-
bringKeyStorageClassParameters["csi.storage.k8s.io/node-stage-secret-name"] = secretName
371+
segments := strings.Split(secretName, "-")
372+
if len(segments) != 5 {
373+
ginkgo.Fail(fmt.Sprintf("%s have %d elements, expected: %d ", secretName, len(segments), 5))
374+
}
375+
accountName := segments[3]
376+
377+
containerName := "csi-inline-blobfuse-volume"
378+
req := makeCreateVolumeReq(containerName)
379+
req.Parameters["storageAccount"] = accountName
380+
resp, err := blobDriver.CreateVolume(context.Background(), req)
381+
if err != nil {
382+
ginkgo.Fail(fmt.Sprintf("create volume error: %v", err))
383+
}
384+
volumeID := resp.Volume.VolumeId
385+
ginkgo.By(fmt.Sprintf("Successfully provisioned Blobfuse volume: %q\n", volumeID))
333386

334387
pods := []testsuites.PodDetails{
335388
{
336-
Cmd: "echo 'hello world' > /mnt/test-1/data && grep 'hello world' /mnt/test-1/data",
337389
Volumes: []testsuites.VolumeDetails{
338390
{
339-
ClaimSize: "10Gi",
391+
ClaimSize: "100Gi",
340392
MountOptions: []string{
341393
"-o allow_other",
342394
"--file-cache-timeout-in-seconds=120",
@@ -349,21 +401,30 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Dynamic Provisioning", func() {
349401
},
350402
},
351403
}
352-
test := testsuites.DynamicallyProvisionedCmdVolumeTest{
353-
CSIDriver: testDriver,
354-
Pods: pods,
355-
StorageClassParameters: bringKeyStorageClassParameters,
404+
405+
test := testsuites.DynamicallyProvisionedInlineVolumeTest{
406+
CSIDriver: testDriver,
407+
Pods: pods,
408+
SecretName: secretName,
409+
ContainerName: containerName,
410+
ReadOnly: false,
356411
}
357412
test.Run(cs, ns)
358413
})
359414

360-
ginkgo.It("should create a volume on demand and resize it [blob.csi.azure.com]", func() {
415+
ginkgo.It("should create a NFSv3 volume on demand with mount options [nfs]", func() {
416+
if isAzureStackCloud {
417+
ginkgo.Skip("test case is not available for Azure Stack")
418+
}
361419
pods := []testsuites.PodDetails{
362420
{
363421
Cmd: "echo 'hello world' > /mnt/test-1/data && grep 'hello world' /mnt/test-1/data",
364422
Volumes: []testsuites.VolumeDetails{
365423
{
366424
ClaimSize: "10Gi",
425+
MountOptions: []string{
426+
"nconnect=16",
427+
},
367428
VolumeMount: testsuites.VolumeMountDetails{
368429
NameGenerate: "test-volume-",
369430
MountPathGenerate: "/mnt/test-",
@@ -372,10 +433,13 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Dynamic Provisioning", func() {
372433
},
373434
},
374435
}
375-
test := testsuites.DynamicallyProvisionedResizeVolumeTest{
376-
CSIDriver: testDriver,
377-
Pods: pods,
378-
StorageClassParameters: map[string]string{"skuName": "Standard_LRS"},
436+
test := testsuites.DynamicallyProvisionedCmdVolumeTest{
437+
CSIDriver: testDriver,
438+
Pods: pods,
439+
StorageClassParameters: map[string]string{
440+
"skuName": "Premium_LRS",
441+
"protocol": "nfs",
442+
},
379443
}
380444
test.Run(cs, ns)
381445
})

test/e2e/pre_provisioning_test.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,7 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Pre-Provisioned", func() {
7979
})
8080

8181
ginkgo.It("[env] should use a pre-provisioned volume and mount it as readOnly in a pod", func() {
82-
req := makeCreateVolumeReq("pre-provisioned-readOnly")
82+
req := makeCreateVolumeReq("pre-provisioned-readonly")
8383
resp, err := blobDriver.CreateVolume(context.Background(), req)
8484
if err != nil {
8585
ginkgo.Fail(fmt.Sprintf("create volume error: %v", err))
@@ -113,7 +113,7 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Pre-Provisioned", func() {
113113
})
114114

115115
ginkgo.It(fmt.Sprintf("[env] should use a pre-provisioned volume and retain PV with reclaimPolicy %q", v1.PersistentVolumeReclaimRetain), func() {
116-
req := makeCreateVolumeReq("pre-provisioned-retain-reclaimPolicy")
116+
req := makeCreateVolumeReq("pre-provisioned-retain-reclaimpolicy")
117117
resp, err := blobDriver.CreateVolume(context.Background(), req)
118118
if err != nil {
119119
ginkgo.Fail(fmt.Sprintf("create volume error: %v", err))
@@ -147,7 +147,7 @@ var _ = ginkgo.Describe("[blob-csi-e2e] Pre-Provisioned", func() {
147147
if err != nil {
148148
ginkgo.Fail(fmt.Sprintf("create volume error: %v", err))
149149
}
150-
volumeID := resp.Volume.VolumeId
150+
volumeID = resp.Volume.VolumeId
151151
ginkgo.By(fmt.Sprintf("Successfully provisioned blob volume: %q\n", volumeID))
152152

153153
pod := testsuites.PodDetails{
@@ -271,7 +271,7 @@ func makeCreateVolumeReq(volumeName string) *csi.CreateVolumeRequest {
271271
},
272272
Parameters: map[string]string{
273273
"skuname": "Standard_LRS",
274-
"containerName": "test",
274+
"containerName": volumeName,
275275
},
276276
}
277277

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
/*
2+
Copyright 2019 The Kubernetes Authors.
3+
4+
Licensed under the Apache License, Version 2.0 (the "License");
5+
you may not use this file except in compliance with the License.
6+
You may obtain a copy of the License at
7+
8+
http://www.apache.org/licenses/LICENSE-2.0
9+
10+
Unless required by applicable law or agreed to in writing, software
11+
distributed under the License is distributed on an "AS IS" BASIS,
12+
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
See the License for the specific language governing permissions and
14+
limitations under the License.
15+
*/
16+
17+
package testsuites
18+
19+
import (
20+
"sigs.k8s.io/blob-csi-driver/test/e2e/driver"
21+
22+
"github.com/onsi/ginkgo"
23+
v1 "k8s.io/api/core/v1"
24+
clientset "k8s.io/client-go/kubernetes"
25+
)
26+
27+
// DynamicallyProvisionedInlineVolumeTest will provision required SecretName, ContainerName
28+
// Waiting for the PV provisioner to create an inline volume
29+
// Testing if the Pod(s) Cmd is run with a 0 exit code
30+
type DynamicallyProvisionedInlineVolumeTest struct {
31+
CSIDriver driver.DynamicPVTestDriver
32+
Pods []PodDetails
33+
SecretName string
34+
ContainerName string
35+
ReadOnly bool
36+
}
37+
38+
func (t *DynamicallyProvisionedInlineVolumeTest) Run(client clientset.Interface, namespace *v1.Namespace) {
39+
for _, pod := range t.Pods {
40+
var tpod *TestPod
41+
var cleanup []func()
42+
tpod, cleanup = pod.SetupWithCSIInlineVolumes(client, namespace, t.CSIDriver, t.SecretName, t.ContainerName, t.ReadOnly)
43+
44+
// defer must be called here for resources not get removed before using them
45+
for i := range cleanup {
46+
defer cleanup[i]()
47+
}
48+
49+
ginkgo.By("deploying the pod")
50+
tpod.Create()
51+
defer tpod.Cleanup()
52+
ginkgo.By("checking that the pods command exits with no error")
53+
tpod.WaitForSuccess()
54+
}
55+
}

test/e2e/testsuites/specs.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,15 @@ type DataSource struct {
8686
Name string
8787
}
8888

89+
func (pod *PodDetails) SetupWithCSIInlineVolumes(client clientset.Interface, namespace *v1.Namespace, csiDriver driver.DynamicPVTestDriver, secretName, shareName string, readOnly bool) (*TestPod, []func()) {
90+
tpod := NewTestPod(client, namespace, pod.Cmd)
91+
cleanupFuncs := make([]func(), 0)
92+
for n, v := range pod.Volumes {
93+
tpod.SetupInlineVolume(fmt.Sprintf("%s%d", v.VolumeMount.NameGenerate, n+1), fmt.Sprintf("%s%d", v.VolumeMount.MountPathGenerate, n+1), secretName, shareName, readOnly)
94+
}
95+
return tpod, cleanupFuncs
96+
}
97+
8998
func (pod *PodDetails) SetupWithDynamicVolumes(client clientset.Interface, namespace *v1.Namespace, csiDriver driver.DynamicPVTestDriver, storageClassParameters map[string]string) (*TestPod, []func()) {
9099
tpod := NewTestPod(client, namespace, pod.Cmd)
91100
cleanupFuncs := make([]func(), 0)

test/e2e/testsuites/testsuites.go

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ import (
2424

2525
"sigs.k8s.io/blob-csi-driver/pkg/blob"
2626

27+
"github.com/Azure/go-autorest/autorest/to"
2728
"github.com/container-storage-interface/spec/lib/go/csi"
2829
"github.com/onsi/ginkgo"
2930
"github.com/onsi/gomega"
@@ -527,6 +528,31 @@ func (t *TestPod) SetupRawBlockVolume(pvc *v1.PersistentVolumeClaim, name, devic
527528
t.pod.Spec.Volumes = append(t.pod.Spec.Volumes, volume)
528529
}
529530

531+
func (t *TestPod) SetupInlineVolume(name, mountPath, secretName, containerName string, readOnly bool) {
532+
volumeMount := v1.VolumeMount{
533+
Name: name,
534+
MountPath: mountPath,
535+
ReadOnly: readOnly,
536+
}
537+
t.pod.Spec.Containers[0].VolumeMounts = append(t.pod.Spec.Containers[0].VolumeMounts, volumeMount)
538+
539+
volume := v1.Volume{
540+
Name: name,
541+
VolumeSource: v1.VolumeSource{
542+
CSI: &v1.CSIVolumeSource{
543+
Driver: blob.DriverName,
544+
VolumeAttributes: map[string]string{
545+
"secretName": secretName,
546+
"secretNamespace": "default",
547+
"containerName": containerName,
548+
},
549+
ReadOnly: to.BoolPtr(readOnly),
550+
},
551+
},
552+
}
553+
t.pod.Spec.Volumes = append(t.pod.Spec.Volumes, volume)
554+
}
555+
530556
func (t *TestPod) SetNodeSelector(nodeSelector map[string]string) {
531557
t.pod.Spec.NodeSelector = nodeSelector
532558
}

0 commit comments

Comments
 (0)