From 037ee1a6cfb35383f34b0fcc70dfc53f9463bd09 Mon Sep 17 00:00:00 2001 From: Robin Jarry Date: Wed, 19 Jul 2023 18:50:12 +0200 Subject: compose: allow removing headers Allow removing headers from the compose window when edit-headers=false (the default) with :header -d . Signed-off-by: Robin Jarry Acked-by: Koni Marti --- CHANGELOG.md | 1 + commands/compose/header.go | 44 ++++++++++++++++++++++++++------------------ doc/aerc.1.scd | 9 +++++++-- widgets/compose.go | 13 +++++++++++++ 4 files changed, 47 insertions(+), 20 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 2d5f4ed9..0af1cb45 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -22,6 +22,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/). - Edit email headers directly in the text editor with `[compose].edit-headers` in `aerc.conf` or with the `-e` flag for all compose related commands (e.g. `:compose`, `:forward`, `:recall`, etc.). +- Remove headers from the compose window with `:header -d `. ### Fixed diff --git a/commands/compose/header.go b/commands/compose/header.go index c512e341..59d01952 100644 --- a/commands/compose/header.go +++ b/commands/compose/header.go @@ -1,7 +1,6 @@ package compose import ( - "errors" "fmt" "strings" @@ -30,47 +29,56 @@ func (Header) Aliases() []string { return []string{"header"} } +func (Header) Options() string { + return "fd" +} + func (Header) Complete(aerc *widgets.Aerc, args []string) []string { return commands.CompletionFromList(aerc, headers, args) } -func (Header) Execute(aerc *widgets.Aerc, args []string) error { - if len(args) < 2 { - return fmt.Errorf("Usage: %s [-f] field [value]", args[0]) +func (h Header) Execute(aerc *widgets.Aerc, args []string) error { + opts, optind, err := getopt.Getopts(args, h.Options()) + args = args[optind:] + if err == nil && len(args) < 1 { + err = fmt.Errorf("not enough arguments") } - - opts, optind, err := getopt.Getopts(args, "f") if err != nil { - return err - } - - if len(args) < optind+1 { - return errors.New("command parsing failed") + return fmt.Errorf("%w. usage: header [-fd] []", err) } var force bool = false + var remove bool = false for _, opt := range opts { - if opt.Option == 'f' { + switch opt.Option { + case 'f': force = true + case 'd': + remove = true } } composer, _ := aerc.SelectedTabContent().(*widgets.Composer) - args[optind] = strings.TrimRight(args[optind], ":") + name := strings.TrimRight(args[0], ":") + + if remove { + return composer.DelEditor(name) + } - value := strings.Join(args[optind+1:], " ") + value := strings.Join(args[1:], " ") if !force { headers, err := composer.PrepareHeader() if err != nil { return err } - - if headers.Has(args[optind]) && value != "" { - return fmt.Errorf("Header %s already exists", args[optind]) + if headers.Get(name) != "" && value != "" { + return fmt.Errorf( + "Header %s is already set to %q (use -f to overwrite)", + name, headers.Get(name)) } } - return composer.AddEditor(args[optind], value, false) + return composer.AddEditor(name, value, false) } diff --git a/doc/aerc.1.scd b/doc/aerc.1.scd index ab1333f8..5b1d36f3 100644 --- a/doc/aerc.1.scd +++ b/doc/aerc.1.scd @@ -640,8 +640,13 @@ message list, the message in the message viewer, etc). *-n*: switch to next account *:header* [*-f*] __ [__] - Add a new email header. If the header already exists, *-f* must be - specified to replace the given value. +*:header* [*-d*] __ + Add a new email header to the compose window. If the header is already + set and is not empty, *-f* must be used to overwrite its value. + + *-f*: Overwrite any existing header. + + *-d*: Remove the header instead of adding it. *:encrypt* Encrypt the message to all recipients. If a key for a recipient cannot diff --git a/widgets/compose.go b/widgets/compose.go index d1bbc547..c0f4af4f 100644 --- a/widgets/compose.go +++ b/widgets/compose.go @@ -1345,8 +1345,21 @@ func (c *Composer) addEditor(header string, value string, appendHeader bool) str return value } +// DelEditor removes a header editor from the compose window. +func (c *Composer) DelEditor(header string) error { + c.Lock() + defer c.Unlock() + if c.editHeaders && c.editor != nil { + return errors.New("header should be removed directly in the text editor") + } + c.delEditor(header) + c.updateGrid() + return nil +} + func (c *Composer) delEditor(header string) { header = strings.ToLower(header) + c.header.Del(header) editor, ok := c.editors[header] if !ok { return -- cgit