aboutsummaryrefslogtreecommitdiffstats
path: root/commands/compose
diff options
context:
space:
mode:
authorRobin Jarry <robin@jarry.cc>2022-12-06 20:08:49 +0100
committerRobin Jarry <robin@jarry.cc>2022-12-07 15:01:33 +0100
commitcbcabfafaab20eaffad642f20151e890161efddc (patch)
tree987a666459ee6d3402f1b50c520b5f97a946a181 /commands/compose
parentc4df1eea3ef4ac89d52a9d80a8151d3999215a6a (diff)
downloadaerc-cbcabfafaab20eaffad642f20151e890161efddc.tar.gz
compose: allow writing multipart/alternative messages
Add a new :multipart command that can be executed on the composer review screen. This command takes a MIME type as argument which needs to match a setting in the new [multipart-converters] section of aerc.conf. A part can be removed by using the -d flag. The [multipart-converters] section has MIME types associated with commands. These commands are executed with sh -c every time the main email body is updated to generate each part content. The commands are expected to output valid UTF-8 text. If a command fails, an explicit error will be printed next to the part MIME type to allow users to debug their issue but the email may still be sent anyway with an empty alternative part. This is mostly intended for people who *really* need to send html messages for their boss or for corporate reasons. For now, it is a manual and explicit action to convert a message in such a way. Here is an example configuration: [multipart-converters] text/html = pandoc -f markdown -t html And the associated binding to append an HTML alternative to a message: [compose::review] H = :multipart text/html<enter> hh = :multipart -d text/html<enter> Link: https://lists.sr.ht/~rjarry/aerc-discuss/%3CCO5KH4W57XNB.2PZLR1CNFK22H%40mashenka%3E Co-authored-by: Eric McConville <emcconville@emcconville.com> Signed-off-by: Robin Jarry <robin@jarry.cc> Tested-by: Bence Ferdinandy <bence@ferdinandy.com> Acked-by: Moritz Poldrack <moritz@poldrack.dev>
Diffstat (limited to 'commands/compose')
-rw-r--r--commands/compose/multipart.go73
1 files changed, 73 insertions, 0 deletions
diff --git a/commands/compose/multipart.go b/commands/compose/multipart.go
new file mode 100644
index 00000000..5a6dd770
--- /dev/null
+++ b/commands/compose/multipart.go
@@ -0,0 +1,73 @@
+package compose
+
+import (
+ "bytes"
+ "fmt"
+
+ "git.sr.ht/~rjarry/aerc/commands"
+ "git.sr.ht/~rjarry/aerc/widgets"
+ "git.sr.ht/~sircmpwn/getopt"
+)
+
+type Multipart struct{}
+
+func init() {
+ register(Multipart{})
+}
+
+func (Multipart) Aliases() []string {
+ return []string{"multipart"}
+}
+
+func (Multipart) Complete(aerc *widgets.Aerc, args []string) []string {
+ var completions []string
+ completions = append(completions, "-d")
+ for mime := range aerc.Config().Converters {
+ completions = append(completions, mime)
+ }
+ return commands.CompletionFromList(aerc, completions, args)
+}
+
+func (a Multipart) Execute(aerc *widgets.Aerc, args []string) error {
+ composer, ok := aerc.SelectedTabContent().(*widgets.Composer)
+ if !ok {
+ return fmt.Errorf(":multipart is only available on the compose::review screen")
+ }
+
+ opts, optind, err := getopt.Getopts(args, "d")
+ if err != nil {
+ return fmt.Errorf("Usage: :multipart [-d] <mime/type>")
+ }
+ var remove bool = false
+ for _, opt := range opts {
+ if opt.Option == 'd' {
+ remove = true
+ }
+ }
+ args = args[optind:]
+ if len(args) != 1 {
+ return fmt.Errorf("Usage: :multipart [-d] <mime/type>")
+ }
+ mime := args[0]
+
+ if remove {
+ return composer.RemovePart(mime)
+ } else {
+ _, found := aerc.Config().Converters[mime]
+ if !found {
+ return fmt.Errorf("no command defined for MIME type: %s", mime)
+ }
+ err = composer.AppendPart(
+ mime,
+ map[string]string{"Charset": "UTF-8"},
+ // the actual content of the part will be rendered
+ // every time the body of the email is updated
+ bytes.NewReader([]byte{}),
+ )
+ if err != nil {
+ return err
+ }
+ }
+
+ return nil
+}