在Windows和Mac OS中都使用Python中的默认OS应用程序打开文档 [英] Open document with default OS application in Python, both in Windows and Mac OS

查看:206
本文介绍了在Windows和Mac OS中都使用Python中的默认OS应用程序打开文档的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我需要能够使用Windows和Mac OS中的默认应用程序打开文档.基本上,我想做的事情与您在资源管理器或Finder中双击文档图标时发生的事情相同.用Python做到这一点的最佳方法是什么?

解决方案

openstart分别是Mac OS/X和Windows的命令解释程序.

要从Python调用它们,可以使用subprocess模块或os.system().

以下是使用哪种软件包的注意事项:

  1. 您可以通过os.system调用它们,该方法有效,但是...

    转义: os.system仅适用于路径名中没有空格或其他shell元字符的文件名(例如A:\abc\def\a.txt),否则需要转义.对于类似Unix的系统,有shlex.quote,但是对于Windows而言,并没有真正的标准.也许还会看到 python,windows:使用shlex解析命令行

    • MacOS/X:os.system("open " + shlex.quote(filename))
    • Windows:os.system("start " + filename)正确说出filename的地方也应转义.
  2. 您也可以通过subprocess模块调用它们,但是...

    对于python 2.7及更高版本,只需使用

    subprocess.check_call(['open', filename])
    

    在Python 3.5及更高版本中,您可以等效地使用稍微复杂一些但也具有更多用途的

    subprocess.run(['open', filename], check=True)
    

    如果您需要一直兼容到Python 2.4,则可以使用subprocess.call()并实现自己的错误检查:

    try:
        retcode = subprocess.call("open " + filename, shell=True)
        if retcode < 0:
            print >>sys.stderr, "Child was terminated by signal", -retcode
        else:
            print >>sys.stderr, "Child returned", retcode
    except OSError, e:
        print >>sys.stderr, "Execution failed:", e
    

    现在,使用subprocess有什么优势?

    • 安全性:从理论上讲,这是更安全的方法,但实际上,我们需要以一种或另一种方式执行命令行.在这两种环境中,我们都需要环境和服务来解释,获取路径等.在任何情况下,我们都不执行任意文本,因此它没有固有的但您可以键入'filename ; rm -rf /'"问题,并且如果可以损坏文件名,使用subprocess.call可以给我们几乎没有额外的保护.
    • 错误处理:实际上,它并没有给我们提供更多的错误检测功能,无论哪种情况,我们仍然取决于retcode;但是在发生错误的情况下明确引发异常的行为肯定会帮助您注意到是否存在故障(尽管在某些情况下,回溯可能比忽略错误根本没有多大帮助).
    • 拥有一个(非阻塞)子流程:我们不需要等待子流程,因为我们通过问题陈述来启动一个单独的流程.

    反对但首选subprocess".但是,不推荐使用os.system(),从某种意义上说,它是完成特定任务的最简单工具.结论:因此,使用os.system()也是正确的答案.

    标记为缺点的是Windows start命令要求传入shell=True,这抵消了使用subprocess的大部分好处.

I need to be able to open a document using its default application in Windows and Mac OS. Basically, I want to do the same thing that happens when you double-click on the document icon in Explorer or Finder. What is the best way to do this in Python?

解决方案

open and start are command-interpreter things for Mac OS/X and Windows respectively, to do this.

To call them from Python, you can either use subprocess module or os.system().

Here are considerations on which package to use:

  1. You can call them via os.system, which works, but...

    Escaping: os.system only works with filenames that don't have any spaces or other shell metacharacters in the pathname (e.g. A:\abc\def\a.txt), or else these need to be escaped. There is shlex.quote for Unix-like systems, but nothing really standard for Windows. Maybe see also python, windows : parsing command lines with shlex

    • MacOS/X: os.system("open " + shlex.quote(filename))
    • Windows: os.system("start " + filename) where properly speaking filename should be escaped, too.
  2. You can also call them via subprocess module, but...

    For Python 2.7 and newer, simply use

    subprocess.check_call(['open', filename])
    

    In Python 3.5+ you can equivalently use the slightly more complex but also somewhat more versatile

    subprocess.run(['open', filename], check=True)
    

    If you need to be compatible all the way back to Python 2.4, you can use subprocess.call() and implement your own error checking:

    try:
        retcode = subprocess.call("open " + filename, shell=True)
        if retcode < 0:
            print >>sys.stderr, "Child was terminated by signal", -retcode
        else:
            print >>sys.stderr, "Child returned", retcode
    except OSError, e:
        print >>sys.stderr, "Execution failed:", e
    

    Now, what are the advantages of using subprocess?

    • Security: In theory, this is more secure, but in fact we're needing to execute a command line one way or the other; in either environment, we need the environment and services to interpret, get paths, and so forth. In neither case are we executing arbitrary text, so it doesn't have an inherent "but you can type 'filename ; rm -rf /'" problem, and if the file name can be corrupted, using subprocess.call gives us little additional protection.
    • Error handling: It doesn't actually give us any more error detection, we're still depending on the retcode in either case; but the behavior to explicitly raise an exception in the case of an error will certainly help you notice if there is a failure (though in some scenarios, a traceback might not at all be more helpful than simply ignoring the error).
    • Spawns a (non-blocking) subprocess: We don't need to wait for the child process, since we're by problem statement starting a separate process.

    To the objection "But subprocess is preferred." However, os.system() is not deprecated, and it's in some sense the simplest tool for this particular job. Conclusion: using os.system() is therefore also a correct answer.

    A marked disadvantage is that the Windows start command requires you to pass in shell=True which negates most of the benefits of using subprocess.

这篇关于在Windows和Mac OS中都使用Python中的默认OS应用程序打开文档的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