github.com/containers/libpod@v1.9.4-0.20220419124438-4284fd425507/pkg/domain/infra/abi/pods.go (about)

     1  // +build ABISupport
     2  
     3  package abi
     4  
     5  import (
     6  	"context"
     7  
     8  	"github.com/containers/libpod/libpod"
     9  	"github.com/containers/libpod/libpod/define"
    10  	lpfilters "github.com/containers/libpod/libpod/filters"
    11  	"github.com/containers/libpod/pkg/domain/entities"
    12  	"github.com/containers/libpod/pkg/signal"
    13  	"github.com/containers/libpod/pkg/specgen"
    14  	"github.com/containers/libpod/pkg/specgen/generate"
    15  	"github.com/pkg/errors"
    16  	"github.com/sirupsen/logrus"
    17  )
    18  
    19  // getPodsByContext returns a slice of pods. Note that all, latest and pods are
    20  // mutually exclusive arguments.
    21  func getPodsByContext(all, latest bool, pods []string, runtime *libpod.Runtime) ([]*libpod.Pod, error) {
    22  	var outpods []*libpod.Pod
    23  	if all {
    24  		return runtime.GetAllPods()
    25  	}
    26  	if latest {
    27  		p, err := runtime.GetLatestPod()
    28  		if err != nil {
    29  			return nil, err
    30  		}
    31  		outpods = append(outpods, p)
    32  		return outpods, nil
    33  	}
    34  	var err error
    35  	for _, p := range pods {
    36  		pod, e := runtime.LookupPod(p)
    37  		if e != nil {
    38  			// Log all errors here, so callers don't need to.
    39  			logrus.Debugf("Error looking up pod %q: %v", p, e)
    40  			if err == nil {
    41  				err = e
    42  			}
    43  		} else {
    44  			outpods = append(outpods, pod)
    45  		}
    46  	}
    47  	return outpods, err
    48  }
    49  
    50  func (ic *ContainerEngine) PodExists(ctx context.Context, nameOrId string) (*entities.BoolReport, error) {
    51  	_, err := ic.Libpod.LookupPod(nameOrId)
    52  	if err != nil && errors.Cause(err) != define.ErrNoSuchPod {
    53  		return nil, err
    54  	}
    55  	return &entities.BoolReport{Value: err == nil}, nil
    56  }
    57  
    58  func (ic *ContainerEngine) PodKill(ctx context.Context, namesOrIds []string, options entities.PodKillOptions) ([]*entities.PodKillReport, error) {
    59  	var (
    60  		reports []*entities.PodKillReport
    61  	)
    62  	sig, err := signal.ParseSignalNameOrNumber(options.Signal)
    63  	if err != nil {
    64  		return nil, err
    65  	}
    66  	pods, err := getPodsByContext(options.All, options.Latest, namesOrIds, ic.Libpod)
    67  	if err != nil {
    68  		return nil, err
    69  	}
    70  
    71  	for _, p := range pods {
    72  		report := entities.PodKillReport{Id: p.ID()}
    73  		conErrs, err := p.Kill(uint(sig))
    74  		if err != nil {
    75  			report.Errs = []error{err}
    76  			reports = append(reports, &report)
    77  			continue
    78  		}
    79  		if len(conErrs) > 0 {
    80  			for _, err := range conErrs {
    81  				report.Errs = append(report.Errs, err)
    82  			}
    83  			reports = append(reports, &report)
    84  			continue
    85  		}
    86  		reports = append(reports, &report)
    87  	}
    88  	return reports, nil
    89  }
    90  
    91  func (ic *ContainerEngine) PodPause(ctx context.Context, namesOrIds []string, options entities.PodPauseOptions) ([]*entities.PodPauseReport, error) {
    92  	var (
    93  		reports []*entities.PodPauseReport
    94  	)
    95  	pods, err := getPodsByContext(options.All, options.Latest, namesOrIds, ic.Libpod)
    96  	if err != nil {
    97  		return nil, err
    98  	}
    99  	for _, p := range pods {
   100  		report := entities.PodPauseReport{Id: p.ID()}
   101  		errs, err := p.Pause()
   102  		if err != nil {
   103  			report.Errs = []error{err}
   104  			continue
   105  		}
   106  		if len(errs) > 0 {
   107  			for _, v := range errs {
   108  				report.Errs = append(report.Errs, v)
   109  			}
   110  			reports = append(reports, &report)
   111  			continue
   112  		}
   113  		reports = append(reports, &report)
   114  	}
   115  	return reports, nil
   116  }
   117  
   118  func (ic *ContainerEngine) PodUnpause(ctx context.Context, namesOrIds []string, options entities.PodunpauseOptions) ([]*entities.PodUnpauseReport, error) {
   119  	var (
   120  		reports []*entities.PodUnpauseReport
   121  	)
   122  	pods, err := getPodsByContext(options.All, options.Latest, namesOrIds, ic.Libpod)
   123  	if err != nil {
   124  		return nil, err
   125  	}
   126  	for _, p := range pods {
   127  		report := entities.PodUnpauseReport{Id: p.ID()}
   128  		errs, err := p.Unpause()
   129  		if err != nil {
   130  			report.Errs = []error{err}
   131  			continue
   132  		}
   133  		if len(errs) > 0 {
   134  			for _, v := range errs {
   135  				report.Errs = append(report.Errs, v)
   136  			}
   137  			reports = append(reports, &report)
   138  			continue
   139  		}
   140  		reports = append(reports, &report)
   141  	}
   142  	return reports, nil
   143  }
   144  
   145  func (ic *ContainerEngine) PodStop(ctx context.Context, namesOrIds []string, options entities.PodStopOptions) ([]*entities.PodStopReport, error) {
   146  	var (
   147  		reports []*entities.PodStopReport
   148  	)
   149  	pods, err := getPodsByContext(options.All, options.Latest, namesOrIds, ic.Libpod)
   150  	if err != nil {
   151  		return nil, err
   152  	}
   153  	for _, p := range pods {
   154  		report := entities.PodStopReport{Id: p.ID()}
   155  		errs, err := p.StopWithTimeout(ctx, false, options.Timeout)
   156  		if err != nil {
   157  			report.Errs = []error{err}
   158  			continue
   159  		}
   160  		if len(errs) > 0 {
   161  			for _, v := range errs {
   162  				report.Errs = append(report.Errs, v)
   163  			}
   164  			reports = append(reports, &report)
   165  			continue
   166  		}
   167  		reports = append(reports, &report)
   168  	}
   169  	return reports, nil
   170  }
   171  
   172  func (ic *ContainerEngine) PodRestart(ctx context.Context, namesOrIds []string, options entities.PodRestartOptions) ([]*entities.PodRestartReport, error) {
   173  	var (
   174  		reports []*entities.PodRestartReport
   175  	)
   176  	pods, err := getPodsByContext(options.All, options.Latest, namesOrIds, ic.Libpod)
   177  	if err != nil {
   178  		return nil, err
   179  	}
   180  	for _, p := range pods {
   181  		report := entities.PodRestartReport{Id: p.ID()}
   182  		errs, err := p.Restart(ctx)
   183  		if err != nil {
   184  			report.Errs = []error{err}
   185  			continue
   186  		}
   187  		if len(errs) > 0 {
   188  			for _, v := range errs {
   189  				report.Errs = append(report.Errs, v)
   190  			}
   191  			reports = append(reports, &report)
   192  			continue
   193  		}
   194  		reports = append(reports, &report)
   195  	}
   196  	return reports, nil
   197  }
   198  
   199  func (ic *ContainerEngine) PodStart(ctx context.Context, namesOrIds []string, options entities.PodStartOptions) ([]*entities.PodStartReport, error) {
   200  	var (
   201  		reports []*entities.PodStartReport
   202  	)
   203  	pods, err := getPodsByContext(options.All, options.Latest, namesOrIds, ic.Libpod)
   204  	if err != nil {
   205  		return nil, err
   206  	}
   207  	for _, p := range pods {
   208  		report := entities.PodStartReport{Id: p.ID()}
   209  		errs, err := p.Start(ctx)
   210  		if err != nil {
   211  			report.Errs = []error{err}
   212  			continue
   213  		}
   214  		if len(errs) > 0 {
   215  			for _, v := range errs {
   216  				report.Errs = append(report.Errs, v)
   217  			}
   218  			reports = append(reports, &report)
   219  			continue
   220  		}
   221  		reports = append(reports, &report)
   222  	}
   223  	return reports, nil
   224  }
   225  
   226  func (ic *ContainerEngine) PodRm(ctx context.Context, namesOrIds []string, options entities.PodRmOptions) ([]*entities.PodRmReport, error) {
   227  	var (
   228  		reports []*entities.PodRmReport
   229  	)
   230  	pods, err := getPodsByContext(options.All, options.Latest, namesOrIds, ic.Libpod)
   231  	if err != nil {
   232  		return nil, err
   233  	}
   234  	for _, p := range pods {
   235  		report := entities.PodRmReport{Id: p.ID()}
   236  		err := ic.Libpod.RemovePod(ctx, p, true, options.Force)
   237  		if err != nil {
   238  			report.Err = err
   239  			continue
   240  		}
   241  		reports = append(reports, &report)
   242  	}
   243  	return reports, nil
   244  }
   245  
   246  func (ic *ContainerEngine) PodCreate(ctx context.Context, opts entities.PodCreateOptions) (*entities.PodCreateReport, error) {
   247  	podSpec := specgen.NewPodSpecGenerator()
   248  	opts.ToPodSpecGen(podSpec)
   249  	pod, err := generate.MakePod(podSpec, ic.Libpod)
   250  	if err != nil {
   251  		return nil, err
   252  	}
   253  	return &entities.PodCreateReport{Id: pod.ID()}, nil
   254  }
   255  
   256  func (ic *ContainerEngine) PodTop(ctx context.Context, options entities.PodTopOptions) (*entities.StringSliceReport, error) {
   257  	var (
   258  		pod *libpod.Pod
   259  		err error
   260  	)
   261  
   262  	// Look up the pod.
   263  	if options.Latest {
   264  		pod, err = ic.Libpod.GetLatestPod()
   265  	} else {
   266  		pod, err = ic.Libpod.LookupPod(options.NameOrID)
   267  	}
   268  	if err != nil {
   269  		return nil, errors.Wrap(err, "unable to lookup requested container")
   270  	}
   271  
   272  	// Run Top.
   273  	report := &entities.StringSliceReport{}
   274  	report.Value, err = pod.GetPodPidInformation(options.Descriptors)
   275  	return report, err
   276  }
   277  
   278  func (ic *ContainerEngine) PodPs(ctx context.Context, options entities.PodPSOptions) ([]*entities.ListPodsReport, error) {
   279  	var (
   280  		filters []libpod.PodFilter
   281  		reports []*entities.ListPodsReport
   282  	)
   283  	for k, v := range options.Filters {
   284  		for _, filter := range v {
   285  			f, err := lpfilters.GeneratePodFilterFunc(k, filter)
   286  			if err != nil {
   287  				return nil, err
   288  			}
   289  			filters = append(filters, f)
   290  
   291  		}
   292  	}
   293  	pds, err := ic.Libpod.Pods(filters...)
   294  	if err != nil {
   295  		return nil, err
   296  	}
   297  	for _, p := range pds {
   298  		var lpcs []*entities.ListPodContainer
   299  		status, err := p.GetPodStatus()
   300  		if err != nil {
   301  			return nil, err
   302  		}
   303  		cons, err := p.AllContainers()
   304  		if err != nil {
   305  			return nil, err
   306  		}
   307  		for _, c := range cons {
   308  			state, err := c.State()
   309  			if err != nil {
   310  				return nil, err
   311  			}
   312  			lpcs = append(lpcs, &entities.ListPodContainer{
   313  				Id:     c.ID(),
   314  				Names:  c.Name(),
   315  				Status: state.String(),
   316  			})
   317  		}
   318  		infraId, err := p.InfraContainerID()
   319  		if err != nil {
   320  			return nil, err
   321  		}
   322  		reports = append(reports, &entities.ListPodsReport{
   323  			Cgroup:     p.CgroupParent(),
   324  			Containers: lpcs,
   325  			Created:    p.CreatedTime(),
   326  			Id:         p.ID(),
   327  			InfraId:    infraId,
   328  			Name:       p.Name(),
   329  			Namespace:  p.Namespace(),
   330  			Status:     status,
   331  		})
   332  	}
   333  	return reports, nil
   334  }
   335  
   336  func (ic *ContainerEngine) PodInspect(ctx context.Context, options entities.PodInspectOptions) (*entities.PodInspectReport, error) {
   337  	var (
   338  		pod *libpod.Pod
   339  		err error
   340  	)
   341  	// Look up the pod.
   342  	if options.Latest {
   343  		pod, err = ic.Libpod.GetLatestPod()
   344  	} else {
   345  		pod, err = ic.Libpod.LookupPod(options.NameOrID)
   346  	}
   347  	if err != nil {
   348  		return nil, errors.Wrap(err, "unable to lookup requested container")
   349  	}
   350  	inspect, err := pod.Inspect()
   351  	if err != nil {
   352  		return nil, err
   353  	}
   354  	return &entities.PodInspectReport{PodInspect: inspect}, nil
   355  }