使用 CSV 作为系统名称的多个位置的 Powershell Copy-Item
Powershell Copy-Item from multiple locations using a CSV for the System name
我有一个包含 98 个系统名称的 CSV,每个系统都有一个我需要的文件。它们都在每台机器上的同一个文件夹中,但文件名是唯一的。
我想使用 copy-item
将文件复制到本地计算机上的某个位置。
$AutoCADs = Import-csv "C:\DTS\BMC\AutoCAD - ANY VERSION_Members.csv"
$AutoPaths = "\" + $AutoCADs + "\C$\DTS\BMC\Autodesk Audit\Information\*"
foreach-object{Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Results" -Force -Recurse}
当我 运行 执行此操作时,98 台机器中的每一台都出现错误。每个错误如下所示:
Copy-Item : Cannot find path 'C:\Users\@{D113978=Y118834}' because it does not exist.
At \CopyAuditFiles.ps1:3 char:16
+ ... each-object{Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Resul ...
@{D113978=Y118834}
让我感到困惑,因为每个错误都有相似的字符串。 D113978
是 CSV 中的第一个系统名称。
另一个系统名称(本例中的Y118834
)会随着每个错误而变化,第一个错误在 csv 中有第二项,第二个错误在 CSV 中有第三项,依此类推
所以脚本似乎看到了每个系统名称,但它根本没有按照我想要的方式处理系统名称。
有人能指出我的缺点吗?
你的 csv 不好。您应该为每列添加一个标题名称。 Powershell 将每列的第一行作为该列的标题名称,这就是为什么会出现令人困惑的错误。因此,在顶部添加另一行并使用像 "Computername".
这样的标题名称
另外 $AutoCADs
本质上是 table object。您正在传递整个 table 以创建动态网络路径。
因此将您的代码更改为:
$AutoCADs = Import-csv "C:\DTS\BMC\AutoCAD - ANY VERSION_Members.csv"
Foreach ($Row in $AutoCADs)
{
$AutoPaths = "\" + $($Row.Computername) + "\C$\DTS\BMC\Autodesk Audit\Information\*"
Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Results" -Force -Recurse
}
Import-csv
将文件中的第一行用于 header,因此它使用 D113978
作为 header 名称而不是项目。
我假设您的 csv 仅包含计算机名称:
D113978
Y118834
D978113
Y842118
如果是,则它不是真正的 csv(因为它没有 headers),它是一个基于文本的列表。
在这种情况下,我只使用 Get-Content
,它将只使用文件中的每一行作为一个项目。
然后将 $AutoPaths = [..]
移动到 foreach
中,以便在每个循环中更新:
$computers = Get-Content "C:\DTS\BMC\AutoCAD - ANY VERSION_Members.csv"
foreach ($system in $computers){
$AutoPaths = "\$system\C$\DTS\BMC\Autodesk Audit\Information\*"
Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Results" -Force -Recurse
}
我有一个包含 98 个系统名称的 CSV,每个系统都有一个我需要的文件。它们都在每台机器上的同一个文件夹中,但文件名是唯一的。
我想使用 copy-item
将文件复制到本地计算机上的某个位置。
$AutoCADs = Import-csv "C:\DTS\BMC\AutoCAD - ANY VERSION_Members.csv"
$AutoPaths = "\" + $AutoCADs + "\C$\DTS\BMC\Autodesk Audit\Information\*"
foreach-object{Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Results" -Force -Recurse}
当我 运行 执行此操作时,98 台机器中的每一台都出现错误。每个错误如下所示:
Copy-Item : Cannot find path 'C:\Users\@{D113978=Y118834}' because it does not exist. At \CopyAuditFiles.ps1:3 char:16 + ... each-object{Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Resul ...
@{D113978=Y118834}
让我感到困惑,因为每个错误都有相似的字符串。 D113978
是 CSV 中的第一个系统名称。
另一个系统名称(本例中的Y118834
)会随着每个错误而变化,第一个错误在 csv 中有第二项,第二个错误在 CSV 中有第三项,依此类推
所以脚本似乎看到了每个系统名称,但它根本没有按照我想要的方式处理系统名称。
有人能指出我的缺点吗?
你的 csv 不好。您应该为每列添加一个标题名称。 Powershell 将每列的第一行作为该列的标题名称,这就是为什么会出现令人困惑的错误。因此,在顶部添加另一行并使用像 "Computername".
这样的标题名称另外 $AutoCADs
本质上是 table object。您正在传递整个 table 以创建动态网络路径。
因此将您的代码更改为:
$AutoCADs = Import-csv "C:\DTS\BMC\AutoCAD - ANY VERSION_Members.csv"
Foreach ($Row in $AutoCADs)
{
$AutoPaths = "\" + $($Row.Computername) + "\C$\DTS\BMC\Autodesk Audit\Information\*"
Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Results" -Force -Recurse
}
Import-csv
将文件中的第一行用于 header,因此它使用 D113978
作为 header 名称而不是项目。
我假设您的 csv 仅包含计算机名称:
D113978 Y118834 D978113 Y842118
如果是,则它不是真正的 csv(因为它没有 headers),它是一个基于文本的列表。
在这种情况下,我只使用 Get-Content
,它将只使用文件中的每一行作为一个项目。
然后将 $AutoPaths = [..]
移动到 foreach
中,以便在每个循环中更新:
$computers = Get-Content "C:\DTS\BMC\AutoCAD - ANY VERSION_Members.csv"
foreach ($system in $computers){
$AutoPaths = "\$system\C$\DTS\BMC\Autodesk Audit\Information\*"
Copy-Item $AutoPaths -Destination "C:\DTS\BMC\Audit Results" -Force -Recurse
}