package integration
import (
"io/ioutil"
"os"
"runtime"
"testing"
"github.com/bazelbuild/sandboxfs/integration/utils"
)
func TestOptions_Allow(t *testing.T) {
root := utils.RequireRoot(t, "Requires root privileges to spawn sandboxfs under different users")
user := utils.GetConfig().UnprivilegedUser
if user == nil {
t.Skipf("unprivileged user not set; must contain the name of an unprivileged user with FUSE access")
}
t.Logf("Using primary unprivileged user: %v", user)
other, err := utils.LookupUserOtherThan(root.Username, user.Username)
if err != nil {
t.Fatal(err)
}
t.Logf("Using secondary unprivileged user: %v", other)
var allowRootWorks bool
switch runtime.GOOS {
case "darwin":
allowRootWorks = true
case "linux":
allowRootWorks = false
default:
t.Fatalf("Don't know how this test behaves in this platform")
}
testData := []struct {
name string
allowFlag string
wantMountOk bool
okUsers []*utils.UnixUser
notOkUsers []*utils.UnixUser
}{
{"Default", "", true, []*utils.UnixUser{user}, []*utils.UnixUser{root, other}},
{"Other", "--allow=other", true, []*utils.UnixUser{user, other, root}, []*utils.UnixUser{}},
{"Root", "--allow=root", allowRootWorks, []*utils.UnixUser{user, root}, []*utils.UnixUser{other}},
{"Self", "--allow=self", true, []*utils.UnixUser{user}, []*utils.UnixUser{root, other}},
}
for _, d := range testData {
t.Run(d.name, func(t *testing.T) {
tempDir, err := ioutil.TempDir("", "test")
if err != nil {
t.Fatalf("Failed to create temporary directory: %v", err)
}
defer os.RemoveAll(tempDir)
if !d.wantMountOk {
_, stderr, err := utils.RunAndWait(1, d.allowFlag, "--mapping=ro:/:/", tempDir)
if err != nil {
t.Fatal(err)
}
if !utils.MatchesRegexp("known.*broken", stderr) {
t.Errorf("Want error message to mention known brokenness; got %v", stderr)
}
return
}
args := []string{"--mapping=ro:/:%ROOT%"}
if d.allowFlag != "" {
args = append(args, d.allowFlag)
}
state := utils.MountSetupWithUser(t, user, args...)
defer state.TearDown(t)
utils.MustWriteFile(t, state.RootPath("file"), 0444, "")
file := state.MountPath("file")
for _, user := range d.okUsers {
if err := utils.FileExistsAsUser(file, user); err != nil {
t.Errorf("Failed to access mount point as user %s: %v", user.Username, err)
}
}
for _, user := range d.notOkUsers {
if err := utils.FileExistsAsUser(file, user); err == nil {
t.Errorf("Was able to access mount point as user %s; want error", user.Username)
}
}
})
}
}
func TestOptions_Syntax(t *testing.T) {
testData := []struct {
name string
args []string
wantStderr string
}{
{"AllowBadValue", []string{"--allow=foo"}, "foo.*must be one of.*other"},
}
for _, d := range testData {
t.Run(d.name, func(t *testing.T) {
stdout, stderr, err := utils.RunAndWait(2, d.args...)
if err != nil {
t.Fatal(err)
}
if len(stdout) > 0 {
t.Errorf("Got %s; want stdout to be empty", stdout)
}
if !utils.MatchesRegexp(d.wantStderr, stderr) {
t.Errorf("Got %s; want stderr to match %s", stderr, d.wantStderr)
}
if !utils.MatchesRegexp("--help", stderr) {
t.Errorf("Got %s; want --help mention in stderr", stderr)
}
})
}
}