
Com o Vim eu posso fazer facilmente
$ echo 123 | vim -
É possível fazer isso com o Emacs?
$ echo 123 | emacs23
... Emacs starts with a Welcome message
$ echo 123 | emacs23 -
... Emacs starts with an empty *scratch* buffer and “Unknown option”
$ echo 123 | emacs23 --insert -
... “No such file or directory”, empty *scratch* buffer
É realmente impossível ler um buffer de um pipe unix?
Editar: Como solução, escrevi um wrapper chamado emacspipe
:
#!/bin/sh
TMP=$(mktemp) && cat > $TMP && emacs23 $TMP ; rm $TMP
Responder1
Correto, é impossível ler um buffer do stdin.
A única menção ao stdin nas páginas de informações do Emacs éesse, que diz:
No modo batch, o Emacs não exibe o texto que está sendo editado e o terminal padrão interrompe caracteres como
C-z
eC-c
continua a ter seu efeito normal. As funçõesprin1
e saída paraprinc
em vez da área de eco, enquanto e mensagens de erro são enviadas para . Funções que normalmente seriam lidas no minibuffer recebem suas entradas .stdout
message
stderr
stdin
E aread
A função pode ler stdin
, mas apenas no modo em lote.
Então, você não pode nem contornar isso escrevendo um elisp personalizado.
Responder2
Você poderia usarsubstituição de processo:
$ emacs --insert <(echo 123)
Responder3
Você pode redirecionar para um arquivo e abri-lo. por exemplo
echo 123 > temp; emacs temp
jweede observa que se quiser que o arquivo temporário seja removido automaticamente, você pode:
echo 123 > temp; emacs temp; rm temp
A maneira do Emacsy de fazer isso épara executar o comando shell no Emacs.
M-! echo 123 RET
Isso fornece um buffer chamado *Shell Command Output* com os resultados do comando.
Responder4
Isso épossível criar uma função shell simplesque funciona enquanto lê stdin (embora na verdade esteja gravando em um arquivo temporário e depois lendo-o). Aqui está o código que estou usando:
# The emacs or emacsclient command to use
function _emacsfun
{
# Replace with `emacs` to not run as server/client
emacsclient -c -n $@
}
# An emacs 'alias' with the ability to read from stdin
function e
{
# If the argument is - then write stdin to a tempfile and open the
# tempfile.
if [[ $# -ge 1 ]] && [[ "$1" == - ]]; then
tempfile="$(mktemp emacs-stdin-$USER.XXXXXXX --tmpdir)"
cat - > "$tempfile"
_emacsfun --eval "(find-file \"$tempfile\")" \
--eval '(set-visited-file-name nil)' \
--eval '(rename-buffer "*stdin*" t))'
else
_emacsfun "$@"
fi
}
Você apenas usa a função como um alias para o emacs, por exemplo
echo "hello world" | e -
ou normalmente a partir de arquivos
e hello_world.txt
Substituir emacs
por emacsclient
na função também funciona.