2023-03-15 16:00:52 +00:00
|
|
|
// Copyright (c) HashiCorp, Inc.
|
|
|
|
// SPDX-License-Identifier: MPL-2.0
|
|
|
|
|
2017-02-07 21:04:27 +00:00
|
|
|
package radius
|
|
|
|
|
|
|
|
import (
|
2018-01-19 06:44:44 +00:00
|
|
|
"context"
|
2017-02-07 21:04:27 +00:00
|
|
|
"fmt"
|
|
|
|
"os"
|
|
|
|
"reflect"
|
2018-04-11 18:26:35 +00:00
|
|
|
"strconv"
|
2020-09-15 14:01:26 +00:00
|
|
|
"strings"
|
2017-02-07 21:04:27 +00:00
|
|
|
"testing"
|
|
|
|
"time"
|
|
|
|
|
2019-04-12 21:54:35 +00:00
|
|
|
logicaltest "github.com/hashicorp/vault/helper/testhelpers/logical"
|
2023-04-24 18:25:50 +00:00
|
|
|
"github.com/hashicorp/vault/sdk/helper/docker"
|
2019-04-13 07:44:06 +00:00
|
|
|
"github.com/hashicorp/vault/sdk/logical"
|
2017-02-07 21:04:27 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
const (
|
|
|
|
testSysTTL = time.Hour * 10
|
|
|
|
testSysMaxTTL = time.Hour * 20
|
2018-04-11 18:26:35 +00:00
|
|
|
|
|
|
|
envRadiusRadiusHost = "RADIUS_HOST"
|
|
|
|
envRadiusPort = "RADIUS_PORT"
|
|
|
|
envRadiusSecret = "RADIUS_SECRET"
|
|
|
|
envRadiusUsername = "RADIUS_USERNAME"
|
|
|
|
envRadiusUserPass = "RADIUS_USERPASS"
|
2017-02-07 21:04:27 +00:00
|
|
|
)
|
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
func prepareRadiusTestContainer(t *testing.T) (func(), string, int) {
|
|
|
|
if os.Getenv(envRadiusRadiusHost) != "" {
|
|
|
|
port, _ := strconv.Atoi(os.Getenv(envRadiusPort))
|
|
|
|
return func() {}, os.Getenv(envRadiusRadiusHost), port
|
|
|
|
}
|
|
|
|
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
// Now allow any client to connect to this radiusd instance by writing our
|
|
|
|
// own clients.conf file.
|
|
|
|
//
|
|
|
|
// This is necessary because we lack control over the container's network
|
|
|
|
// IPs. We might be running in Circle CI (with variable IPs per new
|
|
|
|
// network) or in Podman (which uses an entirely different set of default
|
|
|
|
// ranges than Docker).
|
|
|
|
//
|
|
|
|
// See also: https://freeradius.org/radiusd/man/clients.conf.html
|
|
|
|
ctx := context.Background()
|
2022-10-12 14:29:39 +00:00
|
|
|
clientsConfig := `
|
|
|
|
client 0.0.0.0/1 {
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
ipaddr = 0.0.0.0/1
|
|
|
|
secret = testing123
|
|
|
|
shortname = all-clients-first
|
|
|
|
}
|
|
|
|
|
|
|
|
client 128.0.0.0/1 {
|
|
|
|
ipaddr = 128.0.0.0/1
|
|
|
|
secret = testing123
|
|
|
|
shortname = all-clients-second
|
2022-10-12 14:29:39 +00:00
|
|
|
}
|
|
|
|
`
|
|
|
|
|
|
|
|
containerfile := `
|
2022-11-02 17:33:17 +00:00
|
|
|
FROM docker.mirror.hashicorp.services/jumanjiman/radiusd:latest
|
2022-10-12 14:29:39 +00:00
|
|
|
|
|
|
|
COPY clients.conf /etc/raddb/clients.conf
|
|
|
|
`
|
|
|
|
|
|
|
|
bCtx := docker.NewBuildContext()
|
|
|
|
bCtx["clients.conf"] = docker.PathContentsFromBytes([]byte(clientsConfig))
|
|
|
|
|
|
|
|
imageName := "vault_radiusd_any_client"
|
|
|
|
imageTag := "latest"
|
|
|
|
|
|
|
|
runner, err := docker.NewServiceRunner(docker.RunOptions{
|
|
|
|
ImageRepo: imageName,
|
|
|
|
ImageTag: imageTag,
|
|
|
|
ContainerName: "radiusd",
|
|
|
|
Cmd: []string{"-f", "-l", "stdout", "-X"},
|
|
|
|
Ports: []string{"1812/udp"},
|
|
|
|
LogConsumer: func(s string) {
|
|
|
|
if t.Failed() {
|
|
|
|
t.Logf("container logs: %s", s)
|
|
|
|
}
|
|
|
|
},
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
})
|
|
|
|
if err != nil {
|
2022-10-12 14:29:39 +00:00
|
|
|
t.Fatalf("Could not provision docker service runner: %s", err)
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
}
|
2022-10-12 14:29:39 +00:00
|
|
|
|
|
|
|
output, err := runner.BuildImage(ctx, containerfile, bCtx,
|
|
|
|
docker.BuildRemove(true), docker.BuildForceRemove(true),
|
|
|
|
docker.BuildPullParent(true),
|
|
|
|
docker.BuildTags([]string{imageName + ":" + imageTag}))
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
if err != nil {
|
2022-10-12 14:29:39 +00:00
|
|
|
t.Fatalf("Could not build new image: %v", err)
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
}
|
2022-10-12 14:29:39 +00:00
|
|
|
|
|
|
|
t.Logf("Image build output: %v", string(output))
|
|
|
|
|
|
|
|
svc, err := runner.StartService(context.Background(), func(ctx context.Context, host string, port int) (docker.ServiceConfig, error) {
|
|
|
|
time.Sleep(2 * time.Second)
|
|
|
|
return docker.NewServiceHostPort(host, port), nil
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
})
|
|
|
|
if err != nil {
|
2022-10-12 14:29:39 +00:00
|
|
|
t.Fatalf("Could not start docker radiusd: %s", err)
|
Fix radiusd network connection limitations (#17049)
* Allow exposing access to the underlying container
This exposes the Container response from the Docker API, allowing
consumers of the testhelper to interact with the newly started running
container instance. This will be useful for two reasons:
1. Allowing radiusd container to start its own daemon after modifying
its configuration.
2. For loading certificates into a future similar integration test
using the PKI secrets engine.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
* Allow any client to connect to test radiusd daemon
This fixes test failures of the following form:
> 2022-09-07T10:46:19.332-0400 [TRACE] core: adding local paths: paths=[]
> 2022-09-07T10:46:19.333-0400 [INFO] core: enabled credential backend: path=mnt/ type=test
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=1
> 2022-09-07T10:46:19.334-0400 [WARN] Executing test step: step_number=2
> 2022-09-07T10:46:29.334-0400 [WARN] Executing test step: step_number=3
> 2022-09-07T10:46:29.335-0400 [WARN] Executing test step: step_number=4
> 2022-09-07T10:46:39.336-0400 [WARN] Requesting RollbackOperation
> --- FAIL: TestBackend_acceptance (28.56s)
> testing.go:364: Failed step 4: erroneous response:
>
> &logical.Response{Secret:<nil>, Auth:<nil>, Data:map[string]interface {}{"error":"context deadline exceeded"}, Redirect:"", Warnings:[]string(nil), WrapInfo:(*wrapping.ResponseWrapInfo)(nil), Headers:map[string][]string(nil)}
> FAIL
> FAIL github.com/hashicorp/vault/builtin/credential/radius 29.238s
In particular, radiusd container ships with a default clients.conf which
restricts connections to ranges associated with the Docker daemon. When
creating new networks (such as in CircleCI) or when running via Podman
(which has its own set of network ranges), this initial config will no
longer be applicable. We thus need to write a new config into the image;
while we could do this by rebuilding a new image on top of the existing
layers (provisioning our config), we then need to manage these changes
and give hooks for the service setup to build it.
Thus, post-startup modification is probably easier to execute in our
case.
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
Signed-off-by: Alexander Scheel <alex.scheel@hashicorp.com>
2022-09-07 17:43:22 +00:00
|
|
|
}
|
|
|
|
|
2020-09-15 14:01:26 +00:00
|
|
|
pieces := strings.Split(svc.Config.Address(), ":")
|
|
|
|
port, _ := strconv.Atoi(pieces[1])
|
|
|
|
return svc.Cleanup, pieces[0], port
|
2018-04-11 18:26:35 +00:00
|
|
|
}
|
|
|
|
|
2017-02-07 21:04:27 +00:00
|
|
|
func TestBackend_Config(t *testing.T) {
|
2018-01-19 06:44:44 +00:00
|
|
|
b, err := Factory(context.Background(), &logical.BackendConfig{
|
2017-02-07 21:04:27 +00:00
|
|
|
Logger: nil,
|
|
|
|
System: &logical.StaticSystemView{
|
|
|
|
DefaultLeaseTTLVal: testSysTTL,
|
|
|
|
MaxLeaseTTLVal: testSysMaxTTL,
|
|
|
|
},
|
|
|
|
})
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Unable to create backend: %s", err)
|
|
|
|
}
|
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
configDataBasic := map[string]interface{}{
|
2017-02-07 21:04:27 +00:00
|
|
|
"host": "test.radius.hostname.com",
|
|
|
|
"secret": "test-secret",
|
|
|
|
}
|
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
configDataMissingRequired := map[string]interface{}{
|
2017-02-07 21:04:27 +00:00
|
|
|
"host": "test.radius.hostname.com",
|
|
|
|
}
|
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
configDataEmptyPort := map[string]interface{}{
|
|
|
|
"host": "test.radius.hostname.com",
|
|
|
|
"port": "",
|
|
|
|
"secret": "test-secret",
|
|
|
|
}
|
|
|
|
|
|
|
|
configDataInvalidPort := map[string]interface{}{
|
2017-02-07 21:04:27 +00:00
|
|
|
"host": "test.radius.hostname.com",
|
|
|
|
"port": "notnumeric",
|
|
|
|
"secret": "test-secret",
|
|
|
|
}
|
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
configDataInvalidBool := map[string]interface{}{
|
2017-02-07 21:04:27 +00:00
|
|
|
"host": "test.radius.hostname.com",
|
|
|
|
"secret": "test-secret",
|
|
|
|
"unregistered_user_policies": "test",
|
|
|
|
}
|
|
|
|
|
|
|
|
logicaltest.Test(t, logicaltest.TestCase{
|
|
|
|
AcceptanceTest: false,
|
|
|
|
// PreCheck: func() { testAccPreCheck(t) },
|
2018-11-07 01:21:24 +00:00
|
|
|
CredentialBackend: b,
|
2017-02-07 21:04:27 +00:00
|
|
|
Steps: []logicaltest.TestStep{
|
2018-04-11 18:26:35 +00:00
|
|
|
testConfigWrite(t, configDataBasic, false),
|
|
|
|
testConfigWrite(t, configDataMissingRequired, true),
|
|
|
|
testConfigWrite(t, configDataEmptyPort, true),
|
|
|
|
testConfigWrite(t, configDataInvalidPort, true),
|
|
|
|
testConfigWrite(t, configDataInvalidBool, true),
|
2017-02-07 21:04:27 +00:00
|
|
|
},
|
|
|
|
})
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestBackend_users(t *testing.T) {
|
2018-01-19 06:44:44 +00:00
|
|
|
b, err := Factory(context.Background(), &logical.BackendConfig{
|
2017-02-07 21:04:27 +00:00
|
|
|
Logger: nil,
|
|
|
|
System: &logical.StaticSystemView{
|
|
|
|
DefaultLeaseTTLVal: testSysTTL,
|
|
|
|
MaxLeaseTTLVal: testSysMaxTTL,
|
|
|
|
},
|
|
|
|
})
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Unable to create backend: %s", err)
|
|
|
|
}
|
|
|
|
logicaltest.Test(t, logicaltest.TestCase{
|
2018-11-07 01:21:24 +00:00
|
|
|
CredentialBackend: b,
|
2017-02-07 21:04:27 +00:00
|
|
|
Steps: []logicaltest.TestStep{
|
|
|
|
testStepUpdateUser(t, "web", "foo"),
|
|
|
|
testStepUpdateUser(t, "web2", "foo"),
|
|
|
|
testStepUpdateUser(t, "web3", "foo"),
|
|
|
|
testStepUserList(t, []string{"web", "web2", "web3"}),
|
|
|
|
},
|
|
|
|
})
|
|
|
|
}
|
|
|
|
|
|
|
|
func TestBackend_acceptance(t *testing.T) {
|
2018-01-19 06:44:44 +00:00
|
|
|
b, err := Factory(context.Background(), &logical.BackendConfig{
|
2017-02-07 21:04:27 +00:00
|
|
|
Logger: nil,
|
|
|
|
System: &logical.StaticSystemView{
|
|
|
|
DefaultLeaseTTLVal: testSysTTL,
|
|
|
|
MaxLeaseTTLVal: testSysMaxTTL,
|
|
|
|
},
|
|
|
|
})
|
|
|
|
if err != nil {
|
|
|
|
t.Fatalf("Unable to create backend: %s", err)
|
|
|
|
}
|
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
cleanup, host, port := prepareRadiusTestContainer(t)
|
|
|
|
defer cleanup()
|
|
|
|
|
|
|
|
// These defaults are specific to the jumanjiman/radiusd docker image
|
|
|
|
username := os.Getenv(envRadiusUsername)
|
|
|
|
if username == "" {
|
|
|
|
username = "test"
|
|
|
|
}
|
|
|
|
|
|
|
|
password := os.Getenv(envRadiusUserPass)
|
|
|
|
if password == "" {
|
|
|
|
password = "test"
|
|
|
|
}
|
|
|
|
|
|
|
|
secret := os.Getenv(envRadiusSecret)
|
|
|
|
if len(secret) == 0 {
|
|
|
|
secret = "testing123"
|
|
|
|
}
|
|
|
|
|
2017-02-07 21:04:27 +00:00
|
|
|
configDataAcceptanceAllowUnreg := map[string]interface{}{
|
2018-04-11 18:26:35 +00:00
|
|
|
"host": host,
|
|
|
|
"port": strconv.Itoa(port),
|
|
|
|
"secret": secret,
|
2017-02-07 21:04:27 +00:00
|
|
|
"unregistered_user_policies": "policy1,policy2",
|
|
|
|
}
|
|
|
|
if configDataAcceptanceAllowUnreg["port"] == "" {
|
|
|
|
configDataAcceptanceAllowUnreg["port"] = "1812"
|
|
|
|
}
|
|
|
|
|
|
|
|
configDataAcceptanceNoAllowUnreg := map[string]interface{}{
|
2018-04-11 18:26:35 +00:00
|
|
|
"host": host,
|
|
|
|
"port": strconv.Itoa(port),
|
|
|
|
"secret": secret,
|
2017-02-07 21:04:27 +00:00
|
|
|
"unregistered_user_policies": "",
|
|
|
|
}
|
|
|
|
if configDataAcceptanceNoAllowUnreg["port"] == "" {
|
|
|
|
configDataAcceptanceNoAllowUnreg["port"] = "1812"
|
|
|
|
}
|
|
|
|
|
|
|
|
dataRealpassword := map[string]interface{}{
|
2018-04-11 18:26:35 +00:00
|
|
|
"password": password,
|
2017-02-07 21:04:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
dataWrongpassword := map[string]interface{}{
|
|
|
|
"password": "wrongpassword",
|
|
|
|
}
|
|
|
|
|
|
|
|
logicaltest.Test(t, logicaltest.TestCase{
|
2018-11-07 01:21:24 +00:00
|
|
|
CredentialBackend: b,
|
|
|
|
PreCheck: testAccPreCheck(t, host, port),
|
2017-02-07 21:04:27 +00:00
|
|
|
Steps: []logicaltest.TestStep{
|
2019-03-19 13:32:45 +00:00
|
|
|
// Login with valid but unknown user will fail because unregistered_user_policies is empty
|
2017-02-07 21:04:27 +00:00
|
|
|
testConfigWrite(t, configDataAcceptanceNoAllowUnreg, false),
|
|
|
|
testAccUserLogin(t, username, dataRealpassword, true),
|
|
|
|
// Once the user is registered auth will succeed
|
|
|
|
testStepUpdateUser(t, username, ""),
|
|
|
|
testAccUserLoginPolicy(t, username, dataRealpassword, []string{"default"}, false),
|
|
|
|
|
|
|
|
testStepUpdateUser(t, username, "foopolicy"),
|
|
|
|
testAccUserLoginPolicy(t, username, dataRealpassword, []string{"default", "foopolicy"}, false),
|
|
|
|
testAccStepDeleteUser(t, username),
|
|
|
|
|
|
|
|
// When unregistered_user_policies is specified, an unknown user will be granted access and granted the listed policies
|
|
|
|
testConfigWrite(t, configDataAcceptanceAllowUnreg, false),
|
|
|
|
testAccUserLoginPolicy(t, username, dataRealpassword, []string{"default", "policy1", "policy2"}, false),
|
|
|
|
|
|
|
|
// More tests
|
|
|
|
testAccUserLogin(t, "nonexistinguser", dataRealpassword, true),
|
|
|
|
testAccUserLogin(t, username, dataWrongpassword, true),
|
|
|
|
testStepUpdateUser(t, username, "foopolicy"),
|
|
|
|
testAccUserLoginPolicy(t, username, dataRealpassword, []string{"default", "foopolicy"}, false),
|
|
|
|
testStepUpdateUser(t, username, "foopolicy, secondpolicy"),
|
|
|
|
testAccUserLoginPolicy(t, username, dataRealpassword, []string{"default", "foopolicy", "secondpolicy"}, false),
|
|
|
|
testAccUserLoginPolicy(t, username, dataRealpassword, []string{"default", "foopolicy", "secondpolicy", "thirdpolicy"}, true),
|
|
|
|
},
|
|
|
|
})
|
|
|
|
}
|
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
func testAccPreCheck(t *testing.T, host string, port int) func() {
|
|
|
|
return func() {
|
|
|
|
if host == "" {
|
|
|
|
t.Fatal("Host must be set for acceptance tests")
|
|
|
|
}
|
2017-02-07 21:04:27 +00:00
|
|
|
|
2018-04-11 18:26:35 +00:00
|
|
|
if port == 0 {
|
|
|
|
t.Fatal("Port must be non-zero for acceptance tests")
|
|
|
|
}
|
2017-02-07 21:04:27 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func testConfigWrite(t *testing.T, d map[string]interface{}, expectError bool) logicaltest.TestStep {
|
|
|
|
return logicaltest.TestStep{
|
|
|
|
Operation: logical.UpdateOperation,
|
|
|
|
Path: "config",
|
|
|
|
Data: d,
|
|
|
|
ErrorOk: expectError,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func testAccStepDeleteUser(t *testing.T, n string) logicaltest.TestStep {
|
|
|
|
return logicaltest.TestStep{
|
|
|
|
Operation: logical.DeleteOperation,
|
|
|
|
Path: "users/" + n,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func testStepUserList(t *testing.T, users []string) logicaltest.TestStep {
|
|
|
|
return logicaltest.TestStep{
|
|
|
|
Operation: logical.ListOperation,
|
|
|
|
Path: "users",
|
|
|
|
Check: func(resp *logical.Response) error {
|
|
|
|
if resp.IsError() {
|
2018-04-09 18:35:21 +00:00
|
|
|
return fmt.Errorf("got error response: %#v", *resp)
|
2017-02-07 21:04:27 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
if !reflect.DeepEqual(users, resp.Data["keys"].([]string)) {
|
|
|
|
return fmt.Errorf("expected:\n%#v\ngot:\n%#v\n", users, resp.Data["keys"])
|
|
|
|
}
|
|
|
|
return nil
|
|
|
|
},
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func testStepUpdateUser(
|
2022-09-08 00:31:20 +00:00
|
|
|
t *testing.T, name string, policies string,
|
|
|
|
) logicaltest.TestStep {
|
2017-02-07 21:04:27 +00:00
|
|
|
return logicaltest.TestStep{
|
|
|
|
Operation: logical.UpdateOperation,
|
|
|
|
Path: "users/" + name,
|
|
|
|
Data: map[string]interface{}{
|
|
|
|
"policies": policies,
|
|
|
|
},
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func testAccUserLogin(t *testing.T, user string, data map[string]interface{}, expectError bool) logicaltest.TestStep {
|
|
|
|
return logicaltest.TestStep{
|
|
|
|
Operation: logical.UpdateOperation,
|
|
|
|
Path: "login/" + user,
|
|
|
|
Data: data,
|
|
|
|
ErrorOk: expectError,
|
|
|
|
Unauthenticated: true,
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func testAccUserLoginPolicy(t *testing.T, user string, data map[string]interface{}, policies []string, expectError bool) logicaltest.TestStep {
|
|
|
|
return logicaltest.TestStep{
|
|
|
|
Operation: logical.UpdateOperation,
|
|
|
|
Path: "login/" + user,
|
|
|
|
Data: data,
|
2018-04-11 18:26:35 +00:00
|
|
|
ErrorOk: expectError,
|
2017-02-07 21:04:27 +00:00
|
|
|
Unauthenticated: true,
|
2021-04-08 16:43:39 +00:00
|
|
|
// Check: logicaltest.TestCheckAuth(policies),
|
2017-02-07 21:04:27 +00:00
|
|
|
Check: func(resp *logical.Response) error {
|
|
|
|
res := logicaltest.TestCheckAuth(policies)(resp)
|
|
|
|
if res != nil && expectError {
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
return res
|
|
|
|
},
|
|
|
|
}
|
|
|
|
}
|