16

Mac OS で python を使用して、書き込み用にファイルを開き、いくつかのシェル コマンドを入れたいと思います。後でターミナルで実行します。

with open("my_script.sh", "w") as fd:
    fd.write("#!/bin/sh\n")
    fd.write("echo $PATH\n")

これでファイルが作成されますが、実行ビットを設定する方法がわからないため、ターミナルで実行すると取得できません。

sh: my_script.sh: Permission denied
4

2 に答える 2

23
import os
os.chmod("my_script.sh", 0744)

ただし、適切に値を選択してください。一部の値は安全ではない可能性があります。

于 2012-12-31T18:10:21.663 に答える
13

実行する前に、次を使用して、ターミナルシェルからいつでもこれを行うことができますchmod

chmod a+x my_script.sh

Python から実行する場合は、モジュール内でchmodまたはを使用できます。すでにファイルを開いているので、後者を行います。fchmodos

with open("my_script.sh", "w") as fd:
    fd.write("#!/bin/sh\n")
    fd.write("echo $PATH\n")
    os.fchmod(fd.fileno(), stat.S_IRWXU | stat.S_IRWXG | stat.S_IROTH | stat.S_IXOTH)

残念ながら、ご覧のとおり、すべての人にフラグをchmod a+x追加して、他のすべてをそのままにしておくことに直接相当するものはありません。ただし、コマンドライン ツールが実際にx行うのと同じことを行うことができます。つまり、ファイル (この場合は) で既存のアクセス許可を取得してから、それらを変更します。chmodstatfstat

with open("my_script.sh", "w") as fd:
    fd.write("#!/bin/sh\n")
    fd.write("echo $PATH\n")
    mode = os.fstat(fd.fileno()).st_mode
    mode |= stat.S_IXUSR | stat.S_IXGRP | stat.S_IXOTH
    os.fchmod(fd.fileno(), stat.S_IMODE(mode))

S_IMODE(ほとんどのプラットフォームでは実際にはこのステップは必要ありst_modeません。余分なビットがないか、(f) chmodOS X のように無害に無視するためです。しかし、正しいことを行い、コードを移植可能にする方がよいでしょう。そして将来性があります。)

ほとんどの人は、「フレンドリーな」名前S_IXUSRは特にフレンドリーではないと考えています。モードを 8 進法で考えるようになると、POSIX での省略形を覚えようとするよりも実際には簡単になるため、次のようにすることをお勧めします。

with open("my_script.sh", "w") as fd:
    fd.write("#!/bin/sh\n")
    fd.write("echo $PATH\n")
    mode = os.fstat(fd.fileno()).st_mode
    mode |= 0o111
    os.fchmod(fd.fileno(), mode & 0o7777)

111ユーザー、グループ、およびその他によって実行可能な手段 (さまざまなビットと同じこと)|ST_IX*あり、7777(f) に渡すことが許可されているすべてのビットですchmod(同じことS_IMODE)。

于 2012-12-31T19:47:44.460 に答える