As we reevaluate how to best support and maintain Staging Ref in the future, we encourage development teams using this environment to highlight their use cases in the following issue: https://gitlab.com/gitlab-com/gl-infra/software-delivery/framework/software-delivery-framework-issue-tracker/-/issues/36.

Skip to content
Snippets Groups Projects
Unverified Commit c233b2c5 authored by Igor Drozdov's avatar Igor Drozdov Committed by GitLab
Browse files

Merge branch 'add_pat_config_object' into 'main'

parents 7c3c1ba7 2e8cb44b
No related branches found
No related tags found
No related merge requests found
Loading
Loading
@@ -127,7 +127,9 @@ func Build(args *commandargs.Shell, config *config.Config, readWriter *readwrite
case commandargs.UploadArchive:
return &uploadarchive.Command{Config: config, Args: args, ReadWriter: readWriter}
case commandargs.PersonalAccessToken:
return &personalaccesstoken.Command{Config: config, Args: args, ReadWriter: readWriter}
if config.PATConfig.Enabled {
return &personalaccesstoken.Command{Config: config, Args: args, ReadWriter: readWriter}
}
}
return nil
Loading
Loading
Loading
Loading
@@ -24,7 +24,7 @@ import (
var (
gitlabShellExec = &executable.Executable{Name: executable.GitlabShell}
basicConfig = &config.Config{GitlabUrl: "http+unix://gitlab.socket"}
basicConfig = &config.Config{GitlabUrl: "http+unix://gitlab.socket", PATConfig: config.PATConfig{Enabled: true}}
)
func TestNew(t *testing.T) {
Loading
Loading
@@ -143,6 +143,47 @@ func TestLFSTransferCommands(t *testing.T) {
})
}
}
func TestPATCommands(t *testing.T) {
testCases := []struct {
desc string
executable *executable.Executable
env sshenv.Env
arguments []string
config *config.Config
expectedType interface{}
errorString string
}{
{
desc: "it returns a PersonalAccessToken command",
executable: gitlabShellExec,
env: buildEnv("personal_access_token"),
config: basicConfig,
expectedType: &personalaccesstoken.Command{},
errorString: "",
},
{
desc: "it does not return a PersonalAccessToken command when config disallows it",
executable: gitlabShellExec,
env: buildEnv("personal_access_token"),
config: &config.Config{GitlabUrl: "http+unix://gitlab.socket", PATConfig: config.PATConfig{Enabled: false}},
expectedType: nil,
errorString: "Disallowed command",
},
}
for _, tc := range testCases {
t.Run(tc.desc, func(t *testing.T) {
command, err := cmd.New(tc.arguments, tc.env, tc.config, nil)
if len(tc.errorString) > 0 {
require.Equal(t, err.Error(), tc.errorString)
}
require.IsType(t, tc.expectedType, command)
})
}
}
func TestFailingNew(t *testing.T) {
testCases := []struct {
desc string
Loading
Loading
Loading
Loading
@@ -4,6 +4,7 @@ import (
"context"
"errors"
"fmt"
"slices"
"strconv"
"strings"
"time"
Loading
Loading
@@ -60,9 +61,21 @@ func (c *Command) parseTokenArgs() error {
if len(c.Args.SshArgs) < 3 || len(c.Args.SshArgs) > 4 {
return errors.New(usageText)
}
var rectfiedScopes []string
requestedScopes := strings.Split(c.Args.SshArgs[2], ",")
if len(c.Config.PATConfig.AllowedScopes) > 0 {
for _, requestedScope := range requestedScopes {
if slices.Contains(c.Config.PATConfig.AllowedScopes, requestedScope) {
rectfiedScopes = append(rectfiedScopes, requestedScope)
}
}
} else {
rectfiedScopes = requestedScopes
}
c.TokenArgs = &tokenArgs{
Name: c.Args.SshArgs[1],
Scopes: strings.Split(c.Args.SshArgs[2], ","),
Scopes: rectfiedScopes,
}
if len(c.Args.SshArgs) < 4 {
Loading
Loading
Loading
Loading
@@ -6,6 +6,7 @@ import (
"encoding/json"
"io"
"net/http"
"strings"
"testing"
"github.com/stretchr/testify/require"
Loading
Loading
@@ -41,6 +42,14 @@ func setup(t *testing.T) {
json.NewEncoder(w).Encode(body)
case "broken":
w.WriteHeader(http.StatusInternalServerError)
case "invalidscope":
message := "Invalid scope: '" + strings.Join(requestBody.Scopes, ",") + "'."
message += " Valid scopes are: [\"api\", \"create_runner\", \"k8s_proxy\", \"read_api\", \"read_registry\", \"read_repository\", \"read_user\", \"write_registry\", \"write_repository\"]"
body := map[string]interface{}{
"success": false,
"message": message,
}
json.NewEncoder(w).Encode(body)
case "badresponse":
default:
var expiresAt interface{}
Loading
Loading
@@ -73,6 +82,7 @@ func TestExecute(t *testing.T) {
testCases := []struct {
desc string
PATConfig config.PATConfig
arguments *commandargs.Shell
expectedOutput string
expectedError string
Loading
Loading
@@ -154,6 +164,48 @@ func TestExecute(t *testing.T) {
},
expectedError: "who='' is invalid",
},
{
desc: "With restricted scopes",
PATConfig: config.PATConfig{AllowedScopes: []string{"read_api"}},
arguments: &commandargs.Shell{
GitlabKeyId: "default",
SshArgs: []string{cmdname, "newtoken", "read_api,read_repository"},
},
expectedOutput: "Token: YXuxvUgCEmeePY3G1YAa\n" +
"Scopes: read_api\n" +
"Expires: 9001-11-17\n",
},
{
desc: "With unknown configured scopes",
PATConfig: config.PATConfig{AllowedScopes: []string{"read_reposotory"}},
arguments: &commandargs.Shell{
GitlabKeyId: "default",
SshArgs: []string{cmdname, "newtoken", "read_api,read_repository"},
},
expectedOutput: "Token: YXuxvUgCEmeePY3G1YAa\n" +
"Scopes: \n" +
"Expires: 9001-11-17\n",
},
{
desc: "With unknown requested scopes",
PATConfig: config.PATConfig{AllowedScopes: []string{"read_api", "read_repository"}},
arguments: &commandargs.Shell{
GitlabKeyId: "default",
SshArgs: []string{cmdname, "newtoken", "read_api,read_reposotory"},
},
expectedOutput: "Token: YXuxvUgCEmeePY3G1YAa\n" +
"Scopes: read_api\n" +
"Expires: 9001-11-17\n",
},
{
desc: "With matching unknown requested scopes",
PATConfig: config.PATConfig{AllowedScopes: []string{"read_api", "read_reposotory"}},
arguments: &commandargs.Shell{
GitlabKeyId: "invalidscope",
SshArgs: []string{cmdname, "newtoken", "read_reposotory"},
},
expectedError: "Invalid scope: 'read_reposotory'. Valid scopes are: [\"api\", \"create_runner\", \"k8s_proxy\", \"read_api\", \"read_registry\", \"read_repository\", \"read_user\", \"write_registry\", \"write_repository\"]",
},
}
for _, tc := range testCases {
Loading
Loading
@@ -162,7 +214,7 @@ func TestExecute(t *testing.T) {
input := bytes.NewBufferString("")
cmd := &Command{
Config: &config.Config{GitlabUrl: url},
Config: &config.Config{GitlabUrl: url, PATConfig: tc.PATConfig},
Args: tc.arguments,
ReadWriter: &readwriter.ReadWriter{Out: output, In: input},
}
Loading
Loading
Loading
Loading
@@ -65,6 +65,11 @@ type LFSConfig struct {
PureSSHProtocol bool // `yaml:"pure_ssh_protocol"`
}
type PATConfig struct {
Enabled bool `yaml:"enabled,omitempty"`
AllowedScopes []string `yaml:"allowed_scopes,omitempty"`
}
type Config struct {
User string `yaml:"user,omitempty"`
RootDir string
Loading
Loading
@@ -81,6 +86,7 @@ type Config struct {
HttpSettings HttpSettingsConfig `yaml:"http_settings"`
Server ServerConfig `yaml:"sshd"`
LFSConfig LFSConfig `yaml:"lfs"`
PATConfig PATConfig `yaml:"pat"`
httpClient *client.HTTPClient
httpClientErr error
Loading
Loading
@@ -97,6 +103,7 @@ var (
LogLevel: "info",
Server: DefaultServerConfig,
User: "git",
PATConfig: DefaultPATConfig,
}
DefaultServerConfig = ServerConfig{
Loading
Loading
@@ -115,6 +122,10 @@ var (
"/run/secrets/ssh-hostkeys/ssh_host_ed25519_key",
},
}
DefaultPATConfig = PATConfig{
Enabled: true,
}
)
func (d *YamlDuration) UnmarshalYAML(unmarshal func(interface{}) error) error {
Loading
Loading
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment