Add backend features to docker
This commit is contained in:
parent
1e324ad3bc
commit
d89bdfbd27
4 changed files with 159 additions and 11 deletions
|
@ -2,6 +2,7 @@ package provider
|
|||
|
||||
import (
|
||||
"errors"
|
||||
"math"
|
||||
"net/http"
|
||||
"strconv"
|
||||
"strings"
|
||||
|
@ -150,17 +151,24 @@ func (provider *Docker) Provide(configurationChan chan<- types.ConfigMessage, po
|
|||
|
||||
func (provider *Docker) loadDockerConfig(containersInspected []dockertypes.ContainerJSON) *types.Configuration {
|
||||
var DockerFuncMap = template.FuncMap{
|
||||
"getBackend": provider.getBackend,
|
||||
"getIPAddress": provider.getIPAddress,
|
||||
"getPort": provider.getPort,
|
||||
"getWeight": provider.getWeight,
|
||||
"getDomain": provider.getDomain,
|
||||
"getProtocol": provider.getProtocol,
|
||||
"getPassHostHeader": provider.getPassHostHeader,
|
||||
"getPriority": provider.getPriority,
|
||||
"getEntryPoints": provider.getEntryPoints,
|
||||
"getFrontendRule": provider.getFrontendRule,
|
||||
"replace": replace,
|
||||
"getBackend": provider.getBackend,
|
||||
"getIPAddress": provider.getIPAddress,
|
||||
"getPort": provider.getPort,
|
||||
"getWeight": provider.getWeight,
|
||||
"getDomain": provider.getDomain,
|
||||
"getProtocol": provider.getProtocol,
|
||||
"getPassHostHeader": provider.getPassHostHeader,
|
||||
"getPriority": provider.getPriority,
|
||||
"getEntryPoints": provider.getEntryPoints,
|
||||
"getFrontendRule": provider.getFrontendRule,
|
||||
"hasCircuitBreakerLabel": provider.hasCircuitBreakerLabel,
|
||||
"getCircuitBreakerExpression": provider.getCircuitBreakerExpression,
|
||||
"hasLoadBalancerLabel": provider.hasLoadBalancerLabel,
|
||||
"getLoadBalancerMethod": provider.getLoadBalancerMethod,
|
||||
"hasMaxConnLabels": provider.hasMaxConnLabels,
|
||||
"getMaxConnAmount": provider.getMaxConnAmount,
|
||||
"getMaxConnExtractorFunc": provider.getMaxConnExtractorFunc,
|
||||
"replace": replace,
|
||||
}
|
||||
|
||||
// filter containers
|
||||
|
@ -191,6 +199,63 @@ func (provider *Docker) loadDockerConfig(containersInspected []dockertypes.Conta
|
|||
return configuration
|
||||
}
|
||||
|
||||
func (provider *Docker) hasCircuitBreakerLabel(container dockertypes.ContainerJSON) bool {
|
||||
if _, err := getLabel(container, "traefik.backend.circuitbreaker.expression"); err != nil {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (provider *Docker) hasLoadBalancerLabel(container dockertypes.ContainerJSON) bool {
|
||||
if _, err := getLabel(container, "traefik.backend.loadbalancer.method"); err != nil {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (provider *Docker) hasMaxConnLabels(container dockertypes.ContainerJSON) bool {
|
||||
if _, err := getLabel(container, "traefik.backend.maxconn.amount"); err != nil {
|
||||
return false
|
||||
}
|
||||
if _, err := getLabel(container, "traefik.backend.maxconn.extractorfunc"); err != nil {
|
||||
return false
|
||||
}
|
||||
return true
|
||||
}
|
||||
|
||||
func (provider *Docker) getCircuitBreakerExpression(container dockertypes.ContainerJSON) string {
|
||||
if label, err := getLabel(container, "traefik.backend.circuitbreaker.expression"); err == nil {
|
||||
return label
|
||||
}
|
||||
return "NetworkErrorRatio() > 1"
|
||||
}
|
||||
|
||||
func (provider *Docker) getLoadBalancerMethod(container dockertypes.ContainerJSON) string {
|
||||
if label, err := getLabel(container, "traefik.backend.loadbalancer.method"); err == nil {
|
||||
return label
|
||||
}
|
||||
return "wrr"
|
||||
}
|
||||
|
||||
func (provider *Docker) getMaxConnAmount(container dockertypes.ContainerJSON) int64 {
|
||||
if label, err := getLabel(container, "traefik.backend.maxconn.amount"); err == nil {
|
||||
i, errConv := strconv.ParseInt(label, 10, 64)
|
||||
if errConv != nil {
|
||||
log.Errorf("Unable to parse traefik.backend.maxconn.amount %s", label)
|
||||
return math.MaxInt64
|
||||
}
|
||||
return i
|
||||
}
|
||||
return math.MaxInt64
|
||||
}
|
||||
|
||||
func (provider *Docker) getMaxConnExtractorFunc(container dockertypes.ContainerJSON) string {
|
||||
if label, err := getLabel(container, "traefik.backend.maxconn.extractorfunc"); err == nil {
|
||||
return label
|
||||
}
|
||||
return "request.host"
|
||||
}
|
||||
|
||||
func (provider *Docker) containerFilter(container dockertypes.ContainerJSON, exposedByDefaultFlag bool) bool {
|
||||
_, err := strconv.Atoi(container.Config.Labels["traefik.port"])
|
||||
if len(container.NetworkSettings.Ports) == 0 && err != nil {
|
||||
|
|
|
@ -1016,6 +1016,69 @@ func TestDockerLoadDockerConfig(t *testing.T) {
|
|||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
containers: []docker.ContainerJSON{
|
||||
{
|
||||
ContainerJSONBase: &docker.ContainerJSONBase{
|
||||
Name: "test1",
|
||||
},
|
||||
Config: &container.Config{
|
||||
Labels: map[string]string{
|
||||
"traefik.backend": "foobar",
|
||||
"traefik.frontend.entryPoints": "http,https",
|
||||
"traefik.backend.maxconn.amount": "1000",
|
||||
"traefik.backend.maxconn.extractorfunc": "somethingelse",
|
||||
"traefik.backend.loadbalancer.method": "drr",
|
||||
"traefik.backend.circuitbreaker.expression": "NetworkErrorRatio() > 0.5",
|
||||
},
|
||||
},
|
||||
NetworkSettings: &docker.NetworkSettings{
|
||||
NetworkSettingsBase: docker.NetworkSettingsBase{
|
||||
Ports: nat.PortMap{
|
||||
"80/tcp": {},
|
||||
},
|
||||
},
|
||||
Networks: map[string]*network.EndpointSettings{
|
||||
"bridge": {
|
||||
IPAddress: "127.0.0.1",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
expectedFrontends: map[string]*types.Frontend{
|
||||
"frontend-Host-test1-docker-localhost": {
|
||||
Backend: "backend-foobar",
|
||||
PassHostHeader: true,
|
||||
EntryPoints: []string{"http", "https"},
|
||||
Routes: map[string]types.Route{
|
||||
"route-frontend-Host-test1-docker-localhost": {
|
||||
Rule: "Host:test1.docker.localhost",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
expectedBackends: map[string]*types.Backend{
|
||||
"backend-foobar": {
|
||||
Servers: map[string]types.Server{
|
||||
"server-test1": {
|
||||
URL: "http://127.0.0.1:80",
|
||||
Weight: 1,
|
||||
},
|
||||
},
|
||||
CircuitBreaker: &types.CircuitBreaker{
|
||||
Expression: "NetworkErrorRatio() > 0.5",
|
||||
},
|
||||
LoadBalancer: &types.LoadBalancer{
|
||||
Method: "drr",
|
||||
},
|
||||
MaxConn: &types.MaxConn{
|
||||
Amount: 1000,
|
||||
ExtractorFunc: "somethingelse",
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
}
|
||||
|
||||
provider := &Docker{
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue