Unverified Commit f3c450a1 authored by Kevin Lyda's avatar Kevin Lyda
Browse files

Fix SET BRIEF/READNEW/SHOWNEW

parent e22d01a2
Loading
Loading
Loading
Loading
+4 −0
Original line number Diff line number Diff line
@@ -104,6 +104,10 @@ func IsFolderAccess(name, login string) bool {
// IsFolderOwner checks if a user is a folder owner.
func IsFolderOwner(folder, login string) bool {
	ctx := storage.Context()
	admin, _ := this.Q.IsUserAdmin(ctx, login)
	if admin == 1 {
		return true
	}
	found, _ := this.Q.IsFolderOwner(ctx, storage.IsFolderOwnerParams{
		Folder: folder,
		Login:  login,
+23 −31
Original line number Diff line number Diff line
@@ -270,14 +270,6 @@ BULLCOM.CLD.`,
				OptArg:  true,
				Default: "14",
			},
			"/ID": {
				Description: `  Designates  that the  name specified  as the  owner name  is a  rights
  identifier. The  creator's process must have  the identifier presently
  assigned to it.  Any process which has that identifier  assigned to it
  will be able to  control the folder as if it  were the folder's owner.
  This is used to allow more than one use to control a folder.`,
				OptArg: true,
			},
			"/NOTIFY": {
				Description: `  Specifies  that  all users  automatically  have  NOTIFY set  for  this
  folder. Only a  privileged user can use this qualifier.  (See HELP SET
@@ -286,8 +278,7 @@ BULLCOM.CLD.`,
			"/OWNER": {
				Description: `/OWNER=username

  Specifies the owner of the folder.  This is a privileged command.  See
  also /ID.`,
  Specifies the owner of the folder.  This is a privileged command.`,
				OptArg: true,
			},
			"/PRIVATE": {
@@ -602,15 +593,6 @@ of the folder or a user with privileges can use this command.
			"/DESCRIPTION": {
				Description: `  Specifies a new  description for the folder. You will  be prompted for
  the text of the description.`,
			},
			"/ID": {
				Description: `  Designates  that the  name specified  as the  owner name  is a  rights
  identifier. The  creator's process must have  the identifier presently
  assigned to it.  Any process which has that identifier  assigned to it
  will be able to  control the folder as if it  were the folder's owner.
  This is used to allow more than one use to control a folder.

  Note: This feature will not work during remote access to the folder.`,
			},
			"/NAME": {
				Description: `/NAME=foldername
@@ -623,7 +605,7 @@ of the folder or a user with privileges can use this command.

  Specifies  a new  owner for  the folder.  If the  owner does  not have
  privileges, BULLETIN  will prompt  for the password  of the  new owner
  account in order to okay the modification. See also /ID.`,
  account in order to okay the modification.`,
				OptArg: true,
			},
		},
@@ -1196,11 +1178,11 @@ READNEW setting (and visa versa).
						Description: `  Specifies that the  SET BRIEF option is the default  for all users for
  the specified folder. This is a privileged qualifier.`,
					},
					"/DEFAULT": {
						Description: `  Specifies  that the  BRIEF option  is  the default  for the  specified
  folder. This is a privileged qualifier.  It will only affect brand new
  users (or  those that have  never logged in).  Use /ALL to  modify all
  users.`,
					"/FOLDER": {
						Description: `/FOLDER=foldername

  Specifies the folder for which the option is to modified.  If not
  specified, the selected folder is modified.`,
					},
					"/PERMANENT": {
						Description: `/[NO]PERMANENT
@@ -1221,12 +1203,6 @@ privileged qualifier.`,
					"/ALL": {
						Description: `  Specifies that the SET NOBRIEF option is the default for all users for
  the specified folder. This is a privileged qualifier.`,
					},
					"/DEFAULT": {
						Description: `  Specifies that  the NOBRIEF  option is the  default for  the specified
  folder. This is a privileged qualifier.  It will only affect brand new
  users (or  those that have  never logged in).  Use /ALL to  modify all
  users.`,
					},
					"/FOLDER": {
						Description: `/FOLDER=foldername
@@ -1337,6 +1313,7 @@ PROMPT_EXPIRE is the default.

  Format:
    SET PROMPT_EXPIRE`,
				Action: ActionSetPromptExpire,
			},
			"NOPROMPT_EXPIRE": {
				Description: `The user will not be prompted,  and the default expiration (which is set
@@ -1344,6 +1321,7 @@ by SET DEFAULT_EXPIRE) will be used.

  Format:
    SET NOPROMPT_EXPIRE`,
				Action: ActionSetNoPromptExpire,
			},
			"READNEW": {
				Description: `Controls whether you will be prompted upon logging in  if  you  wish  to
@@ -1367,10 +1345,17 @@ present in those other folders. Also, it is not possible to EXIT the
READNEW mode if there are SYSTEM folders which have new messages. Typing
the EXIT command will cause you to skip to those folders.  (See HELP SET
SYSTEM for a description of a SYSTEM folder).`,
				Action: ActionSetReadNew,
				Flags: dclish.Flags{
					"/ALL": {
						Description: `  Specifies that the SET READNEW option is the default for all users for
  the specified folder.  This is a privileged  qualifier.`,
					},
					"/FOLDER": {
						Description: `/FOLDER=foldername

  Specifies  the folder  for which  the option  is to  modified. If  not
  specified, the selected folder is modified.`,
					},
					"/PERMANENT": {
						Description: `/[NO]PERMANENT
@@ -1384,6 +1369,7 @@ SYSTEM for a description of a SYSTEM folder).`,
				Description: `Turns off READNEW.
  Format:
    SET NOREADNEW`,
				Action: ActionSetNoReadNew,
				Flags: dclish.Flags{
					"/ALL": {
						Description: `  Specifies that the  SET NOREADNEW option is the default  for all users
@@ -1414,6 +1400,12 @@ In order to apply this to a specific folder, first select the folder
					"/ALL": {
						Description: `  Specifies that the SET SHOWNEW option is the default for all users for
  the specified folder.  This is a privileged  qualifier.`,
					},
					"/FOLDER": {
						Description: `/FOLDER=foldername

  Specifies  the folder  for which  the option  is to  modified. If  not
  specified, the selected folder is modified.`,
					},
					"/PERMANENT": {
						Description: `/[NO]PERMANENT
+8 −4
Original line number Diff line number Diff line
@@ -38,7 +38,7 @@ func ActionCreate(cmd *dclish.Command) error {
		options.Always = 1
	}
	if cmd.Flags["/BRIEF"].Value == "true" {
		options.Brief = 1
		options.Alert = 1
	}
	if cmd.Flags["/DESCRIPTION"].Value != "" {
		options.Description = cmd.Flags["/DESCRIPTION"].Value
@@ -47,10 +47,10 @@ func ActionCreate(cmd *dclish.Command) error {
		options.Notify = 1
	}
	if cmd.Flags["/READNEW"].Value == "true" {
		options.Readnew = 1
		options.Alert = 2
	}
	if cmd.Flags["/SHOWNEW"].Value == "true" {
		options.Shownew = 1
		options.Alert = 3
	}
	if cmd.Flags["/SYSTEM"].Value == "true" {
		options.System = 1
@@ -62,6 +62,11 @@ func ActionCreate(cmd *dclish.Command) error {
		}
		options.Expire = int64(expire)
	}
	if (cmd.Flags["/BRIEF"].Set && cmd.Flags["/READNEW"].Set) ||
		(cmd.Flags["/BRIEF"].Set && cmd.Flags["/SHOWNEW"].Set) ||
		(cmd.Flags["/READNEW"].Set && cmd.Flags["/SHOWNEW"].Set) {
		return errors.New("Can only set one of /BRIEF, /READNEW and /SHOWNEW")
	}
	options.Visibility = folders.FolderPublic
	if cmd.Flags["/PRIVATE"].Value == "true" && cmd.Flags["/SEMIPRIVATE"].Value == "true" {
		return errors.New("Private or semi-private - pick one")
@@ -92,7 +97,6 @@ func ActionCreate(cmd *dclish.Command) error {
		return errors.New("Description must exist and be under 53 characters")
	}
	err := folders.CreateFolder(owner, options)
	// TODO: handle the /ID flag.
	return err
}

+63 −66
Original line number Diff line number Diff line
@@ -13,6 +13,47 @@ import (
	"git.lyda.ie/kevin/bulletin/this"
)

func setAlert(cmd *dclish.Command, alert int64) error {
	optAll := cmd.Flags["/ALL"].Value == "true"

	optPerm := false
	if f, ok := cmd.Flags["/PERMANENT"]; ok {
		optPerm = f.Value == "true"
	}

	folder := this.Folder
	if cmd.Flags["/FOLDER"].Value != "" {
		folder = folders.FindFolder(cmd.Flags["/FOLDER"].Value)
	}
	if folder.Name == "" {
		return errors.New("Folder does not exist")
	}

	if optAll || optPerm {
		if !folders.IsFolderOwner(folder.Name, this.User.Login) {
			return errors.New("Not an admin or folder owner")
		}
	}

	ctx := storage.Context()
	if optAll && optPerm {
		return this.Q.UpdateFolderAlert(ctx, storage.UpdateFolderAlertParams{
			Alert: alert + 3,
			Name:  folder.Name,
		})
	}
	if optAll {
		return this.Q.UpdateFolderAlert(ctx, storage.UpdateFolderAlertParams{
			Alert: alert,
			Name:  folder.Name,
		})
	}
	return this.Q.UpdateUserAlert(ctx, storage.UpdateUserAlertParams{
		Alert: alert,
		Login: this.User.Login,
	})
}

// ActionSet handles the `SET` command.
func ActionSet(cmd *dclish.Command) error {
	fmt.Println(cmd.Description)
@@ -46,25 +87,13 @@ func ActionSetNoalways(_ *dclish.Command) error {
}

// ActionSetBrief handles the `SET BRIEF` command.
func ActionSetBrief(_ *dclish.Command) error {
	// TODO: parse flags.
	ctx := storage.Context()
	this.Q.UpdateFolderBrief(ctx, storage.UpdateFolderBriefParams{
		Brief: 1,
		Name:  this.Folder.Name,
	})
	return nil
func ActionSetBrief(cmd *dclish.Command) error {
	return setAlert(cmd, storage.AlertBrief)
}

// ActionSetNobrief handles the `SET NOBRIEF` command.
func ActionSetNobrief(_ *dclish.Command) error {
	// TODO: parse flags.
	ctx := storage.Context()
	this.Q.UpdateFolderBrief(ctx, storage.UpdateFolderBriefParams{
		Brief: 1,
		Name:  this.Folder.Name,
	})
	return nil
func ActionSetNobrief(cmd *dclish.Command) error {
	return setAlert(cmd, storage.AlertNone)
}

// ActionSetDefaultExpire handles the `SET DEFAULT_EXPIRE` command.
@@ -140,76 +169,44 @@ func ActionSetNonotify(_ *dclish.Command) error {
	return nil
}

// ActionSetPrivileges handles the `SET PRIVILEGES` command.
func ActionSetPrivileges(cmd *dclish.Command) error {
	// TODO: OK, need a better parser.
	switch cmd.Args[0] {
	case "CREATE":
		if len(cmd.Args) != 2 {
			fmt.Println("ERROR: Must pass single login.")
			return nil
		}
		fmt.Println("TODO: Create user creation routine - see repl/repl.go.")
	case "DELETE":
		if len(cmd.Args) != 2 {
			fmt.Println("ERROR: Must pass single login.")
			return nil
		}
		fmt.Println("TODO: Create user delete routine - see repl/repl.go.")
	case "SSH":
		fmt.Println("TODO: Create ssh routine.")
	case "ADMIN":
		fmt.Println("TODO: Create an admin bit set/unset routine.")
	case "NOADMIN":
		fmt.Println("TODO: Create an admin bit set/unset routine.")
	case "MOD":
		fmt.Println("TODO: Create a mod bit set/unset routine.")
	case "NOMOD":
		fmt.Println("TODO: Create a mod bit set/unset routine.")
	case "ENABLE":
		fmt.Println("TODO: Create a disable bit set/unset routine.")
	case "DISABLE":
		fmt.Println("TODO: Create a disable bit set/unset routine.")
	default:
		fmt.Println("ERROR: Command not understood.")
	}
	return nil
}

// ActionSetPromptExpire handles the `SET PROMPT_EXPIRE` command.
func ActionSetPromptExpire(_ *dclish.Command) error {
	fmt.Println("TODO: implement ActionSetPromptExpire.")
	ctx := storage.Context()
	this.Q.UpdateUserPrompt(ctx, storage.UpdateUserPromptParams{
		Login:  this.User.Login,
		Prompt: 1,
	})
	return nil
}

// ActionSetNoPromptExpire handles the `SET NOPROMPT_EXPIRE` command.
func ActionSetNoPromptExpire(_ *dclish.Command) error {
	fmt.Println("TODO: implement ActionSetNopromptExpire.")
	ctx := storage.Context()
	this.Q.UpdateUserPrompt(ctx, storage.UpdateUserPromptParams{
		Login:  this.User.Login,
		Prompt: 0,
	})
	return nil
}

// ActionSetReadNew handles the `SET READNEW` command.
func ActionSetReadNew(_ *dclish.Command) error {
	fmt.Println("TODO: implement ActionSetReadNew.")
	return nil
func ActionSetReadNew(cmd *dclish.Command) error {
	return setAlert(cmd, storage.AlertReadNew)
}

// ActionSetNoReadNew handles the `SET READNEW` command.
func ActionSetNoReadNew(_ *dclish.Command) error {
	fmt.Println("TODO: implement ActionSetNoReadNew.")
	return nil
func ActionSetNoReadNew(cmd *dclish.Command) error {
	return setAlert(cmd, storage.AlertNone)
}

// ActionSetShowNew handles the `SET SHOWNEW` command.
func ActionSetShowNew(_ *dclish.Command) error {
	fmt.Println("TODO: implement ActionSetShowNew.")
	return nil
func ActionSetShowNew(cmd *dclish.Command) error {
	return setAlert(cmd, storage.AlertShowNew)
}

// ActionSetNoShowNew handles the `SET SHOWNEW` command.
func ActionSetNoShowNew(_ *dclish.Command) error {
	fmt.Println("TODO: implement ActionSetNoShowNew.")
	return nil
func ActionSetNoShowNew(cmd *dclish.Command) error {
	return setAlert(cmd, storage.AlertNone)
}

// ActionSetSystem handles the `SET SYSTEM` command.
+6 −18
Original line number Diff line number Diff line
@@ -28,16 +28,9 @@ func ActionShowFlags(_ *dclish.Command) error {
		fmt.Println("  NOTIFY is set.")
		flagset = true
	}
	if this.Folder.Readnew != 0 {
		fmt.Println("  READNEW is set.")
		flagset = true
	}
	if this.Folder.Brief != 0 {
		fmt.Println("  BRIEF is set.")
		flagset = true
	}
	if this.Folder.Shownew != 0 {
		fmt.Println("  SHOWNEW is set.")
	if this.Folder.Alert != 0 {
		fmt.Printf("  %s is set.\n",
			strings.ToUpper(storage.AlertString(this.Folder.Alert)))
		flagset = true
	}
	if !flagset {
@@ -100,14 +93,9 @@ func ActionShowFolder(cmd *dclish.Command) error {
	if this.Folder.Notify != 0 {
		fmt.Println("  Default is NOTIFY.")
	}
	if this.Folder.Readnew != 0 {
		fmt.Println("  Default is READNEW.")
	}
	if this.Folder.Brief != 0 {
		fmt.Println("  Default is BRIEF.")
	}
	if this.Folder.Shownew != 0 {
		fmt.Println("  Default is SHOWNEW.")
	if this.Folder.Alert != 0 {
		fmt.Printf("  %s is set.\n",
			strings.ToUpper(storage.AlertString(this.Folder.Alert)))
	}

	return nil
Loading