mirror of
https://github.com/kemko/nomad.git
synced 2026-01-03 08:55:43 +03:00
Merge pull request #797 from hashicorp/reserve-ports
Reserving ports for client in every platform
This commit is contained in:
@@ -7,11 +7,11 @@ import (
|
||||
"net"
|
||||
"os"
|
||||
"path/filepath"
|
||||
"runtime"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/hashicorp/nomad/client"
|
||||
clientconfig "github.com/hashicorp/nomad/client/config"
|
||||
"github.com/hashicorp/nomad/nomad"
|
||||
"github.com/hashicorp/nomad/nomad/structs"
|
||||
)
|
||||
@@ -242,26 +242,8 @@ func (a *Agent) setupClient() error {
|
||||
conf.Node.HTTPAddr = httpAddr
|
||||
|
||||
// Reserve some ports for the plugins
|
||||
if runtime.GOOS == "windows" {
|
||||
deviceName, err := a.findLoopbackDevice()
|
||||
if err != nil {
|
||||
return fmt.Errorf("error finding the device name for loopback: %v", err)
|
||||
}
|
||||
var nr *structs.NetworkResource
|
||||
for _, n := range conf.Node.Reserved.Networks {
|
||||
if n.Device == deviceName {
|
||||
nr = n
|
||||
}
|
||||
}
|
||||
if nr == nil {
|
||||
nr = &structs.NetworkResource{
|
||||
Device: deviceName,
|
||||
ReservedPorts: make([]structs.Port, 0),
|
||||
}
|
||||
}
|
||||
for i := conf.ClientMinPort; i <= conf.ClientMaxPort; i++ {
|
||||
nr.ReservedPorts = append(nr.ReservedPorts, structs.Port{Label: fmt.Sprintf("plugin-%d", i), Value: int(i)})
|
||||
}
|
||||
if err := a.reservePortsForClient(conf); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
// Create the client
|
||||
@@ -273,26 +255,75 @@ func (a *Agent) setupClient() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (a *Agent) findLoopbackDevice() (string, error) {
|
||||
// reservePortsForClient reservers a range of ports for the client to use when
|
||||
// it creates various plugins for log collection, executors, drivers, etc
|
||||
func (a *Agent) reservePortsForClient(conf *clientconfig.Config) error {
|
||||
// finding the device name for loopback
|
||||
deviceName, addr, mask, err := a.findLoopbackDevice()
|
||||
if err != nil {
|
||||
return fmt.Errorf("error finding the device name for loopback: %v", err)
|
||||
}
|
||||
|
||||
// seeing if the user has already reserved some resources on this device
|
||||
var nr *structs.NetworkResource
|
||||
if conf.Node.Reserved == nil {
|
||||
conf.Node.Reserved = &structs.Resources{}
|
||||
}
|
||||
for _, n := range conf.Node.Reserved.Networks {
|
||||
if n.Device == deviceName {
|
||||
nr = n
|
||||
}
|
||||
}
|
||||
// If the user hasn't already created the device, we create it
|
||||
if nr == nil {
|
||||
nr = &structs.NetworkResource{
|
||||
Device: deviceName,
|
||||
IP: addr,
|
||||
CIDR: mask,
|
||||
ReservedPorts: make([]structs.Port, 0),
|
||||
}
|
||||
}
|
||||
// appending the port ranges we want to use for the client to the list of
|
||||
// reserved ports for this device
|
||||
for i := conf.ClientMinPort; i <= conf.ClientMaxPort; i++ {
|
||||
nr.ReservedPorts = append(nr.ReservedPorts, structs.Port{Label: fmt.Sprintf("plugin-%d", i), Value: int(i)})
|
||||
}
|
||||
conf.Node.Reserved.Networks = append(conf.Node.Reserved.Networks, nr)
|
||||
return nil
|
||||
}
|
||||
|
||||
// findLoopbackDevice iterates through all the interfaces on a machine and
|
||||
// returns the ip addr, mask of the loopback device
|
||||
func (a *Agent) findLoopbackDevice() (string, string, string, error) {
|
||||
var ifcs []net.Interface
|
||||
var err error
|
||||
var deviceName string
|
||||
ifcs, err = net.Interfaces()
|
||||
if err != nil {
|
||||
return "", err
|
||||
return "", "", "", err
|
||||
}
|
||||
for _, ifc := range ifcs {
|
||||
addrs, err := ifc.Addrs()
|
||||
if err != nil {
|
||||
return deviceName, err
|
||||
return "", "", "", err
|
||||
}
|
||||
for _, addr := range addrs {
|
||||
if net.ParseIP(addr.String()).IsLoopback() {
|
||||
return ifc.Name, nil
|
||||
var ip net.IP
|
||||
switch v := addr.(type) {
|
||||
case *net.IPNet:
|
||||
ip = v.IP
|
||||
case *net.IPAddr:
|
||||
ip = v.IP
|
||||
}
|
||||
if ip.IsLoopback() {
|
||||
if ip.To4() == nil {
|
||||
continue
|
||||
}
|
||||
return ifc.Name, ip.String(), addr.String(), nil
|
||||
}
|
||||
}
|
||||
}
|
||||
return deviceName, err
|
||||
|
||||
return "", "", "", fmt.Errorf("no loopback devices with IPV4 addr found")
|
||||
}
|
||||
|
||||
// Leave is used gracefully exit. Clients will inform servers
|
||||
|
||||
Reference in New Issue
Block a user