mirror of
https://github.com/containers/podman.git
synced 2025-06-21 09:28:09 +08:00
Merge pull request #14556 from sstosh/system-prune-network
podman system prune support prune unused networks
This commit is contained in:
@ -75,6 +75,7 @@ func prune(cmd *cobra.Command, args []string) error {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Remove all unused pods, containers, images, networks, and volume data.
|
||||||
pruneOptions.Filters, err = parse.FilterArgumentsIntoFilters(filters)
|
pruneOptions.Filters, err = parse.FilterArgumentsIntoFilters(filters)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
@ -106,6 +107,11 @@ func prune(cmd *cobra.Command, args []string) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
// Print Network prune results
|
||||||
|
err = utils.PrintNetworkPruneResults(response.NetworkPruneReports, true)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
fmt.Printf("Total reclaimed space: %s\n", units.HumanSize((float64)(response.ReclaimedSpace)))
|
fmt.Printf("Total reclaimed space: %s\n", units.HumanSize((float64)(response.ReclaimedSpace)))
|
||||||
return nil
|
return nil
|
||||||
|
@ -84,3 +84,18 @@ func PrintImagePruneResults(imagePruneReports []*reports.PruneReport, heading bo
|
|||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func PrintNetworkPruneResults(networkPruneReport []*reports.PruneReport, heading bool) error {
|
||||||
|
var errs OutputErrors
|
||||||
|
if heading && len(networkPruneReport) > 0 {
|
||||||
|
fmt.Println("Deleted Networks")
|
||||||
|
}
|
||||||
|
for _, r := range networkPruneReport {
|
||||||
|
if r.Err == nil {
|
||||||
|
fmt.Println(r.Id)
|
||||||
|
} else {
|
||||||
|
errs = append(errs, r.Err)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return errs.PrintErrors()
|
||||||
|
}
|
||||||
|
@ -1,13 +1,13 @@
|
|||||||
% podman-system-prune(1)
|
% podman-system-prune(1)
|
||||||
|
|
||||||
## NAME
|
## NAME
|
||||||
podman\-system\-prune - Remove all unused pod, container, image and volume data
|
podman\-system\-prune - Remove all unused pods, containers, images, networks, and volume data
|
||||||
|
|
||||||
## SYNOPSIS
|
## SYNOPSIS
|
||||||
**podman system prune** [*options*]
|
**podman system prune** [*options*]
|
||||||
|
|
||||||
## DESCRIPTION
|
## DESCRIPTION
|
||||||
**podman system prune** removes all unused containers (both dangling and unreferenced), pods and optionally, volumes from local storage.
|
**podman system prune** removes all unused containers (both dangling and unreferenced), pods, networks, and optionally, volumes from local storage.
|
||||||
|
|
||||||
With the **--all** option, you can delete all unused images. Unused images are dangling images as well as any image that does not have any containers based on it.
|
With the **--all** option, you can delete all unused images. Unused images are dangling images as well as any image that does not have any containers based on it.
|
||||||
|
|
||||||
@ -16,7 +16,7 @@ By default, volumes are not removed to prevent important data from being deleted
|
|||||||
## OPTIONS
|
## OPTIONS
|
||||||
#### **--all**, **-a**
|
#### **--all**, **-a**
|
||||||
|
|
||||||
Recursively remove all unused pod, container, image and volume data (Maximum 50 iterations.)
|
Recursively remove all unused pods, containers, images, networks, and volume data. (Maximum 50 iterations.)
|
||||||
|
|
||||||
#### **--filter**=*filters*
|
#### **--filter**=*filters*
|
||||||
|
|
||||||
|
@ -12,12 +12,12 @@ The system command allows you to manage the podman systems
|
|||||||
## COMMANDS
|
## COMMANDS
|
||||||
|
|
||||||
| Command | Man Page | Description |
|
| Command | Man Page | Description |
|
||||||
| ------- | ------------------------------------------------------------ | -------------------------------------------------------------------- |
|
| ------- | ------------------------------------------------------------ | ------------------------------------------------------------------------ |
|
||||||
| connection | [podman-system-connection(1)](podman-system-connection.1.md) | Manage the destination(s) for Podman service(s) |
|
| connection | [podman-system-connection(1)](podman-system-connection.1.md) | Manage the destination(s) for Podman service(s) |
|
||||||
| df | [podman-system-df(1)](podman-system-df.1.md) | Show podman disk usage. |
|
| df | [podman-system-df(1)](podman-system-df.1.md) | Show podman disk usage. |
|
||||||
| info | [podman-system-info(1)](podman-info.1.md) | Displays Podman related system information. |
|
| info | [podman-system-info(1)](podman-info.1.md) | Displays Podman related system information. |
|
||||||
| migrate | [podman-system-migrate(1)](podman-system-migrate.1.md) | Migrate existing containers to a new podman version. |
|
| migrate | [podman-system-migrate(1)](podman-system-migrate.1.md) | Migrate existing containers to a new podman version. |
|
||||||
| prune | [podman-system-prune(1)](podman-system-prune.1.md) | Remove all unused pod, container, image and volume data. |
|
| prune | [podman-system-prune(1)](podman-system-prune.1.md) | Remove all unused pods, containers, images, networks, and volume data. |
|
||||||
| renumber | [podman-system-renumber(1)](podman-system-renumber.1.md) | Migrate lock numbers to handle a change in maximum number of locks. |
|
| renumber | [podman-system-renumber(1)](podman-system-renumber.1.md) | Migrate lock numbers to handle a change in maximum number of locks. |
|
||||||
| reset | [podman-system-reset(1)](podman-system-reset.1.md) | Reset storage back to initial state. |
|
| reset | [podman-system-reset(1)](podman-system-reset.1.md) | Reset storage back to initial state. |
|
||||||
| service | [podman-system-service(1)](podman-system-service.1.md) | Run an API service |
|
| service | [podman-system-service(1)](podman-system-service.1.md) | Run an API service |
|
||||||
|
@ -28,6 +28,7 @@ type SystemPruneReport struct {
|
|||||||
PodPruneReport []*PodPruneReport
|
PodPruneReport []*PodPruneReport
|
||||||
ContainerPruneReports []*reports.PruneReport
|
ContainerPruneReports []*reports.PruneReport
|
||||||
ImagePruneReports []*reports.PruneReport
|
ImagePruneReports []*reports.PruneReport
|
||||||
|
NetworkPruneReports []*reports.PruneReport
|
||||||
VolumePruneReports []*reports.PruneReport
|
VolumePruneReports []*reports.PruneReport
|
||||||
ReclaimedSpace uint64
|
ReclaimedSpace uint64
|
||||||
}
|
}
|
||||||
|
@ -142,7 +142,7 @@ func (ic *ContainerEngine) NetworkExists(ctx context.Context, networkname string
|
|||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// Network prune removes unused cni networks
|
// Network prune removes unused networks
|
||||||
func (ic *ContainerEngine) NetworkPrune(ctx context.Context, options entities.NetworkPruneOptions) ([]*entities.NetworkPruneReport, error) {
|
func (ic *ContainerEngine) NetworkPrune(ctx context.Context, options entities.NetworkPruneOptions) ([]*entities.NetworkPruneReport, error) {
|
||||||
cons, err := ic.Libpod.GetAllContainers()
|
cons, err := ic.Libpod.GetAllContainers()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -137,7 +137,7 @@ func (ic *ContainerEngine) SetupRootless(_ context.Context, noMoveProcess bool)
|
|||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// SystemPrune removes unused data from the system. Pruning pods, containers, volumes and images.
|
// SystemPrune removes unused data from the system. Pruning pods, containers, networks, volumes and images.
|
||||||
func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.SystemPruneOptions) (*entities.SystemPruneReport, error) {
|
func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.SystemPruneOptions) (*entities.SystemPruneReport, error) {
|
||||||
var systemPruneReport = new(entities.SystemPruneReport)
|
var systemPruneReport = new(entities.SystemPruneReport)
|
||||||
filters := []string{}
|
filters := []string{}
|
||||||
@ -148,6 +148,9 @@ func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.Sys
|
|||||||
found := true
|
found := true
|
||||||
for found {
|
for found {
|
||||||
found = false
|
found = false
|
||||||
|
|
||||||
|
// TODO: Figure out cleaner way to handle all of the different PruneOptions
|
||||||
|
// Remove all unused pods.
|
||||||
podPruneReport, err := ic.prunePodHelper(ctx)
|
podPruneReport, err := ic.prunePodHelper(ctx)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
@ -155,9 +158,10 @@ func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.Sys
|
|||||||
if len(podPruneReport) > 0 {
|
if len(podPruneReport) > 0 {
|
||||||
found = true
|
found = true
|
||||||
}
|
}
|
||||||
|
|
||||||
systemPruneReport.PodPruneReport = append(systemPruneReport.PodPruneReport, podPruneReport...)
|
systemPruneReport.PodPruneReport = append(systemPruneReport.PodPruneReport, podPruneReport...)
|
||||||
|
|
||||||
// TODO: Figure out cleaner way to handle all of the different PruneOptions
|
// Remove all unused containers.
|
||||||
containerPruneOptions := entities.ContainerPruneOptions{}
|
containerPruneOptions := entities.ContainerPruneOptions{}
|
||||||
containerPruneOptions.Filters = (url.Values)(options.Filters)
|
containerPruneOptions.Filters = (url.Values)(options.Filters)
|
||||||
|
|
||||||
@ -165,16 +169,18 @@ func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.Sys
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
|
|
||||||
reclaimedSpace += reports.PruneReportsSize(containerPruneReports)
|
reclaimedSpace += reports.PruneReportsSize(containerPruneReports)
|
||||||
systemPruneReport.ContainerPruneReports = append(systemPruneReport.ContainerPruneReports, containerPruneReports...)
|
systemPruneReport.ContainerPruneReports = append(systemPruneReport.ContainerPruneReports, containerPruneReports...)
|
||||||
|
|
||||||
|
// Remove all unused images.
|
||||||
imagePruneOptions := entities.ImagePruneOptions{
|
imagePruneOptions := entities.ImagePruneOptions{
|
||||||
All: options.All,
|
All: options.All,
|
||||||
Filter: filters,
|
Filter: filters,
|
||||||
}
|
}
|
||||||
|
|
||||||
imageEngine := ImageEngine{Libpod: ic.Libpod}
|
imageEngine := ImageEngine{Libpod: ic.Libpod}
|
||||||
imagePruneReports, err := imageEngine.Prune(ctx, imagePruneOptions)
|
imagePruneReports, err := imageEngine.Prune(ctx, imagePruneOptions)
|
||||||
reclaimedSpace += reports.PruneReportsSize(imagePruneReports)
|
|
||||||
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
}
|
}
|
||||||
@ -182,10 +188,33 @@ func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.Sys
|
|||||||
found = true
|
found = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
reclaimedSpace += reports.PruneReportsSize(imagePruneReports)
|
||||||
systemPruneReport.ImagePruneReports = append(systemPruneReport.ImagePruneReports, imagePruneReports...)
|
systemPruneReport.ImagePruneReports = append(systemPruneReport.ImagePruneReports, imagePruneReports...)
|
||||||
|
|
||||||
|
// Remove all unused networks.
|
||||||
|
networkPruneOptions := entities.NetworkPruneOptions{}
|
||||||
|
networkPruneOptions.Filters = options.Filters
|
||||||
|
|
||||||
|
networkPruneReport, err := ic.NetworkPrune(ctx, networkPruneOptions)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
if len(networkPruneReport) > 0 {
|
||||||
|
found = true
|
||||||
|
}
|
||||||
|
for _, net := range networkPruneReport {
|
||||||
|
systemPruneReport.NetworkPruneReports = append(systemPruneReport.NetworkPruneReports, &reports.PruneReport{
|
||||||
|
Id: net.Name,
|
||||||
|
Err: net.Error,
|
||||||
|
Size: 0,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
// Remove unused volume data.
|
||||||
if options.Volume {
|
if options.Volume {
|
||||||
volumePruneOptions := entities.VolumePruneOptions{}
|
volumePruneOptions := entities.VolumePruneOptions{}
|
||||||
volumePruneOptions.Filters = (url.Values)(options.Filters)
|
volumePruneOptions.Filters = (url.Values)(options.Filters)
|
||||||
|
|
||||||
volumePruneReport, err := ic.VolumePrune(ctx, volumePruneOptions)
|
volumePruneReport, err := ic.VolumePrune(ctx, volumePruneOptions)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
@ -193,6 +222,7 @@ func (ic *ContainerEngine) SystemPrune(ctx context.Context, options entities.Sys
|
|||||||
if len(volumePruneReport) > 0 {
|
if len(volumePruneReport) > 0 {
|
||||||
found = true
|
found = true
|
||||||
}
|
}
|
||||||
|
|
||||||
reclaimedSpace += reports.PruneReportsSize(volumePruneReport)
|
reclaimedSpace += reports.PruneReportsSize(volumePruneReport)
|
||||||
systemPruneReport.VolumePruneReports = append(systemPruneReport.VolumePruneReports, volumePruneReport...)
|
systemPruneReport.VolumePruneReports = append(systemPruneReport.VolumePruneReports, volumePruneReport...)
|
||||||
}
|
}
|
||||||
|
@ -258,6 +258,29 @@ var _ = Describe("Podman prune", func() {
|
|||||||
Expect(pods.OutputToStringArray()).To(HaveLen(2))
|
Expect(pods.OutputToStringArray()).To(HaveLen(2))
|
||||||
})
|
})
|
||||||
|
|
||||||
|
It("podman system prune networks", func() {
|
||||||
|
// About netavark network backend test.
|
||||||
|
session := podmanTest.Podman([]string{"network", "create", "test"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
|
||||||
|
session = podmanTest.Podman([]string{"system", "prune", "-f"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
|
||||||
|
// Default network should exists.
|
||||||
|
session = podmanTest.Podman([]string{"network", "ls", "-q", "--filter", "name=^podman$"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
Expect(session.OutputToStringArray()).To(HaveLen(1))
|
||||||
|
|
||||||
|
// Remove all unused networks.
|
||||||
|
session = podmanTest.Podman([]string{"network", "ls", "-q", "--filter", "name=^test$"})
|
||||||
|
session.WaitWithDefaultTimeout()
|
||||||
|
Expect(session).Should(Exit(0))
|
||||||
|
Expect(session.OutputToStringArray()).To(HaveLen(0))
|
||||||
|
})
|
||||||
|
|
||||||
It("podman system prune - pod,container stopped", func() {
|
It("podman system prune - pod,container stopped", func() {
|
||||||
session := podmanTest.Podman([]string{"pod", "create"})
|
session := podmanTest.Podman([]string{"pod", "create"})
|
||||||
session.WaitWithDefaultTimeout()
|
session.WaitWithDefaultTimeout()
|
||||||
|
Reference in New Issue
Block a user