如何在PowerShell中输出内容

时间:2010-01-10 19:08:08

标签: windows powershell

我正在批处理文件中运行PowerShell脚本。该脚本获取一个网页并检查该页面的内容是否为“OK”字符串。

PowerShell脚本向批处理脚本返回错误级别。

批处理脚本由FTP自动化程序ScriptFTP执行。如果发生错误,我可以让ScriptFTP通过电子邮件将完整的控制台输出发送给管理员。

在PowerShell脚本中,如果它不是“OK”,我想从网站输出返回值,因此错误消息包含在控制台输出中,因此也包含在状态邮件中。

我是PowerShell的新手,不知道要使用哪个输出函数。我可以看到三个:

  • 写主机
  • 写输出
  • 写入错误

用什么方法来写入等同于stdout的Windows?

8 个答案:

答案 0 :(得分:183)

简单地输出一些东西是PowerShell是一件美丽的东西 - 也是它最大的优势之一。例如,常见的Hello,World!应用程序简化为一行:

"Hello, World!"

它创建一个字符串对象,分配上述值,并作为命令管道上的最后一项,它调用.toString()方法并将结果输出到STDOUT(默认情况下)。美丽的东西。

其他Write-*命令专门用于将文本输出到其关联的流,并具有相应的位置。

答案 1 :(得分:115)

我认为在这种情况下,您需要Write-Output

如果您有像

这样的脚本
Write-Output "test1";
Write-Host "test2";
"test3";

然后,如果您使用重定向输出调用脚本,例如yourscript.ps1 > out.txt,则会在“out.txt”的屏幕test2上显示test1\ntest3\n

请注意,“test3”和Write-Output行将始终在文本中添加一个新行,并且PowerShell无法停止此操作(即,使用本机命令在PowerShell中无法echo -n )。如果您想要echo -n的{​​{3}}}功能(Bash},请参阅samthebest's answer

如果批处理文件运行PowerShell命令,它很可能会捕获Write-Output命令。我与系统管理员就应该写入控制台的内容以及不应该写的内容进行了“长时间的讨论”。我们现在已经同意,如果脚本成功执行或死亡,唯一的信息必须是Write-Host,并且脚本作者的所有内容可能需要了解执行情况(更新了哪些项目,设置了哪些字段)等等)转到写输出。这样,当您向系统管理员提交脚本时,他可以轻松runthescript.ps1 >someredirectedoutput.txt并在屏幕上看到是否一切正常。然后将“someredirectedoutput.txt”发送给开发人员。

答案 2 :(得分:8)

我认为以下是Echo vs. Write-Host的一个很好的展示。注意test()实际上如何返回一个int数组,而不是一个int,因为很容易让人相信。

function test {
    Write-Host 123
    echo 456 # AKA 'Write-Output'
    return 789
}

$x = test

Write-Host "x of type '$($x.GetType().name)' = $x"

Write-Host "`$x[0] = $($x[0])"
Write-Host "`$x[1] = $($x[1])"

以上的终端输出:

123
x of type 'Object[]' = 456 789
$x[0] = 456
$x[1] = 789

答案 3 :(得分:7)

您可以在场景中使用其中任何一个,因为它们会写入默认流(输出和错误)。如果您将输出传递给另一个命令行开关,则需要使用Write-Output,这最终会在Write-Host中终止。

本文介绍了不同的输出选项:PowerShell O is for Output

答案 4 :(得分:2)

你根本无法让PowerShell省略那些讨厌的换行符。没有脚本或cmdlet可以执行此操作。

当然Write-Host绝对是胡说八道,因为你无法重定向/管道!你只需编写自己的:

using System;

namespace WriteToStdout
{
    class Program
    {
        static void Main(string[] args)
        {
            if (args != null)
            {
                Console.Write(string.Join(" ", args));
            }
        }
    }
}

E.g。

PS C:\> writetostdout finally I can write to stdout like echo -n
finally I can write to stdout like echo -nPS C:\>

答案 5 :(得分:2)

Write-Host "Found file - " + $File.FullName -ForegroundColor Magenta

洋红色可以是" System.ConsoleColor"枚举值 - 黑色,深蓝色,深绿色,DarkCyan,DarkRed,DarkMagenta,DarkYellow,灰色,DarkGray,蓝色,绿色,青色,红色,洋红色,黄色,白色。

+ $File.FullName是可选的,并显示如何将变量放入字符串。

答案 6 :(得分:1)

  

什么是正确的方法来写入Windows上的stdout?

效果中,但非常不幸的是 Windows PowerShell和PowerShell Core v7.0或更高版本发送 他们的6(!)output streams中的所有 stdout ,当通过PowerShell的{{3 }}

  • 请参见CLI,以讨论对此问题的行为,出于向后兼容性的考虑,该问题可能不会得到解决。

  • 在实践中,这意味着您将输出发送到的任何PowerShell流都会被外部调用方视为 stdout 输出:

    • 例如,如果您从cmd.exe运行以下命令,则会看到 no 输出,因为到NUL的stdout重定向同样适用于所有PowerShell流:

      • C:\>powershell -noprofile -command "Write-Error error!" >NUL
    • 但是-奇怪的是-如果您重定向stderr ,PowerShell 确实将其错误流发送到stderr ,因此,用{{ 1}}您可以 有选择地捕获错误流输出;以下输出仅2>-成功流输出-捕获文件'hi'中的错误流输出:

      • err.txt

理想行为是:

  • 将PowerShell的 成功输出流(编号C:\>powershell -noprofile -command "'hi'; Write-Error error!" 2>err.txt)发送到 stdout
  • 将所有来自 所有其他流的输出发送到 stderr ,这是唯一的选择,因为在之间仅处理 2 个输出流-用于 data 的stdout(标准输出),以及用于错误消息 的所有其他错误的stderr(标准错误)不是 data 的消息类型(例如状态信息)。

  • 建议您在代码中对此加以区分,即使当前不被尊重


内部 PowerShell

  • 1 用于显示输出,而 绕过成功输出流-这样,其输出既不能(直接)捕获到变量中,也不能被抑制或重定向。

    • 其最初意图只是创建用户反馈并创建基于控制台的简单用户界面(彩色输出)。

    • 由于先前无法捕获或重定向,因此PowerShell版本5将Write-Host引入了新引入的信息流(编号Write-Host),因此那么就可以 捕获并重定向6的输出。

  • Write-Host 用于将非终止错误写入错误流 (数字Write-Error);从概念上讲,错误流等效于stderr。

  • 2 写入 成功[输出]流 (编号Write-Output),在概念上等同于stdout;是向其中写入数据(结果)的流。

    • 但是,由于PowerShell的 隐式输出功能,很少需要明确使用1
      • 未明确捕获,禁止或重定向的任何命令或表达式的输出会自动 发送到成功流;例如Write-OutputWrite-Output "Honey, I'm $HOME"是等效的,后者不仅更简洁,而且速度更快。

答案 7 :(得分:-12)

使用PowerShell脚本中的外部程序:

cmd /c echo "Long string: $LongStr" 

在运行单独的流程方面,这是愚蠢且昂贵的,但PowerShell的设计很差。