如何将独立Python脚本集成到Rails应用程序中?

我有一个程序,它有一个小文件结构,然后运行

python do_work.py foo bar

我想让我的Rails用户按下一个按钮,让他们发生这种情况,结果要么上传到某个地方,要么作为下载链接或类似的东西 - do_work.py的输出(比如result.txt

我还想澄清一下,脚本导致在文件系统上创建3个单独的文件,这些文件不是文本文件(这不应该有问题,这里也不是真正的问题)

什么是最好的方式去做呢? 可以耙运行exec Python吗? 更重要的是,这是可行的heroku?

我在我的系统上安装了Python,但sockmonk提供的答案似乎不起作用 - 它返回nil。 请注意,像ls这样的其他命令似乎可行。

它可能是一个权限问题?

def index
    value = %x( python --version )
    render :text => value
end

顺便说一句,在irb试试这个:

%x(python)

带上irb的Python终端INSIDE。 不过无论如何它都不会采用params。


您的index方法不起作用,因为python --version其版本输出到STDERR,而不是STDOUT。 如果您不需要分开这些流,则可以将STDERR重定向到STDOUT:

value = %x(python --version 2>&1)

这个调用是同步的,所以在运行脚本( python do_work.py foo bar 2>&1 )后,您应该能够读取它生成的文件。

如果脚本由于某种原因无法创建文件,现在您将在value变量中看到异常,因为错误消息通常发送到STDERR。

如果要将STDERR与STDOUT分开,请使用Open3模块。

注意脚本需要一些时间才能运行,因此这些调用可能会重叠。 我会在这里使用一个队列来防止这种情况。

并且不要忘记检查用户输入的数据。 切勿直接将其传递给脚本。


它部分取决于数据的格式。 如果它不太长,并且可以直接在浏览器中呈现,那么您可以在rails控制器中执行如下操作:

result = `python do_work.py foo bar`
render :text => result

假设结果是纯ASCII文本,结果将直接发送到他们的浏览器。 如果do_work.py的参数来自用户,则必须首先验证它们,因此您不会为自己创建一个令人讨厌的漏洞。 在这种情况下使用system()调用可能会更安全。

如果你想把结果作为一个文件发回去,那么查看ruby的Tempfile类来创建文件(以永远不会停留的方式),以及rails的send_file和send_data命令来返回结果的一些不同选项那样。


utapyngo的答案几乎囊括了你需要知道的全部内容。 我会回答这个部分:

顺带一提,在irb中试试这个:%x(python)调出irb的python终端INSIDE。 不过无论如何它都不会采用params。

要传递参数给你的python脚本,只需传递它。 例:

[fotanus@thing ~]$ python a.py 
args:
['a.py']
[fotanus@thing ~]$ irb
1.8.7 :001 > %x(python a.py foo bar)
 => "args:n['a.py', 'foo', 'bar']n" 

这适用于红宝石1.8,1.9和2.0。

链接地址: http://www.djcxy.com/p/25293.html

上一篇: How to integrate a standalone Python script into a Rails application?

下一篇: When to use each method of launching a subprocess in Ruby