2009-11-27 16:43:23 +0000 2009-11-27 16:43:23 +0000
347
347

Como faço para não dar um erro se um ficheiro não existe?

Estou a escrever um makefile que irá limpar alguns ficheiros inúteis no final da compilação. Se um alvo já foi feito, é claro que saltará esse alvo e o ficheiro inútil pode não estar lá. Portanto, se eu fizer isto:

rm lexer.ml interpparse.ml interpparse.mli

posso receber erros porque um dos ficheiros não existe. Existe alguma forma de dizer ao rm para ignorar estes ficheiros?

Ao ler a página man, vejo a seguinte opção:

-f Attempt to remove the files without prompting for confirma-
             tion, regardless of the file's permissions. If the file does
             not exist, do not display a diagnostic message or modify the
             exit status to reflect an error. The -f option overrides any
             previous -i options.

Isso soa a mais o que eu quero, mas não tenho bem a certeza quanto à parte das permissões. Existe uma forma de o fazer?

Respostas (11)

296
296
296
2009-11-27 16:54:52 +0000

A opção -f é definitivamente o que você quer usar.

A confirmação sobre as permissões de arquivo a que se refere é a seguinte:

$ touch myfile    
$ chmod 400 myfile
$ rm myfile       
rm: remove write-protected regular empty file `myfile'?

Então rm irá avisá-lo se você tentar apagar um arquivo no qual você não tem permissões de escrita. Isto é permitido se tiver permissões de escrita no directório mas é um pouco estranho, e é por isso que o rm normalmente o avisa sobre isso.

132
132
132
2015-03-09 12:39:25 +0000

Outra solução é esta: https://stackoverflow.com/questions/11231937/bash-ignoring-error-for-a-particular-command

Basta adicionar uma declaração OR após o seu comando:

rm -rf my/dir || true

Desta forma, quando a declaração #1 falhar (lança erro), execute a declaração #2, que é simplesmente true.

79
79
79
2012-12-23 23:12:06 +0000

Estou muito atrasado para a festa, mas estou sempre a usar isto. Num makefile, acrescente - ao início de uma linha para ignorar o valor de retorno dessa linha. Assim:

-rm lexer.ml interpparse.ml interpparse.mli
14
14
14
2012-06-12 19:46:48 +0000

Se não quiser usar a opção -f, uma alternativa é:

rm filethatdoesntexist 2> /dev/null

Isto apenas evitará que os erros sejam impressos.

8
8
8
2009-11-27 16:48:43 +0000

Se encontrar alguma forma de glob os nomes dos ficheiros, rm não se queixará se não conseguir encontrar uma correspondência. Então algo como lexer.m* interpparse.*, etc. deve funcionar para si (tenha cuidado para não apagar muito, claro). Além disso, o -f é um caminho perfeitamente razoável, desde que não esteja à espera que as permissões do ficheiro o salve de apagar um ficheiro que não queria - se não o quiser apagar, não o coloque na lista.

6
6
6
2009-11-27 19:27:29 +0000

A opção -f significa que não lhe será pedido se algo não for o esperado. Não significa que as permissões não são tidas em conta.

Se não tiver privilégios suficientes para remover um ficheiro, este não será removido.

BUT , se tiver privilégios suficientes para alterar os privilégios, o ficheiro será removido. Este é o caso quando você é o proprietário de um ficheiro com permissões de leitura apenas para o proprietário (-r——–). Como proprietário, pode chmod u+w, depois removê-lo: rm -f irá remover esse ficheiro.

5
5
5
2011-03-11 10:36:07 +0000

Talvez pudesse ajudar uma linha semelhante com:

touch fakefile.exe fakefile.o && rm *.o *.exe

Eu sei que isto não é muito inteligente, mas faz o trabalho.

3
3
3
2015-06-11 13:55:15 +0000

Eis o que eu utilizo nos guiões de shell. Esconde a mensagem de erro e o código de erro.

rm doesnotexist 2> /dev/null || echo > /dev/null
3
3
3
2009-11-27 17:44:12 +0000

Uma alternativa:

RmIfIsFile() { for f in "$@"; do [-f $f] && rm $f; done; }; RmIfIsFile lexer.ml interpparse.ml interpparse.mli

É pena que os Makefiles não possam partilhar as definições da função shell entre linhas.

1
1
1
2017-02-02 16:11:37 +0000

você pode tocar nos ficheiros antes de os criar, caso eles não existam :-)

touch lexer.ml interpparse.ml interpparse.mli
rm lexer.ml interpparse.ml interpparse.mli
1
1
1
2017-08-19 09:47:36 +0000

write rm -rf ppp>/dev/null 2>&1you newer get more error message Problema ocorre, se o erro gerar não STDERR 2 mas STDOUT 1… Ocorre quando o comando gera não erro mas sim aviso. Tem de definir o filtro e remover esta mensagem. Mas este caso é normal.