2014-07-22 1 views
4

Je suis en train de migrer un makefile existant Shake et jusqu'à présent, je l'ai essayé ce qui suit (il suffit de créer un fichier avec le contenu d'un répertoire)Comment exécuter la commande sh à l'aide de Shake

module Main where 
import Development.Shake 

main :: IO() 
main = shakeArgs shakeOptions{shakeFiles="_build"} $ do 
    let ls = "_build/ls.txt" 
    want [ls] 
    ls *> \out -> do 
     cmd "ls > " out 

Quand je exécutez-le, j'obtiens le message d'erreur suivant:

> runghc test.hs _build/ls.txt 
# ls (for _build/ls.txt) 
ls: >: No such file or directory 
ls: _build/ls.txt: No such file or directory 
Error when running Shake build system: 
* _build/ls.txt 
Development.Shake.cmd, system command failed 
Command: ls > _build/ls.txt 
Exit code: 1 
Stderr: 
ls: >: No such file or directory 
ls: _build/ls.txt: No such file or directory 

Qu'est-ce que je fais mal? Comment exécutez-vous une commande sh et redirigez sa sortie?

Répondre

11

Pour commencer par la conversion que vous voulez sans doute:

cmd Shell "ls >" out 

L'argument Shell dit Shake pour utiliser le shell système, ce qui signifie les travaux de redirection. Par la suite, vous voudrez peut-être passer à:

Stdout result <- cmd "ls" 
writeFile' out result 

Maintenant, vous n'êtes pas Invoquer le shell, mais la capture de la sortie avec Shake. Quelque temps plus tard, vous voudrez peut-être passer à:

getDirectoryFiles "." ["*"] 

Ce qui est Shake suivi façon d'obtenir une liste de fichiers.

+1

'Shell' fonctionne en effet. Pourquoi est-il nécessaire alors? Je pensais que 'cmd' exécutait déjà une commande shell, n'est-ce pas? – mb14

+2

Non, 'cmd' exécute la commande directement, par quelque chose comme' exec' (si C était). Éviter 'Shell' donne souvent un comportement plus prévisible multiplate-forme, évite de démarrer le shell, rend l'échappement beaucoup plus simple, etc. –

Questions connexes