mirror of
https://github.com/containers/podman
synced 2024-10-22 10:13:33 +00:00
bf0d359047
Given that we don't have a good way of cleaning up locks, these could potential cause issues if we ever reuse a container or pod ID Also changes locks dir to use tmpfs, as we can't directly clean up locks Signed-off-by: Matthew Heon <matthew.heon@gmail.com> Closes: #138 Approved by: rhatdan
163 lines
3.5 KiB
Go
163 lines
3.5 KiB
Go
package libpod
|
|
|
|
import (
|
|
"path/filepath"
|
|
|
|
"github.com/containers/storage"
|
|
"github.com/docker/docker/pkg/namesgenerator"
|
|
"github.com/docker/docker/pkg/stringid"
|
|
"github.com/pkg/errors"
|
|
)
|
|
|
|
// Pod represents a group of containers that may share namespaces
|
|
type Pod struct {
|
|
id string
|
|
name string
|
|
labels map[string]string
|
|
|
|
containers map[string]*Container
|
|
|
|
valid bool
|
|
lock storage.Locker
|
|
}
|
|
|
|
// ID retrieves the pod's ID
|
|
func (p *Pod) ID() string {
|
|
return p.id
|
|
}
|
|
|
|
// Name retrieves the pod's name
|
|
func (p *Pod) Name() string {
|
|
return p.name
|
|
}
|
|
|
|
// Labels returns the pod's labels
|
|
func (p *Pod) Labels() map[string]string {
|
|
labels := make(map[string]string)
|
|
for key, value := range p.labels {
|
|
labels[key] = value
|
|
}
|
|
|
|
return labels
|
|
}
|
|
|
|
// Creates a new, empty pod
|
|
func newPod(lockDir string) (*Pod, error) {
|
|
pod := new(Pod)
|
|
pod.id = stringid.GenerateNonCryptoID()
|
|
pod.name = namesgenerator.GetRandomName(0)
|
|
|
|
pod.containers = make(map[string]*Container)
|
|
|
|
// TODO: containers and pods share a locks folder, but not tables in the
|
|
// database
|
|
// As the locks are 256-bit pseudorandom integers, collision is unlikely
|
|
// But it's something worth looking into
|
|
|
|
// Path our lock file will reside at
|
|
lockPath := filepath.Join(lockDir, pod.id)
|
|
// Grab a lockfile at the given path
|
|
lock, err := storage.GetLockfile(lockPath)
|
|
if err != nil {
|
|
return nil, errors.Wrapf(err, "error creating lockfile for new pod")
|
|
}
|
|
pod.lock = lock
|
|
|
|
return pod, nil
|
|
}
|
|
|
|
// Adds a container to the pod
|
|
// Does not check that container's pod ID is set correctly, or attempt to set
|
|
// pod ID after adding
|
|
func (p *Pod) addContainer(ctr *Container) error {
|
|
p.lock.Lock()
|
|
defer p.lock.Unlock()
|
|
|
|
if !p.valid {
|
|
return ErrPodRemoved
|
|
}
|
|
|
|
if !ctr.valid {
|
|
return ErrCtrRemoved
|
|
}
|
|
|
|
if _, ok := p.containers[ctr.ID()]; ok {
|
|
return errors.Wrapf(ErrCtrExists, "container with ID %s already exists in pod %s", ctr.ID(), p.id)
|
|
}
|
|
|
|
p.containers[ctr.ID()] = ctr
|
|
|
|
return nil
|
|
}
|
|
|
|
// Removes a container from the pod
|
|
// Does not perform any checks on the container
|
|
func (p *Pod) removeContainer(ctr *Container) error {
|
|
p.lock.Lock()
|
|
defer p.lock.Unlock()
|
|
|
|
if !p.valid {
|
|
return ErrPodRemoved
|
|
}
|
|
|
|
if _, ok := p.containers[ctr.ID()]; !ok {
|
|
return errors.Wrapf(ErrNoSuchCtr, "no container with id %s in pod %s", ctr.ID(), p.id)
|
|
}
|
|
|
|
delete(p.containers, ctr.ID())
|
|
|
|
return nil
|
|
}
|
|
|
|
// Start starts all containers within a pod that are not already running
|
|
func (p *Pod) Start() error {
|
|
return ErrNotImplemented
|
|
}
|
|
|
|
// Stop stops all containers within a pod that are not already stopped
|
|
func (p *Pod) Stop() error {
|
|
return ErrNotImplemented
|
|
}
|
|
|
|
// Kill sends a signal to all running containers within a pod
|
|
func (p *Pod) Kill(signal uint) error {
|
|
return ErrNotImplemented
|
|
}
|
|
|
|
// HasContainer checks if a container is present in the pod
|
|
func (p *Pod) HasContainer(id string) (bool, error) {
|
|
p.lock.Lock()
|
|
defer p.lock.Unlock()
|
|
|
|
if !p.valid {
|
|
return false, ErrPodRemoved
|
|
}
|
|
|
|
_, ok := p.containers[id]
|
|
|
|
return ok, nil
|
|
}
|
|
|
|
// GetContainers retrieves the containers in the pod
|
|
func (p *Pod) GetContainers() ([]*Container, error) {
|
|
p.lock.Lock()
|
|
defer p.lock.Unlock()
|
|
|
|
if !p.valid {
|
|
return nil, ErrPodRemoved
|
|
}
|
|
|
|
ctrs := make([]*Container, 0, len(p.containers))
|
|
for _, ctr := range p.containers {
|
|
ctrs = append(ctrs, ctr)
|
|
}
|
|
|
|
return ctrs, nil
|
|
}
|
|
|
|
// Status gets the status of all containers in the pod
|
|
// TODO This should return a summary of the states of all containers in the pod
|
|
func (p *Pod) Status() error {
|
|
return ErrNotImplemented
|
|
}
|