Udostępnij za pośrednictwem


Rozdział 7 — Korzystanie z usługą WMI

WMI i CIM

Program Windows PowerShell jest domyślnie dostarczany z poleceniami cmdlet do pracy z innymi technologiami, takimi jak Instrumentacja zarządzania Windows (WMI). Polecenia cmdlet usługi WMI są przestarzałe i nie są dostępne w programie PowerShell 6 lub nowszym, ale są tu omówione, ponieważ mogą wystąpić w starszych skryptach uruchomionych w programie Windows PowerShell. W przypadku nowego programowania należy zamiast tego użyć poleceń cmdlet modelu CIM.

W programie PowerShell dostępnych jest kilka natywnych cmdletów WMI, które nie wymagają instalowania żadnego dodatkowego oprogramowania ani modułów. Get-Command można użyć do określenia, jakie polecenia cmdlet usługi WMI istnieją w programie Windows PowerShell. Poniższe wyniki pochodzą z systemu Windows 11 z programem PowerShell w wersji 5.1. Wyniki mogą się różnić w zależności od uruchomionej wersji programu PowerShell.

Get-Command -Noun WMI*
CommandType     Name                                               Version
-----------     ----                                               -------
Cmdlet          Get-WmiObject                                      3.1.0.0
Cmdlet          Invoke-WmiMethod                                   3.1.0.0
Cmdlet          Register-WmiEvent                                  3.1.0.0
Cmdlet          Remove-WmiObject                                   3.1.0.0
Cmdlet          Set-WmiInstance                                    3.1.0.0

Polecenia cmdlet Modelu Wspólnych Informacji (CIM) zostały wprowadzone w PowerShell 3.0 i są pogrupowane w dedykowanym module. Aby wyświetlić listę wszystkich dostępnych poleceń cmdlet CIM, użyj polecenia cmdlet Get-Command, z modułem i parametrem, jak pokazano w poniższym przykładzie.

Get-Command -Module CimCmdlets
CommandType     Name                                               Version
-----------     ----                                               -------
Cmdlet          Export-BinaryMiLog                                 1.0.0.0
Cmdlet          Get-CimAssociatedInstance                          1.0.0.0
Cmdlet          Get-CimClass                                       1.0.0.0
Cmdlet          Get-CimInstance                                    1.0.0.0
Cmdlet          Get-CimSession                                     1.0.0.0
Cmdlet          Import-BinaryMiLog                                 1.0.0.0
Cmdlet          Invoke-CimMethod                                   1.0.0.0
Cmdlet          New-CimInstance                                    1.0.0.0
Cmdlet          New-CimSession                                     1.0.0.0
Cmdlet          New-CimSessionOption                               1.0.0.0
Cmdlet          Register-CimIndicationEvent                        1.0.0.0
Cmdlet          Remove-CimInstance                                 1.0.0.0
Cmdlet          Remove-CimSession                                  1.0.0.0
Cmdlet          Set-CimInstance                                    1.0.0.0

Polecenia cmdlet CIM nadal umożliwiają pracę z usługą WMI, więc nie bądź zdezorientowany, gdy ktoś stwierdza: "Podczas wykonywania zapytań w WMI za pomocą poleceń cmdlet CIM programu PowerShell".

Jak wspomniano wcześniej, technologia WMI jest oddzielną technologią od PowerShell, a używasz poleceń cmdlet CIM do uzyskiwania dostępu do WMI. Możesz znaleźć stary skrypt VBScript, który używa języka WMI Query Language (WQL) do wykonywania zapytań w usłudze WMI, na przykład w poniższym przykładzie.

strComputer = "."
Set objWMIService = GetObject("winmgmts:" _
    & "{impersonationLevel=impersonate}!\\" & strComputer & "\root\CIMV2")

Set colBIOS = objWMIService.ExecQuery _
    ("Select * from Win32_BIOS")

For each objBIOS in colBIOS
    Wscript.Echo "Manufacturer: " & objBIOS.Manufacturer
    Wscript.Echo "Name: " & objBIOS.Name
    Wscript.Echo "Serial Number: " & objBIOS.SerialNumber
    Wscript.Echo "SMBIOS Version: " & objBIOS.SMBIOSBIOSVersion
    Wscript.Echo "Version: " & objBIOS.Version
Next

Możesz pobrać zapytanie WQL z języka VBScript i użyć go z poleceniem cmdlet Get-CimInstance bez żadnych modyfikacji.

