github.com/docker/docker@v299999999.0.0-20200612211812-aaf470eca7b5+incompatible/daemon/network/filter.go (about)

     1  package network // import "github.com/docker/docker/daemon/network"
     2  
     3  import (
     4  	"github.com/docker/docker/api/types"
     5  	"github.com/docker/docker/api/types/filters"
     6  	"github.com/docker/docker/errdefs"
     7  	"github.com/docker/docker/runconfig"
     8  	"github.com/pkg/errors"
     9  )
    10  
    11  // FilterNetworks filters network list according to user specified filter
    12  // and returns user chosen networks
    13  func FilterNetworks(nws []types.NetworkResource, filter filters.Args) ([]types.NetworkResource, error) {
    14  	// if filter is empty, return original network list
    15  	if filter.Len() == 0 {
    16  		return nws, nil
    17  	}
    18  
    19  	displayNet := nws[:0]
    20  	for _, nw := range nws {
    21  		if filter.Contains("driver") {
    22  			if !filter.ExactMatch("driver", nw.Driver) {
    23  				continue
    24  			}
    25  		}
    26  		if filter.Contains("name") {
    27  			if !filter.Match("name", nw.Name) {
    28  				continue
    29  			}
    30  		}
    31  		if filter.Contains("id") {
    32  			if !filter.Match("id", nw.ID) {
    33  				continue
    34  			}
    35  		}
    36  		if filter.Contains("label") {
    37  			if !filter.MatchKVList("label", nw.Labels) {
    38  				continue
    39  			}
    40  		}
    41  		if filter.Contains("scope") {
    42  			if !filter.ExactMatch("scope", nw.Scope) {
    43  				continue
    44  			}
    45  		}
    46  
    47  		if filter.Contains("idOrName") {
    48  			if !filter.Match("name", nw.Name) && !filter.Match("id", nw.Name) {
    49  				continue
    50  			}
    51  		}
    52  		displayNet = append(displayNet, nw)
    53  	}
    54  
    55  	if values := filter.Get("dangling"); len(values) > 0 {
    56  		if len(values) > 1 {
    57  			return nil, errdefs.InvalidParameter(errors.New(`got more than one value for filter key "dangling"`))
    58  		}
    59  
    60  		var danglingOnly bool
    61  		switch values[0] {
    62  		case "0", "false":
    63  			// dangling is false already
    64  		case "1", "true":
    65  			danglingOnly = true
    66  		default:
    67  			return nil, errdefs.InvalidParameter(errors.New(`invalid value for filter 'dangling', must be "true" (or "1"), or "false" (or "0")`))
    68  		}
    69  
    70  		displayNet = filterNetworkByUse(displayNet, danglingOnly)
    71  	}
    72  
    73  	if filter.Contains("type") {
    74  		typeNet := []types.NetworkResource{}
    75  		errFilter := filter.WalkValues("type", func(fval string) error {
    76  			passList, err := filterNetworkByType(displayNet, fval)
    77  			if err != nil {
    78  				return err
    79  			}
    80  			typeNet = append(typeNet, passList...)
    81  			return nil
    82  		})
    83  		if errFilter != nil {
    84  			return nil, errFilter
    85  		}
    86  		displayNet = typeNet
    87  	}
    88  
    89  	return displayNet, nil
    90  }
    91  
    92  func filterNetworkByUse(nws []types.NetworkResource, danglingOnly bool) []types.NetworkResource {
    93  	retNws := []types.NetworkResource{}
    94  
    95  	filterFunc := func(nw types.NetworkResource) bool {
    96  		if danglingOnly {
    97  			return !runconfig.IsPreDefinedNetwork(nw.Name) && len(nw.Containers) == 0 && len(nw.Services) == 0
    98  		}
    99  		return runconfig.IsPreDefinedNetwork(nw.Name) || len(nw.Containers) > 0 || len(nw.Services) > 0
   100  	}
   101  
   102  	for _, nw := range nws {
   103  		if filterFunc(nw) {
   104  			retNws = append(retNws, nw)
   105  		}
   106  	}
   107  
   108  	return retNws
   109  }
   110  
   111  func filterNetworkByType(nws []types.NetworkResource, netType string) ([]types.NetworkResource, error) {
   112  	retNws := []types.NetworkResource{}
   113  	switch netType {
   114  	case "builtin":
   115  		for _, nw := range nws {
   116  			if runconfig.IsPreDefinedNetwork(nw.Name) {
   117  				retNws = append(retNws, nw)
   118  			}
   119  		}
   120  	case "custom":
   121  		for _, nw := range nws {
   122  			if !runconfig.IsPreDefinedNetwork(nw.Name) {
   123  				retNws = append(retNws, nw)
   124  			}
   125  		}
   126  	default:
   127  		return nil, errors.Errorf("invalid filter: 'type'='%s'", netType)
   128  	}
   129  	return retNws, nil
   130  }