mirror of
https://github.com/kubevirt/containerized-data-importer.git
synced 2025-06-03 06:30:22 +00:00

* update k8s deps to 1.18.6 and controller runtime to 0.6.2 Signed-off-by: Michael Henriksen <mhenriks@redhat.com> * remove building code generators from docker image. This way the k8s ligray version only has to be updated in go.mod Do more stuff in the bazel container. Faster and better interop Fix unit tests Signed-off-by: Michael Henriksen <mhenriks@redhat.com> * make format Signed-off-by: Michael Henriksen <mhenriks@redhat.com> * remove unnecessary rsync Signed-off-by: Michael Henriksen <mhenriks@redhat.com> * redo code generator dep management Signed-off-by: Michael Henriksen <mhenriks@redhat.com> * builder uses go modules Signed-off-by: Michael Henriksen <mhenriks@redhat.com>
216 lines
5.8 KiB
Go
216 lines
5.8 KiB
Go
package tests
|
|
|
|
import (
|
|
"context"
|
|
"fmt"
|
|
"time"
|
|
|
|
. "github.com/onsi/ginkgo"
|
|
. "github.com/onsi/ginkgo/extensions/table"
|
|
. "github.com/onsi/gomega"
|
|
|
|
corev1 "k8s.io/api/core/v1"
|
|
rbacv1 "k8s.io/api/rbac/v1"
|
|
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
|
"k8s.io/client-go/kubernetes"
|
|
|
|
"kubevirt.io/containerized-data-importer/pkg/clone"
|
|
"kubevirt.io/containerized-data-importer/tests/framework"
|
|
"kubevirt.io/containerized-data-importer/tests/utils"
|
|
)
|
|
|
|
var _ = Describe("Clone Auth Webhook tests", func() {
|
|
const serviceAccountName = "cdi-auth-webhook-test"
|
|
|
|
var cdiRole = &rbacv1.Role{
|
|
ObjectMeta: metav1.ObjectMeta{
|
|
Name: "explicit-role",
|
|
},
|
|
Rules: []rbacv1.PolicyRule{
|
|
{
|
|
APIGroups: []string{
|
|
"cdi.kubevirt.io",
|
|
},
|
|
Resources: []string{
|
|
"datavolumes",
|
|
},
|
|
Verbs: []string{
|
|
"*",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
|
|
var explicitRole = &rbacv1.Role{
|
|
ObjectMeta: metav1.ObjectMeta{
|
|
Name: "explicit-role",
|
|
},
|
|
Rules: []rbacv1.PolicyRule{
|
|
{
|
|
APIGroups: []string{
|
|
"cdi.kubevirt.io",
|
|
},
|
|
Resources: []string{
|
|
"datavolumes",
|
|
"datavolumes/source",
|
|
},
|
|
Verbs: []string{
|
|
"*",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
|
|
var implicitRole = &rbacv1.Role{
|
|
ObjectMeta: metav1.ObjectMeta{
|
|
Name: "implicit-role",
|
|
},
|
|
Rules: []rbacv1.PolicyRule{
|
|
{
|
|
APIGroups: []string{
|
|
"cdi.kubevirt.io",
|
|
},
|
|
Resources: []string{
|
|
"datavolumes",
|
|
},
|
|
Verbs: []string{
|
|
"*",
|
|
},
|
|
},
|
|
{
|
|
APIGroups: []string{
|
|
"",
|
|
},
|
|
Resources: []string{
|
|
"pods",
|
|
},
|
|
Verbs: []string{
|
|
"create",
|
|
},
|
|
},
|
|
},
|
|
}
|
|
|
|
var createServiceAccount = func(client kubernetes.Interface, namespace, name string) {
|
|
sa := &corev1.ServiceAccount{
|
|
ObjectMeta: metav1.ObjectMeta{
|
|
Name: name,
|
|
},
|
|
}
|
|
|
|
_, err := client.CoreV1().ServiceAccounts(namespace).Create(context.TODO(), sa, metav1.CreateOptions{})
|
|
Expect(err).ToNot(HaveOccurred())
|
|
}
|
|
|
|
var addPermissionToNamespace = func(client kubernetes.Interface, role *rbacv1.Role, saNamespace, sa, targetNamesace string) {
|
|
_, err := client.RbacV1().Roles(targetNamesace).Create(context.TODO(), role, metav1.CreateOptions{})
|
|
Expect(err).ToNot(HaveOccurred())
|
|
|
|
rb := &rbacv1.RoleBinding{
|
|
ObjectMeta: metav1.ObjectMeta{
|
|
Name: sa,
|
|
},
|
|
RoleRef: rbacv1.RoleRef{
|
|
Kind: "Role",
|
|
Name: role.Name,
|
|
APIGroup: "rbac.authorization.k8s.io",
|
|
},
|
|
Subjects: []rbacv1.Subject{
|
|
{
|
|
Kind: "ServiceAccount",
|
|
Name: sa,
|
|
Namespace: saNamespace,
|
|
},
|
|
},
|
|
}
|
|
|
|
_, err = client.RbacV1().RoleBindings(targetNamesace).Create(context.TODO(), rb, metav1.CreateOptions{})
|
|
Expect(err).ToNot(HaveOccurred())
|
|
}
|
|
|
|
f := framework.NewFramework("clone-auth-webhook-test")
|
|
|
|
Describe("Verify DataVolume validation", func() {
|
|
Context("Authorization checks", func() {
|
|
var err error
|
|
var targetNamespace *corev1.Namespace
|
|
|
|
BeforeEach(func() {
|
|
targetNamespace, err = f.CreateNamespace("cdi-auth-webhook-test", nil)
|
|
Expect(err).ToNot(HaveOccurred())
|
|
|
|
createServiceAccount(f.K8sClient, targetNamespace.Name, serviceAccountName)
|
|
|
|
addPermissionToNamespace(f.K8sClient, cdiRole, targetNamespace.Name, serviceAccountName, targetNamespace.Name)
|
|
})
|
|
|
|
AfterEach(func() {
|
|
if targetNamespace != nil {
|
|
err = f.K8sClient.CoreV1().Namespaces().Delete(context.TODO(), targetNamespace.Name, metav1.DeleteOptions{})
|
|
Expect(err).ToNot(HaveOccurred())
|
|
}
|
|
})
|
|
|
|
DescribeTable("should deny/allow user when creating datavolume", func(role *rbacv1.Role) {
|
|
srcPVCDef := utils.NewPVCDefinition("source-pvc", "1G", nil, nil)
|
|
srcPVCDef.Namespace = f.Namespace.Name
|
|
f.CreateAndPopulateSourcePVC(srcPVCDef, "fill-source", fmt.Sprintf("echo \"hello world\" > %s/data.txt", utils.DefaultPvcMountPath))
|
|
|
|
targetDV := utils.NewCloningDataVolume("target-dv", "1G", srcPVCDef)
|
|
|
|
client, err := f.GetCdiClientForServiceAccount(targetNamespace.Name, serviceAccountName)
|
|
Expect(err).ToNot(HaveOccurred())
|
|
|
|
// can't list dvs in source
|
|
_, err = client.CdiV1beta1().DataVolumes(f.Namespace.Name).List(context.TODO(), metav1.ListOptions{})
|
|
Expect(err).To(HaveOccurred())
|
|
|
|
// can list dvs in dest
|
|
_, err = client.CdiV1beta1().DataVolumes(targetNamespace.Name).List(context.TODO(), metav1.ListOptions{})
|
|
Expect(err).ToNot(HaveOccurred())
|
|
|
|
// can't create clone of dv in source
|
|
_, err = client.CdiV1beta1().DataVolumes(targetNamespace.Name).Create(context.TODO(), targetDV, metav1.CreateOptions{})
|
|
Expect(err).To(HaveOccurred())
|
|
|
|
// let's do manual check as well
|
|
allowed, reason, err := clone.CanServiceAccountClonePVC(f.K8sClient,
|
|
srcPVCDef.Namespace,
|
|
srcPVCDef.Name,
|
|
targetNamespace.Name,
|
|
serviceAccountName,
|
|
)
|
|
Expect(allowed).To(BeFalse())
|
|
Expect(reason).ToNot(BeEmpty())
|
|
Expect(err).ToNot(HaveOccurred())
|
|
|
|
addPermissionToNamespace(f.K8sClient, role, targetNamespace.Name, serviceAccountName, f.Namespace.Name)
|
|
|
|
// now can list dvs in source
|
|
Eventually(func() error {
|
|
_, err = client.CdiV1beta1().DataVolumes(f.Namespace.Name).List(context.TODO(), metav1.ListOptions{})
|
|
return err
|
|
}, 60*time.Second, 2*time.Second).ShouldNot(HaveOccurred())
|
|
|
|
// now can create clone of dv in source
|
|
_, err = client.CdiV1beta1().DataVolumes(targetNamespace.Name).Create(context.TODO(), targetDV, metav1.CreateOptions{})
|
|
Expect(err).ToNot(HaveOccurred())
|
|
|
|
// let's do another manual check as well
|
|
allowed, reason, err = clone.CanServiceAccountClonePVC(f.K8sClient,
|
|
srcPVCDef.Namespace,
|
|
srcPVCDef.Name,
|
|
targetNamespace.Name,
|
|
serviceAccountName,
|
|
)
|
|
Expect(allowed).To(BeTrue())
|
|
Expect(reason).To(BeEmpty())
|
|
Expect(err).ToNot(HaveOccurred())
|
|
},
|
|
Entry("[test_id:3935]when using explicit CDI permissions", explicitRole),
|
|
Entry("[test_id:3936]when using implicit CDI permissions", implicitRole),
|
|
)
|
|
})
|
|
})
|
|
})
|