Get-CimInstance -Query 'Select * from Win32_BIOS'
SMBIOSBIOSVersion : 090006
Manufacturer      : American Megatrends Inc.
Name              : Intel(R) Xeon(R) CPU E3-1505M v5 @ 2.80GHz
SerialNumber      : 3810-1995-1654-4615-2295-2755-89
Version           : VRTUAL - 4001628

Poprzedni przykład nie jest sposobem, w jaki zwykle wysyłam zapytanie do usługi WMI przy użyciu programu PowerShell. Działa ona jednak i umożliwia łatwe migrowanie istniejących skryptów języka Visual Basic do programu PowerShell. Podczas pisania jednego wiersza w celu wykonywania zapytań w usłudze WMI używam następującej składni.

Get-CimInstance -ClassName Win32_BIOS
SMBIOSBIOSVersion : 090006
Manufacturer      : American Megatrends Inc.
Name              : Intel(R) Xeon(R) CPU E3-1505M v5 @ 2.80GHz
SerialNumber      : 3810-1995-1654-4615-2295-2755-89
Version           : VRTUAL - 4001628

Jeśli chcesz tylko numer seryjny, należy przekazać dane wyjściowe do Select-Object i określić tylko właściwość SerialNumber.

Get-CimInstance -ClassName Win32_BIOS |
    Select-Object -Property SerialNumber
SerialNumber
------------
3810-1995-1654-4615-2295-2755-89

Domyślnie podczas zapytań do WMI kilka właściwości, które nie są nigdy używane, jest pobieranych w tle. Nie ma to większego znaczenia podczas wykonywania zapytań w usłudze WMI na komputerze lokalnym. Jednak po rozpoczęciu wykonywania zapytań dotyczących komputerów zdalnych jest to nie tylko dodatkowy czas przetwarzania, aby zwrócić te informacje, ale także bardziej niepotrzebne informacje wysyłane przez sieć. Get-CimInstance ma parametr właściwości , który ogranicza ilość pobieranych informacji, dzięki czemu zapytanie WMI jest bardziej wydajne.

Get-CimInstance -ClassName Win32_BIOS -Property SerialNumber |
    Select-Object -Property SerialNumber
SerialNumber
------------
3810-1995-1654-4615-2295-2755-89

Poprzednie wyniki zwróciły obiekt. Aby zwrócić ciąg, użyj parametru ExpandProperty.

Get-CimInstance -ClassName Win32_BIOS -Property SerialNumber |
    Select-Object -ExpandProperty SerialNumber
3810-1995-1654-4615-2295-2755-89

Możesz również użyć kropkowanej składni, aby zwrócić ciąg, eliminując potrzebę sprowadzania do Select-Object.

(Get-CimInstance -ClassName Win32_BIOS -Property SerialNumber).SerialNumber
3810-1995-1654-4615-2295-2755-89

Wykonywanie zapytań dotyczących komputerów zdalnych za pomocą poleceń cmdlet modelu CIM

Nadal należy uruchomić program PowerShell jako administrator lokalny i użytkownik domeny. Podczas próby wykonywania zapytań dotyczących informacji z komputera zdalnego przy użyciu polecenia cmdlet Get-CimInstance zostanie wyświetlony komunikat o błędzie odmowy dostępu.

Get-CimInstance -ComputerName dc01 -ClassName Win32_BIOS
Get-CimInstance : Access is denied.
At line:1 char:1
+ Get-CimInstance -ComputerName dc01 -ClassName Win32_BIOS
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : PermissionDenied: (root\cimv2:Win32_BIOS:Stri
   ng) [Get-CimInstance], CimException
    + FullyQualifiedErrorId : HRESULT 0x80070005,Microsoft.Management.Infra
   structure.CimCmdlets.GetCimInstanceCommand
    + PSComputerName        : dc01

Wiele osób ma obawy dotyczące zabezpieczeń programu PowerShell, ale masz te same uprawnienia w programie PowerShell, co w graficznym interfejsie użytkownika. Ani więcej, ani mniej. Problem w poprzednim przykładzie polega na tym, że użytkownik z uruchomionym programem PowerShell nie ma uprawnień do wykonywania zapytań dotyczących informacji usługi WMI z serwera DC01. Możesz ponownie użyć programu PowerShell jako administratora domeny, ponieważ Get-CimInstance nie ma parametru Credential. Nie jest to jednak dobry pomysł, ponieważ wszystkie elementy uruchamiane z programu PowerShell będą uruchamiane jako administrator domeny. W zależności od sytuacji ten scenariusz może być niebezpieczny z punktu widzenia bezpieczeństwa.

