Беконные биты дали критический указатель в комментарии: используйте Group-Object
, чтобы сгруппировать пользовательские объекты, созданные из строк CSV, через Import-Csv
по идентификатору пользователя.
Вот решениекоторый использует строковые шаблоны для предоставления желаемого текстового вывода XML для каждого пользователя и записывает этот вывод в файл с именем пользователя с идентификатором:
# Per-user template.
# Note how a *literal* (single-quoted) here-string is used, so as to
# *defer* expansion (interpolation) of the embedded expressions.
$docTemplate = @'
<Cv>
<Owner>
<UserID>$($cert.UserID)</UserID>
</Owner>
<Content>
<Certificates>
$($certs -join "`n")
</Certificates>
</Content>
</Cv>
'@
# Per-certificate template.
$entryTemplate = @'
<Certificate>
<Cert>$($cert.Cert)</Cert>
<LastCertDate>$($cert.LastCertDate)</LastCertDate>
<ExpireDate>$($cert.ExpireDate)</ExpireDate>
<CertNumber>$($cert.CertNumber)</CertNumber>
</Certificate>
'@
Import-Csv file.csv -Delimiter ';' | Group-Object UserId -ov grp | ForEach-Object {
# $_.Group contains all certificates associated with the user at hand.
# Create an XML element for each certificate and collect the results
# in array.
$certs = foreach ($cert in $_.Group) {
# Instantiate the per-certificate template.
$ExecutionContext.InvokeCommand.ExpandString($entryTemplate)
}
# Instantiate the per-user template, which encompasses
# the per-certificate elements, and output the result.
$ExecutionContext.InvokeCommand.ExpandString($docTemplate)
} | # Write the resulting XML document string to a file named for the user ID
Set-Content -LiteralPath { $grp.Name + '.xml' }
Обратите внимание, как -ov grp
(сокращение от: -OutVariable grp
)захватывает вывод Group-Object
в каждой итерации конвейера в переменную $grp
, так что вызов Set-Content
позже в конвейере может получить доступ к $grp.Name
- идентификатору пользователя под рукой - в блоке сценария, переданном Set-Content
, поэтомукак для создания выходного файла с именем для идентификатора пользователя.
Примечание. Без аргумента -Encoding
Windows PowerShell будет использовать кодировку символов вашей системы «ANSI» (в PowerShell Core выполучит без спецификации UTF-8).