mirror of
https://github.com/containous/traefik.git
synced 2025-03-11 16:58:23 +03:00
Merge pull request #547 from containous/add-basic-authentication
Add basic/digest auth
This commit is contained in:
commit
a016741918
@ -163,6 +163,7 @@ type EntryPoint struct {
|
|||||||
Address string
|
Address string
|
||||||
TLS *TLS
|
TLS *TLS
|
||||||
Redirect *Redirect
|
Redirect *Redirect
|
||||||
|
Auth *types.Auth
|
||||||
}
|
}
|
||||||
|
|
||||||
// Redirect configures a redirection of an entry point to another, or to an URL
|
// Redirect configures a redirection of an entry point to another, or to an URL
|
||||||
|
18
docs/toml.md
18
docs/toml.md
@ -110,7 +110,23 @@
|
|||||||
# CertFile = "integration/fixtures/https/snitest.org.cert"
|
# CertFile = "integration/fixtures/https/snitest.org.cert"
|
||||||
# KeyFile = "integration/fixtures/https/snitest.org.key"
|
# KeyFile = "integration/fixtures/https/snitest.org.key"
|
||||||
#
|
#
|
||||||
|
# To enable basic auth on an entrypoint
|
||||||
|
# with 2 user/pass: test:test and test2:test2
|
||||||
|
# Passwords can be encoded in MD5, SHA1 and BCrypt: you can use htpasswd to generate those ones
|
||||||
|
# [entryPoints]
|
||||||
|
# [entryPoints.http]
|
||||||
|
# address = ":80"
|
||||||
|
# [entryPoints.http.auth.basic]
|
||||||
|
# users = ["test:$apr1$H6uskkkW$IgXLP6ewTrSuBkTrqE8wj/", "test2:$apr1$d9hr9HBB$4HxwgUir3HP4EsggP/QNo0"]
|
||||||
|
#
|
||||||
|
# To enable digest auth on an entrypoint
|
||||||
|
# with 2 user/realm/pass: test:traefik:test and test2:traefik:test2
|
||||||
|
# You can use htdigest to generate those ones
|
||||||
|
# [entryPoints]
|
||||||
|
# [entryPoints.http]
|
||||||
|
# address = ":80"
|
||||||
|
# [entryPoints.http.auth.basic]
|
||||||
|
# users = ["test:traefik:a2688e031edb4be6a3797f3882655c05 ", "test2:traefik:518845800f9e2bfb1f1f740ec24f074e"]
|
||||||
|
|
||||||
[entryPoints]
|
[entryPoints]
|
||||||
[entryPoints.http]
|
[entryPoints.http]
|
||||||
|
@ -97,3 +97,21 @@ entryPoint = "https"
|
|||||||
backend = "backend2"
|
backend = "backend2"
|
||||||
rule = "Path:/test"
|
rule = "Path:/test"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
## Enable Basic authentication in an entrypoint
|
||||||
|
|
||||||
|
With two user/pass:
|
||||||
|
|
||||||
|
- `test`:`test`
|
||||||
|
- `test2`:`test2`
|
||||||
|
|
||||||
|
Passwords are encoded in MD5: you can use htpasswd to generate those ones.
|
||||||
|
|
||||||
|
```
|
||||||
|
defaultEntryPoints = ["http"]
|
||||||
|
[entryPoints]
|
||||||
|
[entryPoints.http]
|
||||||
|
address = ":80"
|
||||||
|
[entryPoints.http.auth.basic]
|
||||||
|
users = ["test:$apr1$H6uskkkW$IgXLP6ewTrSuBkTrqE8wj/", "test2:$apr1$d9hr9HBB$4HxwgUir3HP4EsggP/QNo0"]
|
||||||
|
```
|
20
glide.lock
generated
20
glide.lock
generated
@ -1,5 +1,5 @@
|
|||||||
hash: 745d05424943c3345ff5fca5b121c6af3930f62fc13195d87d9fcce6686620ea
|
hash: 5cb432175705882247ac2cbf708c879fad8b287afe9e1e18f06dbce1e956acd2
|
||||||
updated: 2016-07-22T15:14:53.608798979+02:00
|
updated: 2016-07-28T18:20:42.864416381+02:00
|
||||||
imports:
|
imports:
|
||||||
- name: github.com/abbot/go-http-auth
|
- name: github.com/abbot/go-http-auth
|
||||||
version: cb4372376e1e00e9f6ab9ec142e029302c9e7140
|
version: cb4372376e1e00e9f6ab9ec142e029302c9e7140
|
||||||
@ -36,7 +36,7 @@ imports:
|
|||||||
subpackages:
|
subpackages:
|
||||||
- spew
|
- spew
|
||||||
- name: github.com/docker/distribution
|
- name: github.com/docker/distribution
|
||||||
version: 2b72dd3927b2958160a2336f16145c0c421aa6a4
|
version: 857d0f15c0a4d8037175642e0ca3660829551cb5
|
||||||
subpackages:
|
subpackages:
|
||||||
- reference
|
- reference
|
||||||
- digest
|
- digest
|
||||||
@ -141,7 +141,7 @@ imports:
|
|||||||
- lookup
|
- lookup
|
||||||
- version
|
- version
|
||||||
- name: github.com/docker/libkv
|
- name: github.com/docker/libkv
|
||||||
version: aabc039ad04deb721e234f99cd1b4aa28ac71a40
|
version: 35d3e2084c650109e7bcc7282655b1bc8ba924ff
|
||||||
subpackages:
|
subpackages:
|
||||||
- store
|
- store
|
||||||
- store/boltdb
|
- store/boltdb
|
||||||
@ -157,7 +157,7 @@ imports:
|
|||||||
- name: github.com/go-check/check
|
- name: github.com/go-check/check
|
||||||
version: 4f90aeace3a26ad7021961c297b22c42160c7b25
|
version: 4f90aeace3a26ad7021961c297b22c42160c7b25
|
||||||
- name: github.com/gogo/protobuf
|
- name: github.com/gogo/protobuf
|
||||||
version: 6abcf94fd4c97dcb423fdafd42fe9f96ca7e421b
|
version: e57a569e1882958f6b188cb42231d6db87701f2a
|
||||||
subpackages:
|
subpackages:
|
||||||
- proto
|
- proto
|
||||||
- name: github.com/golang/glog
|
- name: github.com/golang/glog
|
||||||
@ -169,7 +169,7 @@ imports:
|
|||||||
- name: github.com/gorilla/context
|
- name: github.com/gorilla/context
|
||||||
version: aed02d124ae4a0e94fea4541c8effd05bf0c8296
|
version: aed02d124ae4a0e94fea4541c8effd05bf0c8296
|
||||||
- name: github.com/hashicorp/consul
|
- name: github.com/hashicorp/consul
|
||||||
version: fce7d75609a04eeb9d4bf41c8dc592aac18fc97d
|
version: 8a8271fd81cdaa1bbc20e4ced86531b90c7eaf79
|
||||||
subpackages:
|
subpackages:
|
||||||
- api
|
- api
|
||||||
- name: github.com/hashicorp/go-cleanhttp
|
- name: github.com/hashicorp/go-cleanhttp
|
||||||
@ -220,13 +220,13 @@ imports:
|
|||||||
- name: github.com/miekg/dns
|
- name: github.com/miekg/dns
|
||||||
version: 5d001d020961ae1c184f9f8152fdc73810481677
|
version: 5d001d020961ae1c184f9f8152fdc73810481677
|
||||||
- name: github.com/mitchellh/mapstructure
|
- name: github.com/mitchellh/mapstructure
|
||||||
version: 21a35fb16463dfb7c8eee579c65d995d95e64d1e
|
version: d2dd0262208475919e1a362f675cfc0e7c10e905
|
||||||
- name: github.com/moul/http2curl
|
- name: github.com/moul/http2curl
|
||||||
version: b1479103caacaa39319f75e7f57fc545287fca0d
|
version: b1479103caacaa39319f75e7f57fc545287fca0d
|
||||||
- name: github.com/ogier/pflag
|
- name: github.com/ogier/pflag
|
||||||
version: 45c278ab3607870051a2ea9040bb85fcb8557481
|
version: 45c278ab3607870051a2ea9040bb85fcb8557481
|
||||||
- name: github.com/opencontainers/runc
|
- name: github.com/opencontainers/runc
|
||||||
version: fb221651e5120cd287a76c7c1b6c877520fbd034
|
version: bd1d3ac0480c5d3babac10dc32cff2886563219c
|
||||||
subpackages:
|
subpackages:
|
||||||
- libcontainer/user
|
- libcontainer/user
|
||||||
- name: github.com/parnurzeal/gorequest
|
- name: github.com/parnurzeal/gorequest
|
||||||
@ -294,9 +294,11 @@ imports:
|
|||||||
subpackages:
|
subpackages:
|
||||||
- acme
|
- acme
|
||||||
- name: golang.org/x/crypto
|
- name: golang.org/x/crypto
|
||||||
version: 911fafb28f4ee7c7bd483539a6c96190bbbccc3f
|
version: d81fdb778bf2c40a91b24519d60cdc5767318829
|
||||||
subpackages:
|
subpackages:
|
||||||
- ocsp
|
- ocsp
|
||||||
|
- bcrypt
|
||||||
|
- blowfish
|
||||||
- name: golang.org/x/net
|
- name: golang.org/x/net
|
||||||
version: b400c2eff1badec7022a8c8f5bea058b6315eed7
|
version: b400c2eff1badec7022a8c8f5bea058b6315eed7
|
||||||
subpackages:
|
subpackages:
|
||||||
|
@ -64,8 +64,6 @@ import:
|
|||||||
version: b2fad6198110326662e9e356a97199078a4a775c
|
version: b2fad6198110326662e9e356a97199078a4a775c
|
||||||
subpackages:
|
subpackages:
|
||||||
- acme
|
- acme
|
||||||
- package: github.com/miekg/dns
|
|
||||||
version: 5d001d020961ae1c184f9f8152fdc73810481677
|
|
||||||
- package: golang.org/x/net
|
- package: golang.org/x/net
|
||||||
subpackages:
|
subpackages:
|
||||||
- context
|
- context
|
||||||
|
99
middlewares/authenticator.go
Normal file
99
middlewares/authenticator.go
Normal file
@ -0,0 +1,99 @@
|
|||||||
|
package middlewares
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
log "github.com/Sirupsen/logrus"
|
||||||
|
"github.com/abbot/go-http-auth"
|
||||||
|
"github.com/codegangsta/negroni"
|
||||||
|
"github.com/containous/traefik/types"
|
||||||
|
"net/http"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Authenticator is a middleware that provides HTTP basic and digest authentication
|
||||||
|
type Authenticator struct {
|
||||||
|
handler negroni.Handler
|
||||||
|
users map[string]string
|
||||||
|
}
|
||||||
|
|
||||||
|
// NewAuthenticator builds a new Autenticator given a config
|
||||||
|
func NewAuthenticator(authConfig *types.Auth) (*Authenticator, error) {
|
||||||
|
if authConfig == nil {
|
||||||
|
return nil, fmt.Errorf("Error creating Authenticator: auth is nil")
|
||||||
|
}
|
||||||
|
var err error
|
||||||
|
authenticator := Authenticator{}
|
||||||
|
if authConfig.Basic != nil {
|
||||||
|
authenticator.users, err = parserBasicUsers(authConfig.Basic.Users)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
basicAuth := auth.NewBasicAuthenticator("traefik", authenticator.secretBasic)
|
||||||
|
authenticator.handler = negroni.HandlerFunc(func(w http.ResponseWriter, r *http.Request, next http.HandlerFunc) {
|
||||||
|
if username := basicAuth.CheckAuth(r); username == "" {
|
||||||
|
log.Debugf("Auth failed...")
|
||||||
|
basicAuth.RequireAuth(w, r)
|
||||||
|
} else {
|
||||||
|
next.ServeHTTP(w, r)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
} else if authConfig.Digest != nil {
|
||||||
|
authenticator.users, err = parserDigestUsers(authConfig.Digest.Users)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
digestAuth := auth.NewDigestAuthenticator("traefik", authenticator.secretDigest)
|
||||||
|
authenticator.handler = negroni.HandlerFunc(func(w http.ResponseWriter, r *http.Request, next http.HandlerFunc) {
|
||||||
|
if username, _ := digestAuth.CheckAuth(r); username == "" {
|
||||||
|
digestAuth.RequireAuth(w, r)
|
||||||
|
} else {
|
||||||
|
next.ServeHTTP(w, r)
|
||||||
|
}
|
||||||
|
})
|
||||||
|
}
|
||||||
|
return &authenticator, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func parserBasicUsers(users types.Users) (map[string]string, error) {
|
||||||
|
userMap := make(map[string]string)
|
||||||
|
for _, user := range users {
|
||||||
|
split := strings.Split(user, ":")
|
||||||
|
if len(split) != 2 {
|
||||||
|
return nil, fmt.Errorf("Error parsing Authenticator user: %v", user)
|
||||||
|
}
|
||||||
|
userMap[split[0]] = split[1]
|
||||||
|
}
|
||||||
|
return userMap, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func parserDigestUsers(users types.Users) (map[string]string, error) {
|
||||||
|
userMap := make(map[string]string)
|
||||||
|
for _, user := range users {
|
||||||
|
split := strings.Split(user, ":")
|
||||||
|
if len(split) != 3 {
|
||||||
|
return nil, fmt.Errorf("Error parsing Authenticator user: %v", user)
|
||||||
|
}
|
||||||
|
userMap[split[0]+":"+split[1]] = split[2]
|
||||||
|
}
|
||||||
|
return userMap, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (a *Authenticator) secretBasic(user, realm string) string {
|
||||||
|
if secret, ok := a.users[user]; ok {
|
||||||
|
return secret
|
||||||
|
}
|
||||||
|
log.Debugf("User not found: %s", user)
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func (a *Authenticator) secretDigest(user, realm string) string {
|
||||||
|
if secret, ok := a.users[user+":"+realm]; ok {
|
||||||
|
return secret
|
||||||
|
}
|
||||||
|
log.Debugf("User not found: %s:%s", user, realm)
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
|
||||||
|
func (a *Authenticator) ServeHTTP(rw http.ResponseWriter, r *http.Request, next http.HandlerFunc) {
|
||||||
|
a.handler.ServeHTTP(rw, r, next)
|
||||||
|
}
|
103
middlewares/authenticator_test.go
Normal file
103
middlewares/authenticator_test.go
Normal file
@ -0,0 +1,103 @@
|
|||||||
|
package middlewares
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"github.com/codegangsta/negroni"
|
||||||
|
"github.com/containous/traefik/types"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
"io/ioutil"
|
||||||
|
"net/http"
|
||||||
|
"net/http/httptest"
|
||||||
|
"testing"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestBasicAuthFail(t *testing.T) {
|
||||||
|
authMiddleware, err := NewAuthenticator(&types.Auth{
|
||||||
|
Basic: &types.Basic{
|
||||||
|
Users: []string{"test"},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
assert.Contains(t, err.Error(), "Error parsing Authenticator user", "should contains")
|
||||||
|
|
||||||
|
authMiddleware, err = NewAuthenticator(&types.Auth{
|
||||||
|
Basic: &types.Basic{
|
||||||
|
Users: []string{"test:test"},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
assert.NoError(t, err, "there should be no error")
|
||||||
|
|
||||||
|
handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
fmt.Fprintln(w, "traefik")
|
||||||
|
})
|
||||||
|
n := negroni.New(authMiddleware)
|
||||||
|
n.UseHandler(handler)
|
||||||
|
ts := httptest.NewServer(n)
|
||||||
|
defer ts.Close()
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
req, err := http.NewRequest("GET", ts.URL, nil)
|
||||||
|
req.SetBasicAuth("test", "test")
|
||||||
|
res, err := client.Do(req)
|
||||||
|
assert.NoError(t, err, "there should be no error")
|
||||||
|
assert.Equal(t, http.StatusUnauthorized, res.StatusCode, "they should be equal")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestBasicAuthSuccess(t *testing.T) {
|
||||||
|
authMiddleware, err := NewAuthenticator(&types.Auth{
|
||||||
|
Basic: &types.Basic{
|
||||||
|
Users: []string{"test:$apr1$H6uskkkW$IgXLP6ewTrSuBkTrqE8wj/"},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
assert.NoError(t, err, "there should be no error")
|
||||||
|
|
||||||
|
handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
fmt.Fprintln(w, "traefik")
|
||||||
|
})
|
||||||
|
n := negroni.New(authMiddleware)
|
||||||
|
n.UseHandler(handler)
|
||||||
|
ts := httptest.NewServer(n)
|
||||||
|
defer ts.Close()
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
req, err := http.NewRequest("GET", ts.URL, nil)
|
||||||
|
req.SetBasicAuth("test", "test")
|
||||||
|
res, err := client.Do(req)
|
||||||
|
assert.NoError(t, err, "there should be no error")
|
||||||
|
assert.Equal(t, http.StatusOK, res.StatusCode, "they should be equal")
|
||||||
|
|
||||||
|
body, err := ioutil.ReadAll(res.Body)
|
||||||
|
assert.NoError(t, err, "there should be no error")
|
||||||
|
assert.Equal(t, "traefik\n", string(body), "they should be equal")
|
||||||
|
}
|
||||||
|
|
||||||
|
func TestDigestAuthFail(t *testing.T) {
|
||||||
|
authMiddleware, err := NewAuthenticator(&types.Auth{
|
||||||
|
Digest: &types.Digest{
|
||||||
|
Users: []string{"test"},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
assert.Contains(t, err.Error(), "Error parsing Authenticator user", "should contains")
|
||||||
|
|
||||||
|
authMiddleware, err = NewAuthenticator(&types.Auth{
|
||||||
|
Digest: &types.Digest{
|
||||||
|
Users: []string{"test:traefik:test"},
|
||||||
|
},
|
||||||
|
})
|
||||||
|
assert.NoError(t, err, "there should be no error")
|
||||||
|
assert.NotNil(t, authMiddleware, "this should not be nil")
|
||||||
|
|
||||||
|
handler := http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
|
||||||
|
fmt.Fprintln(w, "traefik")
|
||||||
|
})
|
||||||
|
n := negroni.New(authMiddleware)
|
||||||
|
n.UseHandler(handler)
|
||||||
|
ts := httptest.NewServer(n)
|
||||||
|
defer ts.Close()
|
||||||
|
|
||||||
|
client := &http.Client{}
|
||||||
|
req, err := http.NewRequest("GET", ts.URL, nil)
|
||||||
|
req.SetBasicAuth("test", "test")
|
||||||
|
res, err := client.Do(req)
|
||||||
|
assert.NoError(t, err, "there should be no error")
|
||||||
|
assert.Equal(t, http.StatusUnauthorized, res.StatusCode, "they should be equal")
|
||||||
|
}
|
@ -21,5 +21,7 @@ echo "Updating docker containous/traefik image..."
|
|||||||
docker login -e $DOCKER_EMAIL -u $DOCKER_USER -p $DOCKER_PASS
|
docker login -e $DOCKER_EMAIL -u $DOCKER_USER -p $DOCKER_PASS
|
||||||
docker tag containous/traefik containous/traefik:pr-${PR}
|
docker tag containous/traefik containous/traefik:pr-${PR}
|
||||||
docker push containous/traefik:pr-${PR}
|
docker push containous/traefik:pr-${PR}
|
||||||
|
docker tag containous/traefik containous/traefik:experimental
|
||||||
|
docker push containous/traefik:experimental
|
||||||
|
|
||||||
echo "Deployed"
|
echo "Deployed"
|
||||||
|
@ -27,7 +27,7 @@ sudo chmod +x /usr/bin/ghr
|
|||||||
|
|
||||||
# github release and tag
|
# github release and tag
|
||||||
echo "Github release..."
|
echo "Github release..."
|
||||||
ghr -t $GITHUB_TOKEN -u containous -r traefik --prerelease ${VERSION} dist/
|
ghr -t $GITHUB_TOKEN -u containous -r traefik ${VERSION} dist/
|
||||||
|
|
||||||
# update docs.traefik.io
|
# update docs.traefik.io
|
||||||
echo "Generating and updating documentation..."
|
echo "Generating and updating documentation..."
|
||||||
|
10
server.go
10
server.go
@ -118,7 +118,15 @@ func (server *Server) Close() {
|
|||||||
func (server *Server) startHTTPServers() {
|
func (server *Server) startHTTPServers() {
|
||||||
server.serverEntryPoints = server.buildEntryPoints(server.globalConfiguration)
|
server.serverEntryPoints = server.buildEntryPoints(server.globalConfiguration)
|
||||||
for newServerEntryPointName, newServerEntryPoint := range server.serverEntryPoints {
|
for newServerEntryPointName, newServerEntryPoint := range server.serverEntryPoints {
|
||||||
newsrv, err := server.prepareServer(newServerEntryPointName, newServerEntryPoint.httpRouter, server.globalConfiguration.EntryPoints[newServerEntryPointName], nil, server.loggerMiddleware, metrics)
|
serverMiddlewares := []negroni.Handler{server.loggerMiddleware, metrics}
|
||||||
|
if server.globalConfiguration.EntryPoints[newServerEntryPointName].Auth != nil {
|
||||||
|
authMiddleware, err := middlewares.NewAuthenticator(server.globalConfiguration.EntryPoints[newServerEntryPointName].Auth)
|
||||||
|
if err != nil {
|
||||||
|
log.Fatal("Error starting server: ", err)
|
||||||
|
}
|
||||||
|
serverMiddlewares = append(serverMiddlewares, authMiddleware)
|
||||||
|
}
|
||||||
|
newsrv, err := server.prepareServer(newServerEntryPointName, newServerEntryPoint.httpRouter, server.globalConfiguration.EntryPoints[newServerEntryPointName], nil, serverMiddlewares...)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
log.Fatal("Error preparing server: ", err)
|
log.Fatal("Error preparing server: ", err)
|
||||||
}
|
}
|
||||||
|
@ -143,6 +143,25 @@
|
|||||||
# [entryPoints.http.redirect]
|
# [entryPoints.http.redirect]
|
||||||
# regex = "^http://localhost/(.*)"
|
# regex = "^http://localhost/(.*)"
|
||||||
# replacement = "http://mydomain/$1"
|
# replacement = "http://mydomain/$1"
|
||||||
|
#
|
||||||
|
# To enable basic auth on an entrypoint
|
||||||
|
# with 2 user/pass: test:test and test2:test2
|
||||||
|
# Passwords can be encoded in MD5, SHA1 and BCrypt: you can use htpasswd to generate those ones
|
||||||
|
# [entryPoints]
|
||||||
|
# [entryPoints.http]
|
||||||
|
# address = ":80"
|
||||||
|
# [entryPoints.http.auth.basic]
|
||||||
|
# users = ["test:$apr1$H6uskkkW$IgXLP6ewTrSuBkTrqE8wj/", "test2:$apr1$d9hr9HBB$4HxwgUir3HP4EsggP/QNo0"]
|
||||||
|
#
|
||||||
|
# To enable digest auth on an entrypoint
|
||||||
|
# with 2 user/realm/pass: test:traefik:test and test2:traefik:test2
|
||||||
|
# You can use htdigest to generate those ones
|
||||||
|
# [entryPoints]
|
||||||
|
# [entryPoints.http]
|
||||||
|
# address = ":80"
|
||||||
|
# [entryPoints.http.auth.basic]
|
||||||
|
# users = ["test:traefik:a2688e031edb4be6a3797f3882655c05 ", "test2:traefik:518845800f9e2bfb1f1f740ec24f074e"]
|
||||||
|
|
||||||
|
|
||||||
# Enable retry sending request if network error
|
# Enable retry sending request if network error
|
||||||
#
|
#
|
||||||
|
@ -183,3 +183,22 @@ func (cs *Constraints) SetValue(val interface{}) {
|
|||||||
func (cs *Constraints) Type() string {
|
func (cs *Constraints) Type() string {
|
||||||
return fmt.Sprint("constraint")
|
return fmt.Sprint("constraint")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Auth holds authentication configuration (BASIC, DIGEST, users)
|
||||||
|
type Auth struct {
|
||||||
|
Basic *Basic
|
||||||
|
Digest *Digest
|
||||||
|
}
|
||||||
|
|
||||||
|
// Users authentication users
|
||||||
|
type Users []string
|
||||||
|
|
||||||
|
// Basic HTTP basic authentication
|
||||||
|
type Basic struct {
|
||||||
|
Users
|
||||||
|
}
|
||||||
|
|
||||||
|
// Digest HTTP authentication
|
||||||
|
type Digest struct {
|
||||||
|
Users
|
||||||
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user