Korzystając z zasady najniższych uprawnień, zwiększaj uprawnienia do poziomu konta administratora domeny dla konkretnego polecenia, używając parametru Credential, jeśli polecenie go posiada. Get-CimInstance nie ma parametru credential, więc rozwiązaniem w tym scenariuszu jest najpierw utworzenie CimSession. Następnie użyj CimSession zamiast nazwy komputera, aby wykonać zapytanie w usłudze WMI na komputerze zdalnym.

$CimSession = New-CimSession -ComputerName dc01 -Credential (Get-Credential)
cmdlet Get-Credential at command pipeline position 1
Supply values for the following parameters:
Credential

Sesja CIM była przechowywana w zmiennej o nazwie $CimSession. Zwróć uwagę, że należy również określić polecenie cmdlet Get-Credential w nawiasach, aby było wykonywane najpierw, prosząc o alternatywne poświadczenia, przed utworzeniem nowej sesji. W dalszej części tego rozdziału pokażę ci kolejny bardziej wydajny sposób określania alternatywnych poświadczeń, ale ważne jest, aby zrozumieć tę podstawową koncepcję przed jej bardziej skomplikowanym rozwiązaniem.

Teraz możesz użyć sesji CIM utworzonej w poprzednim przykładzie za pomocą cmdlet Get-CimInstance, aby pobrać informacje o BIOS z usługi WMI na zdalnym komputerze.

Get-CimInstance -CimSession $CimSession -ClassName Win32_BIOS
SMBIOSBIOSVersion : 090006
Manufacturer      : American Megatrends Inc.
Name              : Intel(R) Xeon(R) CPU E3-1505M v5 @ 2.80GHz
SerialNumber      : 0986-6980-3916-0512-6608-8243-13
Version           : VRTUAL - 4001628
PSComputerName    : dc01

Istnieje kilka innych korzyści związanych z używaniem sesji modelu CIM zamiast po prostu określania nazwy komputera. W przypadku uruchamiania wielu zapytań na tym samym komputerze użycie sesji modelu ciM jest bardziej wydajne niż użycie nazwy komputera dla każdego zapytania. Utworzenie sesji CIM powoduje jednorazowe skonfigurowanie połączenia. Następnie wiele zapytań używa tej samej sesji do pobierania informacji. Użycie nazwy komputera wymaga, aby polecenia cmdlet musiały skonfigurować i usunąć połączenie z każdym zapytaniem.

Polecenie cmdlet Get-CimInstance domyślnie używa protokołu WSMan, co oznacza, że do nawiązania połączenia komputer zdalny wymaga programu PowerShell w wersji 3.0 lub nowszej. W rzeczywistości nie jest to wersja programu PowerShell, która ma znaczenie, jest to wersja stosu. Wersję stosu można określić, korzystając z polecenia cmdlet Test-WSMan. Musi to być wersja 3.0, którą można znaleźć w programie PowerShell w wersji 3.0 lub nowszej.

Test-WSMan -ComputerName dc01
wsmid           : http://schemas.dmtf.org/wbem/wsman/identity/1/wsmanidentit
                  y.xsd
ProtocolVersion : http://schemas.dmtf.org/wbem/wsman/1/wsman.xsd
ProductVendor   : Microsoft Corporation
ProductVersion  : OS: 0.0.0 SP: 0.0 Stack: 3.0

Starsze komendy usługi WMI używają protokołu DCOM, który jest zgodny ze starszymi wersjami systemu Windows. Jednak zapora zwykle blokuje DCOM w nowszych wersjach Windows. Polecenie cmdlet New-CimSessionOption umożliwia utworzenie połączenia protokołu DCOM do użycia z New-CimSession. Ta opcja umożliwia Get-CimInstance polecenia cmdlet komunikowanie się z wersjami systemu Windows tak starymi jak Windows Server 2000. Ta możliwość oznacza również, że środowisko PowerShella nie jest wymagane na komputerze zdalnym podczas korzystania z polecenia cmdlet Get-CimInstance z CimSession skonfigurowanym do korzystania z protokołu DCOM.

Utwórz opcję protokołu DCOM przy użyciu polecenia cmdlet New-CimSessionOption i zapisz go w zmiennej.

$DCOM = New-CimSessionOption -Protocol Dcom

