filtrowanie po wartości

potęgą PowerShell jest jego obiektowość, dzięki czemu cały język jest bardzo elastyczny. np filtrowanie wyjścia staje się bardzo proste:

ps|? name -match 'svc'

proste, jasne i przyjemne… i łatwo znaleźć na setkach tysiącach stron…

dla tego inne pytanie – a jak przefiltrować po wartościach wszystkich parametrów? np. „pokaż wszystkie parametry obiektu, które mają 'name’ w nazwie”, albo „pokaż wszystkie wartości parametrów, które zawierają 'abc'”. tego już tak łatwo zrobić się nie da. to będzie nieco nieprzyjemna przejażdżka, bo wymaga rozebrania obiektu na kawałki – czyli tracimy automatykę PS, która tak ślicznie pomaga w 'normalnych’ zapytaniach, i grzebiemy we flakach.

aby osiągnąć cel trzeba skorzystać z ukrytego parametru 'psobject’, który pokazuje wnętrzności obiektu. dodatkowo sprawę kompliqje fakt, że wyjście jest często tablicą obiektów a nie pojedynczym obiektem. pobawmy się 'get-service’ i zrealizujmy takie zadania:

  • wyświetlmy wszystkie nazwy i wartości parametrów, które mają w nazwie 'name’
  • wyświetlmy wszystkie nazwy i wartości parametrów, dla których wartość jest równa 'true’

w pierwszej kolejności zobaczmy jak taki obiekt wygląda wewnątrz. najpierw klasycznie…:

PS C:\_scriptZ> Get-Service|gm


   TypeName: System.ServiceProcess.ServiceController

