ホームフォルダーにfoo.sh
というスクリプトがあります。
このフォルダーに移動し、./foo.sh
と入力すると、
-bash: ./foo.sh: Permission denied
。
Sudo ./foo.sh
を使用すると、
Sudo: foo.sh: command not found
。
なぜこれが起こり、どうすれば修正できますか?
許可が拒否されました
スクリプトを実行するには、ファイルに実行可能アクセス許可ビットセットが必要です。
Linux ファイルのアクセス権 を完全に理解するには、chmod
コマンドのドキュメントを調べることができます。 chmod 、change modeの略語は、ファイルの許可設定を変更するために使用されるコマンドです。
ローカルシステムのchmodドキュメントを読むには、コマンドラインからman chmod
またはinfo chmod
を実行します。一度読んで理解すると、実行の出力を理解できるはずです...
ls -l foo.sh
...これは、ファイル所有者、グループ所有者、およびファイル所有者またはファイルが属するグループのメンバーではないすべてのユーザー(最後のアクセス許可グループが参照される場合がある)の読み取り、書き込み、および実行許可をリストします「世界」または「その他」として)
以下に、あなたの場合のPermission Deniedエラーのトラブルシューティング方法の概要を示します。
$ ls -l foo.sh # Check file permissions of foo
-rw-r--r-- 1 rkielty users 0 2012-10-21 14:47 foo.sh
^^^
^^^ | ^^^ ^^^^^^^ ^^^^^
| | | | |
Owner| World | |
| | Name of
Group | Group
Name of
Owner
所有者には読み取りおよび書き込みアクセスrwがありますが、-は実行可能権限が欠落していることを示します
chmod
コマンドはそれを修正します。 (グループおよびその他のユーザーはファイルに読み取り権限のみが設定されており、書き込みや実行はできません)
$ chmod +x foo.sh # The owner can set the executable permission on foo.sh
$ ls -l foo.sh # Now we see an x after the rw
-rwxr-xr-x 1 rkielty users 0 2012-10-21 14:47 foo.sh
^ ^ ^
linuxに関する限り、foo.shは実行可能になりました。
Sudoを使用すると、コマンドが見つかりません
Sudoを使用してコマンドを実行すると、スーパーユーザーまたはルートとして効果的に実行されます。
Rootユーザーがコマンドを見つけられない理由は、rootのPATH
環境変数にfoo.sh
が置かれているディレクトリが含まれていない可能性があります。したがって、コマンドは見つかりません。
PATH環境変数には、コマンドを検索するディレクトリのリストが含まれています。各ユーザーは、必要に応じて独自のPATH変数を設定します。実行する設定を確認するには
env | grep ^PATH
上記のenv
コマンドを最初に通常のユーザーとして実行し、次にSudoを使用してrootユーザーとして実行したサンプル出力を次に示します。
rkielty@rkielty-laptop:~$ env | grep ^PATH
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games
rkielty@rkielty-laptop:~$ Sudo env | grep ^PATH
[Sudo] password for rkielty:
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/X11R6/bin
似ていますが、この場合、PATHに含まれるディレクトリは非特権ユーザー(rkielty)とスーパーユーザーはではありません。
foo.sh
が存在するディレクトリは、rootユーザーのPATH変数に存在しないため、command not foundエラーです。
これまでに見てきた他のソリューションはいくつかのシステム定義に基づいていますが、実際にはSudo
に現在のPATH
(env
コマンドを使用)および/または残りの環境(-E
オプションを使用)を使用することもできます正しく呼び出すことで:
Sudo -E env "PATH=$PATH" <command> [arguments]
実際、エイリアスを作成できます:
alias mysudo='Sudo -E env "PATH=$PATH"'
(エイリアス自体にSudo
という名前を付けて、元のSudo
を置き換えることもできます。)
Sudoでsecure_pathを確認します
[root@Host ~]# Sudo -V | grep 'Value to override'
Value to override user's $PATH with: /sbin:/bin:/usr/sbin:/usr/bin
$PATH
がオーバーライドされている場合は、visudo
を使用して、/etc/sudoers
を編集します
Defaults secure_path = /sbin:/bin:/usr/sbin:/usr/bin:/usr/local/bin
chmod +x foo.sh
#!/bin/sh
またはそのようなものであることを確認してください。Sudo pwd
で確認するスーパーユーザーPATHのディレクトリの1つ(/usr/local/bin
など)にスクリプトへのソフトリンクを作成することもできます。その後、Sudoで使用できるようになります。
chmod +x foo.sh
Sudo ln -s path-to-foo.sh /usr/local/bin/foo
this answer を見て、どのディレクトリにソフトリンクを配置するのかを考えてください。
上記のガイドに問題がある場合は、chmod u+x foo.sh
ではなくchmod +x foo.sh
を試してください。これは、他のソリューションでは機能しなかったときに機能しました。
OKこれが私の解決策です:〜/ .bash_aliasesに以下を追加してください:
# ADDS MY PATH WHEN SET AS ROOT
if [ $(id -u) = "0" ]; then
export PATH=$PATH:/home/your_user/bin
fi
出来上がり!これで、毎回export PATH = $ PATH:/ home/your_user/binを実行することなく、Sudoを使用して独自のスクリプトを実行したり、ROOTとして設定したりできます。
スーパーユーザーのHOMEは/ rootであるため、PATHを追加するときは明示的にする必要があることに注意してください。
ファイルへのパスを明示的に指定しても、Linuxは「コマンドが見つかりません」と表示するようです。
[veeam@jsandbox ~]$ Sudo /tmp/uid.sh;echo $?
Sudo: /tmp/uid.sh: command not found
1
[veeam@jsandbox ~]$ chmod +x /tmp/uid.sh
[veeam@jsandbox ~]$ Sudo /tmp/uid.sh;echo $?
0
これはやや誤解を招くエラーですが、おそらく技術的には正しいでしょう。ファイルは実行可能になるまでコマンドではないため、見つかりません。
上記の優れた答えがあります。それらを試した後、command not found
が表示される場合は、ファイルパス全体で再試行してください:
Sudo /home/user/path/to/foo.sh