W celu zwiększenia wydajności można przechowywać poświadczeń administratora domeny lub poświadczeń z podwyższonym poziomem uprawnień w zmiennej, aby nie trzeba było stale wprowadzać ich dla każdego polecenia.

$Cred = Get-Credential
cmdlet Get-Credential at command pipeline position 1
Supply values for the following parameters:
Credential

Mam serwer o nazwie SQL03 z systemem Windows Server 2008 (inne niż R2). Jest to najnowszy system operacyjny Windows Server, który domyślnie nie ma zainstalowanego programu PowerShell.

Utwórz CimSession do SQL03 przy użyciu protokołu DCOM.

$CimSession = New-CimSession -ComputerName sql03 -SessionOption $DCOM -Credential $Cred

Zwróć uwagę, że w poprzednim poleceniu określono zmienną o nazwie $Cred jako wartość parametru Credential zamiast ręcznie wprowadzać poświadczenia ponownie.

Dane wyjściowe zapytania są takie same niezależnie od podstawowego protokołu.

Get-CimInstance -CimSession $CimSession -ClassName Win32_BIOS
SMBIOSBIOSVersion : 090006
Manufacturer      : American Megatrends Inc.
Name              : Intel(R) Xeon(R) CPU E3-1505M v5 @ 2.80GHz
SerialNumber      : 7237-7483-8873-8926-7271-5004-86
Version           : VRTUAL - 4001628
PSComputerName    : sql03

Polecenie cmdlet Get-CimSession służy do sprawdzenia, które CimSessions są obecnie połączone i jakich protokołów używają.

Get-CimSession
Id           : 1
Name         : CimSession1
InstanceId   : 80742787-e38e-41b1-a7d7-fa1369cf1402
ComputerName : dc01
Protocol     : WSMAN

Id           : 2
Name         : CimSession2
InstanceId   : 8fcabd81-43cf-4682-bd53-ccce1e24aecb
ComputerName : sql03
Protocol     : DCOM

Pobierz i zapisz wcześniej utworzone cimSessions w zmiennej o nazwie $CimSession.

$CimSession = Get-CimSession

Zapytaj oba komputery za pomocą jednego polecenia, jednego przy użyciu protokołu WSMan, a drugiego z DCOM.

Get-CimInstance -CimSession $CimSession -ClassName Win32_BIOS
SMBIOSBIOSVersion : 090006
Manufacturer      : American Megatrends Inc.
Name              : Intel(R) Xeon(R) CPU E3-1505M v5 @ 2.80GHz
SerialNumber      : 0986-6980-3916-0512-6608-8243-13
Version           : VRTUAL - 4001628
PSComputerName    : dc01

SMBIOSBIOSVersion : 090006
Manufacturer      : American Megatrends Inc.
Name              : Intel(R) Xeon(R) CPU E3-1505M v5 @ 2.80GHz
SerialNumber      : 7237-7483-8873-8926-7271-5004-86
Version           : VRTUAL - 4001628
PSComputerName    : sql03

Jeden z moich artykułów w blogu na temat poleceń cmdlet WMI i CIM zawiera funkcję programu PowerShell, która automatycznie wykrywa, czy używać narzędzia WSMan, czy DCOM, a następnie konfiguruje odpowiednią sesję CIM. Aby uzyskać więcej informacji, sprawdź funkcję PowerShell do tworzenia CimSessions na komputerach zdalnych z przełączeniem na Dcom.

Po zakończeniu korzystania z sesji CIM usuń je za pomocą polecenia cmdlet Remove-CimSession. Aby usunąć wszystkie sesje CIM, przekaż Get-CimSession do Remove-CimSession.

Get-CimSession | Remove-CimSession

Podsumowanie

W tym rozdziale omówiono używanie programu PowerShell do pracy z usługą WMI na komputerach lokalnych i zdalnych. Nauczyłeś się również, jak używać poleceń cmdlet modelu CIM do pracy z komputerami zdalnymi przy użyciu protokołów WSMan i DCOM.

Wykonaj przegląd

  1. Jaka jest różnica w poleceniach cmdlet WMI i CIM?
  2. Domyślnie, jakiego protokołu używa polecenie typu Get-CimInstance cmdlet?
  3. Jakie są niektóre korzyści z używania sesji CIM zamiast określania nazwy komputera z Get-CimInstance?
  4. Jak określić alternatywny protokół inny niż domyślny do użycia z Get-CimInstance?
  5. Jak zamknąć lub usunąć sesje CIM?

Źródła