【问题标题】:Modifying Existing CSV file in Powershell在 Powershell 中修改现有的 CSV 文件
【发布时间】:2013-10-14 12:31:00
【问题描述】:

我正在设置一个脚本,用于将用户的 Exchange 邮箱迁移到 .pst 文件中。我的想法是我会有一个 CSV 文件,我可以将用户名放在上面,然后当脚本每晚启动时,它会打开 CSV 文件并找到已添加的用户,对这些用户帐户执行请求的操作(导出,移动设置权限等),然后写回 CSV 文件将这些用户标记为已完成并写下他们完成的日期。这是我目前所拥有的。

$InPstPath = '\\server1\PST_Store\'
$OutPstPath = '\\server2\PST_Store\'
$User = Get-Content $OutPstPath'login.txt'
$PWord = cat $OutPstPath'pass.txt' | convertto-securestring
$Credentials = New-Object –TypeName System.Management.Automation.PSCredential –ArgumentList $User, $PWord
$PSSession = New-PSSession -ConfigurationName Microsoft.Exchange -ConnectionUri http://Server1/powershell -Credential $Credentials
Import-PSSession $PSSession
$In_List = Invoke-Command {Import-Csv "\\Server1\PST_Store\Admin\To_Be_Exported.csv"} -computername Server1 -Credential $Credentials
foreach ($objUser in $In_List) {
    if ($objUser.Completed -ne "Yes") {
        $TargetUser = $objUser.name
        $ShortDate = (Get-Date).toshortdatestring()
        New-MailboxExportRequest -Mailbox $TargetUser -Filepath "$InPstPath$TargetUser.pst"
        $objUser.Completed = "Yes"
        $objUser.Date = $ShortDate
        }
    }
Remove-PSSession -Session (Get-PSSession)

我想不出一种将 $objUser.Completed 和 $objUser.Date 值写回 CSV 的好方法。

【问题讨论】:

  • 是否有一个 Export-Csv 功能可以反映您使用的 Import-Csv?
  • 有。我不确定如何使用它来仅针对需要更改的值。我发现这个命令的大部分内容使它看起来与'Out-File C:\filename.csv | 类似。 ConvertTo-Csv'
  • 我猜你需要用新内容覆盖整个文件。你会想要测试并确保你只得到你所做的更改,但这对我来说似乎是一种合理的方法。
  • 我研究得越多,我开始认为我应该构建一个新的自定义对象并为其定义属性,然后根据导入的信息(其中 Completed = Yes)或新信息(完成时 = 不是)。

标签: powershell csv powershell-3.0 export-to-csv


【解决方案1】:

首先,这很明显,但还是让我声明一下。第一次运行此脚本时,$objUser.name、$objUser.Completed 和 $objUser.Date 将不存在;所以,这条线

$TargetUser=$objUser.name

将不起作用,除非您实际上在该 csv 中具有适当的结构(即具有标题名称、已完成、日期)。

现在假设你已经完成了那部分,你所要做的就是创建一个对象来捕获对象中的状态,然后将其写回。

$Processed = foreach ($objUser in $In_List) {
    if ($objUser.Completed -ne "Yes") {
        $TargetUser = $objUser.name
        $ShortDate = (Get-Date).toshortdatestring()
        New-MailboxExportRequest -Mailbox $TargetUser -Filepath "$InPstPath$TargetUser.pst"

        [PSCustomObject]@{Name=$objUser.name;Completed="Yes";Date=$ShortDate}
        }
    } else {
        [PSCustomObject]@{Name=$objUser.name;Completed="No";Date=$null}
    }
## export to a temp file
$Processed | export-csv -Path $env:TEMP\processed.csv
## You should probably check to see if original file was modified since you started working on it
# and copy over if not
Copy-Item $env:TEMP\processed.csv $OutPstPath'login.txt' -force

【讨论】:

  • 初始 CSV 确实具有所需的标题。如果我将数据写入新的 CSV,我将需要注意重新创建标题,尽管您建议的方法可能会这样做。这当然是朝着正确方向迈出的一步,我明天会试一试。我认为也许 else 语句应该是... [PSCustomObject]@{Name=$objUser.name;Completed=objUser.Completed;Date=objUser.Date} 好像它失败了 -ne "Yes" 那么用户的帐户有已经被处理了。不过我在这方面还很陌生,所以我可能会误读它。
  • 是的,export-csv 将创建一个 csv 对象,您以后可以按原样再次导入该对象。您当然可以根据自己的喜好使用“是”、“否”来表示已完成,但也可以简单地使用布尔值 $true、$false,因为它正好符合您的目的。除非明确分配,否则任何布尔变量都将为 $false ,您可以利用它来发挥自己的优势。 if ($Completed) {"如果为真" } else {"如果不是"}
  • 经过一番处理后,我得到了使用您规定的解决方案的方法。谢谢! (我会投票,但显然我没有足够的声誉这样做:P)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-09-30
  • 2017-03-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-05-31
  • 1970-01-01
相关资源
最近更新 更多