PET  Computer Science degree (FWLIW)  6 years as a Unix device driver then app developer in C then C++  Started with Citrix (WinFrame) in 1995  Invented & wrote what is now Ivanti Application Control (was AppSense Application Manager)  150+ “useful” scripts on GitHub  Mostly write PowerShell, and other languages, for software vendors  Available for hire (hourly or daily) – code reviews, workshops, training, …
dirty, lazy code hoping you will come back to it someday – you won’t!  Error handling from the get-go  Don’t hard code anything  Make it a parameter with a default value  Or define as a variable near the top of the script  Set-StrictMode –Version Latest (when developing/testing, not in script itself)
happens if …  Check return codes/values  $?  -PassThru  Try/catch  (Script) Users do the stupidest things – code for it, don’t assume sanity  How could this be misused by a bad actor?  Will this work in another language?  Nobody would be stupid enough to … yes, they would  Protect credentials, secrets, etc  SecureString & PSCredendtial types  Azure Key Vault  Is this date/time local or UTC ?  Parameter validation – ValidateRange, ValidateSet, ParameterSetName, check
knows or remembers everything  If they say they do they are either deluded or an idiot or both  Surely I can’t be the first person to have/want to write something like this?  If you use someone else’s code, give credit in your code & socials  And check it isn’t accidentally/deliberately malicious (test, test, test (not in prod))  Don’t get disheartened if it doesn’t work first time or make silly mistakes  Law of diminishing returns – know when to quit/seek help  Throwing time at a problem is no guarantee of success – take a break
going, not once every few months  Personal projects – I find them relaxing & fulfilling (I’m old & sad)  But don’t save 10 minutes by spending 10 days on it – balance!  Troubleshoot & administer via PowerShell not GUI, e.g. event logs  Live in PowerShell
on the PS command line rocks!  History (Get-History or alias h) makes rinse & repeat easy  Ctrl r to search history (requires persistent user profile)  F2 toggles in line/list mode in pwsh 7.x  If running an exe, see if there is a native PS way (think objects!)  ipconfig.exe -> Get-NetIPConfiguration (alias gip)  icacls.exe -> Get-ACL & Set-ACL  Eat your own dog food aka run your own scripts & fix/improve  If it runs in cmd but not PS, work out why rather than admit defeat  Special characters  Quotes  Ctrl z/y, ctrl home/end, ctrl backspace/delete (Get-PSReadLineKeyHandler)
error, get the hell out of Dodge (abort! abort!)  But do you need to expose the actual error?  Can you script around it?  Can you output a link for more information/fix/workaround ?  Write-Warning instead ?  Don’t try/catch an exception & just output “there was an error”  $ErrorActionPreference = ‘SilentlyContinue’ – NO!!!  -ErrorAction SilentyContinue –ErrorVariable thisSpecificError  Try/catch with comment if ignoring exception (check it’s expected exception)
compile  Unless protecting IP & methods are not always 100% secure  Don’t be embarrassed  Likelihood of something similar is usually high – why reinvent the wheel?  Ask the community for feedback  Accept suggestions, improvements & criticism graciously
identifiers – no $i or $pw  Tab completion so length/brevity doesn’t matter & decreases tpyo [sic] risk  Set-StrictMode –Version Latest (when developing/testing, not in script itself)  Comments but allow code to be self-documenting as much as possible  PowerShell Approved Verbs – Verb-Noun for functions  Spaces are not evil – embrace the space  No cmdlet/function aliases  No parameter abbreviations  No positional parameters & use non-abbreviated named ones (tab complete)  Use parameters, with defaults, not variables that need editing in script
 Don’t use Write-Host unless you really, really have to  Output helpful information with Write-Verbose so can be silenced without changing code  But use breakpoints in ISE or VS Code for debugging  Be careful with Write-Output if your script outputs objects – pipeline pollution  Write-Debug can be useful but watch for it prompting to continue  Use Write-Progress cautiously as can slow execution massively  Write-Information ??  Redirection of individual streams useful to separate them out (N>file)
it copies the existing array to new  Hashtables (aka dictionaries) are great for caching  Keep loops lean & mean – evaluate as much outside as possible  Outputting objects in a loop & assigning to variable can be quicker  Beware pipeline pollution  Beware Where-Object on large arrays  Hashtable instead  BinarySearch method of Generic collections if they are sorted  Consider using runspaces for parallelisation  Jobs can be slow  ForEach-Object –Parallel in pwsh 7.x