【问题标题】:VBScript - Capturing output from stdoutVBScript - 从标准输出捕获输出
【发布时间】:2015-10-03 08:52:26
【问题描述】:

我知道这已经在另一个问题中得到了回答,但我只是不明白它是如何完成的。

我正在尝试将命令行程序(Aria2 下载器)的输出转换为 HTA 脚本,以便对其进行解析,并且可以获取下载百分比、文件大小等并将其动态更新为 DIV。

这是我已经调整并一直在尝试使用的代码,但它只是锁定界面,直到命令行完成,然后显示所有输出,而不是在它通过时显示它。

Const WshRunning = 0
Const WshFinished = 1
Const WshFailed = 2
strCommand = "ping.exe 127.0.0.1"

Set WshShell = CreateObject("WScript.Shell")
Set WshShellExec = WshShell.Exec(strCommand)

Do While WshShellExec.Status = WshRunning
    window.setTimeOut "", 100
Loop

Select Case WshShellExec.Status
    Case WshFinished
        strOutput = WshShellExec.StdOut.ReadAll()
    Case WshFailed
        strOutput = WshShellExec.StdErr.ReadAll()
End Select

Set objItem = Document.GetElementByID("status")
    objItem.InnerHTML = "" & strOutput & ""

如何修改它,使其不会锁定我的用户界面并抓取输出并将其显示在“状态”div 中?

【问题讨论】:

标签: vbscript stdout aria2


【解决方案1】:

问题是您的代码没有结束,而是将控件返回给浏览器。在程序结束之前您不会离开循环,并且感知状态是接口挂起直到子进程结束。

您需要设置一个回调,以便浏览器定期调用您的代码,您将在其中更新状态并离开。

<html>
<head>
    <title>pingTest</title>
    <HTA:APPLICATION
        APPLICATIONNAME="pingTest"
        ID="pingTest"
        VERSION="1.0"
    />
</head>

<script language="VBScript">
    Const WshRunning = 0
    Const WshFinished = 1
    Const WshFailed = 2

    Dim WshShellExec, Interval

    Sub Window_onLoad
        LaunchProcess
    End Sub

    Sub LaunchProcess
        Set WshShellExec = CreateObject("WScript.Shell").Exec("ping -n 10 127.0.0.1")
        Interval = window.setInterval(GetRef("UpdateStatus"),500)
    End Sub    

    Sub UpdateStatus
    Dim status 
        Set status = Document.GetElementByID("status")
        Select Case WshShellExec.Status
            Case WshRunning
                status.InnerHTML = status.InnerHTML & "<br>" & WshShellExec.StdOut.ReadLine()
            Case WshFinished, WshFailed
                status.InnerHTML = status.InnerHTML & "<br>" & Replace(WshShellExec.StdOut.ReadAll(),vbCRLF,"<br>")
                window.clearInterval(Interval)
                Interval = Empty
        End Select
    End Sub
</script>

<body>
    <div id="status"></div>
</body>
</html>

【讨论】:

  • 非常感谢,我现在明白了这个概念,说得很有说服力,谢谢。为什么 WshRunning 行写成这样: status.InnerHTML = status.InnerHTML & "
    " & WshShellExec.StdOut.ReadLine() 会不会像 status.InnerHTML = WshShellExec.StdOut.ReadLine() 一样工作??跨度>
  • @Ctrlaltdenied,我试图在阅读命令时保留命令的所有输出。每次使用ReadLine 时,只会检索一行,因此,为了保留所有输出,新行将附加到现有信息的末尾。当然,您评论中的代码会起作用,但不会显示相同的信息。对于每一行,您都丢弃以前检索到的信息并将其替换为新行。
  • 好的,所以这段代码背后的主要原因是启动下载,其中 Aria2 非常棒,http/s,bittorrent 等。我想扩展它并写下整个日志到 log.txt 文件,同时保持输出的关键元素显示在页面上。即相关下载信息,如下载量/总下载大小、速度、百分比等。再次感谢您的帮助。
  • 哦,最后查询一下,本例中的命令是 ping -n 10 127.0.0.1,是否有任何字符或符号(除了 " 不被接受,如果我需要输入一个带有“作为字符串的一部分的命令,我需要在此处留出余量吗?
  • @Ctrlaltdenied,如果您直接调用aria 可执行文件,则除了0x00(空字符)之外,应该没有任何问题字符。引号是允许的,但要将它们包含在 vbs 字符串中,您必须将它们加倍,这只是 vbs 转义引号的语法方式。
猜你喜欢
  • 2017-07-09
  • 1970-01-01
  • 2021-05-21
  • 2011-07-05
  • 2013-08-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多