131 lines
3.8 KiB
Python
131 lines
3.8 KiB
Python
# -*- coding: utf-8 -*- vim:sw=4:sts=4:et:ai:si:sta:fenc=utf-8
|
|
|
|
"""Des fonctions pour éditer des fichiers.
|
|
"""
|
|
|
|
__all__ = ('edit_file', 'edit_template')
|
|
|
|
import os, sys
|
|
|
|
from .base import isseq
|
|
from .env import get_editor, get_editor_options, get_editor_setrow
|
|
from .uio import EditorIO, _s
|
|
from .lines import Lines
|
|
from .args import split_args
|
|
from .tmpfiles import mktemp
|
|
from .paths import in_PATH
|
|
from .procs import spawn
|
|
|
|
# options, setrow, setcol, colplus
|
|
EDITOR_CAPS = {'emacs': ('', '+', ':', 1),
|
|
'xemacs': ('', '+', ':', 1),
|
|
'gvim': ('-f', '+', '', 0),
|
|
'vim': ('-f', '+', '', 0),
|
|
'vi': ('', '+', '', 0),
|
|
}
|
|
def get_default_editors():
|
|
"""Retourner une liste d'éditeurs par défaut pour la plateforme en cours
|
|
"""
|
|
if sys.platform.startswith('linux'):
|
|
return ('emacs', 'xemacs', 'gvim', 'vim', 'vi')
|
|
else:
|
|
return ('xemacs', 'emacs', 'gvim', 'vim', 'vi')
|
|
|
|
def get_editor_caps():
|
|
"""Obtenir les caractéristiques de l'éditeur configuré.
|
|
|
|
@return: (editor, options, setrow, setcol, colplus)
|
|
"""
|
|
options = None
|
|
setrow = None
|
|
setcol = ''
|
|
colplus = 0
|
|
|
|
editor = get_editor()
|
|
if editor is None:
|
|
for editor in get_default_editors():
|
|
if in_PATH(editor): break
|
|
else:
|
|
raise OSError("Unable to find a default editor. Please set UTOOLS_EDITOR.")
|
|
|
|
if EDITOR_CAPS.has_key(editor):
|
|
options, setrow, setcol, colplus = EDITOR_CAPS[editor]
|
|
|
|
if options is None and setrow is None:
|
|
options = split_args(get_editor_options())
|
|
setrow = get_editor_setrow()
|
|
if options is None and setrow is None and EDITOR_CAPS.has_key(editor):
|
|
options, setrow, setcol, colplus = EDITOR_CAPS[editor]
|
|
|
|
return editor, options, setrow or '', setcol or '', int(colplus)
|
|
|
|
def edit_file(file, row=None, col=None):
|
|
"""Lancer un éditeur pour éditer le fichier file.
|
|
|
|
@return: le status d'exécution de l'éditeur.
|
|
"""
|
|
editor, options, setrow, setcol, colplus = get_editor_caps()
|
|
|
|
cmd = [editor]
|
|
if options:
|
|
if isseq(options): cmd.extend(options)
|
|
else: cmd.append(options)
|
|
if setrow and row is not None:
|
|
row = int(row)
|
|
opt = '%s%i' % (setrow, row)
|
|
if setcol and col is not None:
|
|
col = int(col)
|
|
opt += '%s%i' % (setcol, col + colplus)
|
|
cmd.append(opt)
|
|
cmd.append(file)
|
|
return spawn(*cmd)
|
|
|
|
def edit_template(template=None, strip_prefix=None, row=None, col=None, lines=None):
|
|
"""Obtenir une valeur éditée dans un éditeur.
|
|
|
|
Un fichier temporaire vide est initialisé avec le contenu de template,
|
|
puis le fichier est proposé à l'édition.
|
|
|
|
A la sortie, toutes les lignes commençant par strip_prefix sont supprimée,
|
|
et une instance de Lines avec les lignes du fichier est retourné.
|
|
|
|
@return: lines
|
|
@rtype: Lines
|
|
"""
|
|
if lines is None:
|
|
uio = EditorIO()
|
|
lines = Lines(uio=uio)
|
|
else:
|
|
uio = lines.uio
|
|
if uio is None:
|
|
uio = EditorIO()
|
|
lines.uio = uio
|
|
|
|
## préparer le fichier
|
|
tmpf, tmpfile = mktemp('utools')
|
|
try:
|
|
if template is not None:
|
|
template = uio.s(template)
|
|
try: tmpf.write(template)
|
|
finally: tmpf.close()
|
|
else:
|
|
tmpf.close()
|
|
|
|
## l'éditer
|
|
edit_file(tmpfile, row, col)
|
|
|
|
## traiter le résultat
|
|
lines.readlines(tmpfile)
|
|
|
|
# enlever les préfixes
|
|
if strip_prefix is not None:
|
|
lines.filter(lambda l: not l.startswith(strip_prefix))
|
|
|
|
# supprimer les lignes vides au début et à la fin
|
|
while lines and not lines[0].strip(): del lines[0]
|
|
while lines and not lines[-1].strip(): del lines[-1]
|
|
|
|
return lines
|
|
finally:
|
|
os.remove(tmpfile)
|