Тест-NetConnection-AsJob?

Можно ли как-нибудь использовать этот фрагмент кода с Test-NetConnection -ComputerName $_ -Port 5985 вместо Test-Connection -ComputerName $_ -Count 1 -AsJob? Я не могу использовать -AsJob с командлетом Test-NetConnection. Есть ли обходные пути?

Вот мой код:

$online = @()
$pc = Get-Content C:\servers.txt 
$pc | ForEach-Object { 
    Test-Connection -ComputerName $_ -Count 1 -AsJob 
} | Get-Job | Receive-Job -Wait | 
Select-Object @{Name='ComputerName';Expression = {$_.Address}},@{Name='Reachable';Expression = {
    if ($_.StatusCode -eq 0) { 
        $true 
    } else { 
        $false 
    }
}} | ForEach-Object {
    if ($_.Reachable -eq $true) {
        $online += $_.ComputerName
    }
}
$online | ft -AutoSize

В server.txt просто есть имена хостов всех машин в сети.

Какую версию PowerShell вы используете? Это может быть довольно легко с ForEach-Object -Parallel если работает PowerShell 7+, в противном случае эта функция может помочь github.com/santisq/PS-NetScanners/blob/main/…

Santiago Squarzon 11.04.2023 23:20

5.1.19041.2673. 5. Мы не можем обновить все PowerShell в среде. ключ здесь в том, что online будет содержать все работающие серверы, чтобы я мог одновременно взаимодействовать с этими системами. Вот почему работа имеет ключевое значение.

unixpipe 11.04.2023 23:31

А установка модулей? Это также может быть легко с помощью Start-ThreadJob, и вы можете установить его с помощью Install-Module ThreadJob -Scope CurrentUser

Santiago Squarzon 11.04.2023 23:32

Было бы лучше придерживаться значений по умолчанию, если это возможно.

unixpipe 11.04.2023 23:39
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
2
4
68
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

С ванильной Windows PowerShell 5.1 лучшее, что вы можете получить, — это использовать RunspacePool , за кодом непросто следить, и по уважительной причине в PowerShell доступно множество модулей для обработки многопоточности. Наиболее рекомендуемым будет ThreadJob.
Этот ответ предлагает «копируемую» версию функции, которая может обрабатывать многопоточность из конвейера, аналогичную ForEach-Object -Parallel, но совместимую с Windows PowerShell 5.1.

$ProgressPreference = 'Ignore'
$maxThreads = 32 # How many jobs can run at the same time?

$pool = [runspacefactory]::CreateRunspacePool(1, $maxThreads,
    [initialsessionstate]::CreateDefault2(), $Host)

$pool.Open()

$jobs = [System.Collections.Generic.List[hashtable]]::new()

Get-Content C:\servers.txt | ForEach-Object {
    $instance = [powershell]::Create().AddScript({
        param($computer)

        [pscustomobject]@{
            Computer = $computer
            Port     = 5985
            PortOpen = Test-NetConnection $computer -Port 5985 -InformationLevel Quiet
        }
    }).AddParameters(@{ computer = $_ })

    $instance.RunspacePool = $pool

    $jobs.Add(@{
        Instance = $instance
        Async    = $instance.BeginInvoke()
    })
}

$result = while($jobs) {
    $job = $jobs[[System.Threading.WaitHandle]::WaitAny($jobs.Async.AsyncWaitHandle)]
    $job.Instance.EndInvoke($job.Async)
    $job.Instance.Dispose()
    $null = $jobs.Remove($job)
}

$pool.Dispose()

$result | Where-Object PortOpen # filter only for computers with this port open

Означает ли это, что он может запускать это максимум на 32 системах одновременно? Также есть ли способ, как в моем предыдущем вопросе, просто собрать все системы с именем хоста в массив online?

unixpipe 12.04.2023 00:35

@unixpipe это число может быть изменено на столько, сколько вы хотите, или на столько, сколько ваш компьютер может обработать, а что касается хостов в сети, я полагаю, что уже предоставил это в ответе $result | Where-Object PortOpen вам просто нужно расширить свойство Computer оттуда, чтобы получить массив значений

Santiago Squarzon 12.04.2023 00:39

Спасибо. Я смог это получить. Проблема в том, что я могу не знать, сколько систем на самом деле работает. Может быть 4000 или даже 5000. Мне просто установить максимальное значение 5000 или это просто невозможно с помощью этого метода?

unixpipe 12.04.2023 00:41

@unixpipe нет, $maxThreads = 32 никак не влияет на результаты. Эта переменная предназначена для того, чтобы сообщить пулу пространства выполнения, сколько потоков может выполняться одновременно, и больше ничего. 32 — приличное число, если вы поднимете его слишком сильно, вы можете сломать сеанс PowerShell. я бы оставил с этим значением

Santiago Squarzon 12.04.2023 00:43

У @unixpipe была опечатка, моя ошибка, смотрите обновление (отсутствует $instance.RunspacePool = $pool)

Santiago Squarzon 12.04.2023 01:17

Я собирался принять ответ только сейчас, потому что он работал еще до того, как вы упомянули отсутствующий оператор, но не могли бы вы уточнить, почему он работал без него и будет ли он работать без него?

unixpipe 12.04.2023 01:30

@unixpipe это работает, потому что пул пространства выполнения не является обязательным для запуска кода в отдельном потоке, все, что вам нужно, это экземпляр powershell ([powershell]::Create()....), но без пула все экземпляры будут работать одновременно. Пул — это механизм управления потоками, он сообщает потокам, когда они могут «начать работу».

Santiago Squarzon 12.04.2023 01:37

Другие вопросы по теме