ソースファイルが存在しないときに「cp」コマンドでエラーが発生しないようにするにはどうすればよいですか?


59

私はMac OS Xを使用しています。このようなビルドスクリプトのcpコマンドでいくつかのファイルをコピーしようとしています。

cp ./src/*/*.h ./aaa

ただし、。/ srcディレクトリに.hファイルがない場合、このコマンドはエラーを発生させます。コマンドがエラーを発生させないようにする方法は?(サイレント障害)エラーによりビルド結果が失敗しますが、ヘッダーファイルがある場合にのみコピーしたいです。

回答:


69

エラーメッセージについて話している場合は、ビットバケットに送信することでそれを抑制することができます。

cp ./src/*/*.h ./aaa 2>/dev/null

終了コードとエラーメッセージを抑制したい場合:

cp ./src/*/*.h ./aaa 2>/dev/null || :

8
:この文脈で何を意味するのかを説明しておくといいでしょう。
ピョートルドブロゴスト14

23
@PiotrDobrogost:Bashおよび他のいくつかのシェルでは、コロンはヌルユーティリティです(no-op)。それはだ指定POSIX。常にtrueを返すため、ここでは失敗したcp(必要な場合)の終了コードを抑制するために使用されます。true代わりにシェルビルトインを使用でき、読みやすくなります。
デニスウィリアムソン14


1
これは他のエラーも無視します(ソース/宛先ディレクトリは存在せず、ソースファイルは存在しますが、読み取り不可、ディスクがいっぱい、読み取り専用ファイルシステム、IOエラー、何らかのcp理由でPATH...)
Vladimir Panteleev

予期しないトークン `|| 'の近くの構文エラー
タン

13

あなたはの線に沿って何かを探しています

if [ -e file ]
 then cp file /somewhere
fi

(残念ながら、この-fオプションは探しているドロイドではありません。)

グロブを一致させたい場合、それは機能しません。find代わりに使用します。例:

find ./src -name \*.h -exec cp {} ./destination \;

このようなアプローチには潜在的なTOCTOU問題があることに注意してください(たとえば、を使用しset -e、呼び出し[cp呼び出しの間にファイルが消えると、スクリプトがクラッシュします)。
ウラジミールパンテレエフ

9

古い質問ですが、他の人にも関連があるかもしれません。cpを使用する必要
がない場合は、rsyncを試してください。 すべてのファイルをソースから宛先ディレクトリにコピーするには、次を実行します。

rsync -avzh --ignore-errors /path/to/source /path/to/destination

Rsyncは、Linux、Mac OS X、FreeBSDなど、ほとんどのUnixライクなシステムに付属しています。


4
cpの代わりにrsyncを使用してパラメーターを追加することもできます--ignore-missing-argsrsync -av --ignore-missing-args ./src/*/*.h ./aaaこれには、--ignore-errors無視されるエラーが存在しないソースファイルに関連するエラーのみであるという利点があります。では--ignore-errors、すべてのエラーは無視され、危険なことかもしれません。また、このパラメーターはかなり新しいため、古いバージョンのrsyncには存在しない可能性があることを考慮してください。
jesjimher

6

結果をtrueにパイピングすると、コマンドは常に成功します。Linuxでこれを試しましたが、Mac OSでは試していません。

cp ./src/*/*.h ./aaa | true

5
単純なパイプ|は常に実行さ||れますが、エラーの場合にのみ実行されます。またtrue、通常はバイナリですが、コロン:は組み込みであり、PIDを消費しません。
-ott--

MacOSのbashスクリプト-"cp ./src/*/*.h ./aaa"コマンドを含むYosemiteは、.hファイルが存在しない場合でもエラーになりません。
ビベック

2

強制的に正しいエラー状態にすることができます。機能付き:

$ cpalways () { cp $1 $2 2>/dev/null ; return 0 ; }

次の場合:

$ ls foo bar baz
ls: baz: No such file or directory
bar foo

通常のコピーはエラーを返します。終了ステータス1を返します。

$ cp baz bar ; echo $?
cp: baz: No such file or directory
1

上記のcpalways()関数を使用すると、エラーは表示されなくなります。

$ cpalways baz bar ; echo $?
0
$ cpalways foo bar ; echo $?
0
$ cpalways baz bar ; echo $?
0
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.