Closed PrzemyslawKlys closed 2 years ago
Hey @PrzemyslawKlys,
for Get-PodeWebUsername
and $WebEvent
these only exist/work when dealing with a web request; when just creating a the elements/layouts these will always return $null
as they're no request to handle.
A -ScriptBlock
is something I've got noted down to add onto New-PodeWebTexbox
, so the value can be generated during a request - not on server start.
Here though, you can get around that by building the New-PodeWebSteps
within the Page's scriptblock - this will build the elements on the fly during a request, rather than once on server start, and the $WebEvent
will be available within the Page's scriptblock:
Start-PodeServer -StatusPageExceptions Show {
Add-PodeEndpoint -Address 127.0.0.1 -Protocol Http
Enable-PodeSessionMiddleware -Duration 120 -Extend
Add-PodeAuthIIS -Name 'IISAuth'
New-PodeLoggingMethod -Terminal
# set the use of templates, and set a login page
Use-PodeWebTemplates -Title 'Administrative Requests' -Theme Dark -NoPageFilter
Add-PodeWebPage -Name 'Admin 1' -Icon 'Settings' -ArgumentList $EmailParameters -ScriptBlock {
param($EmailParameters)
New-PodeWebSteps -Name 'AddUser' -ArgumentList $EmailParameters -Steps @(
New-PodeWebStep -Name 'Details' -Icon 'User-Plus' -Content @(
New-PodeWebTextBox -Name 'Please provide ID' -Type Text -Value $WebEvent.Auth.User
New-PodeWebTextbox -Name 'FirstName' -Type Text -Value (Get-PodeWebUsername)
)
) -ScriptBlock {}
}
}
^ That should do the trick. Also worth noting that Add-PodeAuthIIS
doesn't return the user object inline. The return is handled within Pode's middleware, and it's the user object set as $WebEvent.Auth.User
:)
(also, I removed -Sessionless
as here you'll definitely want sessions. Sessionless is mostly just for REST APIs where authentication doesn't require a session)
Doesn't seem to work. Had to remove argument list from Add-PodeWebpage, but still no user is shown in textbox.
Start-PodeServer -StatusPageExceptions Show {
Add-PodeEndpoint -Address 127.0.0.1 -Protocol Http
Enable-PodeSessionMiddleware -Duration 120 -Extend
Add-PodeAuthIIS -Name 'IISAuth'
New-PodeLoggingMethod -Terminal
# set the use of templates, and set a login page
Use-PodeWebTemplates -Title 'Administrative Requests' -Theme Dark -NoPageFilter
Add-PodeWebPage -Name 'Admin 1' -Icon 'Settings' -ScriptBlock {
param($EmailParameters)
New-PodeWebSteps -Name 'AddUser' -ArgumentList $EmailParameters -Steps @(
New-PodeWebStep -Name 'Details' -Icon 'User-Plus' -Content @(
New-PodeWebTextBox -Name 'Please provide ID' -Type Text -Value $WebEvent.Auth.User
New-PodeWebTextbox -Name 'FirstName' -Type Text -Value (Get-PodeWebUsername)
)
) -ScriptBlock {}
}
}
Oh wow, Add-PodeWebPage
doesn't have an ArgumentList! 😱 Well, that... needs adding!
That will need to be added to make it function properly (or set the email parameters using the [shared state]()). For IIS, try doing Add-PodeAuthMiddleware -Name 'IISAuth' -Authentication 'IISAuth'
just after Add-PodeAuthIIS
- That could do it, as right now the auth method has been created, but hasn't been bound to anything as middleware for use. Usually Set-LoginPage would do this, expect in this case there's not really any need for the login page.
I just resolved Kerberos authentication/impersonation issues using Domain Account and Group Managed Service Account
Wrong settings in documentation!
web.config file:
<configuration>
<location path="." inheritInChildApplications="false">
<system.webServer>
<handlers>
<remove name="WebDAV" />
<add name="aspNetCore" path="*" verb="*" modules="AspNetCoreModuleV2" resourceType="Unspecified" />
<remove name="ExtensionlessUrlHandler-Integrated-4.0" />
<add name="ExtensionlessUrlHandler-Integrated-4.0" path="*." verb="*" type="System.Web.Handlers.TransferRequestHandler" preCondition="integratedMode,runtimeVersionv4.0" />
<remove name="ExtensionlessUrl-Integrated-4.0" />
<add name="ExtensionlessUrl-Integrated-4.0" path="*." verb="*" type="System.Web.Handlers.TransferRequestHandler" preCondition="integratedMode,runtimeVersionv4.0" />
</handlers>
<modules>
<remove name="WebDAVModule" />
</modules>
<aspNetCore processPath="pwsh.exe" arguments="C:\tools\Pode\server.ps1" stdoutLogEnabled="true" stdoutLogFile="C:\tools\Pode\logs\stdout" hostingModel="OutOfProcess" />
<security>
<authorization>
<remove users="*" roles="" verbs="" />
<add accessType="Allow" users="*" verbs="GET,HEAD,POST,PUT,DELETE,DEBUG,OPTIONS" />
</authorization>
</security>
</system.webServer>
</location>
<system.web>
<identity impersonate="false" />
</system.web>
<system.webServer>
<validation validateIntegratedModeConfiguration="true" />
<security>
<authentication>
<windowsAuthentication useKernelMode="true" useAppPoolCredentials="true" />
</authentication>
</security>
</system.webServer>
</configuration>
Import-Module Pode
Import-Module Pode.Web
Start-PodeServer -StatusPageExceptions Show {
# add a simple endpoint
Add-PodeEndpoint -Address localhost -Port 443 -Protocol Https
# set the use of the pode.web templates
Use-PodeWebTemplates -Title 'Example' -Theme Dark
# add the page
Add-PodeWebPage -Name Processes -Icon Activity -Layouts @(
New-PodeWebChart -Name 'Top Processes' -Type Bar -AutoRefresh -AsCard -ScriptBlock {
Get-Process |
Sort-Object -Property CPU -Descending |
Select-Object -First 10 |
ConvertTo-PodeWebChartData -LabelProperty ProcessName -DatasetProperty CPU
}
)
Add-PodeAuthIIS -Name 'IISAuth' -Sessionless
Add-PodeRoute -Method Get -Path '/test-kerberos' -Authentication 'IISAuth' -ScriptBlock {
Write-PodeJsonResponse -Value @{ User = $WebEvent.Auth.User }
}
Add-PodeRoute -Method Get -Path '/test-kerberos-impersonation' -Authentication 'IISAuth' -ScriptBlock {
[System.Security.Principal.WindowsIdentity]::RunImpersonated($WebEvent.Auth.User.Identity.AccessToken, {
$newIdentity = [Security.Principal.WindowsIdentity]::GetCurrent() | Select-Object -ExpandProperty 'Name'
Write-PodeTextResponse -Value "You are running this command as the server user $newIdentity"
})
}
}
### Configuration steps for _Domain Account_:
1. Create Domain Users in AD for Pode AppPool - **Pode.Svc**
2. Create SPNs:
``` cmd
setspn -d HTTP/PodeServer Contoso\pode.svc
setspn -d HTTP/PodeServer.Contoso.com Contoso\pode.svc
New-ADGroup -Name "Pode Authorized Hosts" -SamAccountName "pode.hosts" -GroupScope Global
New-ADServiceAccount -Name "gmsaPodeSvc" -DnsHostName "PodeServer.Contoso.com" `
-ServicePrincipalNames "host/PodeServer", "host/PodeServer.Contoso.com","http/PodeServer", "http/PodeServer.Contoso.com" `
-PrincipalsAllowedToRetrieveManagedPassword "pode.hosts"
Set-ADAccountControl -Identity gmsaPodeSvc$ -TrustedForDelegation $true -TrustedToAuthForDelegation $false
Add-ADGroupMember -Identity "pode.hosts" -Members "iis1$","iis2$"
Restart-Computer -ComputerName "iis1","iis2" -force
Add-WindowsFeature RSAT-AD-PowerShell
Install-ADServiceAccount gmsaPodeSvc
Hey @ittchmh,
This write-up is amazing! The IIS settings in the documentation are more for simple IIS setups to get going. It would be great to have the above in the IIS hosting docs for more complex IIS/Kerberos setups, would you want to update the docs with the above under like an "Advanced Kerberos" heading? :)
Sure, will do
Oh wow,
Add-PodeWebPage
doesn't have an ArgumentList! 😱 Well, that... needs adding!That will need to be added to make it function properly (or set the email parameters using the shared state). For IIS, try doing
Add-PodeAuthMiddleware -Name 'IISAuth' -Authentication 'IISAuth'
just afterAdd-PodeAuthIIS
- That could do it, as right now the auth method has been created, but hasn't been bound to anything as middleware for use. Usually Set-LoginPage would do this, expect in this case there's not really any need for the login page.
Hello, by setting:
Add-PodeAuthMiddleware -Name 'IISAuth' -Authentication 'IISAuth'
Kerberos authentication doesn't work, it is switching to basic NTLM
How to enable Kerberos authentication with Pode.Web ? Please help!
I added Set-PodeWebHomePage
and Kerberos auth now works, but $WebEvent.Auth
is null
WWW-Authenticate: Negotiate HTTP Header set, means $WebEvent.Auth
must be populated with logged in user data, but it's not
Get-PodeState -Name "pode.web.auth"
-eq $null as well
Here is the code:
Import-Module Pode.Web
Import-Module AWS.Tools.Route53 -UseWindowsPowerShell
# . .\Setup.ps1
# . ~\Documents\PowerShell\Modules\SR-Azure\AzureCredsFunctions.ps1
Start-PodeServer -StatusPageExceptions Show {
Import-PodeModule -Name ActiveDirectory
Import-PodeModule -Name Microsoft.PowerShell.SecretManagement
Import-PodeModule -Name AzFilesHybrid
Import-PodeModule -Name ExchangeOnlineManagement
Import-PodeModule -Path 'C:\Users\gmsaAdmin$\Documents\PowerShell\Modules\SR-Azure\SR-Azure.psm1'
Connect-AzAccount -ApplicationId $DefaultAzAccount.ApplicationId -TenantId $DefaultTenantId -CertificateThumbprint $DefaultAzAccount.CertificateThumbprint -SubscriptionId $DefaultSubscriptionId
$Global:CacheExpired = $null
New-PodeLoggingMethod -File -Name 'errors' | Enable-PodeErrorLogging -Levels Error, Warning, Informational, Verbose
# add a simple endpoint
Add-PodeEndpoint -Address localhost -Port 80 -Protocol Http -Name Admin
Enable-PodeSessionMiddleware -Duration 120 -Extend
Add-PodeAuthIIS -Name 'IISAuth' -Groups @("mgm") # -Sessionless
Add-PodeAuthMiddleware -Name 'IISAuth' -Authentication 'IISAuth'
# set the use of the pode.web templates
Use-PodeWebTemplates -Title 'SR Admin' -EndpointName Admin
Import-PodeWebStylesheet -Url '/my-styles.css'
New-PodeWebNavLink -Name "Projects" -Id "Project" -Url "/pages/projects"
Set-PodeWebHomePage -Layouts @(
New-PodeWebHero -Title 'Welcome!' -Message 'This is the home page' -Content @(
New-PodeWebText -Value '$WebEvent.Auth value is:' -InParagraph #-Alignment Center
New-PodeWebCodeBlock -Value $($WebEvent.Auth | ConvertTo-Json -Depth 10)
New-PodeWebText -Value 'Get-PodeWebUsername output' -InParagraph
New-PodeWebCodeBlock -Value $(Get-PodeWebUsername | ConvertTo-Json -Depth 10)
)
)
}
If the authentication is being done by IIS, then Pode shouldn't affect the authentication via IIS 🤔 a little strange if it is somehow, causing the NTLM check, not too sure how though.
For $WebEvent.Auth
, at the point the elements are being created $WebEvent
won't exist. -Layouts
creates the elements there and then on server start, and not in the scope of a request; which is why they'll be null/empty. Add-PodeWebPage
has a -ScriptBlock
parameter which creates the elements dynamically, but within the scope of a request; so $WebEvent
will exist:
Add-PodeWebPage -Name 'Example' -ScriptBlock {
New-PodeWebHero -Title 'Welcome!' -Message 'This is the home page' -Content @(
New-PodeWebText -Value '$WebEvent.Auth value is:' -InParagraph #-Alignment Center
New-PodeWebCodeBlock -Value $($WebEvent.Auth | ConvertTo-Json -Depth 10)
New-PodeWebText -Value 'Get-PodeWebUsername output' -InParagraph
New-PodeWebCodeBlock -Value $(Get-PodeWebUsername | ConvertTo-Json -Depth 10)
)
}
Set-PodeWebHomePage
doesn't have the -ScriptBlock
yet, something that needs to be added.
Add-PodeWebPage -Name 'Example' -ScriptBlock {
Works! thanks
I was testing using Add-PodeWebPage -Name 'Example' -Layouts @(
, so that's why it was epmty
I was able to enable Kerberos Authentication by adding parameter -Authentication to Set-PodeWebHomePage
function
And setting $auth
variable like this:
https://github.com/ittchmh/Pode.Web/commit/4a70ed5ef526372c53dd08ac552e8627ccad483c
I am adding code to set state, but those states are visible only on other Pages and not visible on HomePage
I see good objects in exported Export-Clixml
Files authdata.xml
and authprops.xml
after HomePage opened
So it is probably because Set-PodeWebHomePage
need -ScriptBlock
parameter
And function like Initialize-PodeWebIISAuth
to set states and authentication property to all Add-PodeRoute
functions
I know it sounds noobish but I'm trying to get information who is the person filling up the form and whatever I do I can't get it to work. I tried Get-PodeWebUserName, $WebEvent.Auth.User and nothing is being displayed. I have IIS with Windows Auth enabled. Any tip what I'm doing wrong?