# Powershell remote script execution pattern

On a CredSSP enabled server is a .psm1 script file that gets executed remotely from a client technology. The client passes in a couple execution parameters and the server script returns an object back to the client. This works great but the pattern I've implemented feels clunky. Is there room for improvement?

Client code calling remote server script:

$firstStanza=@{ a = "Mary had" b = "a little" c = "lamb" }$secondStanza=@{
d = "its fleece"
e = "was white"
f = "as snow"
}

$scriptBlock = { Param([Parameter(Mandatory=$true)]$param1,[Parameter(Mandatory=$true)]$param2) Import-Module C:\CreateNewObject.psm1 CombineBothStanzas -firstStanza$param1 -secondStanza $param2 }$bothStanzasCombined = Invoke-Command -ComputerName serverName.internalDomain.com -ScriptBlock $scriptBlock -ArgumentList$firstStanza,$secondStanza Write-Output$bothStanzasCombined


Contents of remote script on server c:\CreateNewObject.psm1:

function CombineBothStanzas {
Param([Parameter(Mandatory=$true)]$firstStanza,[Parameter(Mandatory=$true)]$secondStanza)
return ($firstStanza +$secondStanza).GetEnumerator() | sort -Property name
}


Remote server script operation returns this object to the client:

Name                           Value
----                           -----
b                              a little
c                              lamb
d                              its fleece
e                              was white
f                              as snow


A couple of things I see, if it is as simple as you suggest. First is the $using: context, where you can use local variables in remote execution. For example, you could remove the parameters from your scriptblock, and not have to pass arguments to the Invoke-Command call by doing this: $scriptBlock = {
Import-Module C:\CreateNewObject.psm1
CombineBothStanzas -firstStanza $using:firstStanza -secondStanza$using:secondStanza
}


Second is that if your .psm1 file has but one purpose, and that is a singular function, why not just make it a script with parameters? Then you don't have to first import it then execute it.

Contents of remote script on server c:\CreateNewObject.ps1:

Param([Parameter(Mandatory=$true)]$firstStanza,[Parameter(Mandatory=$true)]$secondStanza)
return ($firstStanza +$secondStanza).GetEnumerator() | sort -Property name


Putting both of those into use, you end up with something like:

$firstStanza=@{ a = "Mary had" b = "a little" c = "lamb" }$secondStanza=@{
d = "its fleece"
e = "was white"
f = "as snow"
}

$scriptBlock = { . C:\CreateNewObject.ps1 -firstStanza$using:firstStanza -secondStanza $using:secondStanza } Invoke-Command -ComputerName serverName.internalDomain.com -ScriptBlock$scriptBlock

• Thank you. That is a much more straight-forward approach. – Neville Dec 19 '17 at 18:43