Name                      MemberType    Definition
----                      ----------    ----------
Name                      AliasProperty Name = ServiceName
RequiredServices          AliasProperty RequiredServices = ServicesDependedOn
Disposed                  Event         System.EventHandler Disposed(System.Object, System.EventArgs)
Close                     Method        void Close()
Continue                  Method        void Continue()
CreateObjRef              Method        System.Runtime.Remoting.ObjRef CreateObjRef(type requestedType)
Dispose                   Method        void Dispose(), void IDisposable.Dispose()
Equals                    Method        bool Equals(System.Object obj)
ExecuteCommand            Method        void ExecuteCommand(int command)
GetHashCode               Method        int GetHashCode()
GetLifetimeService        Method        System.Object GetLifetimeService()
GetType                   Method        type GetType()
InitializeLifetimeService Method        System.Object InitializeLifetimeService()
Pause                     Method        void Pause()
Refresh                   Method        void Refresh()
Start                     Method        void Start(), void Start(string[] args)
Stop                      Method        void Stop()
WaitForStatus             Method        void WaitForStatus(System.ServiceProcess.ServiceControllerStatus desiredStat...
CanPauseAndContinue       Property      bool CanPauseAndContinue {get;}
CanShutdown               Property      bool CanShutdown {get;}
CanStop                   Property      bool CanStop {get;}
Container                 Property      System.ComponentModel.IContainer Container {get;}
DependentServices         Property      System.ServiceProcess.ServiceController[] DependentServices {get;}
DisplayName               Property      string DisplayName {get;set;}
MachineName               Property      string MachineName {get;set;}
ServiceHandle             Property      System.Runtime.InteropServices.SafeHandle ServiceHandle {get;}
ServiceName               Property      string ServiceName {get;set;}
ServicesDependedOn        Property      System.ServiceProcess.ServiceController[] ServicesDependedOn {get;}
ServiceType               Property      System.ServiceProcess.ServiceType ServiceType {get;}
Site                      Property      System.ComponentModel.ISite Site {get;set;}
StartType                 Property      System.ServiceProcess.ServiceStartMode StartType {get;}
Status                    Property      System.ServiceProcess.ServiceControllerStatus Status {get;}
ToString                  ScriptMethod  System.Object ToString();

a potem… od środka:

PS C:\_scriptZ> (get-service).psobject

Members : {Count = Length, int Length {get;}, long LongLength {get;}, int Rank {get;}...}
Properties : {Count = Length, int Length {get;}, long LongLength {get;}, int Rank {get;}...}
Methods : {void Set(int , System.Object ), System.Object&, mscorlib, Version=4.0.0.0, Culture=neutral, Publ
          icKeyToken=b77a5c561934e089 Address(int ), System.Object Get(int ), System.Object GetValue(Params
          int[] indices), System.Object GetValue(int index), System.Object GetValue(int index1, int index2
          ), System.Object GetValue(int index1, int index2, int index3), System.Object GetValue(long index)
          , System.Object GetValue(long index1, long index2), System.Object GetValue(long index1, long inde
          x2, long index3), System.Object GetValue(Params long[] indices)...}
ImmediateBaseObject : {aciseagent, AdobeARMservice, AdobeFlashPlayerUpdateSvc, agiptd...}
BaseObject : {aciseagent, AdobeARMservice, AdobeFlashPlayerUpdateSvc, agiptd...}
TypeNames : {System.Object[], System.Array, System.Object}

nas będą interesować 'properties’, których nazwy zawierają 'name’. nie będę się bawił w step-by-step, myślę, że taki początek wystarczy, a całą resztę trzeba po prostu usiąść i się pobawić. mamy podstawy więc teraz trzeba po PowerShellowemu zapisać zadanie „wyświetl wszystkie usługi (obiekty), następnie dla każdej usługi przefiltruj te parametry, który mają w nazwie 'name’ a następnie wyświetl tylko nazwę i wartość”. po takim zapisie to już bułka z masłem:

Get-Service|%{$_.psobject.properties|? name -match 'name'}|ft name,value

a teraz drugie zadanie – i tu robi się na prawdę pasqdnie, bo wartości mogą być różnych typów i też są obiektami. ponadto samo 'property, value’ będzie bezużyteczne bez dodatkowej informacji – nazwy usługi dla której je znaleźliśmy. poniżej rozwiązanie, zachęcam do zrozumienia – czyli samodzielnych testów:

get-service|%{$sn=$_.name;$_.psobject.members|?{$_.membertype -eq 'property' -and $_.value -eq $true}}|select @{N='ServiceName';E={$sn}},name,value

żeby nie było za łatwo… i tego nie potrafię wyjaśnić – z jakiegoś powodu 'Stopped’ jest traktowany jako $true. fragment wyjścia:

ServiceName Name Value
----------- ---- -----
aciseagent CanStop True
AdobeARMservice CanStop True
AdobeFlashPlayerUpdateSvc Status Stopped
agiptd CanStop True
AJRouter Status Stopped
ALG Status Stopped
ApHidMonitorService CanS... True
ApHidMonitorService CanStop True
AppHostSvc CanP... True
AppHostSvc CanS... True
AppHostSvc CanStop True
AppIDSvc Status Stopped
Appinfo CanStop True
AppMgmt Status Stopped
AppReadiness Status Stopped

… ale już nie chce mi się zagłębiać dalej.

sztuka dla sztuki? niekoniecznie. często trafiam na scenariusz, prostszy niż zaprezentowane, gdzie dostaję obiekt o dużej liczbie parametrów – np. obiekty EXO – i chcę sprawdzić czy gdzieś nie siedzi jakaś wartość, przy czym nie mam pojęcia jak może nazywać się parametr. o ile w ogóle istnienie. np. wyświetlmy wszystkie URI jakie są skonfigurowane dla grupy o365:

PS C:\_scriptZ> (Get-UnifiedGroup -Identity GuestGroupTest).psobject.Members.value|Select-String 'http'

https://outlook.office365.com/owa/?path=/group/GuestGroupTest@w-files.pl/calendar
https://outlook.office365.com/owa/?path=/group/GuestGroupTest@w-files.pl/mail
https://outlook.office365.com/owa/?path=/group/GuestGroupTest@w-files.pl/people
https://outlook.office365.com/EWS/Exchange.asmx/s/GetUserPhoto?email=GuestGroupTest@w-files.pl

to tak w ramach przygotowań do ShareCon365 (; zapraszam na moją sesję!

PS. aahhh… jeśli ktoś czytał z uwagą, to powinien zadać pytanie – „a jakie jeszcze ukryte parametry mają obiekty?„. i jeśli ktoś takie pytanie by zadał, otrzymałby zapewne odpowiedź: „<your-command>|gm -force

eN.

 

 

 

 

zmieniłeś nazwę kanału Teams? możesz go stracić

jest w MS Teams bug – jeśli kiedykolwiek zmieniłeś nazwę kanału, może ci go 'rozpiąć’ od katalogu biblioteki SharePoint. same pliki nie są gubione, można się do nich dostać poprzez widok SharePoint.

problem dodatkowy jest taki, że nie ma jak takiego problemu zaudytować – logi nic nie powiedzą. nie dość, że akcja jest w tle, i po prostu nagle znika kanał na Teams, to nawet samej zmiany kanału się nie zaudytuje, bo logi są max 9o dni a zmiana kanału mogła się wydarzyć dawno – w moim przypadq był to luty O_o

dobre informacje

  • jak zostałem zapewniony, fix będzie wkrótce rolloutowany. nie zmapuje z powrotem rozłączonych katalogów, ale zabezpieczy przed takimi incydentami
  • w private preview jest opcja trzymania logów audytowych przez rok – funkcja ma być dostępna w planie E5 i w jakimś add-onie dla E3. i to jest super wiadomość, bo te 9o dni to stanowczo na mało!

eN.

ruszamy! ITechDay i WGUiSW

koniec sezonu ogórkowego, czas wrócić do nauki!

już jutro 112 WGUiSW – i wracamy do Microsoft, po remoncie siedziby. jak zwykle ciekawi ludzie i tematy – tym razem o Citrix i konfiguracji Windows 1o.

jednak większy 'news’ dotyczy ITechDay 2o19. tym razem po prostu zacytuję:

*************

Warszawska Grupa Użytkowników i Specjalistów Windows (WGUiSW) wraz z Partnerami gorąco zapraszają na kolejną konferencję z cyklu ITechDay.

Tematami wiodącymi będą:

  • rozwiązania chmury publicznej i prywatnej,
  • aspekty gromadzenia i bezpiecznego przechowywania danych,
  • zapewnienie wysokiej dostępności,
  • automatyzacja zadań w środowiskach IT,
  • analiza i ocena zabezpieczeń infrastruktury IT.

Sesje będą odbywały się równolegle na czterech ścieżkach technicznych i poprowadzą je znani prelegenci posiadający bardzo bogate doświadczenie praktyczne poparte wieloma certyfikatami zawodowym.

Patronat honorowy nad wydarzeniem objęło Ministerstwo Obrony Narodowej a Partnerami strategicznymi konferencji są Aruba Cloud, CBSG Polska, CodeTwo, Dell, Eversys, HP Enterprise, GreyCortex, IT Solution Factor, Kingston, Microsoft, Mine Master, MWT Solutions, Narodowe Centrum Bezpieczeństwa Cyberprzestrzeni, QNAP, Palo Alto Networks, Tech Data, Veeam.

Konferencja odbędzie się 17 września 2019r. w siedzibie Wyższej Szkoły Menedżerskiej na warszawskiej Pradze. Udział w konferencji ITechDay będzie bezpłatny.

Informacje o ITechDay dostępne są na stronie internetowej www.ITechDay.pl a aktualności można śledzić na tablicy www.facebook.com/ITechDay.

***********

od siebie dodam, że będę miał zaszczyt prezentować podczas ITD – i to wraz z Pawłem Pławiakiem! ciekawy eksperyment, ponieważ takie sesje we dwóch raczej robi się rzadko i ich przygotowanie jest trudniejsze. jak wyszło – mam nadzieję, ocenicie sami.

eN.