Forum Discussion
Post to external web page
I am new to F5 systems. I am trying to find the best way to take the contents of a session veriable (session.server.initial_req_body) SAML payload, decrypt it and POST it to an external URL
Any assistance appreciated.
Thanks
5 Replies
- Kevin_Stewart
Employee
A few considerations:
-
Are you looking at AuthnRequest or AuthnResponse SAML payload?
-
I'm assuming you're the IdP in this case? If so, is the SP/RP sending the request via GET or POST?
-
By "external", do you mean some service that isn't a pool member? For the purpose of some non-SAML validation of the content?
-
- Doug_129661
Nimbostratus
Kevin This is a SAML payload but we are the SP in this case. It is a post form the IDP In this case the SAML is not being used for SSO it is to get data in the payload to us. I do have the external server in the pool but being a newbie I am not sure of the best way to make the post to the web server.
- Kevin_Stewart
Employee
Okay, so if I understand this, you need to take some value from the SAML assertion (consumed by your APM SP configuration), and then POST it to a downstream server. Is that correct? If so, then the decoded/decrypted assertion should already be in the session table under session.saml.last.assertion, as well as individual assertion values in the session.saml.last. namespace. Do you need the whole thing or just a specific value?
The next question then is how to send that data to the web server. Is the application expecting a POST as the first request? If so, then you'd need to reformat the incoming GET request (after policy evaluation) to a POST and add the new payload. Would you need to do this more than once?
- Kevin_Stewart
Employee
This one was a little tricky, but I think I have something that'll work. The biggest issues were that 1) after the APM SP consumes the assertion, it redirects back to the originally requested URI, which is a GET request, 2) the only way to change a GET to a POST is to replace it in the TCP payload (HTTP::method is read-only), and 3) you cannot simply capture the TCP payload and replace the GET with a POST and add the payload, because APM still needs to be able to see the session cookie on ingress. Here's what I have:
when ACCESS_ACL_ALLOWED { if { [ACCESS::session data get session.saml.last.sent] == "" } { ACCESS::session data set session.saml.last.sent 1 ACCESS::respond 302 Location "[ACCESS::session data get session.server.landinguri]" "Set-Cookie" "SAMLASSERT=true; path=/; secure" "Connection" "Close" } } when CLIENTSSL_HANDSHAKE { SSL::collect } when CLIENTSSL_DATA { if { [SSL::payload] contains "SAMLASSERT" } { set mrhsession [findstr [SSL::payload] "MRHSession=" 11 ";"] set assertion "SAMLResponse=[b64encode [ACCESS::session data get -sid $mrhsession session.saml.last.assertion]]" regsub -all -nocase "GET" [SSL::payload] "POST" newdata regsub -all -nocase "Cookie:" $newdata "Content-Type: application/x-www-form-urlencoded\r\nContent-Length: [string length $assertion]\r\nCookie:" newdata1 SSL::payload replace 0 [SSL::payload length] "${newdata1}$assertion" SSL::release } SSL::release } when HTTP_RESPONSE { if { [info exists mrhsession] } { unset mrhsession HTTP::header insert "Set-Cookie" "SAMLASSERT=false; path=/; expires=Tuesday, 29-Mar-1970 00:15:00 GMT;" } }Here's the idea:
-
The ACCESS_POLICY_COMPLETED event redirects the user back to the original URI. Once there, the ACCESS_ACL_ALLOWED event is triggered for each subsequent request. This event looks for a special session value, and if it doesn't exist (the first time through), sets it, and then generates a redirect to itself with a new cookie (SAMLASSERT). The added Connection: Close header guarantees that the next request will start a new TCP session.
-
Because this is presumably SSL data, I'm using the CLIENTSSL_HANDSHAKE and CLIENTSSL_DATA events instead of CLIENT_ACCEPTED and CLIENT_DATA to first capture the payload and then evaluate it for the cookie.
-
If the request contains the SAMLASSERT cookie, I grab the MRHSession cookie from the request and use that to fetch the SAML assertion data from the session table. I then change the GET to POST, add POST-specific headers (Content-Length and Content-Type), and then add the base64-encoded SAMLResponse payload, being careful not to touch the APM session token.
-
On first HTTP response after the GET/POST transformation, the mrhsession variable exists, so I delete that variable and the SAMLASSERT cookie to prevent a loop.
This generates a POST request to the original URI and inserts the SAMLReponse payload data. Because I'm forcing the client to return via redirect to start a new TCP session, I needed something that the client would relay, like a cookie or URI. I had originally chosen a URI trigger, but then switched to a cookie so that the client wouldn't see any of the magic. This POST request only happens once (at the first request), so the application needs to be able to consume the SAML payload and react accordingly.
This was also developed with APM as both IdP and SP, so your mileage may vary.
-
- praque_135655
Nimbostratus
Hi, i could not able to get the SAML token using HTTP::PAYLOAD or HTTP::Collect.
usecase: 1) Enter the url IDP url http://xmppt.airservices.eds.com:8080/iam/code.asp
2) Siteminder challenges the user( enter credentials)
3) Internally page invoked the SSO service and grap the saml token from html body and post it to the saml assertion consumer(http://usclspcim021.airservices.eds.com/affwebservices/public/saml2assertionconsumer).
http://xmppt.airservices.eds.com/affwebservices/public/saml2sso?SPID=service_provider&ProtocolBinding=urn:oasis:names:tc:SAML:2.0:bindings:HTTP-POST
Can i achieve the functionality using F5 Version 10.2.2?
My usecase also same like above usecase. Please help me on this
- Praque
Help guide the future of your DevCentral Community!
What tools do you use to collaborate? (1min - anonymous)Recent Discussions
Related Content
* Getting Started on DevCentral
* Community Guidelines
* Community Terms of Use / EULA
* Community Ranking Explained
* Community Resources
* Contact the DevCentral Team
* Update MFA on account.f5.com