当前位置: 首页 > 面试题库 >

如何从PHP内部传递和接收参数来运行Ruby / Python脚本?

罗翰
2023-03-14
问题内容

我需要将HTML转换成Markdown结构的文本。

OBS
.:使用PHP和Python进行此操作的快速清晰的方法。

当我使用PHP进行编程时,有人指出 Markdownify 可以完成这项工作,但是不幸的是,代码并未得到更新,实际上 却无法正常工作
。在sourceforge.net/projects/markdownify上有一个“注释:不支持-
您要维护该项目吗?请与我联系!Markdownify是用PHP编写的HTML到Markdown转换器。将其视为html2text.php的后继者更好的设计,更好的性能和更少的角落情况。”

据我发现,我只有两个不错的选择:

  • Python:Aaron Swartz的html2text.py

  • Ruby:Singpolyma的html2markdown.rb,基于Nokogiri

因此,从PHP,我需要传递HTML代码,调用Ruby / Python脚本并接收返回的输出。

(顺便说一句,一个人在这里提出了类似的问题(“如何从php调用ruby脚本?”),但我的案例没有任何实用信息。

遵循Tin Man的技巧(波纹管),我明白了这一点:

PHP代码:

$t='<p><b>Hello</b><i>world!</i></p>';
$scaped=preg_quote($t,"/");
$program='python html2md.py';

//exec($program.' '.$scaped,$n); print_r($n); exit; //Works!!!

$input=$t;

$descriptorspec=array(
   array('pipe','r'),//stdin is a pipe that the child will read from
   array('pipe','w'),//stdout is a pipe that the child will write to
   array('file','./error-output.txt','a')//stderr is a file to write to
);

$process=proc_open($program,$descriptorspec,$pipes);

if(is_resource($process)){
    fwrite($pipes[0],$input);
    fclose($pipes[0]);
    $r=stream_get_contents($pipes[1]);
    fclose($pipes[1]);
    $return_value=proc_close($process);
    echo "command returned $return_value\n";
    print_r($pipes);
    print_r($r);
}

Python代码:

#! /usr/bin/env python
import html2text
import sys
print html2text.html2text(sys.argv[1])
#print "Hi!" #works!!!

有了以上我得到这个:

命令返回1个数组([0] =>资源ID#17 1
=>资源ID#18)

并且“ error-output.txt”文件显示:

追溯(最近一次呼叫最近):文件“ html2md.py”,第5行,打印中html2text.html2text(sys.argv
1)IndexError:列表索引超出范围

有任何想法吗???

Ruby代码( 仍在分析中

#!/usr/bin/env ruby
require_relative 'html2markdown'
puts HTML2Markdown.new("<h1>#{ ARGF.read }</h1>").to_s

仅作记录,我曾尝试使用PHP最简单的“ exec()”,但对于HTML语言非常常见的一些特殊字符,我遇到了一些问题。

PHP代码:

echo exec('./hi.rb');
echo exec('./hi.py');

Ruby代码:

#!/usr/bin/ruby
puts "Hello World!"

Python代码:

#!usr/bin/python
import sys
print sys.argv[1]

两者都工作正常。但是当字符串有点复杂时:

$h='<p><b>Hello</b><i>world!</i></p>';
echo exec("python hi.py $h");

它根本不起作用。

这是因为html字符串需要转义其特殊字符。我用这个得到它:

$t='<p><b>Hello</b><i>world!</i></p>';
$scaped=preg_quote($t,"/");

现在它就像我在这里所说的那样工作。

我是runnig:Fedora 14 ruby​​ 1.8.7 Python 2.7 perl 5.12.2 PHP 5.3.4 nginx 0.8.53


问题答案:

让PHP通过打开proc_openHTML到脚本中的STDIN来打开Ruby或Python脚本。Ruby /
Python脚本读取并处理数据,并通过STDOUT将其返回给PHP脚本,然后退出。这是通过popenPerl,Ruby或Python中的类似功能来执行操作的一种常见方式,它很不错,因为它可以让您访问STDERR,以防万一某些东西大块地散了,不需要临时文件,但这要复杂一些。

替代方法是将数据从PHP写入临时文件,然后使用systemexec或类似的调用Ruby
/ Python脚本来打开和处理它,并使用其STDOUT打印输出。

编辑:

请参阅@Jonke的答案“
Ruby中使用STDIN的最佳实践?”。有关使用Ruby读取STDIN和写入STDOUT有多简单的示例。“您如何从python中的stdin中读取信息”对该语言提供了一些很好的示例。

这是一个简单的示例,显示了如何调用Ruby脚本,如何通过PHP的STDIN管道向其传递字符串以及如何读取Ruby脚本的STDOUT:

将此保存为“ test.php”:

<?php
$descriptorspec = array(
   0 => array("pipe", "r"),  // stdin is a pipe that the child will read from
   1 => array("pipe", "w"),  // stdout is a pipe that the child will write to
   2 => array("file", "./error-output.txt", "a") // stderr is a file to write to
);
$process = proc_open('ruby ./test.rb', $descriptorspec, $pipes);

if (is_resource($process)) {
    // $pipes now looks like this:
    // 0 => writeable handle connected to child stdin
    // 1 => readable handle connected to child stdout
    // Any error output will be appended to /tmp/error-output.txt

    fwrite($pipes[0], 'hello world');
    fclose($pipes[0]);

    echo stream_get_contents($pipes[1]);
    fclose($pipes[1]);

    // It is important that you close any pipes before calling
    // proc_close in order to avoid a deadlock
    $return_value = proc_close($process);

    echo "command returned $return_value\n";
}
?>

将此保存为“ test.rb”:

#!/usr/bin/env ruby

puts "<b>#{ ARGF.read }</b>"

运行PHP脚本可以得到:

Greg:Desktop greg$ php test.php 
<b>hello world</b>
command returned 0

PHP脚本正在打开Ruby解释器,后者将打开Ruby脚本。然后,PHP向其发送“ hello
world”。Ruby将接收到的文本用粗体标签包装,然后将其输出(由PHP捕获),然后输出。没有临时文件,没有在命令行上传递任何内容,如果需要的话,您可以传递很多数据,而且速度非常快。可以很容易地使用Python或Perl代替Ruby。

编辑:

如果你有:

HTML2Markdown.new('<h1>HTMLcode</h1>').to_s

作为示例代码,那么您可以开始开发具有以下内容的Ruby解决方案:

#!/usr/bin/env ruby

require_relative 'html2markdown'

puts HTML2Markdown.new("<h1>#{ ARGF.read }</h1>").to_s

假设您已经下载了HTML2Markdown代码并将其保存在当前目录中并且正在运行Ruby 1.9.2。



 类似资料:
  • 问题内容: 我的以下代码有问题: callBash.py: sleep.sh: 我希望10秒钟后打印“结束”。(我知道这是一个愚蠢的示例,我可以简单地在python中睡眠,但是这个简单的sleep.sh文件只是作为测试) 问题答案: 使sleep.sh可执行并添加到参数列表中(如先前答案中所建议)可以正常工作。根据搜索路径,您可能还需要添加或其他合适的路径。(即,更改为。) 如果bash脚本的第一

  • 问题内容: 我有一个名为的python文件,该python文件需要两个命令行参数:,Dockerfile如下所示: 如何通过这两个命令行参数,并以?我试过了但是没用。 问题答案: 您不能按预期使用和,因为它们是的选项。 启动一个终端。 将Docker容器作为守护程序启动。 要在Dockerfile中设置环境变量,请使用命令。 请参阅Dockerfile参考。 另一种选择是通过以下方式传递环境变量:

  • 问题内容: 我想从PHP运行Python脚本。该脚本的语法很好,当我从命令行运行它时,它会在它旁边生成一个图像文件。当我从命令行运行PHP文件(包含Python exec)时,它将生成一个图像文件。很好。问题是:当我使用浏览器并运行PHP时,它不会生成任何图像文件。我使用的是Xubuntu OS。 问题答案: 问题是matplotlib后端设置。我更改为“ Agg”,并且plot函数正常运行。

  • 这里是HTML文件,在脚本部分,我发出了一个ajax请求,将一些字符串传递给python函数。 在中,我设置了python脚本的路径。Python文件,我希望在该文件中从JS获取所请求的数据并将其打印出来。 注意:这里我没有使用任何框架。只是纯HTML、JS和Python文件。

  • 问题内容: 我想从另一个Python脚本运行一个Python脚本。我想像使用命令行一样传递变量。 例如,我会跑我的,将通过值(0,1,2,3)的列表迭代第一个脚本,并通过那些到第二脚本,然后,等 我发现了Stack Overflow问题1186789,这是一个类似的问题,但是ars的答案调用了一个函数,在这里我想运行整个脚本,而不仅仅是函数,而balpha的答案则调用了脚本,但没有参数。我将其更改

  • 问题内容: 我在很多地方都看到过,包括Python使用的Python文档通过“赋值”语义传递。来自Java背景,说“ Java按值传递基元,按引用传递对象”的常见错误是由于按值传递了对象引用,我不禁怀疑Python是否真的在做同样的事情事情。 在我看来,按值传递对象引用和按赋值传递对象的概念似乎相同。Python使用术语“传递分配”是否是为了减轻诸如我上面所述的错误语句的问题?如果是这样,可以公平