首页 > 解决方案 > powershell : 不支持给定路径的格式

问题描述

我不是程序员,但我正在尝试运行此 powershell 脚本以使用 Internet exporer 获取多个网站截图(不是我的脚本)

任何人都可以帮助找出问题所在,因为我是堆栈,我不知道该怎么做。

提前谢谢

# Author: Shawn Keene
# Date: 09/12/2019
# Powershell script to automate Internet Explorer and grab screenshots

$ScriptPath = Split-Path $MyInvocation.MyCommand.Path
cd $ScriptPath

[Reflection.Assembly]::LoadWithPartialName("System.Drawing")

function screenshot([Drawing.Rectangle]$bounds, $path) {
$bmp = New-Object Drawing.Bitmap $bounds.width, $bounds.height
$graphics = [Drawing.Graphics]::FromImage($bmp)

$graphics.CopyFromScreen($bounds.Location, [Drawing.Point]::Empty, $bounds.size)

$bmp.Save($path)

$graphics.Dispose()
$bmp.Dispose()
}

$bounds = [Drawing.Rectangle]::FromLTRB(4, 110, 1580, 1584)      #area for screenshot

cls
Write-Host -ForegroundColor Yellow "Starting... Move or minimize this window."
sleep 3                                                          #give the user 3 seconds to minimize 
or move the powershell window out of the way

$iterator = 1;
$OutputFile = "screenshot-log.log"                               #just in case we need to debug 
something later

$products = import-csv "urls.csv" | foreach {                    #load a 2-column CSV with headers of 
"filename" (for picture file) and "url" to visit

$ie = New-Object -com internetexplorer.application;          #initialize a fresh browser window for 
each row of the CSV
$ie.top = 0;
$ie.left = -8;                                               #because windows 10 has an invisible 
grab borders unless you use AeroLite theme
$ie.height = 1600;
$ie.width = 1600;
$ie.visible = $true;

$ie.navigate("about:blank");
while ($ie.Busy -eq $true) { Start-Sleep -Seconds 1};

$startTime = Get-Date                                       #start the stopwatch and log it
write-host $iterator.ToString() `t $_.url

$ie.navigate($_.url);                                       #go to the website and wait for browser 
to become idle

while ($ie.Busy -eq $true) { Start-Sleep -Seconds 1};
sleep 3                                                     #wait at least 3 seconds and then check 
for idle one more time to be sure
while ($ie.Busy -eq $true) { Start-Sleep -Seconds 1};

$endTime = get-date                                         #end timer

$filepath = "Results\" + $_.filename + ".png"               #place screenshots into the Results 
subfolder of the current working directory

screenshot $bounds $scriptpath\$filepath                    #say cheese

#log the result to the log file
$iterator.ToString() + "`t" + $_.filename + "`t" + $_.url + "`t" + $startTime.DateTime + "`t" + 
($endTime - $startTime).TotalSeconds + " seconds" >> $outputFile

$ie.quit();                                                 #close the browser process

$iterator = $iterator+1;
}

Write-Host -ForegroundColor Green "All Done!";

我得到了这个错误

Exception calling "Save" with "1" argument(s): "The given path's format is not supported."
At line:7 char:4
+    $bmp.Save($path)
+    ~~~~~~~~~~~~~~~~
+ CategoryInfo          : NotSpecified: (:) [], MethodInvocationException
+ FullyQualifiedErrorId : NotSupportedException

任何人都可以帮助找出问题所在,因为我是堆栈,我不知道该怎么做。

提前谢谢

标签: powershell

解决方案


笔记:

  • 以下答案适用于Windows

  • 类 Unix 平台(由 PowerShell [Core] v6+ 支持)有不同的规则;值得注意的是,没有驱动器号 [1]:因此是文件名中的合法字符;除了/始终是路径分隔符之外,对于您可以在文件名中使用的字符几乎没有任何限制,包括\. [2]


正如您已经确认的那样,问题是您的输入 CSV 文件中filename列值包含:(冒号) character,但不允许仅包含文件:

:只允许在文件路径中,一次,作为驱动器规范的一部分(例如,C:

:路径的任何其他部分中的 A 会触发您看到的异常,该异常在 PowerShell 中显示为语句终止错误(错误消息缩写如下);例如:

# On Windows
PS> [System.IO.StreamWriter]::new("C:\foo:bar")
"The given path's format is not supported."

如果您尝试使用文件名中根本不支持的字符,则会出现一个相关错误,特别是以下之一:(也不能在文件中使用,只能作为路径中的分隔符);请注意,PowerShell [Core] v6+ 中的错误消息已更改:: * ? " < > | \ /

# Windows PowerShell
PS> [System.IO.StreamWriter]::new("foo?bar")
"Illegal characters in path."

# PowerShell [Core] v6+ on Windows
PS> [System.IO.StreamWriter]::new("foo?bar")
"The filename, directory name, or volume label syntax is incorrect."

上述错误都是由于无效的文件系统路径语法造成的。

相反,如果路径在语法上有效但目标目录不存在,您将看到另一个错误

# On Windows.
PS> [System.IO.StreamWriter]::new("NoSuchSubdir\file.txt")
"Could not find a part of the path '...'."

使用/分隔符,您会在类 Unix 平台上看到相同的错误。


[1] 基于PowerShell-only驱动器定义的路径(使用 创建New-PSDrive)也可以在 Unix 上具有驱动器规范,但您不能将此类路径传递给.NET 方法(例如在本例中),因为 .NET 不理解它们。

[2] 这适用于 .NET 方法调用和对本机实用程序的调用;PowerShell,为了统一跨平台的行为,也允许\在 Unix 上用作路径分隔符,这可能会出现问题 - 请参阅此 GitHub 问题


推荐阅读