This isn’t the best of examples but I’ll come to that later…
So what is this all about? This is about making the site server do stuff on a client’s behalf.
But the difference from my earlier posts is that now I’ve found a way for the site server to return the outcome, or data, to the client at hand.
This is only a made up scenario.
(The clients don’t have any internet connection at all due to 802.1x (*Not made up*)) The standard status message rules pretty much allows the site server to run scripts like this:
· ReportTeams-TSFailed.ps1 –ComputerName %msgsys
· ReportTeams-TSSucceeded.ps1 –ComputerName %msgsys
My earlier posts allowed a client to send any arguments at all, with any MessageID and whenever you wanted it to, which would allow the site server to run numerous of scripts and do something like this in the middle of a sequence without the need to supply credentials:
· Add-ToCollection.ps1 –ResourceID $resID –CollectionID $colID
· Set-ComputerVariable.ps1 –ResourceID $resID –Variable TSDisableProgressUI –Value $False
· MoveToOU.ps1 – ResourceID $resID –OU $OU
So, again, what is this post all about? The previous scenario only allows one way communications. Client(Get-Command) | Server($_.DoThis)
Imagine what you could do if you could get something back from the Server. Client(Get-Command) | Server($_.DoThis) | Client. :)
Would allow almost everything, and if you need it, you know what to use it for but these are some examples.
Outside of a TS:
(Hooked Setup, unattend.xml and in some cases prestart command)
· Client triggers script on server -> (Get-TimeZoneInfo.ps1) -> Gets answer back. (Set-AndAdjustTime.ps1 $TimeZoneInfo)
· Client triggers script on server -> (Get-MbamTPMInfo.ps1) -> Gets answer back. (Clear-TPM.ps1 $OwnerAuth)
· Client triggers script on server -> (Store_Get-Variable.ps1) -> Client can use a stored (TS)Variable before the TS is initiated after a reboot.
· Client triggers script on server -> (GetBitlockerRecKey.ps1) -> Gets answer back.(Manage-bde -unlock c: -recoverypassword)
Inside of a TS the usefulness depends on your network. Maybe get something from the HW-inventory, topconsoleuser the list of installed applications. In our case we can’t query the AD, run Remote WMI or PSSession, even if we supply credentials. Nor do we have Internet access (802.1x) until the computer is domain joined.
That’s where the actual need arose. Such a small thing as sending a report to Teams, if the TS failed during the WinPE phase, wasn’t even possible.
This is highly experimental and just a POC.
Client Side:
Send-CMMessageRC.ps1:
The httplistener’s address is built this way.
http://$IP:8081/MessageID(Guid)/
I'm also using another script I've made to add firewall rules within WinPE, Create-FireWallRule.ps1.
Every status message generates a MessageID(Guid) and that will make sure that the reply address is somewhat unique even if a client sends multiple messages. MessageID(Guid) and MessageID is not the same thing but have the property name in common.
Just so you know when looking at the scripts.
The template-files (“TemplateName”prop/quals.txt) Contains the default values of the message.
Arguments to the script, eg. –MachineName or -SMS_MessageID will be chosen before what’s in the template files with -ClassName as an exception. $*** -Pointers that will be replaced dynamically by the script.
Server Side:
I know there are easier options for the script triggered on the server (WebbReq2.ps1). Httpclient and webclient just to mention two. But I use TCPClient, on purpose, to make sure that if anyone finds a weakness wont’t be able to make the site server authenticate and reflect its credentials.
WebbReq2.ps1
This is how it's called in the POC.
Results:
The POC will sync the time and timezone of the site server.
So why isn't this the best of examles ?
Well, when the client registers with the MP, before the actual status message is sent, it'll receive a response with both a UTC timestamp and the local time. And besides, running this just as a prestart command isn't enough, the timezone will reset on a reboot.
Side Notes: I will continue to try to send the reply using nothing but the ConfigMgr API, but havn't managed to make it work so far. That beeing said it's at least easier to persuade the network team to open up communications from the site server to the clients than the other way around.
The files of this POC is available on my Github: https://github.com/MattiasC85/TimezonePOC
How to run something on each reboot during WinPE:
https://deploymentresearch.com/Research/Post/528/Fixing-the-ldquo-Failed-to-find-a-valid-network-adapter-rdquo-error-in-ConfigMgr-Current-Branch
Or hooking it even earlier in the setup it self. (needs some TLC and init of the PE-Environment etc)
https://www.windows-noob.com/forums/topic/12150-how-can-i-check-for-network-connectivity-before-starting-a-task-sequence-in-system-center-2012-r2-configuration-manager/
Comments