...
1
16
17 package storageobjectinuseprotection
18
19 import (
20 "context"
21 "io"
22
23 "k8s.io/apiserver/pkg/admission"
24 "k8s.io/klog/v2"
25 api "k8s.io/kubernetes/pkg/apis/core"
26 volumeutil "k8s.io/kubernetes/pkg/volume/util"
27 )
28
29 const (
30
31 PluginName = "StorageObjectInUseProtection"
32 )
33
34
35 func Register(plugins *admission.Plugins) {
36 plugins.Register(PluginName, func(config io.Reader) (admission.Interface, error) {
37 plugin := newPlugin()
38 return plugin, nil
39 })
40 }
41
42
43 type storageProtectionPlugin struct {
44 *admission.Handler
45 }
46
47 var _ admission.Interface = &storageProtectionPlugin{}
48
49
50 func newPlugin() *storageProtectionPlugin {
51 return &storageProtectionPlugin{
52 Handler: admission.NewHandler(admission.Create),
53 }
54 }
55
56 var (
57 pvResource = api.Resource("persistentvolumes")
58 pvcResource = api.Resource("persistentvolumeclaims")
59 )
60
61
62
63
64
65
66 func (c *storageProtectionPlugin) Admit(ctx context.Context, a admission.Attributes, o admission.ObjectInterfaces) error {
67 switch a.GetResource().GroupResource() {
68 case pvResource:
69 return c.admitPV(a)
70 case pvcResource:
71 return c.admitPVC(a)
72
73 default:
74 return nil
75 }
76 }
77
78 func (c *storageProtectionPlugin) admitPV(a admission.Attributes) error {
79 if len(a.GetSubresource()) != 0 {
80 return nil
81 }
82
83 pv, ok := a.GetObject().(*api.PersistentVolume)
84
85 if !ok {
86 return nil
87 }
88 for _, f := range pv.Finalizers {
89 if f == volumeutil.PVProtectionFinalizer {
90
91 return nil
92 }
93 }
94 klog.V(4).Infof("adding PV protection finalizer to %s", pv.Name)
95 pv.Finalizers = append(pv.Finalizers, volumeutil.PVProtectionFinalizer)
96
97 return nil
98 }
99
100 func (c *storageProtectionPlugin) admitPVC(a admission.Attributes) error {
101 if len(a.GetSubresource()) != 0 {
102 return nil
103 }
104
105 pvc, ok := a.GetObject().(*api.PersistentVolumeClaim)
106
107 if !ok {
108 return nil
109 }
110
111 for _, f := range pvc.Finalizers {
112 if f == volumeutil.PVCProtectionFinalizer {
113
114 return nil
115 }
116 }
117
118 klog.V(4).Infof("adding PVC protection finalizer to %s/%s", pvc.Namespace, pvc.Name)
119 pvc.Finalizers = append(pvc.Finalizers, volumeutil.PVCProtectionFinalizer)
120 return nil
121 }
122
View as plain text