User:Carpetsmoker/S-nail

From ArchWiki

Arch Linux uses S-nail as its POSIX mailx incarnation, which is the "traditional" Unix email client. S-nail is MIME capable and has extensions for line editing, S/MIME, SMTP, IMAP, POP3, and more.

The s-nail package is part of the Arch Linux base group, and should be installed for most users. Once installed it is available as the mail command. The documentation is available in mail(1). The mailx command and manpage are links to the mail ones; it doesn't matter which one you use.

Version 14.9.0 released in July 2017 brought a lot of changes and improvements, reading the announcement may be helpful.

Configuration

One of S-nail's goals is to maintain POSIX mailx compliance, as well as historical compatibility. Due to this using it interactively with the defaults baffles all descriptions. It does come with a /etc/mail.rc file by default which sets various useful options for sanity. This file will be loaded even when a user-specific ~/.mailrc is found.

Warning: It is not allowed to have a space before or after the equals sign in the configuration. So set inbox = ... is not valid; it needs to be as set inbox=...
Warning: Always put set v15-compat at the top of the configuration file to tell S-nail to use the new file format.

Account setup

The first things you will want to do is setup S-nail to be able to read and receive your emails. There are two ways of doing this:

  1. The "classic" method is to read from a set of local mbox files, and to send emails directly through a locally running MTA.
  2. The "modern" method. is to directly connect to a remote IMAP and SMTP server.

This section only describes the second method, as this is by far the easiest to get started with and works for most people.

~/.mailrc
# Load authentication from ~/.netrc in the standard format.
set netrc-lookup

# Encrypted netrc file; to encrypt it use:
#   gpg --symmetric --cipher-algo AES256 -o ~/.netrc.gpg ~/.netrc
# Don't forget to remove ~/.netrc
set netrc-pipe='gpg -qd ~/.netrc.gpg'

# Send NOOP command every 240 second to keep the connection alive.
set imap-keepalive=240

# Keep cache.
set imap-cache=~/.cache/mailx

# Define accounts; use "mailx -A personal" to load this account on startup, or
# use "account personal" to load/switch at runtime.
#
# This is optional; you can just define the same options at the global level to
# always load the same account.
account "personal" {
	# Forget options when changing accounts.
	localopts yes

	# Your name and email; set in the From: header.
	set from="Donald Duck <donald@example.com>"

	# Connect to IMAP; use a shortcut for this so that we can do
	# "file root" or "file root/foldername".
	shortcut root "imaps://imap.fastmail.com:993"
	set inbox=root

	# Send with S-nail's SMTP. See "Using an MTA" 
	set mta=smtps://smtp.fastmail.com:465"
}

account "work" {
	localopts yes
	set from="Donald Duck <donald.duck@work.example.com>"
	shortcut root "imaps://imap.gmail.com:993"
	set inbox=root
	set mta=smtps://smtp.gmail.com:465"
}

# Use the "personal" acocunt when started as just "mailx".
account personal

Other useful settings

Again, S-nail's defaults are not great but /etc/mail.rc – which will be loaded even when a ~/.mailrc is present – sets a bunch of sane defaults. This section doesn't repeat any settings already enabled in /etc/mail.rc by default.

~/.mailrc
# Automatically use $EDITOR or $VISUAL for composing emails.
# You can also type "~e" in the default screen to switch to the editor.
set editalong
 
# Enter threaded mode automatically
set autosort=thread
 
# Add more entries to the history, and make that persistent
set history-gabby history-file=+.s-nailhist

Interactive use

When starting into interactive mode a summary of the content of the initially opened mailbox is printed. You can print this again with the headers command if you need it later.

In the header display messages are shown with numbers (starting at 1) which uniquely identify messages.

Messages can be printed with the print command, which can abbreviated to just p.

By default the current message is printed. You can specify a list of messages; for example p:u will display all unread messages, p. will print the dot, p 1 5 will print the messages 1 and 5 and p- and p+ will print the last and the next message, respectively.

Many command accepts lists of messages in this syntax; see the "Specifying messages" section in the manpage.

Simply typing Return in an empty line acts like next (n) and prints the next message.

The from command can be used to filter the message list. For example from martin will show all messages with martin in the From: header. A more complex example is f '@<@arch linux, which will print the header summary of all messages that contain the string "arch linux" in some message header, whereas f '@arch linux will only match those with "arch linux" in their subject.

Finally you can use mail to write new emails.

Most common commands

These are some of the most commonly used commands. This is hardly an exhaustive list though; see the manpage for everything else.

Command Description
file open a new mailbox.
newmail checks for new mail and prints a listing of new messages.
headers, he reprints the message list.
folders shows a listing of mailboxes under the currently set folder.
p Prints message(s) and all non-ignored headers.
P Prints message(s) with all headers.
show Prints the raw message contents of the message(s).
r Reply to all addressees of the given message(s).
R Reply to the sender of the given message(s).
Lreply "Mailing-list" reply to the given message(s).
mail Write a new message.
move, mv Move message(s).
flag, unflag Mark message(s) as (un)flagged.
new Mark message(s) unread.
seen Mark message(s) as read.
write, w Download message(s) and attachment(s) in native format to local storage.

Commandline use

mailx (and by extension, S-nail) is what vi is to ed: an interactive enhancement of the commandline tool. As a result S-nail still works very well from just the commandline, making it very easy to use from scripts and such.

For example:

$ echo 'Message body' |
	mailx -d \
		-s 'A subject' \
		-a an_attachment.txt \
		-. \
		to@example.com 'The name <another@example.com>'

Will send an email to to@example.com and another@example.com with an attachment (the -debug flag in this example will enable debug output and disable actual message delivery).

The -. will force termination of option processing and will put mailx in send mode. It will prevent option injection from variables and other nasty surprises.

Since mailx reads various configuration files it's generally considered best to add -:/ to prevent loading them and set required options explicitly with {{ic|-S} and -X. For example:

$ env LC_ALL=C mailx -:/ \
	-Sv15-compat -Ssendwait -Sttycharset=utf-8 \
	-Sexpandaddr=fail,-all,failinvaddr \
	-S mta=smtps://mylogin@example.com:465 -Ssmtp-auth=login \
	-S from=scriptreply@example.com \
	-s 'Subject to go' \
	-. 'Recipient 1 <rec1@exam.ple>' rec2@exam.ple \
	< content_file

In cases when in the USER and PASS are specified as part of an URL (and only then), they must be percent-encoded. mailx offers the urlcodec command which does this for you:

$ printf 'urlcodec encode user@example.com secret' | mailx -#
user%40example.com%20secret

Tips and tricks

Verify GPG messages

S-nail does not support GPG; but mailx(1) contains a macro to verify --clearsign'd messages:

~/.mailrc
define V {
  localopts yes
  wysh set pipe-text/plain=$'@*#++=@\
    < "${MAILX_FILENAME_TEMPORARY}" awk \
        -v TMPFILE="${MAILX_FILENAME_TEMPORARY}" \'\
      BEGIN{done=0}\
      /^-----BEGIN PGP SIGNED MESSAGE-----/,/^$/ {\
        if(done++ != 0)\
          next;\
        print "--- GPG --verify ---";\
        system("gpg --verify " TMPFILE " 2>&1");\
        print "--- GPG --verify ---";\
        print "";\
        next;\
      }\
      /^-----BEGIN PGP SIGNATURE-----/,\
          /^-----END PGP SIGNATURE-----/{\
        next;\
      }\
      {print}\
    \
    print
}
commandalias V '\'call V

See also