2011-04-26 16 views
5

actualmente estoy usando el siguiente código para conectar flymake y pyflakes en emacs:¿Se puede crear el archivo temporal de flymake en el directorio temporal del sistema?

(defun flymake-create-temp-in-system-tempdir (filename prefix) 
    (make-temp-file (or prefix "flymake"))) 

y luego me pase esta función para flymake-init-create-temp-buffer-copy. (Tomado de http://hustoknow.blogspot.com/2010/09/emacs-and-pyflakes-using-tmp-directory.html).

Este código funcionó bien hasta ayer. Cuando vuelva a ciertos archivos de Python, me sale el siguiente error:

switched OFF Flymake mode for buffer admin.py due to fatal status 
CFGERR, warning Configuration error has occured while running  
(pyflakes ../../../../../../../tmp/flymake28459SVv) 

qué está pasando flymake lo que parece ser el nombre de archivo erróneo pyflakes? Espero que pase algo como "/ tmp/efe234234" y no he modificado ninguna de las configuraciones del directorio tmp.

No recuerdo que emacs se haya actualizado recientemente para Ubuntu y no se puede pensar en nada que pueda haber causado un error (los archivos .emacs están versionados).

El único problema que puedo pensar es que este es un directorio fuertemente anidado enlazado a un directorio en mi ~/directorio de Dropbox, pero esto no sucede con otros enlaces simbólicos de una manera similar.

¿Cómo puedo solucionar este problema?

ACTUALIZACIÓN

he hecho algunas depuración y ahora veo que no está pasando el camino correcto como argumento. Necesita un directorio padre más insertado en la ruta para que funcione, lo que me hace pensar que se está arruinando debido a los enlaces simbólicos.

Aquí hay un ejemplo de sesión shell para mostrar a qué me refiero. Estoy haciendo esto desde el directorio relativa correcta:

$ pyflakes ../../../../../tmp/flymake13382xHi 
../../../../../tmp/flymake13382xHi: No such file or directory 

Esa es la flymake comando está intentando ejecutar. Si lo cambio:

$ pyflakes ../../../../../../tmp/flymake13382xHi 

No obtengo salida (como se esperaba). Tenga en cuenta el extra ".." en la ruta.

¿Cómo puedo hacer que flymake pase un camino absoluto en lugar de estos locos caminos relativos?

ACTUALIZACIÓN 2

He conseguido que todo funcione. Básicamente existe esta función:

(defun flymake-pyflakes-init() 
    ; Make sure it's not a remote buffer or flymake would not work 
    (when (not (subsetp (list (current-buffer)) (tramp-list-remote-buffers))) 
     (let* ((temp-file (flymake-init-create-temp-buffer-copy 
        'flymake-create-temp-in-system-tempdir)) 
      (local-file (file-relative-name 
         temp-file 
         (file-name-directory buffer-file-name)))) 
    (list "pyflakes" (list temp-file))))) 

En la última parte que tenía que cambiar el argumento de list a partir local-file a temp-file porque local-file fue la ruta relativa loca que no quería. ¿Por qué el autor de ese fragmento usó local-file en primer lugar?

Gracias, Ryan

Respuesta

0

que no tienen una solución directa a la pregunta pyflakes, pero aquí hay algo similar para usted.

no me gusta la forma en C# fue manejado en flymake, por lo que he modificado el C# entrada en el flymake-allowed-file-name-masks para referirse a distintas rutinas de inicialización y limpieza, con este código:

(let ((csharpentry (assoc "\\.cs\\'" flymake-allowed-file-name-masks))) 
    (if csharpentry 
     (setcdr csharpentry '(csharp-flymake-init csharp-flymake-cleanup)) 
    (add-to-list 
    'flymake-allowed-file-name-masks 
    (list key 'csharp-flymake-init 'csharp-flymake-cleanup)))) 

La documentación es una especie de irregular en estas cosas, pero el código es la documentación, y por lo que pude ver, se supone que la rutina de inicio devuelve la línea de comando para una ejecución de comprobación de sintaxis. Está formateado como una lista de 2 elementos, el carro es el comando para ejecutar, y el cadr es en sí mismo una lista de los argumentos. En mi ejemplo, el valor de retorno es la siguiente:

("csc.exe" ("/t:module" "/nologo" "nameOfFileToCheck.cs")) 

La rutina de inicialización que devuelve line copia de este comando el búfer existente en un archivo temporal, utilizando incorporado copia fn de flymake, y luego utiliza el nombre del archivo temporal como lo que hay que verificar Así que si el nombre del archivo es "búfer Source.cs", el valor real de regresar de la fn init es

("csc.exe" ("/t:module" "/nologo" "source_flymake.cs")) 

El código es el siguiente:

(defun csharp-flymake-init() 
    (csharp-flymake-init-impl 
    'flymake-create-temp-inplace t t 'csharp-flymake-get-cmdline)) 

(defun csharp-flymake-init-impl (create-temp-f use-relative-base-dir use-relative-source get-cmdline-f) 
    "Create syntax check command line for a directly checked source file. 
Use CREATE-TEMP-F for creating temp copy." 
    (let* ((args nil) 
     (temp-source-file-name (flymake-init-create-temp-buffer-copy create-temp-f))) 
    (setq args (flymake-get-syntax-check-program-args 
       temp-source-file-name "." 
       use-relative-base-dir use-relative-source 
       get-cmdline-f)) 
    args)) 

he implementado en 2 funciones distintas, sólo se para seguir el patrón que vi en flymake.el.

De todos modos ... Lo que puede ver es que el init fn crea el archivo temporal y luego devuelve los argumentos. La llamada a flymake-get-syntax-check-program-args en realidad se reduce a una llamada al get-cmdline-f, que en el caso de C# es csharp-flymake-get-cmdline. ¿Por qué toda esta estratificación e indirección? No lo sé; así es como Flymake.

En la limpieza específica de C# fn, solo compruebo los archivos de "producto" de la comprobación de sintaxis y los elimino, y luego también encadenan a flymake-simple-cleanup, para eliminar el archivo temporal _ _lowmake.cs que se creó.

Tal vez su camino dir anidada tiene algo que ver con los use-relative-base-dir y use-relative-source argumentos que Flymake usos en su propia rutina de inicio por defecto, que creo que es flymake-simple-make-init-impl.

0

La función make-temp-file utiliza la variable temporary-file-directory, por lo que quizás podría intentar configurar temporary-file-directory en otra cosa para solucionar su problema.

0

Esto es lo que uso para PHP en Windows. Utiliza la sugerencia make-temp-file de Trey. También establece explícitamente las funciones de inicio y limpieza para PHP, a las cosas que quiero. Podría usar básicamente lo mismo para Python.

(defun cheeso-flymake-create-temp-intemp (file-name prefix) 
    "Return file name in temporary directory for checking FILE-NAME. 
This is a replacement for `flymake-create-temp-inplace'. The 
difference is that it gives a file name in 
`temporary-file-directory' instead of the same directory as 
FILE-NAME. 

For the use of PREFIX see that function. 

This won't always work; it will fail if the source module 
refers to relative paths. 
" 
    (unless (stringp file-name) 
    (error "Invalid file-name")) 
    (or prefix 
     (setq prefix "flymake")) 
    (let* ((name (concat 
       (file-name-nondirectory 
       (file-name-sans-extension file-name)) 
       "_" prefix)) 
     (ext (concat "." (file-name-extension file-name))) 
     (temp-name (make-temp-file name nil ext)) 
     ) 
    (flymake-log 3 "create-temp-intemp: file=%s temp=%s" file-name temp-name) 
    temp-name)) 


(defun cheeso-php-flymake-get-cmdline (source base-dir) 
    "Gets the cmd line for running a flymake session in a PHP buffer. 
This gets called by flymake itself." 

     (list "c:\\Progra~2\\PHP\\v5.3\\php.exe" 
       (list "-f" source "-l"))) 


(defun cheeso-php-flymake-init() 
    "initialize flymake for php" 
    (let ((create-temp-f 'cheeso-flymake-create-temp-intemp) 
     ;;(create-temp-f 'flymake-create-temp-inplace) 
     (use-relative-base-dir t) 
     (use-relative-source t) 
     (get-cmdline-f 'cheeso-php-flymake-get-cmdline) 
     args 
     temp-source-file-name) 

    (setq temp-source-file-name (flymake-init-create-temp-buffer-copy create-temp-f) 

      args (flymake-get-syntax-check-program-args 
       temp-source-file-name "." 
       use-relative-base-dir use-relative-source 
       get-cmdline-f)) 
    args)) 


(defun cheeso-php-flymake-cleanup() 
) 

(eval-after-load "flymake" 
    '(progn 

    ;; 1. add a PHP entry to the flymake-allowed-file-name-masks 
    (let* ((key "\\.php\\'") 
     (phpentry (assoc key flymake-allowed-file-name-masks))) 
    (if phpentry 
     (setcdr phpentry '(cheeso-php-flymake-init cheeso-php-flymake-cleanup)) 
     (add-to-list 
     'flymake-allowed-file-name-masks 
     (list key 'cheeso-php-flymake-init 'cheeso-php-flymake-cleanup)))))) 
+0

Muchas gracias por esto. Estoy de vacaciones ahora, pero cuando regrese lo probaré. –

1

Para mí, que he resuelto por el usuario modifique el guión/usr/bin// pyflakes locales, puedo probar si el archivo existe, si no, puedo añadir una barra inclinada.

#!/bin/bash 

FILE=$1 

# Test if folder exist 
if [ ! -e "$FILE" ]; then 
FILE="/$1" 
fi 

epylint "$FILE" 2>/dev/null 
pep8 --ignore=E221,E701,E202 --repeat "$FILE" 
true 
Cuestiones relacionadas