Имя пользователя:
Пароль:  
Помощь | Регистрация | Забыли пароль?  | Правила  

Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » Скриптовые языки администрирования Windows » PowerShell - [решено] Проблема с двойным Foreach

Ответить
Настройки темы
PowerShell - [решено] Проблема с двойным Foreach

Аватара для ivan.vas

Новый участник


Сообщения: 27
Благодарности: 0

Профиль | Отправить PM | Цитировать


Всем привет!
Помогите понять логику Foreach... Не могу понять почему скрипт который выглядит вот так:
Код: Выделить весь код
$Time = (Get-Date) - (New-TimeSpan -Hours 24)
$events = @()
$events += Get-WinEvent -FilterHashtable @{Logname = "Security" ; ID = 4800,4801; StartTime = $Time}
$events += Get-WinEvent -FilterHashtable @{Logname = "System" ; ID = 7001,7002; StartTime = $Time}
$Date = Get-Date -format yyyy-MM-dd
$ArrayList = New-Object System.Collections.ArrayList
	Foreach ($Event in $Events)
	{
	[xml]$Xml = $Event.ToXml()
	$Row = "" | Select Username,TimeCreated,Operation
	$Row.Username = $EventProperties[1].value
	$Row.TimeCreated = $Event.TimeCreated.ToString()
	$Row.Operation = $Event.ID
	[void]$ArrayList.Add($Row)
	}
$ArrayList | Sort TimeCreated
работает исправно, но когда я хочу сделать выборку из файла где содержатся имена компьютеров, то получается не пойми что...

Код: Выделить весь код
$Time = (Get-Date) - (New-TimeSpan -Hours 24)
$Servers = Get-Content "C:\temp\Comp.txt"
Foreach ($Server in $Servers)
{
	if(Test-Connection $Server -Count 2 -Quiet ) {
	$events = @()
	$events += Get-WinEvent -ComputerName $Server -FilterHashtable @{Logname = "Security" ; ID = 4800,4801; StartTime = $Time}
	$events += Get-WinEvent -ComputerName $Server -FilterHashtable @{Logname = "System" ; ID = 7001,7002; StartTime = $Time}
	$Date = Get-Date -format yyyy-MM-dd
	$ArrayList = New-Object System.Collections.ArrayList
	
	Foreach ($Event in $Events)
	{
	[xml]$Xml = $Event.ToXml()
	$Row = "" | Select Username,TimeCreated,Operation
	$Row.Username = $EventProperties[1].value
	$Row.TimeCreated = $Event.TimeCreated.ToString()
	$Row.Operation = $Event.ID
	[void]$ArrayList.Add($Row)
	}
	}
	else {}
}
$ArrayList | Sort TimeCreated
Хочу к варианту который исправно работает (1 листинг) добавить возможность выборки имен компьютеров из файла txt.

Отправлено: 15:57, 15-09-2021

 

Ветеран


Сообщения: 27449
Благодарности: 8086

Профиль | Отправить PM | Цитировать


ivan.vas, Вы на каждом проходе внешнего цикла пересоздаёте содержимое переменной $ArrayList:
Код: Выделить весь код
Foreach ($Server in $Servers) {
    if(Test-Connection $Server -Count 2 -Quiet ) {
        …
        $ArrayList = New-Object System.Collections.ArrayList
	
	Foreach ($Event in $Events) {
	    …
	    [void]$ArrayList.Add($Row)
        }
    …
    }
}
$ArrayList | Sort TimeCreated
Это сообщение посчитали полезным следующие участники:

Отправлено: 17:29, 15-09-2021 | #2



Для отключения данного рекламного блока вам необходимо зарегистрироваться или войти с учетной записью социальной сети.

Если же вы забыли свой пароль на форуме, то воспользуйтесь данной ссылкой для восстановления пароля.


Аватара для ivan.vas

Новый участник


Сообщения: 27
Благодарности: 0

Профиль | Отправить PM | Цитировать


Цитата Iska:
$ArrayList »
честно говоря не понял. А где тогда правильно создать $ArrayList?

Отправлено: 17:59, 15-09-2021 | #3


Ветеран


Сообщения: 27449
Благодарности: 8086

Профиль | Отправить PM | Цитировать


ivan.vas, перед первым циклом.
Это сообщение посчитали полезным следующие участники:

Отправлено: 18:04, 15-09-2021 | #4


Аватара для ivan.vas

Новый участник


Сообщения: 27
Благодарности: 0

Профиль | Отправить PM | Цитировать


