github.com/Ilhicas/nomad@v1.0.4-0.20210304152020-e86851182bc3/client/fingerprint/cni.go (about)

     1  package fingerprint
     2  
     3  import (
     4  	"fmt"
     5  	"os"
     6  	"strings"
     7  
     8  	"github.com/containernetworking/cni/libcni"
     9  	log "github.com/hashicorp/go-hclog"
    10  	"github.com/hashicorp/nomad/nomad/structs"
    11  )
    12  
    13  type CNIFingerprint struct {
    14  	StaticFingerprinter
    15  	logger log.Logger
    16  }
    17  
    18  func NewCNIFingerprint(logger log.Logger) Fingerprint {
    19  	return &CNIFingerprint{logger: logger}
    20  }
    21  
    22  func (f *CNIFingerprint) Fingerprint(req *FingerprintRequest, resp *FingerprintResponse) error {
    23  	confDir := req.Config.CNIConfigDir
    24  	networks := map[string]struct{}{}
    25  	if _, err := os.Stat(confDir); os.IsNotExist(err) {
    26  		f.logger.Debug("CNI config dir is not set or does not exist, skipping", "cni_config_dir", confDir)
    27  		resp.Detected = false
    28  		return nil
    29  	}
    30  
    31  	files, err := libcni.ConfFiles(confDir, []string{".conf", ".conflist", ".json"})
    32  	if err != nil {
    33  		return fmt.Errorf("failed to detect CNI conf files: %v", err)
    34  	}
    35  
    36  	for _, confFile := range files {
    37  		if strings.HasSuffix(confFile, ".conflist") {
    38  			confList, err := libcni.ConfListFromFile(confFile)
    39  			if err != nil {
    40  				return fmt.Errorf("failed to load CNI config list file %s: %v", confFile, err)
    41  			}
    42  			if _, ok := networks[confList.Name]; ok {
    43  				f.logger.Warn("duplicate CNI config names found, ignoring file", "name", confList.Name, "file", confFile)
    44  				continue
    45  			}
    46  			networks[confList.Name] = struct{}{}
    47  		} else {
    48  			conf, err := libcni.ConfFromFile(confFile)
    49  			if err != nil {
    50  				return fmt.Errorf("failed to load CNI config file %s: %v", confFile, err)
    51  			}
    52  			if _, ok := networks[conf.Network.Name]; ok {
    53  				f.logger.Warn("duplicate CNI config names found, ignoring file", "name", conf.Network.Name, "file", confFile)
    54  				continue
    55  			}
    56  			networks[conf.Network.Name] = struct{}{}
    57  		}
    58  	}
    59  
    60  	var nodeNetworks structs.Networks
    61  	var newNodeNetworks []*structs.NodeNetworkResource
    62  
    63  	for name := range networks {
    64  		mode := fmt.Sprintf("cni/%s", name)
    65  		nodeNetworks = append(nodeNetworks, &structs.NetworkResource{
    66  			Mode: mode,
    67  		})
    68  		newNodeNetworks = append(newNodeNetworks, &structs.NodeNetworkResource{
    69  			Mode: mode,
    70  		})
    71  		f.logger.Debug("detected CNI network", "name", name)
    72  	}
    73  
    74  	resp.NodeResources = &structs.NodeResources{
    75  		Networks:     nodeNetworks,
    76  		NodeNetworks: newNodeNetworks,
    77  	}
    78  
    79  	resp.Detected = true
    80  	return nil
    81  }
    82  
    83  func (f *CNIFingerprint) Reload() {}