Active IQ Unified Manager Discussions
Active IQ Unified Manager Discussions
So it seems simple to find some high level WFA talks and examples, but I can't seem to find anything where some detail or more complex tasks are discussed in the last few years. The few dar files that seem inline with my question which I have dug up won't import to 4.0 because they are so old.
I'm simply looking on how to setup a command that will invoke an external ps1 script with a var being passed to it.
Any examples or insight would greatly be appreciated.
Thanks
Hi there,
Yes it's absolutely possible to have WFA call external powershell scripts and pass parameters to those scripts.
Here is a very basic example and framework that can be used to achieve that.
Create a directory structure within the WFA install directory. EG
For example here is a simple script that will accept a hostname as an input parameter, attempt to ping that hostname and write the output to log file by date in the scripts directory:
Save the code below as:
<%wfa_install_path%>\Scripts\PowerShell\PingHostName\PingHostName.ps1
param( [Parameter(Mandatory=$True, HelpMessage="The hostname or IP address of the system to ping.")] [String]$HostName ) #'------------------------------------------------------------------------------ #'Initialization Section. #'------------------------------------------------------------------------------ [String]$scriptPath = Split-Path($MyInvocation.MyCommand.Path) [String]$scriptSpec = $MyInvocation.MyCommand.Definition [String]$scriptBaseName = (Get-Item $scriptSpec).BaseName [String]$scriptName = (Get-Item $scriptSpec).Name [String]$isoDate = Get-Date -uformat "%Y-%m-%d" [String]$scriptLogSpec = $scriptPath + "\" + $isoDate + ".log" #'------------------------------------------------------------------------------ #'Ping the hostname and write the output to a file by date in the scripts directory. #'------------------------------------------------------------------------------ ping $HostName | Out-File -FilePath $scriptLogSpec #'------------------------------------------------------------------------------
Now create a WFA command as follows (I called the command "invoke_powershell_script"). EG
param( [Parameter(Mandatory=$True, HelpMessage="The hostname or IP address to pass as a parameter to the script.")] [String]$HostName, [Parameter(Mandatory=$True, HelpMessage="The name of the script to run within the '\Scripts\PowerShell\<scriptname>' folder in the WFA installation directory.")] [String]$ScriptName ) #'--------------------------------------------------------------------------------- #'Read the WFA installation Path from the registry. #'--------------------------------------------------------------------------------- [String]$registryPath = "hklm:\system\currentcontrolset\services\na_wfa_srv"; Try{ [System.Object]$result = Get-ItemProperty -Path $registryPath -ErrorAction Stop [String]$wfaPath = $result.ImagePath.Split("/")[0].Trim() -Replace("""", "") Get-WFALogger -Info -Message "Read registry path ""$registryPath""" }Catch{ Get-WFALogger -Error -Message $("Failed Reading Registry Path ""$registryPath"". Error " + $_.Exception.Message) Throw "Failed Reading Registry Path ""$registryPath""" } #'--------------------------------------------------------------------------------- #'Check the format of the registry key value as it changes between WFA versions. #'--------------------------------------------------------------------------------- #' <= WFA 3.0 = "C:\Program Files\NetApp\WFA/bin/NA_WFA_SRV.exe" //RS//NA_WFA_SRV #' >= WFA 3.1 = "C:\Program Files\NetApp\WFA\bin\NA_WFA_SRV.exe" //RS//NA_WFA_SRV #'--------------------------------------------------------------------------------- If(($wfaPath.SubString($wfaPath.Length - 3, 3)) -eq "WFA"){ [String]$installPath = $wfaPath }Else{ [String]$wfaBinPath = $wfaPath.SubString(0, $wfaPath.LastIndexOf("\")) [String]$installPath = $wfaBinPath.SubString(0, $wfaBinPath.LastIndexOf("\")) } Get-WFALogger -Info -Message "Enumerated WFA installation Path from Registry key ""$registryPath"" as ""$installPath""" #'--------------------------------------------------------------------------------- #'Ensure the script exists in the WFA install path. #'--------------------------------------------------------------------------------- [String]$scriptFolder = $scriptName.Split(".")[0] [String]$scriptSpec = "$installPath\Scripts\PowerShell\$scriptFolder\$scriptName" If(-Not(Test-Path -Path $scriptSpec)){ Throw "The file ""$scriptSpec"" does not exist" } #'--------------------------------------------------------------------------------- #'Invoke the script in the WFA install path. #'--------------------------------------------------------------------------------- [String]$command = "powershell.exe -ExecutionPolicy Bypass -File ""$scriptSpec"" -HostName $HostName" Try{ Invoke-Expression -Command $command -ErrorAction Stop Get-WFALogger -Info -Message "Executed command`: $command" }Catch{ Get-WFALogger -Error -Message $("Failed executing command`: $command. Error " + $_.Exception.Message) Throw "Failed executing command`: $command" } #'---------------------------------------------------------------------------------
Add the WFA command to a WFA workflow and execute it as follows.
Note: I used an an enum type for the "ScriptName" parameter so you can add other scripts into a list of scripts to run against the hostname. EG:
When you run the run the workflow you enter a hostname and WFA will call the external powershell script and pass the hostname parameter to it. EG
Then check the workflow logs to verify the execution status and note the highlighted command it ran:
Then if you check the <%wfa_install_path%>\Scripts\PowerShell\<%ScriptName%> directory you will find a log file by date created by the external powershell script (called by WFA) containing the ping results for the hostname. EG:
<%wfa_install_path%>\Scripts\PowerShell\<%ScriptName%>dir /b 2016-09-27.log PingHostName.ps1 <%wfa_install_path%>\Scripts\PowerShell\<%ScriptName%>type 2016-09-27.log Pinging cluster1.testlab.local [192.168.100.2] with 32 bytes of data: Reply from 192.168.100.2: bytes=32 time<1ms TTL=255 Reply from 192.168.100.2: bytes=32 time<1ms TTL=255 Reply from 192.168.100.2: bytes=32 time<1ms TTL=255 Reply from 192.168.100.2: bytes=32 time<1ms TTL=255 Ping statistics for 192.168.100.2: Packets: Sent = 4, Received = 4, Lost = 0 (0% loss), Approximate round trip times in milli-seconds: Minimum = 0ms, Maximum = 0ms, Average = 0ms
Whilst I realise this is a very "hello world" type of example the concept is meant to give you some ideas of the possibilities and provide a framework for using WFA to call external powershell scripts that you can expand on. Hope that helps?
/Matt
Hi,
Also keep in mind that any external script that is called by WFA will be executed within the security context of the account that the WFA server services are running as (by default local system) which has no network access. Therefore if you want your external script to be able to interact with networked systems then consider using an Active Directory service account to run the WFA services as and ensure that this account is a local administrator account on your WFA server. EG:
Note: the WFA server services are configured to logon as an Active Directory user. The WFA AD service account is a member of the local administrators group
C:\>net localgroup administrators Alias name administrators Comment Administrators have complete and unrestricted access to the computer/domain Members ------------------------------------------------------------------------------- Administrator TESTLAB\Domain Admins TESTLAB\srv_netapp_wfa The command completed successfully.
/Matt
Hi Acrux:
Just wanted to know why you want to call a PS script from WFA and not execute
the PS script as a command in WFA.
There are plenty of workflows available at http://automationstore.netapp.com/home.shtml.
If you have already seen it, you can ignore.
Regards
Abhi