Skip to content

Commit

Permalink
Export test-specific functions without go:linkname
Browse files Browse the repository at this point in the history
Using go:linkname is poorly supported by tooling, for example it breaks
code navigation because IDEs don't support going to the function's
implementation.

To still make it clear that those functions are only for use in tests,
and to group test-specific functions together in code completion lists,
we are now prefixing them with "Z_ForTests". The "Z_" should ensure that
they are listed at the end (although that doesn't work for Intellij
unfortunately).
  • Loading branch information
adombeck committed Dec 2, 2024
1 parent dc25e00 commit 3f9eb52
Show file tree
Hide file tree
Showing 17 changed files with 150 additions and 222 deletions.
4 changes: 2 additions & 2 deletions cmd/authd/daemon/daemon_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ import (
"github.com/ubuntu/authd/cmd/authd/daemon"
"github.com/ubuntu/authd/internal/consts"
"github.com/ubuntu/authd/internal/testutils"
cachetestutils "github.com/ubuntu/authd/internal/users/cache/testutils"
"github.com/ubuntu/authd/internal/users/cache"
)

func TestHelp(t *testing.T) {
Expand Down Expand Up @@ -176,7 +176,7 @@ func TestAppRunFailsOnComponentsCreationAndQuit(t *testing.T) {
err := os.MkdirAll(config.Paths.Cache, 0700)
require.NoError(t, err, "Setup: could not create cache directory")
//nolint: gosec // This is a file with invalid permission for tests.
err = os.WriteFile(filepath.Join(config.Paths.Cache, cachetestutils.DbName), nil, 0644)
err = os.WriteFile(filepath.Join(config.Paths.Cache, cache.Z_ForTests_DBName()), nil, 0644)
require.NoError(t, err, "Setup: could not create database with invalid permissions")
}

Expand Down
10 changes: 5 additions & 5 deletions cmd/authd/integrationtests.go
Original file line number Diff line number Diff line change
Expand Up @@ -6,21 +6,21 @@ import (
"os"
"strings"

permissionstestutils "github.com/ubuntu/authd/internal/services/permissions/testutils"
localgroupstestutils "github.com/ubuntu/authd/internal/users/localgroups/testutils"
"github.com/ubuntu/authd/internal/services/permissions"
"github.com/ubuntu/authd/internal/users/localgroups"
)

// load any behaviour modifiers from env variable.
func init() {
if os.Getenv("AUTHD_INTEGRATIONTESTS_CURRENT_USER_AS_ROOT") != "" {
permissionstestutils.DefaultCurrentUserAsRoot()
permissions.Z_ForTests_DefaultCurrentUserAsRoot()
}

gpasswdArgs := os.Getenv("AUTHD_INTEGRATIONTESTS_GPASSWD_ARGS")
grpFilePath := os.Getenv("AUTHD_INTEGRATIONTESTS_GPASSWD_GRP_FILE_PATH")
if gpasswdArgs == "" || grpFilePath == "" {
panic("AUTHD_INTEGRATIONTESTS_GPASSWD_ARGS and AUTHD_INTEGRATIONTESTS_GPASSWD_GRP_FILE_PATH must be set")
}
localgroupstestutils.SetGpasswdCmd(strings.Split(gpasswdArgs, " "))
localgroupstestutils.SetGroupPath(grpFilePath)
localgroups.Z_ForTests_SetGpasswdCmd(strings.Split(gpasswdArgs, " "))
localgroups.Z_ForTests_SetGroupPath(grpFilePath)
}
7 changes: 3 additions & 4 deletions internal/services/nss/nss_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,10 +14,9 @@ import (
"github.com/ubuntu/authd/internal/services/errmessages"
"github.com/ubuntu/authd/internal/services/nss"
"github.com/ubuntu/authd/internal/services/permissions"
permissionstestutils "github.com/ubuntu/authd/internal/services/permissions/testutils"
"github.com/ubuntu/authd/internal/testutils"
"github.com/ubuntu/authd/internal/users"
cachetestutils "github.com/ubuntu/authd/internal/users/cache/testutils"
"github.com/ubuntu/authd/internal/users/cache"
localgroupstestutils "github.com/ubuntu/authd/internal/users/localgroups/testutils"
"google.golang.org/grpc"
"google.golang.org/grpc/codes"
Expand Down Expand Up @@ -285,7 +284,7 @@ func newNSSClient(t *testing.T, sourceDB string, currentUserNotRoot bool) (clien

var opts []permissions.Option
if !currentUserNotRoot {
opts = append(opts, permissionstestutils.WithCurrentUserAsRoot())
opts = append(opts, permissions.Z_ForTests_WithCurrentUserAsRoot())
}
pm := permissions.New(opts...)

Expand Down Expand Up @@ -329,7 +328,7 @@ func newUserManagerForTests(t *testing.T, sourceDB string) *users.Manager {
if sourceDB == "" {
sourceDB = "cache.db.yaml"
}
cachetestutils.CreateDBFromYAML(t, filepath.Join("testdata", sourceDB), cacheDir)
cache.Z_ForTests_CreateDBFromYAML(t, filepath.Join("testdata", sourceDB), cacheDir)

m, err := users.NewManager(users.DefaultConfig, cacheDir)
require.NoError(t, err, "Setup: could not create user manager")
Expand Down
27 changes: 13 additions & 14 deletions internal/services/pam/pam_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,10 +21,9 @@ import (
"github.com/ubuntu/authd/internal/services/errmessages"
"github.com/ubuntu/authd/internal/services/pam"
"github.com/ubuntu/authd/internal/services/permissions"
permissionstestutils "github.com/ubuntu/authd/internal/services/permissions/testutils"
"github.com/ubuntu/authd/internal/testutils"
"github.com/ubuntu/authd/internal/users"
cachetestutils "github.com/ubuntu/authd/internal/users/cache/testutils"
"github.com/ubuntu/authd/internal/users/cache"
localgroupstestutils "github.com/ubuntu/authd/internal/users/localgroups/testutils"
userstestutils "github.com/ubuntu/authd/internal/users/testutils"
"google.golang.org/grpc"
Expand Down Expand Up @@ -154,7 +153,7 @@ func TestGetPreviousBroker(t *testing.T) {
d, err := io.ReadAll(f)
require.NoError(t, err, "Setup: could not read fixture database file")
d = bytes.ReplaceAll(d, []byte("MOCKBROKERID"), []byte(mockBrokerGeneratedID))
err = cachetestutils.DbfromYAML(bytes.NewBuffer(d), cacheDir)
err = cache.Z_ForTests_FromYAML(bytes.NewBuffer(d), cacheDir)
require.NoError(t, err, "Setup: could not prepare cache database file")

m, err := users.NewManager(users.DefaultConfig, cacheDir)
Expand Down Expand Up @@ -297,7 +296,7 @@ func TestGetAuthenticationModes(t *testing.T) {
}

// Now, set tests permissions for this use case
permissionstestutils.SetCurrentUserAsRoot(&pm, !tc.currentUserNotRoot)
pm.Z_ForTests_SetCurrentUserAsRoot(!tc.currentUserNotRoot)

if tc.supportedUILayouts == nil {
tc.supportedUILayouts = []*authd.UILayout{requiredEntry}
Expand Down Expand Up @@ -391,7 +390,7 @@ func TestSelectAuthenticationMode(t *testing.T) {
}

// Now, set tests permissions for this use case
permissionstestutils.SetCurrentUserAsRoot(&pm, !tc.currentUserNotRoot)
pm.Z_ForTests_SetCurrentUserAsRoot(!tc.currentUserNotRoot)

samReq := &authd.SAMRequest{
SessionId: tc.sessionID,
Expand Down Expand Up @@ -461,7 +460,7 @@ func TestIsAuthenticated(t *testing.T) {

cacheDir := t.TempDir()
if tc.existingDB != "" {
cachetestutils.CreateDBFromYAML(t, filepath.Join(testutils.TestFamilyPath(t), tc.existingDB), cacheDir)
cache.Z_ForTests_CreateDBFromYAML(t, filepath.Join(testutils.TestFamilyPath(t), tc.existingDB), cacheDir)
}

m, err := users.NewManager(users.DefaultConfig, cacheDir)
Expand All @@ -482,7 +481,7 @@ func TestIsAuthenticated(t *testing.T) {
}

// Now, set tests permissions for this use case
permissionstestutils.SetCurrentUserAsRoot(&pm, !tc.currentUserNotRoot)
pm.Z_ForTests_SetCurrentUserAsRoot(!tc.currentUserNotRoot)

var firstCall, secondCall string
ctx, cancel := context.WithCancel(context.Background())
Expand Down Expand Up @@ -525,12 +524,12 @@ func TestIsAuthenticated(t *testing.T) {
<-done

got := firstCall + secondCall
got = permissionstestutils.IdempotentPermissionError(got)
got = permissions.Z_ForTests_IdempotentPermissionError(got)
want := testutils.LoadWithUpdateFromGolden(t, got, testutils.WithGoldenPath(filepath.Join(testutils.GoldenPath(t), "IsAuthenticated")))
require.Equal(t, want, got, "IsAuthenticated should return the expected combined data, but did not")

// Check that cache has been updated too.
gotDB, err := cachetestutils.DumpNormalizedYAML(userstestutils.GetManagerCache(m))
gotDB, err := userstestutils.GetManagerCache(m).Z_ForTests_DumpNormalizedYAML()
require.NoError(t, err, "Setup: failed to dump database for comparing")
wantDB := testutils.LoadWithUpdateFromGolden(t, gotDB, testutils.WithGoldenPath(filepath.Join(testutils.GoldenPath(t), "cache.db")))
require.Equal(t, wantDB, gotDB, "IsAuthenticated should update the cache database as expected")
Expand Down Expand Up @@ -571,7 +570,7 @@ func TestIDGeneration(t *testing.T) {
require.NoError(t, err, "Setup: could not authenticate user")
require.Equal(t, "granted", resp.GetAccess(), "Setup: authentication should be granted")

gotDB, err := cachetestutils.DumpNormalizedYAML(userstestutils.GetManagerCache(m))
gotDB, err := userstestutils.GetManagerCache(m).Z_ForTests_DumpNormalizedYAML()
require.NoError(t, err, "Setup: failed to dump database for comparing")
wantDB := testutils.LoadWithUpdateFromGolden(t, gotDB, testutils.WithGoldenPath(filepath.Join(testutils.GoldenPath(t), "cache.db")))
require.Equal(t, wantDB, gotDB, "IsAuthenticated should update the cache database as expected")
Expand Down Expand Up @@ -603,7 +602,7 @@ func TestSetDefaultBrokerForUser(t *testing.T) {
t.Parallel()

cacheDir := t.TempDir()
cachetestutils.CreateDBFromYAML(t, filepath.Join(testutils.TestFamilyPath(t), "set-default-broker.db"), cacheDir)
cache.Z_ForTests_CreateDBFromYAML(t, filepath.Join(testutils.TestFamilyPath(t), "set-default-broker.db"), cacheDir)

m, err := users.NewManager(users.DefaultConfig, cacheDir)
require.NoError(t, err, "Setup: could not create user manager")
Expand Down Expand Up @@ -631,7 +630,7 @@ func TestSetDefaultBrokerForUser(t *testing.T) {
require.Equal(t, tc.brokerID, gpbResp.GetPreviousBroker(), "SetDefaultBrokerForUser should set the default broker as expected")

// Check that cache has been updated too.
gotDB, err := cachetestutils.DumpNormalizedYAML(userstestutils.GetManagerCache(m))
gotDB, err := userstestutils.GetManagerCache(m).Z_ForTests_DumpNormalizedYAML()
require.NoError(t, err, "Setup: failed to dump database for comparing")
wantDB := testutils.LoadWithUpdateFromGolden(t, gotDB, testutils.WithGoldenPath(filepath.Join(testutils.GoldenPath(t), "cache.db")))
require.Equal(t, wantDB, gotDB, "SetDefaultBrokerForUser should update the cache database as expected")
Expand Down Expand Up @@ -676,7 +675,7 @@ func TestEndSession(t *testing.T) {
}

// Now, set tests permissions for this use case
permissionstestutils.SetCurrentUserAsRoot(&pm, !tc.currentUserNotRoot)
pm.Z_ForTests_SetCurrentUserAsRoot(!tc.currentUserNotRoot)

esReq := &authd.ESRequest{
SessionId: tc.sessionID,
Expand Down Expand Up @@ -769,7 +768,7 @@ func newPermissionManager(t *testing.T, currentUserNotRoot bool) permissions.Man

var opts = []permissions.Option{}
if !currentUserNotRoot {
opts = append(opts, permissionstestutils.WithCurrentUserAsRoot())
opts = append(opts, permissions.Z_ForTests_WithCurrentUserAsRoot())
}
return permissions.New(opts...)
}
Expand Down
3 changes: 1 addition & 2 deletions internal/services/permissions/export_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,5 @@ func NewTestPeerCredsInfo(uid uint32, pid int32) PeerCredsInfo {
}

var (
CurrentUserUID = currentUserUID
WithCurrentUserAsRoot = withCurrentUserAsRoot
CurrentUserUID = currentUserUID
)
3 changes: 1 addition & 2 deletions internal/services/permissions/permissions_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,6 @@ import (

"github.com/stretchr/testify/require"
"github.com/ubuntu/authd/internal/services/permissions"
permissionstestutils "github.com/ubuntu/authd/internal/services/permissions/testutils"
"google.golang.org/grpc"
"google.golang.org/grpc/credentials"
"google.golang.org/grpc/peer"
Expand Down Expand Up @@ -63,7 +62,7 @@ func TestIsRequestFromRoot(t *testing.T) {

var opts []permissions.Option
if !tc.currentUserNotRoot {
opts = append(opts, permissionstestutils.WithCurrentUserAsRoot())
opts = append(opts, permissions.Z_ForTests_WithCurrentUserAsRoot())
}
pm := permissions.New(opts...)

Expand Down
31 changes: 26 additions & 5 deletions internal/services/permissions/testutils.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,12 +8,15 @@ import (
"math"
"os/user"
"strconv"
"strings"

"github.com/ubuntu/authd/internal/testsdetection"
)

// withCurrentUserAsRoot returns an Option that sets the rootUID to the current user's UID.
func withCurrentUserAsRoot() Option {
// Z_ForTests_WithCurrentUserAsRoot returns an Option that sets the rootUID to the current user's UID.
//
// nolint:revive,nolintlint // We want to use underscores in the function name here.
func Z_ForTests_WithCurrentUserAsRoot() Option {
testsdetection.MustBeTesting()

uid := currentUserUID()
Expand All @@ -38,10 +41,10 @@ func currentUserUID() uint32 {
return uint32(uid)
}

// setCurrentUserAsRoot mutates a default permission to the current user's UID if currentUserAsRoot is true.
// Z_ForTests_SetCurrentUserAsRoot mutates a default permission to the current user's UID if currentUserAsRoot is true.
//
//nolint:unused // false positive as used in permissionstests with linkname.
func (m *Manager) setCurrentUserAsRoot(currentUserAsRoot bool) {
// nolint:revive,nolintlint // We want to use underscores in the function name here.
func (m *Manager) Z_ForTests_SetCurrentUserAsRoot(currentUserAsRoot bool) {
testsdetection.MustBeTesting()

if !currentUserAsRoot {
Expand All @@ -51,3 +54,21 @@ func (m *Manager) setCurrentUserAsRoot(currentUserAsRoot bool) {

m.rootUID = currentUserUID()
}

// Z_ForTests_IdempotentPermissionError strips the UID from the permission error message.
//
// nolint:revive,nolintlint // We want to use underscores in the function name here.
func Z_ForTests_IdempotentPermissionError(msg string) string {
testsdetection.MustBeTesting()

return strings.ReplaceAll(msg, fmt.Sprint(currentUserUID()), "XXXX")
}

// Z_ForTests_DefaultCurrentUserAsRoot mocks the current user as root for the permission manager.
//
// nolint:revive,nolintlint // We want to use underscores in the function name here.
func Z_ForTests_DefaultCurrentUserAsRoot() {
testsdetection.MustBeTesting()

defaultOptions.rootUID = currentUserUID()
}
55 changes: 0 additions & 55 deletions internal/services/permissions/testutils/permissions.go

This file was deleted.

4 changes: 2 additions & 2 deletions internal/testutils/daemon.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import (

"github.com/stretchr/testify/require"
"github.com/ubuntu/authd/internal/services/errmessages"
cachetestutils "github.com/ubuntu/authd/internal/users/cache/testutils"
"github.com/ubuntu/authd/internal/users/cache"
"google.golang.org/grpc"
"google.golang.org/grpc/connectivity"
"google.golang.org/grpc/credentials/insecure"
Expand Down Expand Up @@ -77,7 +77,7 @@ func RunDaemon(ctx context.Context, t *testing.T, execPath string, args ...Daemo
}

if opts.existentDB != "" {
cachetestutils.CreateDBFromYAML(t, filepath.Join("testdata", "db", opts.existentDB+".db.yaml"), opts.cachePath)
cache.Z_ForTests_CreateDBFromYAML(t, filepath.Join("testdata", "db", opts.existentDB+".db.yaml"), opts.cachePath)
}

if opts.socketPath == "" {
Expand Down
Loading

0 comments on commit 3f9eb52

Please sign in to comment.