From 987f21d10dc723180aeff4579bfae717924984b6 Mon Sep 17 00:00:00 2001 From: tss24 <tss24@inf.ufpr.br> Date: Fri, 21 Mar 2025 11:14:58 -0300 Subject: [PATCH] Add user blocking/unblocking and finish bulk prototype --- cmd/bulk.go | 170 ++++++++++++++++++ cmd/root.go | 1 + cmd/user.go | 6 +- cmd/user/block.go | 36 ++++ cmd/user/bulk.go | 52 +++++- cmd/user/create.go | 81 ++------- cmd/user/mod.go | 9 +- cmd/user/temp.go | 16 +- cmd/user/unblock.go | 41 +++++ model/krb.go | 11 ++ model/ltype.go | 13 ++ model/opts.go | 4 +- model/user.go | 167 ++++++++++++++++- utils/utils.go | 12 +- .../validation.go => validate/validate.go | 12 +- 15 files changed, 518 insertions(+), 113 deletions(-) create mode 100644 cmd/bulk.go create mode 100644 cmd/user/block.go create mode 100644 cmd/user/unblock.go rename cmd/user/validation.go => validate/validate.go (83%) diff --git a/cmd/bulk.go b/cmd/bulk.go new file mode 100644 index 0000000..24c26e1 --- /dev/null +++ b/cmd/bulk.go @@ -0,0 +1,170 @@ +package cmd + +import ( + "bufio" + "fmt" + "os" + "strings" + + "github.com/spf13/cobra" + "gitlab.c3sl.ufpr.br/tss24/useradm/model" + "gitlab.c3sl.ufpr.br/tss24/useradm/utils" + //"gitlab.c3sl.ufpr.br/tss24/useradm/validate" +) + +var ( + // if you start asking yourself wtf is the difference between fis and fisica, + // im pretty sure it is that fisica has profs and/or MSc/Doctorate... + supp_groups = [...]string{"ppginf", "espinf", "temp", + "bcc", "ibm", "est", "fis"} +) + +var bulkCmd = &cobra.Command{ + Use: "bulk [group] [path]", + Args: cobra.ExactArgs(2), + Short: "Subcommand to create a lot of accounts", + Long: ` + This subcommand is used when you have a file with + a lot of names and want to create the accounts. + The next argument is the group of the users, so + please take care when choosing it. + + Be aware the results will be printed to the screen, + so if you want to save it, redirect the command's + output to a file! + + Supported groups are: + bcc, ibm, est, ppginf, espinf, temp, fis + + If your group is not here and you want to create a + lot of user similarly, contact root@c3sl.ufpr.br + for us to update the script.`, + Example: ` + useradm bulk bcc path/to/file # base command + useradm bulk ibm path/to/file -e 12.03.25 # setting expiry + useradm bulk ppginf path/to/file -r "Prof John Doe" # setting resp + useradm bulk est path/to/file > out-file.txt # redirecting to file`, + RunE: bulkCreate, +} + +func init() { + bulkCmd.Flags().StringP("resp", "r", "_", "Person responsible for the accounts") + bulkCmd.Flags().StringP("expiry", "e", "_", "Expiry date of the accounts, format dd.mm.yy") +} + +func bulkCreate(cmd *cobra.Command, args []string) error { + var opts model.Opts + + group := args[0] + path := args[1] + + err := isGroupSupported(group) + if err != nil { + return err + } + + if !utils.PathExists(path) { + return fmt.Errorf("Path %v not found", path) + } + + err = opts.RetrieveOpts(cmd) + if err != nil { + return err + } + + accounts, err := extractModelsFile(opts, group, path) + if err != nil { + return err + } + + l, err := model.ConnLDAP() + if err != nil { + return err + } + defer l.Close() + + users, err := model.GetAllUsersLDAP(l) + if err != nil { + return err + } + + for _, u := range accounts { + + err = u.GenMissingFields(false) + if err != nil { + return err + } + + if !model.LoginExists(users, u.UID) { + err = u.Create(l) + if err != nil { + return err + } + } else { + fmt.Printf(` +First login generation alternative for "%v" is already taken! +User was NOT created! +Please check if the user exists with: + + useradm user show -e -l %v + useradm user show -i -n "%v" + +If it really is a new user, use one of these: + + useradm user create -n "%v" -g %v -e %v -i %v -t %v -r %v -w # with webdir + useradm user create -n "%v" -g %v -e %v -i %v -t %v -r %v # no webdir +`, u.UID, u.UID, u.Name, u.Name, u.GID, u.Expiry, u.Resp, u.Ltype.SmallString(), + u.GRR, u.Name, u.GID, u.Expiry, u.Resp, u.Ltype.SmallString(), u.GRR) + } + + } + + return nil +} + +func isGroupSupported(group string) error { + err := fmt.Errorf("Group %v is not supported, see help", group) + for _, g := range supp_groups { + if g == group { + err = nil + break + } + } + return err +} + +func extractModelsFile(opts model.Opts, group, path string) ([]model.User, error) { + var users []model.User + + file, err := os.Open(path) + if err != nil { + return users, fmt.Errorf("Error opening file %v", err) + } + defer file.Close() + + var ltype model.LoginType + if group == "ppginf" || group == "espinf" { + ltype = model.LastName + } else { + ltype = model.Initials + } + + scanner := bufio.NewScanner(file) + for scanner.Scan() { + var u model.User + line := scanner.Text() + parts := strings.Split(line, ":") + u.Name = parts[0] + u.GRR = parts[1] + u.GID = group + u.Ltype = ltype + u.Resp = opts.Resp + u.Expiry = opts.Expiry + users = append(users, u) + } + + if err := scanner.Err(); err != nil { + fmt.Println("Error reading file:", err) + } + return users, nil +} diff --git a/cmd/root.go b/cmd/root.go index c8d2f2d..475101c 100644 --- a/cmd/root.go +++ b/cmd/root.go @@ -30,4 +30,5 @@ func Execute() { func init() { rootCmd.AddCommand(userCmd) rootCmd.AddCommand(groupCmd) + rootCmd.AddCommand(bulkCmd) } diff --git a/cmd/user.go b/cmd/user.go index c2347b0..83497f4 100644 --- a/cmd/user.go +++ b/cmd/user.go @@ -8,15 +8,17 @@ import ( var userCmd = &cobra.Command{ Use: "user", Short: "User subcommand", - Long: `Subcommand for managing users in general.`, + Long: `Subcommand for managing users in general.`, } func init() { userCmd.AddCommand(user.ModCmd) userCmd.AddCommand(user.ShowCmd) userCmd.AddCommand(user.TempCmd) - userCmd.AddCommand(user.BulkCmd) + //userCmd.AddCommand(user.BulkCmd) userCmd.AddCommand(user.ResetCmd) userCmd.AddCommand(user.CreateCmd) userCmd.AddCommand(user.RemoveCmd) + userCmd.AddCommand(user.BlockCmd) + userCmd.AddCommand(user.UnblockCmd) } diff --git a/cmd/user/block.go b/cmd/user/block.go new file mode 100644 index 0000000..6255f13 --- /dev/null +++ b/cmd/user/block.go @@ -0,0 +1,36 @@ +package user + +import ( + "fmt" + + "github.com/spf13/cobra" + "gitlab.c3sl.ufpr.br/tss24/useradm/model" + "gitlab.c3sl.ufpr.br/tss24/useradm/utils" +) + +var BlockCmd = &cobra.Command{ + Use: "block [username]", + Short: "Block a user", + Args: cobra.ExactArgs(1), + RunE: BlockUserCmd, +} + +func BlockUserCmd(cmd *cobra.Command, args []string) error { + l, err := model.ConnLDAP() + if err != nil { + return err + } + defer l.Close() + + login := args[0] + u, err := model.Locate(l, login) + if err != nil { + return err + } + + fmt.Printf("%v\n", u.FullToString()) + + utils.ConfirmationPrompt(false, "blocking") + u.Block() + return nil +} diff --git a/cmd/user/bulk.go b/cmd/user/bulk.go index ed92d59..6c35444 100644 --- a/cmd/user/bulk.go +++ b/cmd/user/bulk.go @@ -1,7 +1,10 @@ package user import ( + "bufio" "fmt" + "os" + "strings" "github.com/spf13/cobra" "gitlab.c3sl.ufpr.br/tss24/useradm/model" @@ -43,26 +46,57 @@ func bulkCreate(cmd *cobra.Command, args []string) error { return err } - if !utils.PathExists(opts.Path) { - return fmt.Errorf("Path: \"%v\": no such file", opts.Path) - } - - accounts, err = extractModelsFile(opts.Path) + accounts, err = extractModelsFile(opts.Path, opts.GID) if err != nil { return err } - for i := range accounts { - err = accounts[i].Create(l) + for _, account := range accounts { + + err = account.GenMissingFields(false) if err != nil { return err } + // if model.LoginExists(account.UID) { + // return + // } + + err = account.Create(l) + if err != nil { + return err + } + } return nil } -func extractModelsFile(path string) ([]model.User, error) { - // TODO +func extractModelsFile(path, group string) ([]model.User, error) { + var users []model.User + + if !utils.PathExists(path) { + return users, fmt.Errorf("Path: \"%v\": no such file", path) + } + + file, err := os.Open(path) + if err != nil { + return users, fmt.Errorf("Error opening file %v", err) + } + defer file.Close() + + scanner := bufio.NewScanner(file) + for scanner.Scan() { + var u model.User + line := scanner.Text() + parts := strings.Split(line, ":") + u.Name = parts[0] + u.GRR = parts[1] + u.GID = group + users = append(users, u) + } + + if err := scanner.Err(); err != nil { + fmt.Println("Error reading file:", err) + } return nil, nil } diff --git a/cmd/user/create.go b/cmd/user/create.go index 540dc54..100d8ed 100644 --- a/cmd/user/create.go +++ b/cmd/user/create.go @@ -7,6 +7,7 @@ import ( "github.com/spf13/cobra" "gitlab.c3sl.ufpr.br/tss24/useradm/model" "gitlab.c3sl.ufpr.br/tss24/useradm/utils" + "gitlab.c3sl.ufpr.br/tss24/useradm/validate" ) var CreateCmd = &cobra.Command{ @@ -20,7 +21,6 @@ func init() { // FIXME: maybe leave less flags for user input CreateCmd.Flags().StringP("grr", "r", "_", "User GRR, required for ini type") CreateCmd.Flags().StringP("type", "t", "ini", "Type of auto-generated login: ini, first or last") - CreateCmd.Flags().StringP("web", "w", "", "Full path to webdir, /home/html/inf/login if empty") CreateCmd.Flags().StringP("name", "n", "_", "User full name, required, use quotes for spaces") CreateCmd.Flags().StringP("login", "l", "", "User login name, auto-generated if empty") CreateCmd.Flags().StringP("group", "g", "", "User base group, required") @@ -31,6 +31,7 @@ func init() { CreateCmd.Flags().StringP("resp", "i", "_", "Person responsible for the account") CreateCmd.Flags().StringP("expiry", "e", "_", "Expiry date in format dd.mm.yy") CreateCmd.Flags().StringP("nobkp", "b", "", "User nobackup directory path") + CreateCmd.Flags().BoolP("web", "w", false, "Generate webdir") // required flags CreateCmd.MarkFlagRequired("name") @@ -57,10 +58,6 @@ func createUserCmd(cmd *cobra.Command, args []string) error { //fmt.Printf("%v\n Passwd: %v\n\n", usr.ToString(), usr.Password) utils.ConfirmationPrompt(confirm, "creation") - if usr.Password == "[auto-generate]" { - usr.Password = utils.GenPassword() - } - err = usr.Create(l) if err != nil { return err @@ -68,15 +65,9 @@ func createUserCmd(cmd *cobra.Command, args []string) error { err = utils.ClearCache() if err != nil { - fmt.Printf("Failed to reload cache, changes might take a while\nError: %v", err) + fmt.Printf("Failed to reload cache, changes might take a while\nError: %v\n", err) } - fmt.Println("User created!") - fmt.Printf("\nUser Login: %v", usr.UID) - fmt.Printf("\nUser Password: %v\n\n", usr.Password) - fmt.Printf("%v:%v:%v:%v:%v:%v:%v:%v:%v:\n", usr.UID, usr.Password, usr.GID, - usr.Name, usr.Gecos, usr.GRR, usr.Shell, usr.Homedir, usr.Webdir) - return nil } @@ -94,16 +85,6 @@ func createNewUserModel(cmd *cobra.Command, l *ldap.Conn) (model.User, bool, err return u, false, err } - users, err := model.GetAllUsersLDAP(l) - if err != nil { - return u, false, err - } - - groups, err := model.GetAllGroupsLDAP(l) - if err != nil { - return u, false, err - } - if opts.Status == "Blocked" { opts.Shell = "/bin/false" } @@ -121,56 +102,14 @@ func createNewUserModel(cmd *cobra.Command, l *ldap.Conn) (model.User, bool, err Shell: opts.Shell, Status: opts.Status, Expiry: opts.Expiry, - Webdir: opts.Webdir, Homedir: opts.Homedir, Nobackup: opts.Nobkp, - Password: utils.IfThenElse(opts.Passwd != "", opts.Passwd, "[auto-generate]"), + Password: opts.Passwd, } u.Ltype.Parse(opts.Ltype) - if opts.UID == "" { - err = u.GenUniqueUID(users) - if err != nil { - return u, false, err - } - } - - if opts.Homedir == "" { - u.Homedir, err = utils.GenDirPath("/home", u.GID, u.UID, u.Homedir) - if err != nil { - return u, false, err - } - } - - if opts.Nobkp == "" { - u.Nobackup, err = utils.GenDirPath("/nobackup", u.GID, u.UID, u.Nobackup) - if err != nil { - return u, false, err - } - } - - if opts.Webdir == "" { - u.Webdir, err = utils.GenDirPath("/home/html/inf", "", u.UID, u.Webdir) - if err != nil { - return u, false, err - } - } - - // get a new UIDNumber - err = u.GetNewUIDNumber(l) - if err != nil { - return u, false, fmt.Errorf("failed to generate new UIDNumber for user: %v", err) - } - - // assign GIDNumber by traversing the groups - u.GIDNumber, err = utils.GetGIDNumFromGID(groups, u.GID) - if err != nil { - return u, false, err - } - - u.GenGecos() - u.SetDN(u.UID) + u.GenMissingFields(true) return u, opts.Confirm, nil } @@ -193,29 +132,29 @@ func validateInputs(opts model.Opts) error { return err } - err = validateGID(groups, opts.GID) + err = validate.GID(groups, opts.GID) if err != nil { return err } - err = validateGRR(users, opts.GRR) + err = validate.GRR(users, opts.GRR) if err != nil { return err } - err = validateExpiry(opts.Expiry) + err = validate.Expiry(opts.Expiry) if err != nil { return err } - err = validateStatus(opts.Status) + err = validate.Status(opts.Status) if err != nil { return err } // it’s OK if UID is empty here, we generate it later :) if opts.UID != "" { - err := validateUID(users, opts.UID) + err := validate.UID(users, opts.UID) if err != nil { return err } diff --git a/cmd/user/mod.go b/cmd/user/mod.go index 4b9e9f3..9b9b1d7 100644 --- a/cmd/user/mod.go +++ b/cmd/user/mod.go @@ -10,6 +10,7 @@ import ( "github.com/spf13/cobra" "gitlab.c3sl.ufpr.br/tss24/useradm/model" "gitlab.c3sl.ufpr.br/tss24/useradm/utils" + "gitlab.c3sl.ufpr.br/tss24/useradm/validate" "gopkg.in/yaml.v3" ) @@ -78,23 +79,23 @@ func modUserCmd(cmd *cobra.Command, args []string) error { changes, err := promptUserYaml(state) if changes.GRR != curr.GRR { - err = validateGRR(users, changes.GRR) + err = validate.GRR(users, changes.GRR) if err != nil { return err } } - err = validateGID(groups, changes.Group) + err = validate.GID(groups, changes.Group) if err != nil { return err } - err = validateStatus(changes.Status) + err = validate.Status(changes.Status) if err != nil { return err } - err = validateExpiry(changes.Expiry) + err = validate.Expiry(changes.Expiry) if err != nil { return err } diff --git a/cmd/user/temp.go b/cmd/user/temp.go index 7170e14..ff46b6d 100644 --- a/cmd/user/temp.go +++ b/cmd/user/temp.go @@ -9,6 +9,7 @@ import ( "github.com/spf13/cobra" "gitlab.c3sl.ufpr.br/tss24/useradm/model" "gitlab.c3sl.ufpr.br/tss24/useradm/utils" + "gitlab.c3sl.ufpr.br/tss24/useradm/validate" ) var TempCmd = &cobra.Command{ @@ -62,7 +63,7 @@ func tempCreate(cmd *cobra.Command, args []string) error { } } - err = validateGID(groups, opts.GID) + err = validate.GID(groups, opts.GID) if err != nil { return err } @@ -81,14 +82,15 @@ func tempCreate(cmd *cobra.Command, args []string) error { Password: opts.Passwd + "#", } - base.Homedir, err = utils.GenDirPath("/home", base.GID, base.UID, "") - if err != nil { - return err + var exists bool + base.Homedir, exists = utils.GenDirPath("/home", base.GID, base.UID) + if exists { + return fmt.Errorf("Path %v already exists", base.Homedir) } - base.Nobackup, err = utils.GenDirPath("/nobackup", base.GID, base.UID, "") - if err != nil { - return err + base.Nobackup, exists = utils.GenDirPath("/nobackup", base.GID, base.UID) + if exists { + return fmt.Errorf("Path %v already exists", base.Nobackup) } i := 1 diff --git a/cmd/user/unblock.go b/cmd/user/unblock.go new file mode 100644 index 0000000..56ec9b6 --- /dev/null +++ b/cmd/user/unblock.go @@ -0,0 +1,41 @@ +package user + +import ( + "github.com/spf13/cobra" + "gitlab.c3sl.ufpr.br/tss24/useradm/model" + "gitlab.c3sl.ufpr.br/tss24/useradm/utils" +) + +var UnblockCmd = &cobra.Command{ + Use: "unblock [username]", + Short: "Unblock a user", + Args: cobra.ExactArgs(1), + RunE: UnblockUserCmd, +} + +func init() { + UnblockCmd.Flags().StringP("passwd", "p", "_", "User's new password") +} + +func UnblockUserCmd(cmd *cobra.Command, args []string) error { + pass, err := cmd.Flags().GetString("passwd") + if err != nil { + return err + } + + l, err := model.ConnLDAP() + if err != nil { + return err + } + defer l.Close() + + login := args[0] + u, err := model.Locate(l, login) + if err != nil { + return err + } + + utils.ConfirmationPrompt(false, "unblocking") + u.Unblock(pass) + return nil +} diff --git a/model/krb.go b/model/krb.go index 8f90546..d461d8a 100644 --- a/model/krb.go +++ b/model/krb.go @@ -64,3 +64,14 @@ func DelKRBPrincipal(login string) error { return nil } + +func KRBRandKey(login string) error { + cmd := exec.Command("kadmin.local", "-q", fmt.Sprintf("cpw -randkey %s", login)) + + output, err := cmd.CombinedOutput() + if err != nil { + return fmt.Errorf("Fail to set randkey in Kerberos: %v\nOutput: %s", err, output) + } + + return nil +} diff --git a/model/ltype.go b/model/ltype.go index 4fbbc0f..02df3c1 100644 --- a/model/ltype.go +++ b/model/ltype.go @@ -38,3 +38,16 @@ func (lt *LoginType) Parse(s string) { *lt = LoginTypeUnknown } } + +func (lt LoginType) SmallString() string { + switch lt { + case Initials: + return "ini" + case FirstName: + return "first" + case LastName: + return "last" + default: + return "unknown" + } +} diff --git a/model/opts.go b/model/opts.go index a89fdce..b399d8b 100644 --- a/model/opts.go +++ b/model/opts.go @@ -17,10 +17,10 @@ type Opts struct { Ltype string Shell string Passwd string - Webdir string Status string Expiry string Homedir string + Webdir bool Ignore bool Exact bool Block bool @@ -94,7 +94,7 @@ func (o *Opts) RetrieveOpts(cmd *cobra.Command) error { return err } - o.Webdir, err = getFlagString(cmd, "web") + o.Webdir, err = getFlagBool(cmd, "web") if err != nil { return err } diff --git a/model/user.go b/model/user.go index 45490f6..35c932f 100644 --- a/model/user.go +++ b/model/user.go @@ -28,6 +28,7 @@ var ( NO_BKP_TRASH = "/nobackup/contas_removidas/" + ANO HOME_TRASH = "/home/contas_removidas/" + ANO WEB_TRASH = "/home/contas_removidas/html/" + ANO + GID_HAS_WEB = [...]string{"bcc", "ibm", "ppginf", "c3sl", "prof", "especial"} ) type User struct { @@ -116,6 +117,8 @@ func (u *User) Create(l *ldap.Conn) error { return err } + fmt.Printf("%v:%v:%v:%v:%v:%v:%v:%v:%v:%v:add-ok\n", u.UID, u.Password, u.GID, + u.Name, u.Ltype.String(), u.GRR, u.Shell, u.Homedir, u.Webdir, u.Expiry) success = true return nil } @@ -340,9 +343,11 @@ func (u *User) DirsToTrash() error { return err } - err = utils.MoveAndChown(u.Webdir, WEB_TRASH, "nobody", "nogroup") - if err != nil { - return err + if u.Webdir != "_" { + err = utils.MoveAndChown(u.Webdir, WEB_TRASH, "nobody", "nogroup") + if err != nil { + return err + } } return nil @@ -470,3 +475,159 @@ func (u *User) CreateWeb() error { success = true return nil } + +// needs the name, group, ltype. +// will derivate the rest of the information. +// if it can't infer the field, will set to "_" +func (u *User) GenMissingFields(force bool) error { + var err error + + l, err := ConnLDAP() + if err != nil { + return err + } + defer l.Close() + + if u.UID == "" { + if force { + users, err := GetAllUsersLDAP(l) + if err != nil { + return err + } + u.GenUniqueUID(users) + } else { + u.genLogin(0) + } + } + + if u.DN == "" { + u.SetDN(u.UID) + } + + if u.GRR == "" { + u.GRR = "_" + } + + if u.Expiry == "" { + u.Expiry = "_" + } + + if u.Status == "" { + u.Status = "Active" + } + + if u.Shell == "" { + u.Shell = "/bin/bash" + } + + groups, err := GetAllGroupsLDAP(l) + if err != nil { + return err + } + + if u.Password == "" { + u.Password = utils.GenPassword() + } + + u.GIDNumber, err = utils.GetGIDNumFromGID(groups, u.GID) + if err != nil { + return err + } + + if u.Homedir == "" { + u.Homedir, _ = utils.GenDirPath("/home", u.GID, u.UID) + } + + if u.Nobackup == "" { + u.Nobackup, _ = utils.GenDirPath("/nobackup", u.GID, u.UID) + } + + u.Webdir = "_" + for _, e := range GID_HAS_WEB { + if e == u.GID { + u.Webdir, _ = utils.GenDirPath("/home/html/inf", "", u.UID) + break + } + } + + if u.UIDNumber == "" { + err = u.GetNewUIDNumber(l) + if err != nil { + return fmt.Errorf("Failed to generate new UIDNumber for user: %v", err) + } + } + + u.GenGecos() + + return nil +} + +func (u *User) Block() error { + err := KRBRandKey(u.UID) + if err != nil { + return err + } + cmd := exec.Command("chmod", "0000", u.Homedir) + if err := cmd.Run(); err != nil { + return fmt.Errorf("Failed to set permissions: %w", err) + } + + cmd = exec.Command("chmod", "0000", u.Nobackup) + if err := cmd.Run(); err != nil { + return fmt.Errorf("Failed to set permissions: %w", err) + } + + l, err := ConnLDAP() + if err != nil { + return err + } + defer l.Close() + + mod := ldap.NewModifyRequest(u.DN, nil) + mod.Replace("loginShell", []string{"/bin/false"}) + + if err := l.Modify(mod); err != nil { + return fmt.Errorf("failed to update loginShell for %s: %w", u.UID, err) + } + + u.Status = "Blocked" + return nil +} + +func (u *User) Unblock(pass string) error { + cmd := exec.Command("chmod", "0700", u.Homedir) + if err := cmd.Run(); err != nil { + return fmt.Errorf("Failed to set permissions: %w", err) + } + + cmd = exec.Command("chmod", "0700", u.Nobackup) + if err := cmd.Run(); err != nil { + return fmt.Errorf("Failed to set permissions: %w", err) + } + + l, err := ConnLDAP() + if err != nil { + return err + } + defer l.Close() + + mod := ldap.NewModifyRequest(u.DN, nil) + mod.Replace("loginShell", []string{"/bin/bash"}) + + if err := l.Modify(mod); err != nil { + return fmt.Errorf("Failed to update loginShell for %s: %w", u.UID, err) + } + + if pass == "_" { + pass = utils.GenPassword() + } + + err = ModKRBPassword(u.UID, pass) + if err != nil { + return err + } + + u.Status = "Active" + fmt.Printf("New Password: %v\n", pass) + return nil +} diff --git a/utils/utils.go b/utils/utils.go index 81e340d..cc0fa14 100644 --- a/utils/utils.go +++ b/utils/utils.go @@ -70,17 +70,11 @@ func GetGIDNumFromGID(groups map[string]string, GID string) (string, error) { return "", fmt.Errorf("Couldn't find group GIDNumber") } -func GenDirPath(base, group, login, input string) (string, error) { - if input != "" { - return input, nil - } +// returns a path and if it exists +func GenDirPath(base, group, login string) (string, bool) { p := filepath.Join(base, group, login) - if PathExists(p) { - return p, fmt.Errorf("Path %v already exists: %v, %v, %v, %v", p, base, group, login, input) - } - - return p, nil + return p, PathExists(p) } func PathExists(path string) bool { diff --git a/cmd/user/validation.go b/validate/validate.go similarity index 83% rename from cmd/user/validation.go rename to validate/validate.go index ec2c952..67f2527 100644 --- a/cmd/user/validation.go +++ b/validate/validate.go @@ -1,4 +1,4 @@ -package user +package validate import ( "fmt" @@ -9,7 +9,7 @@ import ( "gitlab.c3sl.ufpr.br/tss24/useradm/utils" ) -func validateExpiry(expiry string) error { +func Expiry(expiry string) error { if expiry == "_" { return nil } @@ -23,7 +23,7 @@ func validateExpiry(expiry string) error { } // TODO: change this check -func validateStatus(status string) error { +func Status(status string) error { if status != "Blocked" && status != "Active" { err := fmt.Errorf("User status can only be \"Active\" or \"Blocked\"") return err @@ -31,7 +31,7 @@ func validateStatus(status string) error { return nil } -func validateGRR(users []model.User, grr string) error { +func GRR(users []model.User, grr string) error { // OK if empty, only "ini" login type requires it and we check :) if grr == "_" { return nil @@ -52,7 +52,7 @@ Note: To search for the account use "useradm user show -r %s"`, grr) return nil } -func validateGID(groups map[string]string, group string) error { +func GID(groups map[string]string, group string) error { var err error for _, value := range groups { @@ -64,7 +64,7 @@ func validateGID(groups map[string]string, group string) error { return err } -func validateUID(users []model.User, login string) error { +func UID(users []model.User, login string) error { res := model.Search(users, false, true, login, "", "", "", "", "") if len(res) != 0 { return fmt.Errorf(`The informed Login already exists in LDAP database -- GitLab