2017-11-13 23:31:36 +00:00
|
|
|
/*
|
2020-08-18 19:16:26 +00:00
|
|
|
Copyright 2020 the Velero contributors.
|
2017-11-13 23:31:36 +00:00
|
|
|
|
|
|
|
Licensed under the Apache License, Version 2.0 (the "License");
|
|
|
|
you may not use this file except in compliance with the License.
|
|
|
|
You may obtain a copy of the License at
|
|
|
|
|
|
|
|
http://www.apache.org/licenses/LICENSE-2.0
|
|
|
|
|
|
|
|
Unless required by applicable law or agreed to in writing, software
|
|
|
|
distributed under the License is distributed on an "AS IS" BASIS,
|
|
|
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
|
|
See the License for the specific language governing permissions and
|
|
|
|
limitations under the License.
|
|
|
|
*/
|
|
|
|
|
2019-03-15 18:32:11 +00:00
|
|
|
package clientmgmt
|
2017-11-13 23:31:36 +00:00
|
|
|
|
|
|
|
import (
|
2019-04-12 19:24:38 +00:00
|
|
|
"strings"
|
2018-05-13 13:28:09 +00:00
|
|
|
"sync"
|
|
|
|
|
2021-11-16 21:13:31 +00:00
|
|
|
v1 "github.com/vmware-tanzu/velero/pkg/plugin/velero/item_snapshotter/v1"
|
|
|
|
|
2017-11-13 23:31:36 +00:00
|
|
|
"github.com/sirupsen/logrus"
|
|
|
|
|
2019-09-30 21:26:56 +00:00
|
|
|
"github.com/vmware-tanzu/velero/pkg/plugin/framework"
|
|
|
|
"github.com/vmware-tanzu/velero/pkg/plugin/velero"
|
2017-11-13 23:31:36 +00:00
|
|
|
)
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// Manager manages the lifecycles of plugins.
|
|
|
|
type Manager interface {
|
|
|
|
// GetObjectStore returns the ObjectStore plugin for name.
|
2019-03-14 20:35:06 +00:00
|
|
|
GetObjectStore(name string) (velero.ObjectStore, error)
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2019-03-27 18:22:04 +00:00
|
|
|
// GetVolumeSnapshotter returns the VolumeSnapshotter plugin for name.
|
|
|
|
GetVolumeSnapshotter(name string) (velero.VolumeSnapshotter, error)
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetBackupItemActions returns all backup item action plugins.
|
2019-03-14 20:35:06 +00:00
|
|
|
GetBackupItemActions() ([]velero.BackupItemAction, error)
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetBackupItemAction returns the backup item action plugin for name.
|
2019-03-14 20:35:06 +00:00
|
|
|
GetBackupItemAction(name string) (velero.BackupItemAction, error)
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetRestoreItemActions returns all restore item action plugins.
|
2019-03-14 20:35:06 +00:00
|
|
|
GetRestoreItemActions() ([]velero.RestoreItemAction, error)
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetRestoreItemAction returns the restore item action plugin for name.
|
2019-03-14 20:35:06 +00:00
|
|
|
GetRestoreItemAction(name string) (velero.RestoreItemAction, error)
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2020-08-18 19:16:26 +00:00
|
|
|
// GetDeleteItemActions returns all delete item action plugins.
|
|
|
|
GetDeleteItemActions() ([]velero.DeleteItemAction, error)
|
|
|
|
|
|
|
|
// GetDeleteItemAction returns the delete item action plugin for name.
|
|
|
|
GetDeleteItemAction(name string) (velero.DeleteItemAction, error)
|
|
|
|
|
2021-11-16 21:13:31 +00:00
|
|
|
// GetItemSnapshotter returns the item snapshotter plugin for name
|
|
|
|
GetItemSnapshotter(name string) (v1.ItemSnapshotter, error)
|
|
|
|
|
|
|
|
// GetItemSnapshotters returns all item snapshotter plugins
|
|
|
|
GetItemSnapshotters() ([]v1.ItemSnapshotter, error)
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// CleanupClients terminates all of the Manager's running plugin processes.
|
2018-05-11 16:26:15 +00:00
|
|
|
CleanupClients()
|
2017-11-13 23:31:36 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// manager implements Manager.
|
2017-11-13 23:31:36 +00:00
|
|
|
type manager struct {
|
2018-05-13 13:28:09 +00:00
|
|
|
logger logrus.FieldLogger
|
|
|
|
logLevel logrus.Level
|
|
|
|
registry Registry
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
restartableProcessFactory RestartableProcessFactory
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// lock guards restartableProcesses
|
|
|
|
lock sync.Mutex
|
|
|
|
restartableProcesses map[string]RestartableProcess
|
2017-11-13 23:31:36 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// NewManager constructs a manager for getting plugins.
|
|
|
|
func NewManager(logger logrus.FieldLogger, level logrus.Level, registry Registry) Manager {
|
|
|
|
return &manager{
|
|
|
|
logger: logger,
|
|
|
|
logLevel: level,
|
|
|
|
registry: registry,
|
|
|
|
|
|
|
|
restartableProcessFactory: newRestartableProcessFactory(),
|
|
|
|
|
|
|
|
restartableProcesses: make(map[string]RestartableProcess),
|
2017-11-13 23:31:36 +00:00
|
|
|
}
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
func (m *manager) CleanupClients() {
|
|
|
|
m.lock.Lock()
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
for _, restartableProcess := range m.restartableProcesses {
|
|
|
|
restartableProcess.stop()
|
2017-11-13 23:31:36 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
m.lock.Unlock()
|
2017-11-13 23:31:36 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// getRestartableProcess returns a restartableProcess for a plugin identified by kind and name, creating a
|
|
|
|
// restartableProcess if it is the first time it has been requested.
|
2019-03-15 01:25:52 +00:00
|
|
|
func (m *manager) getRestartableProcess(kind framework.PluginKind, name string) (RestartableProcess, error) {
|
2018-05-13 13:28:09 +00:00
|
|
|
m.lock.Lock()
|
|
|
|
defer m.lock.Unlock()
|
2018-02-27 19:32:45 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
logger := m.logger.WithFields(logrus.Fields{
|
2022-04-11 13:43:16 +00:00
|
|
|
"kind": kind.String(),
|
2018-05-13 13:28:09 +00:00
|
|
|
"name": name,
|
|
|
|
})
|
|
|
|
logger.Debug("looking for plugin in registry")
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
info, err := m.registry.Get(kind, name)
|
2017-11-15 02:35:02 +00:00
|
|
|
if err != nil {
|
2018-05-13 13:28:09 +00:00
|
|
|
return nil, err
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
logger = logger.WithField("command", info.Command)
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
restartableProcess, found := m.restartableProcesses[info.Command]
|
|
|
|
if found {
|
|
|
|
logger.Debug("found preexisting restartable plugin process")
|
|
|
|
return restartableProcess, nil
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
logger.Debug("creating new restartable plugin process")
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
restartableProcess, err = m.restartableProcessFactory.newRestartableProcess(info.Command, m.logger, m.logLevel)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
m.restartableProcesses[info.Command] = restartableProcess
|
|
|
|
|
|
|
|
return restartableProcess, nil
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetObjectStore returns a restartableObjectStore for name.
|
2019-03-14 20:35:06 +00:00
|
|
|
func (m *manager) GetObjectStore(name string) (velero.ObjectStore, error) {
|
2020-12-15 00:52:52 +00:00
|
|
|
name = sanitizeName(name)
|
|
|
|
|
2019-03-15 01:25:52 +00:00
|
|
|
restartableProcess, err := m.getRestartableProcess(framework.PluginKindObjectStore, name)
|
2017-11-13 23:31:36 +00:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
r := newRestartableObjectStore(name, restartableProcess)
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
return r, nil
|
2017-11-13 23:31:36 +00:00
|
|
|
}
|
|
|
|
|
2019-03-27 18:22:04 +00:00
|
|
|
// GetVolumeSnapshotter returns a restartableVolumeSnapshotter for name.
|
|
|
|
func (m *manager) GetVolumeSnapshotter(name string) (velero.VolumeSnapshotter, error) {
|
2020-12-15 00:52:52 +00:00
|
|
|
name = sanitizeName(name)
|
|
|
|
|
2019-03-27 18:22:04 +00:00
|
|
|
restartableProcess, err := m.getRestartableProcess(framework.PluginKindVolumeSnapshotter, name)
|
2017-11-13 23:31:36 +00:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2019-03-27 18:22:04 +00:00
|
|
|
r := newRestartableVolumeSnapshotter(name, restartableProcess)
|
2017-11-13 23:31:36 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
return r, nil
|
2017-11-13 23:31:36 +00:00
|
|
|
}
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetBackupItemActions returns all backup item actions as restartableBackupItemActions.
|
2019-03-14 20:35:06 +00:00
|
|
|
func (m *manager) GetBackupItemActions() ([]velero.BackupItemAction, error) {
|
2019-03-15 01:25:52 +00:00
|
|
|
list := m.registry.List(framework.PluginKindBackupItemAction)
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2019-03-14 20:35:06 +00:00
|
|
|
actions := make([]velero.BackupItemAction, 0, len(list))
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
for i := range list {
|
|
|
|
id := list[i]
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
r, err := m.GetBackupItemAction(id.Name)
|
2017-11-15 02:35:02 +00:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
actions = append(actions, r)
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
return actions, nil
|
|
|
|
}
|
2017-11-15 02:35:02 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetBackupItemAction returns a restartableBackupItemAction for name.
|
2019-03-14 20:35:06 +00:00
|
|
|
func (m *manager) GetBackupItemAction(name string) (velero.BackupItemAction, error) {
|
2020-12-15 00:52:52 +00:00
|
|
|
name = sanitizeName(name)
|
|
|
|
|
2019-03-15 01:25:52 +00:00
|
|
|
restartableProcess, err := m.getRestartableProcess(framework.PluginKindBackupItemAction, name)
|
2018-05-13 13:28:09 +00:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
r := newRestartableBackupItemAction(name, restartableProcess)
|
|
|
|
return r, nil
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetRestoreItemActions returns all restore item actions as restartableRestoreItemActions.
|
2019-03-14 20:35:06 +00:00
|
|
|
func (m *manager) GetRestoreItemActions() ([]velero.RestoreItemAction, error) {
|
2019-03-15 01:25:52 +00:00
|
|
|
list := m.registry.List(framework.PluginKindRestoreItemAction)
|
2017-11-21 17:24:43 +00:00
|
|
|
|
2019-03-14 20:35:06 +00:00
|
|
|
actions := make([]velero.RestoreItemAction, 0, len(list))
|
2017-11-21 17:24:43 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
for i := range list {
|
|
|
|
id := list[i]
|
2017-11-21 17:24:43 +00:00
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
r, err := m.GetRestoreItemAction(id.Name)
|
2017-11-21 17:24:43 +00:00
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
actions = append(actions, r)
|
2017-11-21 17:24:43 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
return actions, nil
|
2017-11-21 17:24:43 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
// GetRestoreItemAction returns a restartableRestoreItemAction for name.
|
2019-03-14 20:35:06 +00:00
|
|
|
func (m *manager) GetRestoreItemAction(name string) (velero.RestoreItemAction, error) {
|
2020-12-15 00:52:52 +00:00
|
|
|
name = sanitizeName(name)
|
|
|
|
|
2019-03-15 01:25:52 +00:00
|
|
|
restartableProcess, err := m.getRestartableProcess(framework.PluginKindRestoreItemAction, name)
|
2017-11-15 02:35:02 +00:00
|
|
|
if err != nil {
|
2018-05-13 13:28:09 +00:00
|
|
|
return nil, err
|
2017-11-15 02:35:02 +00:00
|
|
|
}
|
|
|
|
|
2018-05-13 13:28:09 +00:00
|
|
|
r := newRestartableRestoreItemAction(name, restartableProcess)
|
|
|
|
return r, nil
|
2018-05-11 16:26:15 +00:00
|
|
|
}
|
2020-08-18 19:16:26 +00:00
|
|
|
|
|
|
|
// GetDeleteItemActions returns all delete item actions as restartableDeleteItemActions.
|
|
|
|
func (m *manager) GetDeleteItemActions() ([]velero.DeleteItemAction, error) {
|
|
|
|
list := m.registry.List(framework.PluginKindDeleteItemAction)
|
|
|
|
|
|
|
|
actions := make([]velero.DeleteItemAction, 0, len(list))
|
|
|
|
|
|
|
|
for i := range list {
|
|
|
|
id := list[i]
|
|
|
|
|
|
|
|
r, err := m.GetDeleteItemAction(id.Name)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
actions = append(actions, r)
|
|
|
|
}
|
|
|
|
|
|
|
|
return actions, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
// GetDeleteItemAction returns a restartableDeleteItemAction for name.
|
|
|
|
func (m *manager) GetDeleteItemAction(name string) (velero.DeleteItemAction, error) {
|
2020-12-15 00:52:52 +00:00
|
|
|
name = sanitizeName(name)
|
|
|
|
|
2020-08-18 19:16:26 +00:00
|
|
|
restartableProcess, err := m.getRestartableProcess(framework.PluginKindDeleteItemAction, name)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
r := newRestartableDeleteItemAction(name, restartableProcess)
|
|
|
|
return r, nil
|
|
|
|
}
|
2020-12-15 00:52:52 +00:00
|
|
|
|
2021-11-16 21:13:31 +00:00
|
|
|
func (m *manager) GetItemSnapshotter(name string) (v1.ItemSnapshotter, error) {
|
|
|
|
name = sanitizeName(name)
|
|
|
|
|
|
|
|
restartableProcess, err := m.getRestartableProcess(framework.PluginKindItemSnapshotter, name)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
r := newRestartableItemSnapshotter(name, restartableProcess)
|
|
|
|
return r, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (m *manager) GetItemSnapshotters() ([]v1.ItemSnapshotter, error) {
|
|
|
|
list := m.registry.List(framework.PluginKindItemSnapshotter)
|
|
|
|
|
|
|
|
actions := make([]v1.ItemSnapshotter, 0, len(list))
|
|
|
|
|
|
|
|
for i := range list {
|
|
|
|
id := list[i]
|
|
|
|
|
|
|
|
r, err := m.GetItemSnapshotter(id.Name)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
actions = append(actions, r)
|
|
|
|
}
|
|
|
|
|
|
|
|
return actions, nil
|
|
|
|
}
|
|
|
|
|
2020-12-15 00:52:52 +00:00
|
|
|
// sanitizeName adds "velero.io" to legacy plugins that weren't namespaced.
|
|
|
|
func sanitizeName(name string) string {
|
|
|
|
// Backwards compatibility with non-namespaced Velero plugins, following principle of least surprise
|
|
|
|
// since DeleteItemActions were not bundled with Velero when plugins were non-namespaced.
|
|
|
|
if !strings.Contains(name, "/") {
|
|
|
|
name = "velero.io/" + name
|
|
|
|
}
|
|
|
|
|
|
|
|
return name
|
|
|
|
}
|