When designing web applications becomes extremely sophisticated, CI/CD is keeping accelerating and supporting and troubleshooting is every day more challenging and complex, talking about webservers seems completely old fashioned, Well… I don’t think so. Let me explain!
Web development, Networking, Security are still moving targets, but webservers are still a key component for the delivery of our content.
Focusing on implementing scripting and automation to improve one of these: web development tools, testing, network operations, security… can have a positive impact on making more meaningful use of your time and your energies.
Internet Information Service
On a Windows Server, the default choice for a Web Server is Internet Information Services ( IIS), it is extensible and has a rich user interface that makes it easier to configure it. If we think of all .Net web app, Sharepoint, Dynamics CRM, etc… well IIS the common denominator webserver!
Let’s see how popular is IIS
Have a look at some stats from we can see that IIS is still popular https://w3techs.com/technologies/details/ws-microsoftiis/all/all
Installing IIS with a oneliner
To install on a Windows Server with a powershell (run as administrator) oneliner without even opening Server Manager :
1 |
Install-WindowsFeature -Name Web-Server -IncludeAllSubFeature -IncludeManagementTools |
Let’s Look at the alternatives
I love the versatility, organisation, and modularity and the large number of options offered by apache or nginx and I like being able to manage them or duplicate the text format of the configuration of webservers or simply compare them with a diff command. Of course, there is the risk of complicating things along the way is always there.
How I change my approach to IIS and why
Where the CLI helped me a lot in the past, with powershell or netsh.exe, is not just for configuration, but mainly for management or simple troubleshooting purposes. So I’ve started to threat IIS as the same way I approach other webservers like apache and nginx, regardless of the difference is that treating the tool via its configuration and not via the UI helped me out to find errors and automating checks and mitigations.
Some surprises moving from the UI to the CLI
Where automation shows more options but can also be the ins and outs of the tool with possible issues.
If you stop a website from the UI, you’re not just setting the website but you’re at the same time setting the “SERVERAUTORESTART” to $False, and if you’re starting the website to start that property is set to $True. So from the UI, as far as I know, these settings will always be tightly/strongly coupled.
The result is that the expectation from start and stop operations from the CLI of having the same behavior, well is wrong. Some of us would say that is not a BUG, it’s a FEATURE!
I like that the CLI is giving a more granular control and options, but if you’re not testing it properly you’ll get caught by a really bad surprise at the next reboot.
For this reason, my logical approach is checking the expected state before and after the execution of my tasks and logging the steps and the states of my system to be able to rewind and analyze it if needed and something goes wrong.
That’s the IIS Administration blog
https://blogs.iis.net/iisteam/introducing-iisadministration-in-the-powershell-gallery
WebAdministrations VS IIS Administration
What module to use to manage IIS via PowerShell? Good question. The older module has more than double the cmd-lets. The choice seems obvious, but it’s maybe the wrong one.
1 2 3 4 5 6 7 8 9 |
Compare the number of cmd let PS IIS:\Sites> (Get-Command -module webadministration ).count 79 PS IIS:\Sites> (Get-Command -module iisadministration ).count 34 |
I came across this article https://docs.microsoft.com/en-us/iis/get-started/whats-new-in-iis-10/iisadministration-powershell-cmdlets and I started using iisadministrator and considering to gradually replacing the webadministrator module.
Webadministration Module
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 |
Get-Command -module webadministration CommandType Name Version Source ----------- ---- ------- ------ Function IIS: 1.0.0.0 WebAdministration Cmdlet Add-WebConfiguration 1.0.0.0 WebAdministration Cmdlet Add-WebConfigurationLock 1.0.0.0 WebAdministration Cmdlet Add-WebConfigurationProperty 1.0.0.0 WebAdministration Cmdlet Backup-WebConfiguration 1.0.0.0 WebAdministration Cmdlet Clear-WebCentralCertProvider 1.0.0.0 WebAdministration Cmdlet Clear-WebConfiguration 1.0.0.0 WebAdministration Cmdlet Clear-WebRequestTracingSetting 1.0.0.0 WebAdministration Cmdlet Clear-WebRequestTracingSettings 1.0.0.0 WebAdministration Cmdlet ConvertTo-WebApplication 1.0.0.0 WebAdministration Cmdlet Disable-WebCentralCertProvider 1.0.0.0 WebAdministration Cmdlet Disable-WebGlobalModule 1.0.0.0 WebAdministration Cmdlet Disable-WebRequestTracing 1.0.0.0 WebAdministration Cmdlet Enable-WebCentralCertProvider 1.0.0.0 WebAdministration Cmdlet Enable-WebGlobalModule 1.0.0.0 WebAdministration Cmdlet Enable-WebRequestTracing 1.0.0.0 WebAdministration Cmdlet Get-WebAppDomain 1.0.0.0 WebAdministration Cmdlet Get-WebApplication 1.0.0.0 WebAdministration Cmdlet Get-WebAppPoolState 1.0.0.0 WebAdministration Cmdlet Get-WebBinding 1.0.0.0 WebAdministration Cmdlet Get-WebCentralCertProvider 1.0.0.0 WebAdministration Cmdlet Get-WebConfigFile 1.0.0.0 WebAdministration Cmdlet Get-WebConfiguration 1.0.0.0 WebAdministration Cmdlet Get-WebConfigurationBackup 1.0.0.0 WebAdministration Cmdlet Get-WebConfigurationLocation 1.0.0.0 WebAdministration Cmdlet Get-WebConfigurationLock 1.0.0.0 WebAdministration Cmdlet Get-WebConfigurationProperty 1.0.0.0 WebAdministration Cmdlet Get-WebFilePath 1.0.0.0 WebAdministration Cmdlet Get-WebGlobalModule 1.0.0.0 WebAdministration Cmdlet Get-WebHandler 1.0.0.0 WebAdministration Cmdlet Get-WebItemState 1.0.0.0 WebAdministration Cmdlet Get-WebManagedModule 1.0.0.0 WebAdministration Cmdlet Get-WebRequest 1.0.0.0 WebAdministration Cmdlet Get-Website 1.0.0.0 WebAdministration Cmdlet Get-WebsiteState 1.0.0.0 WebAdministration Cmdlet Get-WebURL 1.0.0.0 WebAdministration Cmdlet Get-WebVirtualDirectory 1.0.0.0 WebAdministration Cmdlet New-WebApplication 1.0.0.0 WebAdministration Cmdlet New-WebAppPool 1.0.0.0 WebAdministration Cmdlet New-WebBinding 1.0.0.0 WebAdministration Cmdlet New-WebFtpSite 1.0.0.0 WebAdministration Cmdlet New-WebGlobalModule 1.0.0.0 WebAdministration Cmdlet New-WebHandler 1.0.0.0 WebAdministration Cmdlet New-WebManagedModule 1.0.0.0 WebAdministration Cmdlet New-Website 1.0.0.0 WebAdministration Cmdlet New-WebVirtualDirectory 1.0.0.0 WebAdministration Cmdlet Remove-WebApplication 1.0.0.0 WebAdministration Cmdlet Remove-WebAppPool 1.0.0.0 WebAdministration Cmdlet Remove-WebBinding 1.0.0.0 WebAdministration Cmdlet Remove-WebConfigurationBackup 1.0.0.0 WebAdministration Cmdlet Remove-WebConfigurationLocation 1.0.0.0 WebAdministration Cmdlet Remove-WebConfigurationLock 1.0.0.0 WebAdministration Cmdlet Remove-WebConfigurationProperty 1.0.0.0 WebAdministration Cmdlet Remove-WebGlobalModule 1.0.0.0 WebAdministration Cmdlet Remove-WebHandler 1.0.0.0 WebAdministration Cmdlet Remove-WebManagedModule 1.0.0.0 WebAdministration Cmdlet Remove-Website 1.0.0.0 WebAdministration Cmdlet Remove-WebVirtualDirectory 1.0.0.0 WebAdministration Cmdlet Rename-WebConfigurationLocation 1.0.0.0 WebAdministration Cmdlet Restart-WebAppPool 1.0.0.0 WebAdministration Cmdlet Restart-WebItem 1.0.0.0 WebAdministration Cmdlet Restore-WebConfiguration 1.0.0.0 WebAdministration Cmdlet Select-WebConfiguration 1.0.0.0 WebAdministration Cmdlet Set-WebBinding 1.0.0.0 WebAdministration Cmdlet Set-WebCentralCertProvider 1.0.0.0 WebAdministration Cmdlet Set-WebCentralCertProviderCredential 1.0.0.0 WebAdministration Cmdlet Set-WebConfiguration 1.0.0.0 WebAdministration Cmdlet Set-WebConfigurationProperty 1.0.0.0 WebAdministration Cmdlet Set-WebGlobalModule 1.0.0.0 WebAdministration Cmdlet Set-WebHandler 1.0.0.0 WebAdministration Cmdlet Set-WebManagedModule 1.0.0.0 WebAdministration Cmdlet Start-WebAppPool 1.0.0.0 WebAdministration Cmdlet Start-WebCommitDelay 1.0.0.0 WebAdministration Cmdlet Start-WebItem 1.0.0.0 WebAdministration Cmdlet Start-Website 1.0.0.0 WebAdministration Cmdlet Stop-WebAppPool 1.0.0.0 WebAdministration Cmdlet Stop-WebCommitDelay 1.0.0.0 WebAdministration Cmdlet Stop-WebItem 1.0.0.0 WebAdministration Cmdlet Stop-Website 1.0.0.0 WebAdministration |
IISAdministration Module
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 |
Get-Command -module iisadministration CommandType Name Version Source ----------- ---- ------- ------ Cmdlet Clear-IISCentralCertProvider 1.1.0.0 iisadministration Cmdlet Clear-IISConfigCollection 1.1.0.0 iisadministration Cmdlet Disable-IISCentralCertProvider 1.1.0.0 iisadministration Cmdlet Disable-IISSharedConfig 1.1.0.0 iisadministration Cmdlet Enable-IISCentralCertProvider 1.1.0.0 iisadministration Cmdlet Enable-IISSharedConfig 1.1.0.0 iisadministration Cmdlet Export-IISConfiguration 1.1.0.0 iisadministration Cmdlet Get-IISAppPool 1.1.0.0 iisadministration Cmdlet Get-IISCentralCertProvider 1.1.0.0 iisadministration Cmdlet Get-IISConfigAttributeValue 1.1.0.0 iisadministration Cmdlet Get-IISConfigCollection 1.1.0.0 iisadministration Cmdlet Get-IISConfigCollectionElement 1.1.0.0 iisadministration Cmdlet Get-IISConfigElement 1.1.0.0 iisadministration Cmdlet Get-IISConfigSection 1.1.0.0 iisadministration Cmdlet Get-IISServerManager 1.1.0.0 iisadministration Cmdlet Get-IISSharedConfig 1.1.0.0 iisadministration Cmdlet Get-IISSite 1.1.0.0 iisadministration Cmdlet Get-IISSiteBinding 1.1.0.0 iisadministration Cmdlet New-IISConfigCollectionElement 1.1.0.0 iisadministration Cmdlet New-IISSite 1.1.0.0 iisadministration Cmdlet New-IISSiteBinding 1.1.0.0 iisadministration Cmdlet Remove-IISConfigAttribute 1.1.0.0 iisadministration Cmdlet Remove-IISConfigCollectionElement 1.1.0.0 iisadministration Cmdlet Remove-IISConfigElement 1.1.0.0 iisadministration Cmdlet Remove-IISSite 1.1.0.0 iisadministration Cmdlet Remove-IISSiteBinding 1.1.0.0 iisadministration Cmdlet Reset-IISServerManager 1.1.0.0 iisadministration Cmdlet Set-IISCentralCertProvider 1.1.0.0 iisadministration Cmdlet Set-IISCentralCertProviderCredential 1.1.0.0 iisadministration Cmdlet Set-IISConfigAttributeValue 1.1.0.0 iisadministration Cmdlet Start-IISCommitDelay 1.1.0.0 iisadministration Cmdlet Start-IISSite 1.1.0.0 iisadministration Cmdlet Stop-IISCommitDelay 1.1.0.0 iisadministration Cmdlet Stop-IISSite 1.1.0.0 iisadministration |
https://docs.microsoft.com/en-us/powershell/module/webadministration/?view=win10-ps
SCALING OUT IIS
Scaling out to multiple IIS web servers is possible with some feature like IIS shared configuration settings, central certificates store that powershell made easier to perform, I will link to some example that replicates what I’ve done sometimes from the UI via powershell and make it cleaner and easier to reproduce programmatically.
Where I can start scripting? What is the first step script?
If you’re passionate about security, well there are infinite possibilities…, but simple wikis (https://docs.microsoft.com/en-us/previous-versions/windows/it-pro/windows-server-2008-R2-and-2008/dd450371(v=ws.10) ) or https://www.owasp.org/index.php/Hardening_IIS are a good place to start.
Why don’t start from a github or book?
Today, I found this interesting GitHub repository of Thomas Lee AKA DoctorDNS and he is the author of this book, the foreword is by Jeffrey Snover and the book title is Window Server 2019 Automation with PowerShell. I haven’t read the book, but I’ve read the code snippet and the book content seems interesting and also to cover a lot of ground.
The author seems to abuse of hash tables, but except these minor things that are my personal preference… there are a lot of interesting examples that can be reused and useful for everybody.