【问题标题】:How to interact with a subprocess through its stdin, stdout, stderr in Smalltalk?如何通过 Smalltalk 中的 stdin、stdout、stderr 与子进程交互?
【发布时间】:2021-03-20 12:48:36
【问题描述】:

此 Python 代码展示了如何在 Windows 10 中调用某个进程并向其发送字符串命令,以通过进程的 stdin、stdout 管道读取其字符串响应:

Python 3.8.0 (tags/v3.8.0:fa919fd, Oct 14 2019, 19:37:50) [MSC v.1916 64 bit (AMD64)] on win32
Type "help", "copyright", "credits" or "license" for more information.
>>> from subprocess import *
>>> p = Popen("c:/python38/python.exe", stdin=PIPE, stdout=PIPE)
>>> p.stdin.write(b"print(1+9)\n")
11
>>> p.communicate()
(b'10\r\n', None)
>>>

如您所见,python.exe 进程返回 10 作为对 print(1+9) 的回答。现在我想在 Pharo(或 Squeak)中做同样的事情:在 Windows 10 操作系统中 - 我想类似的东西,即简短、简单、易于理解、真正有效。

我安装了 OSProcess、ProcessWrapper(它们在 Pharo 中丢失了,奇怪的是我收到警告说它们没有被标记为 Pharo 8.0 并且没有检查在 Pharo 8.0 中工作,但是可以),我尝试了 ProcessWrapper、PipeableOSProcess (从 Web 复制粘贴不同的 sn-ps)等 - 成功率为零!结果是:

  • 没有任何反应,python.exe 没有启动
  • VM 错误控制台已打开(Pharo 底部的白色控制台,由 F2 菜单控制)
  • 不同的例外情况

有人能告诉我简单的工作示例如何启动一个进程并发送命令、读取答案、然后再次发送,等等在某个循环中 - 我计划在一个分离的线程中进行这样的通信并使用它作为一些服务,因为 Pharo,Smalltalk 通常缺少大多数绑定,所以我将像过去那样使用子进程通信......

我知道如何调用命令并获得其输出:

out := LibC resultOfCommand: 'dir ', aDir.

但我说的是另一种场景:以交互方式与正在运行的进程进行通信(例如,使用 SSH 或上面示例中的类似内容 - python.exe)。

PS。也许甚至可以使用 LibC #pipe:mode 来做到这一点?

【问题讨论】:

  • 您是否尝试阅读我在stackoverflow.com/questions/51363155/… 的帖子?那里有标准输入、管道等。这有帮助吗?
  • waitForCommand 有效,但这无关紧要。在userInput := OSProcess thisOSProcess stdIn.... 示例中,我没有看到任何命令行。 PipeableOsProcess 不起作用。它甚至会冻结 Pharo(Windows 终端正在打开,然后 Pharo 冻结)。
  • 你知道有一个 Pharo 邮件列表,不是吗?
  • 哦,真的!有一个邮件列表...我是一个非常新手,所以我还没有加入,谢谢提醒,也许在那里问ST问题会更好:)

标签: smalltalk pharo squeak


【解决方案1】:

让我先说PipeableOsProcess 在 Windows 上可能已损坏。我已经尝试过了,它只是打开了一个命令行,没有别的(它不会冻结我的 Pharo 8)。整个OSProcess 在我眼里都不能正常工作。

所以我对LibC 进行了拍摄,这应该不适用于 Windows。

我是一个定义访问标准 LibC 的模块。我在 Linux 和 OSX 下可用,但在 Windows 下不可用,原因很明显:)

接下来要说的是 Python 对 Windows 的支持可能比 Pharo 的要好很多。

解决方案更像是使用文件的解决方法,是使用LibC#runCommand:(我试图想出一个与您在上面显示的类似的示例):

| count command result outputFile errorFile  |

count := 9+1.  "The counting"
command := 'echo ', count asString. "command run at the command line"

outputFile := 'output'. "a file into which the output is redirected"
errorFile := 'error'. "a file where the error output is redirected "

result := LibC runCommand: command, "run the command "
    ' >', outputFile, "redirect the output to output file"
    ' 2>', errorFile.

"reading back the value from output file"
outputFile asFileReference contents lines.
"reading back the value from the error file - which is empty in this case" 
errorFile asFileReference contents lines. 

【讨论】:

  • 本地变量不在 Markdown 代码块中
  • @RandomB 谢谢你的警告,我已经解决了。
猜你喜欢
  • 1970-01-01
  • 2014-02-14
  • 2011-06-22
  • 2012-05-20
  • 2017-08-18
  • 2022-11-25
  • 1970-01-01
  • 2013-11-08
  • 1970-01-01
相关资源
最近更新 更多