Цитата Iska:
перед первым циклом. »
Спасибо, помогло. Теперь скрипт выглядит вот так:
Код: Выделить весь код
$Time = (Get-Date) - (New-TimeSpan -Hours 24)
$Date = Get-Date -format yyyy-MM-dd
$Servers = Get-Content "C:\temp\Comp.txt"
$ArrayList = New-Object System.Collections.ArrayList
Foreach ($Server in $Servers)
{
	if(Test-Connection $Server -Count 2 -Quiet ) {
	$events = @()
	$events += Get-WinEvent -ComputerName $Server -FilterHashtable @{Logname = "Security" ; ID = 4800,4801; StartTime = $Time}
	$events += Get-WinEvent -ComputerName $Server -FilterHashtable @{Logname = "System" ; ID = 7001,7002; StartTime = $Time}
	Foreach ($Event in $Events)
	{
	$Row = "" | Select PC,Username,TimeCreated,Operation
	$Row.PC = $Server
	$Row.Username = $EventProperties[1].value
	$Row.TimeCreated = $Event.TimeCreated.ToString()
	$Row.Operation = $Event.ID
	[void]$ArrayList.Add($Row)
	}
	}
	else {}
}
$ArrayList | Sort TimeCreated
Единственное, что смущает, графы TimeCreated и Operation он выводит верно. Я даже добавил вывод имени компьютера вначале, но вот вывод имени пользователя дублирует одно и тоже. Не можете подсказать почему так?

Отправлено: 09:17, 16-09-2021 | #5


Аватара для DJ Mogarych

fascinating rhythm


Moderator


Сообщения: 6493
Благодарности: 1465

Профиль | Отправить PM | Цитировать


Гораздо быстрее будет работать, если воспользоваться Invoke-Command, типа

Код: Выделить весь код
$Servers = Get-Content "C:\temp\Comp.txt"

Invoke-Command -ComputerName $Servers  -ScriptBlock {
$time = (get-date).AddDays(-1)
Get-WinEvent -FilterHashtable @{Logname = "System" ; ID = 7001,7002; StartTime = $Time} |select PSComputername,@{n="Username";e={$_.properties[1].value}},Timecreated,id
}

-------
Powershell 7.x | Powershell 5.1 | ffmpeg (docs)

Это сообщение посчитали полезным следующие участники:

Отправлено: 10:12, 16-09-2021 | #6


Аватара для ivan.vas

Новый участник


Сообщения: 27
Благодарности: 0

Профиль | Отправить PM | Цитировать


DJ Mogarych, но тогда нужно будет активировать у всех кто в списке Comp.txt - PSRemoting?

Отправлено: 10:26, 16-09-2021 | #7


Аватара для DJ Mogarych

fascinating rhythm


Moderator


Сообщения: 6493
Благодарности: 1465

Профиль | Отправить PM | Цитировать


Да, но у серверов это уже должно быть включено по умолчанию.

-------
Powershell 7.x | Powershell 5.1 | ffmpeg (docs)

Это сообщение посчитали полезным следующие участники:

Отправлено: 10:52, 16-09-2021 | #8


Аватара для ivan.vas

Новый участник


Сообщения: 27
Благодарности: 0

Профиль | Отправить PM | Цитировать


DJ Mogarych, сервера разные бывают, иногда это даже 7

Отправлено: 12:49, 16-09-2021 | #9


Ветеран


Сообщения: 27449
Благодарности: 8086

Профиль | Отправить PM | Цитировать


Цитата ivan.vas:
но вот вывод имени пользователя дублирует одно и тоже. Не можете подсказать почему так? »
А откуда у Вас берётся $EventProperties[1]? Я вижу, что из воздуха. Может быть, $Event.Properties[1].value?

Отправлено: 17:04, 16-09-2021 | #10



Компьютерный форум OSzone.net » Программирование, базы данных и автоматизация действий » Скриптовые языки администрирования Windows » PowerShell - [решено] Проблема с двойным Foreach

Участник сейчас на форуме Участник сейчас на форуме Участник вне форума Участник вне форума Автор темы Автор темы Шапка темы Сообщение прикреплено

Похожие темы
Название темы Автор Информация о форуме Ответов Последнее сообщение
PowerShell - Как добавить исключение в foreach Nightwolf_82 Скриптовые языки администрирования Windows 3 02-01-2018 06:21
PowerShell - ForEach и ForEach-Object начать с конца (наоборот)... Buddha.g Скриптовые языки администрирования Windows 2 12-10-2016 03:10
Разное - [решено] Проблема с двойным кликом мыши kirillius Microsoft Windows 7 3 07-05-2016 11:59
PowerShell - Обработка коллекции через foreach () rudimko Скриптовые языки администрирования Windows 12 25-06-2013 21:51
.NET - Перекрытие области видимости в цикле foreach Delirium Программирование и базы данных 2 18-09-2010 02:06




 
Переход