diff options
author | Tom Ryder <tom@sanctum.geek.nz> | 2020-01-01 16:08:21 +1300 |
---|---|---|
committer | Tom Ryder <tom@sanctum.geek.nz> | 2020-01-01 16:09:11 +1300 |
commit | 80227fc6263ca864227de8b9d8d9f93f19ad173a (patch) | |
tree | f0183af0e7fc5a73cc2427653ac7fd67a3848a2e /vim | |
parent | Add trailing commas (diff) | |
download | dotfiles-80227fc6263ca864227de8b9d8d9f93f19ad173a.tar.gz dotfiles-80227fc6263ca864227de8b9d8d9f93f19ad173a.zip |
Reimplement mail header importance flagging
Just for fun, write something a little more comprehensive to read in the
entire mail header as a data structure, in order to add or set header
fields correctly. I don't think this is totally RFC-compliant yet; I'll
need to check.
Diffstat (limited to 'vim')
-rw-r--r-- | vim/after/ftplugin/mail.vim | 17 | ||||
-rw-r--r-- | vim/autoload/mail.vim | 32 | ||||
-rw-r--r-- | vim/autoload/mail/header.vim | 54 | ||||
-rw-r--r-- | vim/autoload/mail/header/field.vim | 39 | ||||
-rw-r--r-- | vim/autoload/mail/importance.vim | 24 |
5 files changed, 129 insertions, 37 deletions
diff --git a/vim/after/ftplugin/mail.vim b/vim/after/ftplugin/mail.vim index f81be691..dbb2f7c5 100644 --- a/vim/after/ftplugin/mail.vim +++ b/vim/after/ftplugin/mail.vim @@ -9,10 +9,14 @@ let b:undo_ftplugin .= '|delcommand SuggestStart' SuggestStart " Normalise quoting -command -buffer -bar -range=% StrictQuote +command -bar -buffer -range=% StrictQuote \ call mail#StrictQuote(<q-line1>, <q-line2>) let b:undo_ftplugin .= '|delcommand StrictQuote' +command -bar -buffer -nargs=1 SetImportance + \ call mail#importance#Set(<f-args>) +let b:undo_ftplugin .= '|delcommand SetImportance' + " Add a space to the end of wrapped lines for format-flowed mail setlocal formatoptions+=w let b:undo_ftplugin .= '|setlocal formatoptions<' @@ -35,12 +39,15 @@ if exists('no_plugin_maps') || exists('no_mail_maps') endif " Flag messages as important/unimportant -nnoremap <buffer> <LocalLeader>h - \ :<C-U>call mail#FlagImportant()<CR> +nnoremap <buffer> <LocalLeader>ih + \ :<C-U>SetImportance high<CR> let b:undo_ftplugin .= '|nunmap <buffer> <LocalLeader>h' -nnoremap <buffer> <LocalLeader>l - \ :<C-U>call mail#FlagUnimportant()<CR> +nnoremap <buffer> <LocalLeader>il + \ :<C-U>SetImportance low<CR> let b:undo_ftplugin .= '|nunmap <buffer> <LocalLeader>l' +nnoremap <buffer> <LocalLeader>in + \ :<C-U>SetImportance normal<CR> +let b:undo_ftplugin .= '|nunmap <buffer> <LocalLeader>n' " Quote operator nnoremap <buffer> <expr> <LocalLeader>q diff --git a/vim/autoload/mail.vim b/vim/autoload/mail.vim index abed119a..cd585af4 100644 --- a/vim/autoload/mail.vim +++ b/vim/autoload/mail.vim @@ -1,35 +1,3 @@ -" Add a header to a mail message -function! mail#AddHeaderField(name, body) abort - let num = 0 - while num < line('$') && getline(num + 1) !=# '' - let num += 1 - endwhile - call append(num, a:name.': '.a:body) -endfunction - -" Add a set of headers to a mail message -function! mail#AddHeaderFields(fields) abort - for name in sort(keys(a:fields)) - call mail#AddHeaderField(name, a:fields[name]) - endfor -endfunction - -" Flag a message as important -function! mail#FlagImportant() abort - call mail#AddHeaderFields({ - \ 'Importance': 'High', - \ 'X-Priority': 1, - \ }) -endfunction - -" Flag a message as unimportant -function! mail#FlagUnimportant() abort - call mail#AddHeaderFields({ - \ 'Importance': 'Low', - \ 'X-Priority': 5, - \ }) -endfunction - " Move through quoted paragraphs like normal-mode `{` and `}` function! mail#NewBlank(count, up, visual) abort diff --git a/vim/autoload/mail/header.vim b/vim/autoload/mail/header.vim new file mode 100644 index 00000000..8495a721 --- /dev/null +++ b/vim/autoload/mail/header.vim @@ -0,0 +1,54 @@ +function! mail#header#Read() abort + let fields = [] + for lnum in range(1, line('$')) + let line = getline(lnum) + let matchlist = matchlist( + \ line, + \ '^\([a-zA-Z0-9-]\+\):\s*\(\_.*\)', + \) + if !empty(matchlist) + let field = { + \ 'name': matchlist[1], + \ 'body': matchlist[2], + \} + call add(fields, field) + elseif line =~ '^\s' && exists('field') + let field['body'] .= "\n" . line + elseif line ==# '' + break + else + throw 'Parse error' + endif + endfor + let header = { + \'fields': fields, + \} + return header +endfunction + +function! mail#header#String(header) abort + let fields = copy(a:header['fields']) + return join( + \ map( + \ copy(a:header['fields']), + \ 'v:val[''name''] . '': '' . v:val[''body''] . "\n"'), + \ '', + \) +endfunction + +function! mail#header#Write(header) abort + let start = 1 + for lnum in range(1, line('$')) + if getline(lnum) ==# '' + break + endif + let end = lnum + endfor + let curpos = getpos('.') + if exists('end') + let range = join([start, end], ',') + execute join(['silent', range, 'delete']) + endif + silent 0 put =mail#header#String(a:header) + call setpos('.', curpos) +endfunction diff --git a/vim/autoload/mail/header/field.vim b/vim/autoload/mail/header/field.vim new file mode 100644 index 00000000..ab3d405a --- /dev/null +++ b/vim/autoload/mail/header/field.vim @@ -0,0 +1,39 @@ +function! mail#header#field#Add(header, name, body) abort + let new = { + \ 'name': a:name, + \ 'body': a:body, + \} + call add(a:header['fields'], new) +endfunction + +function! mail#header#field#Set(header, name, body) abort + let fields = [] + let new = { + \ 'name': a:name, + \ 'body': a:body, + \} + for field in a:header['fields'] + if field['name'] ==? a:name + if exists('new') + let field = new | unlet new + else + continue + endif + endif + call add(fields, field) + endfor + if exists('new') + call add(fields, new) | unlet new + endif + let a:header['fields'] = fields +endfunction + +function! mail#header#field#Clear(header, name) abort + let fields = [] + for field in a:header['fields'] + if field['name'] !=? a:name + call add(fields, field) + endif + endfor + let a:header['fields'] = fields +endfunction diff --git a/vim/autoload/mail/importance.vim b/vim/autoload/mail/importance.vim new file mode 100644 index 00000000..6a5ed096 --- /dev/null +++ b/vim/autoload/mail/importance.vim @@ -0,0 +1,24 @@ +let s:fields = { + \ 'high': { + \ 'Importance': 'High', + \ 'X-Priority': '1', + \}, + \ 'low': { + \ 'Importance': 'Low', + \ 'X-Priority': '5', + \}, + \ 'normal': {}, + \} + +function! mail#importance#Set(level) abort + let header = mail#header#Read() + let fields = s:fields[a:level] + for name in ['Importance', 'X-Priority'] + if has_key(fields, name) + call mail#header#field#Set(header, name, fields[name]) + else + call mail#header#field#Clear(header, name) + endif + endfor + call mail#header#Write(header) +endfunction |