Quellcode durchsuchen

Support configuration networks

- They are configuration-only networks which
  can be used to supply the configuration
  when creating regular networks.
- They do not get allocated and do net get plumbed.
  Drivers do not get to know about them.
- They can be removed, once no other network is
  using them.
- When user creates a network specifying a
  configuration network for the config, no
  other network specific configuration field
  is are accepted. User can only specify
  network operator fields (attachable, internal,...)

Signed-off-by: Alessandro Boch <aboch@docker.com>
Alessandro Boch vor 8 Jahren
Ursprung
Commit
9ee7b4dda9

+ 5 - 0
api/server/router/network/network_routes.go

@@ -299,6 +299,11 @@ func (n *networkRouter) buildNetworkResource(nw libnetwork.Network) *types.Netwo
 	r.Containers = make(map[string]types.EndpointResource)
 	buildIpamResources(r, info)
 	r.Labels = info.Labels()
+	r.ConfigOnly = info.ConfigOnly()
+
+	if cn := info.ConfigFrom(); cn != "" {
+		r.ConfigFrom = network.ConfigReference{Network: cn}
+	}
 
 	peers := info.Peers()
 	if len(peers) != 0 {

+ 5 - 0
api/types/network/network.go

@@ -100,3 +100,8 @@ func (es *EndpointSettings) Copy() *EndpointSettings {
 type NetworkingConfig struct {
 	EndpointsConfig map[string]*EndpointSettings // Endpoint configs for each connecting network
 }
+
+// ConfigReference specifies the source which provides a network's configuration
+type ConfigReference struct {
+	Network string
+}

+ 4 - 0
api/types/types.go

@@ -403,6 +403,8 @@ type NetworkResource struct {
 	Internal   bool                           // Internal represents if the network is used internal only
 	Attachable bool                           // Attachable represents if the global scope is manually attachable by regular containers from workers in swarm mode.
 	Ingress    bool                           // Ingress indicates the network is providing the routing-mesh for the swarm cluster.
+	ConfigFrom network.ConfigReference        // ConfigFrom specifies the source which will provide the configuration for this network.
+	ConfigOnly bool                           // ConfigOnly networks are place-holder networks for network configurations to be used by other networks. ConfigOnly networks cannot be used directly to run containers or services.
 	Containers map[string]EndpointResource    // Containers contains endpoints belonging to the network
 	Options    map[string]string              // Options holds the network specific options to use for when creating the network
 	Labels     map[string]string              // Labels holds metadata specific to the network being created
@@ -435,6 +437,8 @@ type NetworkCreate struct {
 	Internal       bool
 	Attachable     bool
 	Ingress        bool
+	ConfigOnly     bool
+	ConfigFrom     *network.ConfigReference
 	Options        map[string]string
 	Labels         map[string]string
 }

+ 18 - 4
daemon/network.go

@@ -320,6 +320,10 @@ func (daemon *Daemon) createNetwork(create types.NetworkCreateRequest, id string
 		libnetwork.NetworkOptionIngress(create.Ingress),
 	}
 
+	if create.ConfigOnly {
+		nwOptions = append(nwOptions, libnetwork.NetworkOptionConfigOnly())
+	}
+
 	if create.IPAM != nil {
 		ipam := create.IPAM
 		v4Conf, v6Conf, err := getIpamConfig(ipam.Config)
@@ -337,6 +341,10 @@ func (daemon *Daemon) createNetwork(create types.NetworkCreateRequest, id string
 		nwOptions = append(nwOptions, libnetwork.NetworkOptionPersist(false))
 	}
 
+	if create.ConfigFrom != nil {
+		nwOptions = append(nwOptions, libnetwork.NetworkOptionConfigFrom(create.ConfigFrom.Network))
+	}
+
 	n, err := c.NewNetwork(driver, create.Name, id, nwOptions...)
 	if err != nil {
 		if _, ok := err.(libnetwork.ErrDataStoreNotInitialized); ok {
@@ -501,10 +509,16 @@ func (daemon *Daemon) deleteNetwork(networkID string, dynamic bool) error {
 	if err := nw.Delete(); err != nil {
 		return err
 	}
-	daemon.pluginRefCount(nw.Type(), driverapi.NetworkPluginEndpointType, plugingetter.Release)
-	ipamType, _, _, _ := nw.Info().IpamConfig()
-	daemon.pluginRefCount(ipamType, ipamapi.PluginEndpointType, plugingetter.Release)
-	daemon.LogNetworkEvent(nw, "destroy")
+
+	// If this is not a configuration only network, we need to
+	// update the corresponding remote drivers' reference counts
+	if !nw.Info().ConfigOnly() {
+		daemon.pluginRefCount(nw.Type(), driverapi.NetworkPluginEndpointType, plugingetter.Release)
+		ipamType, _, _, _ := nw.Info().IpamConfig()
+		daemon.pluginRefCount(ipamType, ipamapi.PluginEndpointType, plugingetter.Release)
+		daemon.LogNetworkEvent(nw, "destroy")
+	}
+
 	return nil
 }
 

+ 3 - 0
daemon/prune.go

@@ -315,6 +315,9 @@ func (daemon *Daemon) localNetworksPrune(ctx context.Context, pruneFilters filte
 			return true
 		default:
 		}
+		if nw.Info().ConfigOnly() {
+			return false
+		}
 		if !until.IsZero() && nw.Info().Created().After(until) {
 			return false
 		}