From ee5c82965302c6aaa35a6f36e2e30b2624942416 Mon Sep 17 00:00:00 2001 From: Simone Gotti Date: Fri, 5 Jul 2019 13:33:29 +0200 Subject: [PATCH] *: add remote source option to disable registration/login * Make the new fields RegistrationEnabled/LoginEnabled in types.RemoteSource bool pointers (since they are new fields that don't exist in previously saved remote sources) and default them to true if null when unmarshaling (or existing remotesources will have registration and login disabled) * Add options to cmd remotesource create/update to set the registration/login disabled. --- cmd/agola/cmd/remotesourcecreate.go | 7 ++++++ cmd/agola/cmd/remotesourceupdate.go | 10 ++++++++ .../services/gateway/action/remotesource.go | 12 +++++++++ internal/services/gateway/action/user.go | 6 +++++ internal/services/gateway/api/remotesource.go | 24 +++++++++++++----- internal/services/types/types.go | 25 +++++++++++++++++++ 6 files changed, 78 insertions(+), 6 deletions(-) diff --git a/cmd/agola/cmd/remotesourcecreate.go b/cmd/agola/cmd/remotesourcecreate.go index 2da3a52..3ebca9b 100644 --- a/cmd/agola/cmd/remotesourcecreate.go +++ b/cmd/agola/cmd/remotesourcecreate.go @@ -20,6 +20,7 @@ import ( "agola.io/agola/internal/gitsources/github" "agola.io/agola/internal/services/gateway/api" "agola.io/agola/internal/services/types" + "agola.io/agola/internal/util" "github.com/spf13/cobra" errors "golang.org/x/xerrors" @@ -45,6 +46,8 @@ type remoteSourceCreateOptions struct { oauth2ClientSecret string sshHostKey string skipSSHHostKeyCheck bool + registrationEnabled bool + loginEnabled bool } var remoteSourceCreateOpts remoteSourceCreateOptions @@ -61,6 +64,8 @@ func init() { flags.StringVar(&remoteSourceCreateOpts.oauth2ClientSecret, "secret", "", "remotesource oauth2 secret") flags.StringVar(&remoteSourceCreateOpts.sshHostKey, "ssh-host-key", "", "remotesource ssh public host key") flags.BoolVarP(&remoteSourceCreateOpts.skipSSHHostKeyCheck, "skip-ssh-host-key-check", "s", false, "skip ssh host key check") + flags.BoolVar(&remoteSourceCreateOpts.registrationEnabled, "registration-enabled", true, "enabled/disable user registration with this remote source") + flags.BoolVar(&remoteSourceCreateOpts.loginEnabled, "login-enabled", true, "enabled/disable user login with this remote source") if err := cmdRemoteSourceCreate.MarkFlagRequired("name"); err != nil { log.Fatal(err) @@ -98,6 +103,8 @@ func remoteSourceCreate(cmd *cobra.Command, args []string) error { Oauth2ClientSecret: remoteSourceCreateOpts.oauth2ClientSecret, SSHHostKey: remoteSourceCreateOpts.sshHostKey, SkipSSHHostKeyCheck: remoteSourceCreateOpts.skipSSHHostKeyCheck, + RegistrationEnabled: util.BoolP(remoteSourceCreateOpts.registrationEnabled), + LoginEnabled: util.BoolP(remoteSourceCreateOpts.loginEnabled), } log.Infof("creating remotesource") diff --git a/cmd/agola/cmd/remotesourceupdate.go b/cmd/agola/cmd/remotesourceupdate.go index 62a5d48..b3cdd40 100644 --- a/cmd/agola/cmd/remotesourceupdate.go +++ b/cmd/agola/cmd/remotesourceupdate.go @@ -43,6 +43,8 @@ type remoteSourceUpdateOptions struct { oauth2ClientSecret string sshHostKey string skipSSHHostKeyCheck bool + registrationEnabled bool + loginEnabled bool } var remoteSourceUpdateOpts remoteSourceUpdateOptions @@ -58,6 +60,8 @@ func init() { flags.StringVar(&remoteSourceUpdateOpts.oauth2ClientSecret, "secret", "", "remotesource oauth2 secret") flags.StringVar(&remoteSourceUpdateOpts.sshHostKey, "ssh-host-key", "", "remotesource ssh public host key") flags.BoolVarP(&remoteSourceUpdateOpts.skipSSHHostKeyCheck, "skip-ssh-host-key-check", "s", false, "skip ssh host key check") + flags.BoolVar(&remoteSourceUpdateOpts.registrationEnabled, "registration-enabled", false, "enabled/disable user registration with this remote source") + flags.BoolVar(&remoteSourceUpdateOpts.loginEnabled, "login-enabled", false, "enabled/disable user login with this remote source") if err := cmdRemoteSourceUpdate.MarkFlagRequired("ref"); err != nil { log.Fatal(err) @@ -93,6 +97,12 @@ func remoteSourceUpdate(cmd *cobra.Command, args []string) error { if flags.Changed("skip-ssh-host-key-check") { req.SkipSSHHostKeyCheck = &remoteSourceUpdateOpts.skipSSHHostKeyCheck } + if flags.Changed("registration-enabled") { + req.RegistrationEnabled = &remoteSourceUpdateOpts.registrationEnabled + } + if flags.Changed("login-enabled") { + req.LoginEnabled = &remoteSourceUpdateOpts.loginEnabled + } log.Infof("updating remotesource") remoteSource, _, err := gwclient.UpdateRemoteSource(context.TODO(), remoteSourceUpdateOpts.ref, req) diff --git a/internal/services/gateway/action/remotesource.go b/internal/services/gateway/action/remotesource.go index a30ea5a..1791964 100644 --- a/internal/services/gateway/action/remotesource.go +++ b/internal/services/gateway/action/remotesource.go @@ -55,6 +55,8 @@ type CreateRemoteSourceRequest struct { Oauth2ClientSecret string SSHHostKey string SkipSSHHostKeyCheck bool + RegistrationEnabled *bool + LoginEnabled *bool } func (h *ActionHandler) CreateRemoteSource(ctx context.Context, req *CreateRemoteSourceRequest) (*types.RemoteSource, error) { @@ -103,6 +105,8 @@ func (h *ActionHandler) CreateRemoteSource(ctx context.Context, req *CreateRemot Oauth2ClientSecret: req.Oauth2ClientSecret, SSHHostKey: req.SSHHostKey, SkipSSHHostKeyCheck: req.SkipSSHHostKeyCheck, + RegistrationEnabled: req.RegistrationEnabled, + LoginEnabled: req.LoginEnabled, } h.log.Infof("creating remotesource") @@ -125,6 +129,8 @@ type UpdateRemoteSourceRequest struct { Oauth2ClientSecret *string SSHHostKey *string SkipSSHHostKeyCheck *bool + RegistrationEnabled *bool + LoginEnabled *bool } func (h *ActionHandler) UpdateRemoteSource(ctx context.Context, req *UpdateRemoteSourceRequest) (*types.RemoteSource, error) { @@ -158,6 +164,12 @@ func (h *ActionHandler) UpdateRemoteSource(ctx context.Context, req *UpdateRemot if req.SkipSSHHostKeyCheck != nil { rs.SkipSSHHostKeyCheck = *req.SkipSSHHostKeyCheck } + if req.RegistrationEnabled != nil { + rs.RegistrationEnabled = req.RegistrationEnabled + } + if req.LoginEnabled != nil { + rs.LoginEnabled = req.LoginEnabled + } h.log.Infof("updating remotesource") rs, resp, err = h.configstoreClient.UpdateRemoteSource(ctx, req.RemoteSourceRef, rs) diff --git a/internal/services/gateway/action/user.go b/internal/services/gateway/action/user.go index 0a43498..6d9c2aa 100644 --- a/internal/services/gateway/action/user.go +++ b/internal/services/gateway/action/user.go @@ -311,6 +311,9 @@ func (h *ActionHandler) RegisterUser(ctx context.Context, req *RegisterUserReque if err != nil { return nil, errors.Errorf("failed to get remote source %q: %w", req.RemoteSourceName, ErrFromRemote(resp, err)) } + if !*rs.RegistrationEnabled { + return nil, util.NewErrBadRequest(errors.Errorf("remote source user registration is disabled")) + } accessToken, err := common.GetAccessToken(rs, req.UserAccessToken, req.Oauth2AccessToken) if err != nil { @@ -370,6 +373,9 @@ func (h *ActionHandler) LoginUser(ctx context.Context, req *LoginUserRequest) (* if err != nil { return nil, errors.Errorf("failed to get remote source %q: %w", req.RemoteSourceName, ErrFromRemote(resp, err)) } + if !*rs.LoginEnabled { + return nil, util.NewErrBadRequest(errors.Errorf("remote source user login is disabled")) + } accessToken, err := common.GetAccessToken(rs, req.UserAccessToken, req.Oauth2AccessToken) if err != nil { diff --git a/internal/services/gateway/api/remotesource.go b/internal/services/gateway/api/remotesource.go index a9bd4c6..421720b 100644 --- a/internal/services/gateway/api/remotesource.go +++ b/internal/services/gateway/api/remotesource.go @@ -38,6 +38,8 @@ type CreateRemoteSourceRequest struct { Oauth2ClientSecret string `json:"oauth_2_client_secret"` SSHHostKey string `json:"ssh_host_key"` SkipSSHHostKeyCheck bool `json:"skip_ssh_host_key_check"` + RegistrationEnabled *bool `json:"registration_enabled"` + LoginEnabled *bool `json:"login_enabled"` } type CreateRemoteSourceHandler struct { @@ -69,6 +71,8 @@ func (h *CreateRemoteSourceHandler) ServeHTTP(w http.ResponseWriter, r *http.Req Oauth2ClientSecret: req.Oauth2ClientSecret, SSHHostKey: req.SSHHostKey, SkipSSHHostKeyCheck: req.SkipSSHHostKeyCheck, + RegistrationEnabled: req.RegistrationEnabled, + LoginEnabled: req.LoginEnabled, } rs, err := h.ah.CreateRemoteSource(ctx, creq) if httpError(w, err) { @@ -90,6 +94,8 @@ type UpdateRemoteSourceRequest struct { Oauth2ClientSecret *string `json:"oauth_2_client_secret"` SSHHostKey *string `json:"ssh_host_key"` SkipSSHHostKeyCheck *bool `json:"skip_ssh_host_key_check"` + RegistrationEnabled *bool `json:"registration_enabled"` + LoginEnabled *bool `json:"login_enabled"` } type UpdateRemoteSourceHandler struct { @@ -123,6 +129,8 @@ func (h *UpdateRemoteSourceHandler) ServeHTTP(w http.ResponseWriter, r *http.Req Oauth2ClientSecret: req.Oauth2ClientSecret, SSHHostKey: req.SSHHostKey, SkipSSHHostKeyCheck: req.SkipSSHHostKeyCheck, + RegistrationEnabled: req.RegistrationEnabled, + LoginEnabled: req.LoginEnabled, } rs, err := h.ah.UpdateRemoteSource(ctx, creq) if httpError(w, err) { @@ -137,16 +145,20 @@ func (h *UpdateRemoteSourceHandler) ServeHTTP(w http.ResponseWriter, r *http.Req } type RemoteSourceResponse struct { - ID string `json:"id"` - Name string `json:"name"` - AuthType string `json:"auth_type"` + ID string `json:"id"` + Name string `json:"name"` + AuthType string `json:"auth_type"` + RegistrationEnabled bool `json:"registration_enabled"` + LoginEnabled bool `json:"login_enabled"` } func createRemoteSourceResponse(r *types.RemoteSource) *RemoteSourceResponse { rs := &RemoteSourceResponse{ - ID: r.ID, - Name: r.Name, - AuthType: string(r.AuthType), + ID: r.ID, + Name: r.Name, + AuthType: string(r.AuthType), + RegistrationEnabled: *r.RegistrationEnabled, + LoginEnabled: *r.LoginEnabled, } return rs } diff --git a/internal/services/types/types.go b/internal/services/types/types.go index adccedc..c809171 100644 --- a/internal/services/types/types.go +++ b/internal/services/types/types.go @@ -15,9 +15,12 @@ package types import ( + "encoding/json" "fmt" "regexp" "time" + + "agola.io/agola/internal/util" ) // Configstore types @@ -175,6 +178,28 @@ type RemoteSource struct { SSHHostKey string `json:"ssh_host_key,omitempty"` // Public ssh host key of the remote source SkipSSHHostKeyCheck bool `json:"skip_ssh_host_key_check,omitempty"` + + RegistrationEnabled *bool `json:"registration_enabled,omitempty"` + LoginEnabled *bool `json:"login_enabled,omitempty"` +} + +func (rs *RemoteSource) UnmarshalJSON(b []byte) error { + type remoteSource RemoteSource + + trs := (*remoteSource)(rs) + + if err := json.Unmarshal(b, &trs); err != nil { + return err + } + + if trs.RegistrationEnabled == nil { + trs.RegistrationEnabled = util.BoolP(true) + } + if trs.LoginEnabled == nil { + trs.LoginEnabled = util.BoolP(true) + } + + return nil } func SourceSupportedAuthTypes(rsType RemoteSourceType) []RemoteSourceAuthType {