1
0
Fork 0
mirror of https://github.com/vim/vim synced 2025-03-16 06:47:52 +01:00
vim/runtime/ftplugin/debchangelog.vim

Ignoring revisions in .git-blame-ignore-revs. Click here to bypass and see the normal blame view.

395 lines
12 KiB
VimL
Raw Normal View History

2008-06-24 21:16:56 +00:00
" Vim filetype plugin file (GUI menu, folding and completion)
2010-05-14 23:24:24 +02:00
" Language: Debian Changelog
2022-07-29 21:36:21 +01:00
" Maintainer: Debian Vim Maintainers <team+vim@tracker.debian.org>
2010-05-14 23:24:24 +02:00
" Former Maintainers: Michael Piefel <piefel@informatik.hu-berlin.de>
" Stefano Zacchiroli <zack@debian.org>
" Last Change: 2023 Aug 18
" License: Vim License
2023-02-02 13:59:48 +00:00
" URL: https://salsa.debian.org/vim-team/vim-debian/blob/main/ftplugin/debchangelog.vim
2006-04-28 22:34:45 +00:00
2008-07-13 17:41:49 +00:00
" Bug completion requires apt-listbugs installed for Debian packages or
2010-05-14 23:24:24 +02:00
" python-launchpadlib installed for Ubuntu packages
2008-07-13 17:41:49 +00:00
2018-05-06 17:57:30 +02:00
if exists('b:did_ftplugin')
2006-04-28 22:34:45 +00:00
finish
endif
2007-05-05 17:54:07 +00:00
let b:did_ftplugin=1
2006-04-28 22:34:45 +00:00
" {{{1 Local settings (do on every load)
2018-05-06 17:57:30 +02:00
if exists('g:debchangelog_fold_enable')
2008-06-24 21:16:56 +00:00
setlocal foldmethod=expr
setlocal foldexpr=DebGetChangelogFold(v:lnum)
setlocal foldtext=DebChangelogFoldText()
endif
2006-04-28 22:34:45 +00:00
" Debian changelogs are not supposed to have any other text width,
" so the user cannot override this setting
setlocal tw=78
setlocal comments=f:*
" Clean unloading
2018-05-06 17:57:30 +02:00
let b:undo_ftplugin = 'setlocal tw< comments< foldmethod< foldexpr< foldtext<'
2006-04-28 22:34:45 +00:00
" }}}1
2004-06-13 20:20:40 +00:00
2018-05-06 17:57:30 +02:00
if exists('g:did_changelog_ftplugin')
2004-06-13 20:20:40 +00:00
finish
endif
2023-02-02 13:59:48 +00:00
" Don't load another plugin (this is global)
let g:did_changelog_ftplugin = 1
2022-07-29 21:36:21 +01:00
" Make sure the '<' and 'C' flags are not included in 'cpoptions', otherwise
" <CR> would not be recognized. See ":help 'cpoptions'".
let s:cpo_save = &cpo
set cpo&vim
2006-04-27 00:02:13 +00:00
" {{{1 GUI menu
2004-06-13 20:20:40 +00:00
" Helper functions returning various data.
" Returns full name, either from $DEBFULLNAME or debianfullname.
" TODO Is there a way to determine name from anywhere else?
function <SID>FullName()
2018-05-06 17:57:30 +02:00
if exists('$DEBFULLNAME')
2004-06-13 20:20:40 +00:00
return $DEBFULLNAME
2018-05-06 17:57:30 +02:00
elseif exists('g:debianfullname')
2004-06-13 20:20:40 +00:00
return g:debianfullname
else
2018-05-06 17:57:30 +02:00
return 'Your Name'
2004-06-13 20:20:40 +00:00
endif
endfunction
" Returns email address, from $DEBEMAIL, $EMAIL or debianemail.
function <SID>Email()
2018-05-06 17:57:30 +02:00
if exists('$DEBEMAIL')
2004-06-13 20:20:40 +00:00
return $DEBEMAIL
2018-05-06 17:57:30 +02:00
elseif exists('$EMAIL')
2004-06-13 20:20:40 +00:00
return $EMAIL
2018-05-06 17:57:30 +02:00
elseif exists('g:debianemail')
2005-08-15 21:41:48 +00:00
return g:debianemail
2004-06-13 20:20:40 +00:00
else
2018-05-06 17:57:30 +02:00
return 'your@email.address'
2004-06-13 20:20:40 +00:00
endif
endfunction
" Returns date in RFC822 format.
function <SID>Date()
let savelang = v:lc_time
2018-05-06 17:57:30 +02:00
execute 'language time C'
let dateandtime = strftime('%a, %d %b %Y %X %z')
execute 'language time ' . savelang
2004-06-13 20:20:40 +00:00
return dateandtime
endfunction
function <SID>WarnIfNotUnfinalised()
2018-05-06 17:57:30 +02:00
if match(getline('.'), ' -- [[:alpha:]][[:alnum:].]')!=-1
2004-06-13 20:20:40 +00:00
echohl WarningMsg
2018-05-06 17:57:30 +02:00
echo 'The entry has not been unfinalised before editing.'
2004-06-13 20:20:40 +00:00
echohl None
return 1
endif
return 0
endfunction
function <SID>Finalised()
2018-05-06 17:57:30 +02:00
let savelinenum = line('.')
1
call search('^ -- ')
if match(getline('.'), ' -- [[:alpha:]][[:alnum:].]')!=-1
2004-06-13 20:20:40 +00:00
let returnvalue = 1
else
let returnvalue = 0
endif
execute savelinenum
return returnvalue
endfunction
" These functions implement the menus
function NewVersion()
" The new entry is unfinalised and shall be changed
2022-07-29 21:36:21 +01:00
amenu disable &Changelog.&New\ Version
amenu enable &Changelog.&Add\ Entry
amenu enable &Changelog.&Close\ Bug
amenu enable &Changelog.Set\ &Distribution
amenu enable &Changelog.Set\ &Urgency
amenu disable &Changelog.U&nfinalise
amenu enable &Changelog.&Finalise
2006-04-28 22:34:45 +00:00
call append(0, substitute(getline(1), '-\([[:digit:]]\+\))', '-$$\1)', ''))
2018-05-06 17:57:30 +02:00
call append(1, '')
call append(2, '')
call append(3, ' -- ')
call append(4, '')
call Urgency('low')
normal! 1G0
call search(')')
normal! h
" ':normal' doesn't support key annotation (<c-a>) directly.
2022-07-29 21:36:21 +01:00
" Vim's manual recommends using ':exe' to use key annotation indirectly (backslash-escaping needed though).
exe "normal! \<c-a>"
2006-04-28 22:34:45 +00:00
call setline(1, substitute(getline(1), '-\$\$', '-', ''))
2018-05-06 17:57:30 +02:00
if exists('g:debchangelog_fold_enable')
2008-07-13 17:41:49 +00:00
foldopen
endif
2004-06-13 20:20:40 +00:00
call AddEntry()
endfunction
function AddEntry()
2018-05-06 17:57:30 +02:00
1
call search('^ -- ')
.-2
call append('.', ' * ')
.+3
2004-06-13 20:20:40 +00:00
let warn=<SID>WarnIfNotUnfinalised()
2018-05-06 17:57:30 +02:00
.-2
2004-06-13 20:20:40 +00:00
if warn
echohl MoreMsg
2018-05-06 17:57:30 +02:00
call input('Hit ENTER')
2004-06-13 20:20:40 +00:00
echohl None
endif
startinsert!
endfunction
function CloseBug()
2018-05-06 17:57:30 +02:00
1
call search('^ -- ')
2004-06-13 20:20:40 +00:00
let warn=<SID>WarnIfNotUnfinalised()
2018-05-06 17:57:30 +02:00
.-2
call append('.', ' * (closes: #' . input('Bug number to close: ') . ')')
normal! j^ll
2004-06-13 20:20:40 +00:00
startinsert
endfunction
function Distribution(dist)
2018-05-06 17:57:30 +02:00
call setline(1, substitute(getline(1), ') *\%(UNRELEASED\|\l\+\);', ') ' . a:dist . ';', ''))
2004-06-13 20:20:40 +00:00
endfunction
function Urgency(urg)
2018-05-06 17:57:30 +02:00
call setline(1, substitute(getline(1), 'urgency=.*$', 'urgency=' . a:urg, ''))
2004-06-13 20:20:40 +00:00
endfunction
function <SID>UnfinaliseMenu()
" This means the entry shall be changed
2022-07-29 21:36:21 +01:00
amenu disable &Changelog.&New\ Version
amenu enable &Changelog.&Add\ Entry
amenu enable &Changelog.&Close\ Bug
amenu enable &Changelog.Set\ &Distribution
amenu enable &Changelog.Set\ &Urgency
amenu disable &Changelog.U&nfinalise
amenu enable &Changelog.&Finalise
2004-06-13 20:20:40 +00:00
endfunction
function Unfinalise()
call <SID>UnfinaliseMenu()
2018-05-06 17:57:30 +02:00
1
call search('^ -- ')
call setline('.', ' -- ')
2004-06-13 20:20:40 +00:00
endfunction
function <SID>FinaliseMenu()
" This means the entry should not be changed anymore
2022-07-29 21:36:21 +01:00
amenu enable &Changelog.&New\ Version
amenu disable &Changelog.&Add\ Entry
amenu disable &Changelog.&Close\ Bug
amenu disable &Changelog.Set\ &Distribution
amenu disable &Changelog.Set\ &Urgency
amenu enable &Changelog.U&nfinalise
amenu disable &Changelog.&Finalise
2004-06-13 20:20:40 +00:00
endfunction
function Finalise()
call <SID>FinaliseMenu()
2018-05-06 17:57:30 +02:00
1
call search('^ -- ')
call setline('.', ' -- ' . <SID>FullName() . ' <' . <SID>Email() . '> ' . <SID>Date())
2004-06-13 20:20:40 +00:00
endfunction
function <SID>MakeMenu()
amenu &Changelog.&New\ Version :call NewVersion()<CR>
2022-07-29 21:36:21 +01:00
amenu &Changelog.&Add\ Entry :call AddEntry()<CR>
amenu &Changelog.&Close\ Bug :call CloseBug()<CR>
menu &Changelog.-sep- <nul>
amenu &Changelog.Set\ &Distribution.&unstable :call Distribution("unstable")<CR>
amenu &Changelog.Set\ &Distribution.&frozen :call Distribution("frozen")<CR>
amenu &Changelog.Set\ &Distribution.&stable :call Distribution("stable")<CR>
menu &Changelog.Set\ &Distribution.-sep- <nul>
amenu &Changelog.Set\ &Distribution.frozen\ unstable :call Distribution("frozen unstable")<CR>
amenu &Changelog.Set\ &Distribution.stable\ unstable :call Distribution("stable unstable")<CR>
amenu &Changelog.Set\ &Distribution.stable\ frozen :call Distribution("stable frozen")<CR>
amenu &Changelog.Set\ &Distribution.stable\ frozen\ unstable :call Distribution("stable frozen unstable")<CR>
amenu &Changelog.Set\ &Urgency.&low :call Urgency("low")<CR>
amenu &Changelog.Set\ &Urgency.&medium :call Urgency("medium")<CR>
amenu &Changelog.Set\ &Urgency.&high :call Urgency("high")<CR>
menu &Changelog.-sep- <nul>
amenu &Changelog.U&nfinalise :call Unfinalise()<CR>
amenu &Changelog.&Finalise :call Finalise()<CR>
2004-06-13 20:20:40 +00:00
if <SID>Finalised()
call <SID>FinaliseMenu()
else
call <SID>UnfinaliseMenu()
endif
endfunction
augroup changelogMenu
au BufEnter * if &filetype == "debchangelog" | call <SID>MakeMenu() | endif
2022-07-29 21:36:21 +01:00
au BufLeave * if &filetype == "debchangelog" | silent! aunmenu &Changelog | endif
2004-06-13 20:20:40 +00:00
augroup END
2006-04-27 00:02:13 +00:00
" }}}
" {{{1 folding
2007-05-05 17:54:07 +00:00
" look for an author name in the [zonestart zoneend] lines searching backward
function! s:getAuthor(zonestart, zoneend)
let linepos = a:zoneend
while linepos >= a:zonestart
let line = getline(linepos)
2018-05-06 17:57:30 +02:00
if line =~# '^ --'
2007-05-05 17:54:07 +00:00
return substitute(line, '^ --\s*\([^<]\+\)\s*.*', '\1', '')
endif
let linepos -= 1
2006-04-27 00:02:13 +00:00
endwhile
2007-05-05 17:54:07 +00:00
return '[unknown]'
2006-04-27 00:02:13 +00:00
endfunction
2008-06-24 21:16:56 +00:00
" Look for a package source name searching backward from the givenline and
" returns it. Return the empty string if the package name can't be found
function! DebGetPkgSrcName(lineno)
let lineidx = a:lineno
let pkgname = ''
while lineidx > 0
let curline = getline(lineidx)
2018-05-06 17:57:30 +02:00
if curline =~# '^\S'
2008-06-24 21:16:56 +00:00
let pkgname = matchlist(curline, '^\(\S\+\).*$')[1]
break
endif
let lineidx = lineidx - 1
endwhile
return pkgname
endfunction
2006-04-27 00:02:13 +00:00
function! DebChangelogFoldText()
2018-05-06 17:57:30 +02:00
if v:folddashes ==# '-' " changelog entry fold
2007-05-05 17:54:07 +00:00
return foldtext() . ' -- ' . s:getAuthor(v:foldstart, v:foldend) . ' '
2006-04-27 00:02:13 +00:00
endif
return foldtext()
endfunction
2008-06-24 21:16:56 +00:00
function! DebGetChangelogFold(lnum)
2006-04-27 00:02:13 +00:00
let line = getline(a:lnum)
2018-05-06 17:57:30 +02:00
if line =~# '^\w\+'
2006-04-27 00:02:13 +00:00
return '>1' " beginning of a changelog entry
endif
2018-05-06 17:57:30 +02:00
if line =~# '^\s\+\[.*\]'
2006-04-27 00:02:13 +00:00
return '>2' " beginning of an author-specific chunk
endif
2018-05-06 17:57:30 +02:00
if line =~# '^ --'
2006-04-27 00:02:13 +00:00
return '1'
endif
return '='
endfunction
2018-05-06 17:57:30 +02:00
if exists('g:debchangelog_fold_enable')
2008-07-13 17:41:49 +00:00
silent! foldopen! " unfold the entry the cursor is on (usually the first one)
endif
2008-06-24 21:16:56 +00:00
" }}}
" {{{1 omnicompletion for Closes: #
if !exists('g:debchangelog_listbugs_severities')
let g:debchangelog_listbugs_severities = 'critical,grave,serious,important,normal,minor,wishlist'
endif
fun! DebCompleteBugs(findstart, base)
if a:findstart
let line = getline('.')
2008-07-13 17:41:49 +00:00
" try to detect whether this is closes: or lp:
let g:debchangelog_complete_mode = 'debbugs'
let try_colidx = col('.') - 1
let colidx = -1 " default to no-completion-possible
2018-05-06 17:57:30 +02:00
while try_colidx > 0 && line[try_colidx - 1] =~# '\s\|\d\|#\|,\|:'
2008-07-13 17:41:49 +00:00
let try_colidx = try_colidx - 1
2018-05-06 17:57:30 +02:00
if line[try_colidx] ==# '#' && colidx == -1
2008-07-13 17:41:49 +00:00
" found hash, where we complete from:
let colidx = try_colidx
2018-05-06 17:57:30 +02:00
elseif line[try_colidx] ==# ':'
if try_colidx > 1 && strpart(line, try_colidx - 2, 3) =~? '\clp:'
2008-07-13 17:41:49 +00:00
let g:debchangelog_complete_mode = 'lp'
endif
break
endif
endwhile
2008-06-24 21:16:56 +00:00
return colidx
2008-07-13 17:41:49 +00:00
else " return matches:
let bug_lines = []
2018-05-06 17:57:30 +02:00
if g:debchangelog_complete_mode ==? 'lp'
2008-07-13 17:41:49 +00:00
if ! has('python')
echoerr 'vim must be built with Python support to use LP bug completion'
return
endif
let pkgsrc = DebGetPkgSrcName(line('.'))
python << EOF
import vim
try:
2010-05-14 23:24:24 +02:00
from launchpadlib.launchpad import Launchpad
from lazr.restfulclient.errors import HTTPError
# login anonymously
lp = Launchpad.login_anonymously('debchangelog.vim', 'production')
ubuntu = lp.distributions['ubuntu']
try:
sp = ubuntu.getSourcePackage(name=vim.eval('pkgsrc'))
status = ('New', 'Incomplete', 'Confirmed', 'Triaged',
'In Progress', 'Fix Committed')
tasklist = sp.searchTasks(status=status, order_by='id')
liststr = '['
for task in tasklist:
bug = task.bug
liststr += "'#%d - %s'," % (bug.id, bug.title.replace('\'', '\'\''))
liststr += ']'
vim.command('silent let bug_lines = %s' % liststr.encode('utf-8'))
except HTTPError:
pass
2008-07-13 17:41:49 +00:00
except ImportError:
2010-05-14 23:24:24 +02:00
vim.command('echoerr \'python-launchpadlib >= 1.5.4 needs to be installed to use Launchpad bug completion\'')
2008-07-13 17:41:49 +00:00
EOF
else
if ! filereadable('/usr/sbin/apt-listbugs')
echoerr 'apt-listbugs not found, you should install it to use Closes bug completion'
return
endif
let pkgsrc = DebGetPkgSrcName(line('.'))
let listbugs_output = system('/usr/sbin/apt-listbugs -s ' . g:debchangelog_listbugs_severities . ' list ' . pkgsrc . ' | grep "^ #" 2> /dev/null')
let bug_lines = split(listbugs_output, '\n')
2008-06-24 21:16:56 +00:00
endif
let completions = []
for line in bug_lines
let parts = matchlist(line, '^\s*\(#\S\+\)\s*-\s*\(.*\)$')
2008-07-13 17:41:49 +00:00
" filter only those which match a:base:
2018-05-06 17:57:30 +02:00
if parts[1] !~ '^' . a:base
2008-07-13 17:41:49 +00:00
continue
endif
2008-06-24 21:16:56 +00:00
let completion = {}
let completion['word'] = parts[1]
let completion['menu'] = parts[2]
let completion['info'] = parts[0]
let completions += [completion]
endfor
return completions
endif
endfun
setlocal omnifunc=DebCompleteBugs
2007-05-05 17:54:07 +00:00
2006-04-27 00:02:13 +00:00
" }}}
2022-07-29 21:36:21 +01:00
" Restore the previous value of 'cpoptions'.
let &cpo = s:cpo_save
unlet s:cpo_save
2006-04-27 00:02:13 +00:00
" vim: set foldmethod=marker: