Configure CRM 2011 and ADFS 2.0 on a single server on port 443
June 21, 2012 31 Comments
Before I start in with the technical bit, a quick review of some terms, the “problem statement” and the alternative solutions before doing this more awkward setup.
You want to deploy CRM 2011 using an “Internet Facing Deployment” (IFD), which in turn must be configured to use a Secure Token Service (STS) such as Active Directory Federations Services (ADFS). Both CRM and ADFS have to be secured with SSL, ie users will connect to them using https.
I’m not going to cover the same ground as has already been detailed in various places about the basics of doing this configuration. The main document to guide you through this installation process for claims based authentication for IFD is on the Microsoft download page along with the implementation guide here:
http://www.microsoft.com/download/en/details.aspx?id=3621
and there a various blog posts and a handy YouTube video to show you how easy this all is. You have two main options to set this up fairly easily:
Install CRM and ADFS on two different servers
By fair the easiest way to configure this with both services using https on port 443 (and using an appropriate certificate). This does mean you have to make sure two separate servers are both highly available (ie don’t fail). While you can install ADFS on pretty much any other server you may not want to do that and expose those servers to the internet at all (especially not something like a domain controller).
If you don’t have another suitable server do you want the outlay for a new server just for ADFS? (even if it is virtualised to avoid the hardware cost, there is still a cost for software licences, including Windows).
Install CRM and ADFS on the same server but on different ports
It is perfectly possible to configure CRM and ADFS to both run on the same web server on different ports. For this setup my preference would be to put CRM on port 443 so users don’t have to remember to add the port number in their URL, and ADFS on another port such as 444 (although the users will be redirected to ADFS and see the port number in the URL, they don’t have to remember this at all).
To do this you need to make sure to add a Windows Firewall rule to allow 444 in to the server in the first place (or whatever third party software you are using). Configure the default web site to use port 444 before installing ADFS and it should all get set up just fine.
The down side of this configuration can be if your users are likely to be using an internet connection where ‘unusual’ ports are not allowed. So if they visit a customer site and are allowed to use a ‘guest’ wireless connection which only allows them to browse to ports 80 and 443, then they won’t be able to reach ADFS and therefore won’t be able to use CRM. If that matters to you, then read on!
The ‘hard’ way – CRM and ADFS on one server, both on port 443
Imagine you don’t have another server you want to / can install ADFS on, other than the CRM server. But you anticipate times your users will not have access to the internet except on standard ports such as 80 and 443. The only option is to install ADFS on the CRM server and configure both to use port 443 (on different IP addresses of course, otherwise they will totally clash, so do make sure you change the bindings in IIS so each is on a single IP which is configured on your server, not just set to “all unassigned”).
The problem is that many people may tell you this can’t be done, and certainly if you just follow the normal configuration steps you will come unstuck. Also, just to be absolutely clear, I am not suggesting this should be the way you usually configure IFD, only a solution when you have the constraints outlined above. Using two servers or two different ports will almost always be easier to set up and troubleshoot.
(Aside: the discussion below is also useful if you installed ADFS on one port and want to switch it to another. Changing the bindings in IIS is definitely not enough on its own, and uninstalling, reinstalling and reconfiguring ADFS is longwinded and still may leave the wrong port being used a well as the right one, so it may come back to bite you later on.)
The problem is that both CRM and ADFS expect to be able to read information about each other’s configuration from a file called FederationMetadata.xml. CRM finds ADFS just fine, and then you add a relying party trust to ADFS and tell it to read from (for example):
https://auth.mydomain.com/federationmetadata/2007-06/federationmetadata.xml
it fails with an error message reading “an error occurred during an attempt to read the federation metadata. Verify that the specified URL or host name is a valid federation metadata endpoint”
The usual test is to then try the URL in a browser instead, but this gives a 503 error “service unavailable”.
You can access CRM at this point using https://internalcrm.mydomain.com (or whatever your server and domain are) but ADFS can’t read the federationmetadata from it. So what is going on?
Reserved URLs
When you install ADFS it actually reserves certain URLs so that requests to these are directed to the ADFS service before it even gets as far as IIS. This is why changing the bindings in IIS from port 443 to 444 (for example) does not work as expected, as that does not change these reservations.
So, firstly let’s take a look at the reservations and then look at changing these to allow CRM to serve the federation metadata file we need. You need to fire up an elevated command prompt (ie one which gives you local admin rights) to make the changes. Start > type “com” and when you see “Windows Command Processor” in the list of applications, right click and choose “Run As Administrator”. Type:
netsh http show urlacl
You will probably see a whole load of reservations, but there are two in particular that relate to ADFS. Since you will want to copy one of these fairly precisely later on, it will make more sense to redirect the output of this command to a text file where you can read and copy things more easily:
netsh http show urlacl > c:\temp\urlacls.txt
Find the one which contains this string:
https://+:443/FederationMetadata/2007-06/
and select and copy it to the clipboard (saves a lot of tricksy typing in a minute). This reservation is the one causing the problem, since the “+” character is a wildcard, so it looks for any URL on port 443 which contains FederationMetadata/2007-06/ – just like the CRM URL we provided when setting up a relying party trust earlier. It is this wildcard which makes this request get redirected not to IIS and the CRM web service but to ADFS itself, and it can’t return the data expected.
Notice also that this reservation has nothing to relate it only to a specific IP address, so even if you configure the default web site to use a given IP before installing ADFS, this does not prevent it from hitting this problem.
Fixing the problem
I have been through various hoops in a vain effort to fix this issue on a recent project, following the advice in various articles which might fix things if they are broken – such as this one which will help if your URLrewrite module is actually missing or corrupt, or if your reservations are there but have errors such as invalid SIDs, but does not really help to ‘fix’ something which is working as it was designed, but that design causes a conflict.
So, step 1 – delete it with this command:
netsh http delete urlacl url=https://+:443/FederationMetadata/2007-06/
(Tip: to paste into a command line you can use the mouse to right click > paste or press Alt+Space together to get a menu, then press E, then P to Edit > Paste)
Now you have deleted the reservation which was getting in the way you could continue to configure your relying party trusts, but now CRM won’t be able to reach ADFS federationmetadata when it needs t. So we need to put it back, but in a more specific format so it no longer has a wildcard and therefore does not conflict with CRM. Go back to your text file and find the entry reading something like:
https://+:443/FederationMetadata/2007-06/ user =”NT Service\adfssrv” listen=Yes delegate=Yes SDDL=D:(A;;GA;;;S-1-5-80-2246541234-21801234-3603974321-117615432-975697654)
and edit it to replace that + wildcard with an explicit URL for your ADFS server such as adfs.contoso.com or sts.yourdomain.com, then copy and past it into a command to add a new reservation (DO NOT just copy and paste the example below, partly because the domain won’t be right, and nor will the fictitious account SID):
netsh http add urlacl url=https://adfs.contoso.com:443/FederationMetadata/2007-06/ user ="NT Service\adfssrv" listen=Yes delegate=Yes SDDL=D:(A;;GA;;;S-1-5-80-2246541234-21801234-3603974321-117615432-975697654)
(if you need to change the port number as well, eg from 444 to 443, this is the command you would do that with, but you will also want to change the other ADFS URL as well
So now you can continue to configure your relying party trust, ADFS can get the federationmetadata from CRM without interference and everything should work.
(Tip: you can shorten some of the commands above by typing netsh http on its own to enter that ‘context’, then start all the commands from the ‘verb’ eg show, delete, add.)
Many thanks to Richard L and Malcolm S for their extra ideas and pairs of eyes, and their patience while I figured all this out on a recent upgrade project. I was very pleased to be able to deliver this in the way we wanted to give the end users the best possible experience of their shiny new CRM 2011 system.
Have you tried this with a single IP but using HTTPS host-headers to distinguish between the sites? Curious to know if that can be made to work…
No, I have not tried doing this with host headers since there are already enough DNS names to worry about for internal URL + one per organisation for external access plus ADFS itself. Also not sure what the impact would be on firewall rules simply forwarding everything through to same IP and port, especially with more ‘active’ devices such as TMG. I was trying to come up with a method that can be followed every time (when needed) and reliably work.
You can’t get round the need for separate URLs for all the CRM organisations for external access, as that is how ADFS determines this is an external logon and prompts for user credentials rather than requesting a Kerberos token for SSO which it does for internal access (where the org is determined by the folder on the end of the URL eg crm.internal.com/MyOrg – if none specified it will redirect to user’s default organisation).
Also, if using https then whatever name is used has to match your certificate, so with multiple names it quickly becomes easier, cheaper and more manageable to use a single wildcard certificate (from an external trusted authority rather than self-signed) for all these services (and possibly others, such as SSRS).
I don’t have a problem with the multiple hostnames – after all that’s what aliases are for – but I dislike having server adaptors with multiple IPs because of other problems that can then bring. It’s a personal thing I guess as there are pros and cons with each…
I agree that it’s a pain that wildcards are STILL not supported in hostheaders in IIS. On the certificate side I beleive that a wildcard (or a SAN cert) is **required** to implement hostheaders with https. (Because IIS needs to decrypt the request from the client to figure out what hostname the client was using in the first place).
I guess it’s unlikey that people trying to do this will have lots of CRM organisations to handle so the number of hostheaders should still be reasonably manageable. I’ll add it to my list of things to try one day…
Thanks for your help Adam.
Thanks for your input! It would be interesting to hear back when you have a chance to test this.
I have seen some reports of issues with multiple server IPs in some virtualised environments (usually older versions of hyper-V, from memory), but was able to use this approach with no problems at all in a recent ESX hosted deployment.
As always, keeping it simple will usually result in better availability of the system and ease of maintenance, troubleshooting and so on. Two separate servers for CRM and ADFS is still probably easier for most deployments.
Pingback: Did You Know, Dynamics CRM & xRM #16 « North52
Adam,
I’m new to CRM but after deploying the server I now want to put it online instead of having internal access only.
I need to know if it is mandatory to have multiple SAN certificate or Wildcard to do this or would it also work with one SAN certificate?
thanks
Short answer is no, you need a certificate which has lots of names on or just a wildcard one since there are so many different URLs you are trying to secure at the same time, for the user to access CRM internally eg myserver.mydomain.com/mycrmorg, or CRM externally mycrmorg.mydomain.com (a different URL), and ADFS eg sts.mydomain.com or adfs.mydomain.com, and for ADFS to talk to CRM at auth.mydomain.com and for third party apps or the Outlook client wizard to talk to at crmdev.mydomain.com. Of course you might have multiple organisations too (eg for dev, test, training, live).
So you could use lots of individual certs for each of these but frankly that seems like too much work. A wildcard is always my preference
Hi…I have wild card certificate which is going to expire on 21st nov,2012.So please tell me what are the steps which I have to follow to to update certificate and ADFS 2.0.
1.Does I have to attached renewed certificate again to default website and CRM website.
2.Does I have to add these entry again to MMC for personal and Trusted certificate.
If Not,then do let me know what are the steps that need to perform as still there are 20 days for certificate expiration.
You will have to import and associate the renewed certificate with your sites, and both CRM server and ADFS will need the public key in the personal store so they can encrypt data to be used at the other end.
As a rule of thumb, a certificate which is actually renewed via a renewal request will work more easily than simply buying a new unrelated one which starts from the end of the previous one.
Hi Adam
I felt compelled to write and thank you for this article as I have been pulling my hair out trying to get an ADFS test bed set up for use with a local network SSL wildcard system. I had been going round in circles with creating new sub domains for sites that had originally been created for the default site in IIS 7.5 on 2008, but was constantly getting the 503 Service Unavailable error. What your article helped prove was what the Microsoft uninstall program for ADFS doesn’t do! It fails to remove the reserved URLs from a server it has been originally installed on as I had moved it from the DC to a stand alone server and kept the sites on the DC. The show urlacl list presented me with a list of reservations that were stopping any ADFS traffic that wasn’t under the default site on the DC and once deleted manually using your instructions above everything sprang into life.
Many, many thanks for sharing your wisdom.
Kind regards
Ian
You’re very welcome, glad it helped!
Thanks for this post Adam. It seems that every time I setup a CRM 2011 IFD I run into a new issue (and learn something new). I have now implemented this a dozen times and this week was the first time we had ADFS and CRM (2 IPs) both on 443 on the same server (not ideal). Your post was very helpful.
Cheers
Nick
Nick, I hope it made your life a little easier than the first time I did this and had to figure it out for myself.
Hello Adam,
Could you please help me here.
I deploy crm 2011 and ADFS2.0 in the same server, using different IP@ with default port 443 for CRM and ADFs. The installation goes successully but I am having issue signing into CRM. When I put CRM URL it redirect to IDFS and give the error :”There was a problem accessing the site. Try to browse to the site again.
If the problem persists, contact the administrator of this site and provide the reference number to identify the problem.
Reference number: 25a92579-8d45-4f4e-b40e-308ab531cb1d ”
When I verify the relying Party Trusts on ADFS,
– Identifiers is pointing on the ASFS URL instead of CRM URL
– Accepted claim all are No required.
It look like my XML file do not have the right contain.
Can you please help here?
Can you go directly to the ADFS federation metadata URL? eg https://adfs.mydomain.com/federationmetadata/2007-06/federationmetadata.xml
What do you see?
Do all your domain names resolve to the correct IPs? (crmserver, adfs, mycrmorg, etc)?
Is the ADFS website (the default site) bound only to one IP and only to https on 443? Likewise CRM? (you should not have multiple IPs, nor “all unassigned”, nor http and https at the same time)
I don’t quite understand what you mean by “Accepted claim all are No required” – can you elaborate?
yes I can itand have the contain of the XML file.
I fixed the issue now by uninstalling ADFS, remove the default URL and reconfigure the binding to point to port 444 instead of port 443.
Reinstall ADFS and setup the relying party trust and now I am pointing to the right site.
So now, I am using only one IP, CRM in port 443 and ADFS in port 444
Everything works fine.
Your post helped me a lot.
Thank you again.
Hello Adam,
I deployed CRM2011 with ADFS and it is working very well inside my organization.
I don’t want to you use IFD, but would like to use CBA to pointed to the public IP.
Can this work that way?
I register the DNS for both CRM and ADFS, but when trying to access the site from outside, ADSF will fail loading. But inside my network CRM will work fine.
Can someone explain the raison why it is failing.
A couple of things to test:
Can you access CRM from your internal network but using the external URL? (if you don’t already have an internal IP address published in your internal DNS for this, edit your hosts file temporarily to test this). You should get redirected to ADFS and prompted for credentials on the form (NOT a pop up windows authentication dialogue)
Can you browse to the ADFS server from outside the LAN? Do you have the right port forwarding rules on your firewall to redirect the request to the right place?
Hello UK, thank you for your reply.
Actually, I fixed the issue. The problem was, my ASA Firewall was blocking ADFS port (444). I opened the port for the specific server and it works fine.
Thank you for getting back to me. Now I am fully operational.
Hi ukcrmguru
I have tried the steps above, but I am seeing slightly different behaviour and wondering if you have any ideas where I’m going wrong.
Before removing the URL ACL for https://+:443/FederationMetadata/2007-06/ I can actually create the Relying Party Trust in ADFS and browse to the CRM federationmetadata.xml file (e.g. https://internalcrm.mydomain.com/federationmetadata/2007-06/federationmetadata.xml) without any error.
However, it looks like the CRM federation metadata URL is actually serving the ADFS federation metadata, because the XML shown in the browser is exactly the same as the ADFS federation metadata and the entityID at the top of the page shows as http://adfs.mydomain.com/adfs/services/trust where I would expect to see https://internalcrm.mydomain.com. In addition, the Relying Party Trust for internalcrm.mydomain.com shows several Relying Party Identifiers such as https://adfs.mydomain.com/… whereas, based on our other ADFS implementations, I would expect to see only 1 Relying Party Identifier of https://internalcrm.mydomain.com.
When I then remove the URL ACL for https://+:443/FederationMetadata/2007-06/ and add it back as https://adfs.mydomain.com:443/FederationMetadata/2007-06/ I can still get to the CRM and ADFS federationmetadata xml in the browser, but both still return the same XML.
If I then restart the AD FS 2.0 Windows Service, the CRM federation metadata now looks correct (i.e. the entityID is now https://internalcrm.mydomain.com/), but the ADFS federation metadata URL returns a 503 service unavailable error.
I can get back to where I was if I remove the URL ACL for https://adfs.mydomain.com:443/FederationMetadata/2007-06/, reinstate it as https://+:443/FederationMetadata/2007, and restart the AD FS 2.0 Windows Service, but at this point I’m pretty stuck!
Have you got any ideas why the URL ACL for https://adfs.mydomain.com:443/FederationMetadata/2007-06/ doesn’t seem to work?
Thanks
Ben
Hey Ben:
Have you got any news for your problem?. eVERY FORUM AND BLOG REDIRECTS TO YOUR POST, but still no details on this exact issue are resolved or answered. I have the same EXACT problem.
Please some help would be greatly aprecciated.
Thanks
Daniel
see my last comment for some possible resolution steps
Firstly, make sure you really need to do this configuration. If you can put ADFS on port 444 it would simplify the whole job. Having said that, you got this far, so try these steps:
Delete the URL ACL for ADFS https://+:443/….. (Ben it looks like you did this already, so skip this).
Add the new URL ACL for ADFS https://adfs.somedomain.com:443/…. (again skip if you did this).
An IISReset is always a good idea at this point (NB: not on a production system when users are working!)
Re-run through the wizard to configure Claims-Based authentication, so that CRM publishes it’s metadata again.
Now check the ADFS metadata URL in a browser again. If it comes up OK, add and configure the relying party for internal access in ADFS.
Now run the IFD config wizard for external access, and then configure ADFS to add and configure the relying party for external access.
Hello UK, thanks for your reply.
Actually the problem is just after the step you mentioned : “Add the new URL ACL for ADFS https://adfs.somedomain.com:443/…. (again skip if you did this).” After doing this, an IISRESET, the ADFS service restarted, the ADFS federation metadata URL returns a 503 service unavailable error.
The requiremnts must be in a single server and on port 443 due to a PROXY server (which is apache http mod-proxy module). We cant use another server. I would really like to know how to debug the issue on why the service cant listen to the urlacl.
Please any help would be greatly aprecciated.
Thanks
Daniel
Hi Adam,
Great post. We’re trying to configure CRM 2013 Claims & IFD but we’re having issues. Would you please take a look and see if there’s anything you can help us with?
I have 2 issues related to CBA and IFD configuration:
1)
http://social.microsoft.com/Forums/en-US/61775cff-bdf7-430b-92c3-67deea42369c/crm-2013-claims-based-authentication-ifd-configuration-errors-help?forum=crmdeployment
2)
http://social.microsoft.com/Forums/en-US/c058804c-8a1d-4a3b-bb3a-c89fec9ea182/http-error-50019-internal-server-error-after-reinstalling-crm-2013-and-browsing-it-in-iis?forum=crmdeployment
Thanks.
ProgCRM
@ProgCRM. Your community post is very long and detailed. At the moment I spotted a few things in there that I would question:
1) you configured CRM to use HTTPS by changing the bindings to use SSL on port 443 (as far as I can tell) and tested this, and it worked
2) you configured ADFS to use port 443 as well – why would you do this? You would be MUCH better off uninstalling ADFS, removing any reserved URL ACL entries and configuring the default website to use port 444 with SSL before installing ADFS. That way you have CRM and ADFS configured for different ports and avoid lots of issue with conflicts
3) Your relying party trust identifiers are completely wrong. When the ADFS config is requesting the federation metadata file from CRM, this should contain a list of CRM URLs (specifically including one for each CRM organisation as for example CRMTest.mydomain.com). The fact that this list is wrong is usually an indication that you have a conflict and the ADFS reserved URL is redirecting the request before IIS or CRM even sees it. By configuring on two different port numbers, you can avoid this issue. Alternatively you have configured CBA incorrectly in deployment manager and used the wrong names there.
4) You used CNAME DNS records. I tend to use A records, but I can’t immediately give you a good reason why CNAMEs would not work, or why one would be better.
5) For your setup on a single server, I cannot see any reason you should need to use SPNs. If you do use them, then you need to set them using Domain Admin privileges (and check for conflicting ones before you do, by listing them). I don’t think the domain functional level (or schema, if you want to call it that) has any bearing here. Also, if I understand correctly, you should register the SPN for the ADFS computername account, not the CRMAppPool account (I see conflicting information about this, but my understanding is that prior to IIS 7, the website was run in the service account context, and since then it uses the local computer account for our purposes here. I am not an IIS expert so this may be wrong, or has been superceded in later versions).
Hi, we have a problem with CRM and ADFS config. They are on one server, and need to use 443 port togother. Now CRM is working on 443, but ADFS is not. Send error message:
A token request was received for a relying party identified by the key ‘https://crm.pannoniaethanol.hu/’, but the request could not be fulfilled because the key does not identify any known relying party trust.
Key: https://crm.pannoniaethanol.hu/
This request failed.
User Action
If this key represents a URI for which a token should be issued, verify that its prefix matches the relying party trust that is configured in the AD FS configuration database.
Encountered error during federation passive request.
Additional Data
Exception details:
Microsoft.IdentityServer.Web.InvalidScopeException: MSIS7007: The requested relying party trust ‘https://crm.pannoniaethanol.hu/’ is unspecified or unsupported. If a relying party trust was specified, it is possible that you do not have permission to access the trust relying party. Contact your administrator for details.
at Microsoft.IdentityServer.Web.FederationPassiveAuthentication.SubmitRequest(MSISRequestSecurityToken request)
at Microsoft.IdentityServer.Web.FederationPassiveAuthentication.RequestBearerToken(MSISSignInRequestMessage signInRequest, SecurityTokenElement onBehalfOf, SecurityToken primaryAuthToken, String desiredTokenType, Uri& replyTo)
at Microsoft.IdentityServer.Web.FederationPassiveAuthentication.RequestBearerToken(MSISSignInRequestMessage signInRequest, SecurityTokenElement onBehalfOf, SecurityToken primaryAuthToken, String desiredTokenType, MSISSession& session)
at Microsoft.IdentityServer.Web.FederationPassiveAuthentication.BuildSignInResponseCoreWithSerializedToken(String signOnToken, WSFederationMessage incomingMessage)
at Microsoft.IdentityServer.Web.FederationPassiveAuthentication.BuildSignInResponseCoreWithSecurityToken(SecurityToken securityToken, WSFederationMessage incomingMessage)
at Microsoft.IdentityServer.Web.FederationPassiveAuthentication.BuildSignInResponseForProtocolRequest(FederationPassiveContext federationPassiveContext, SecurityToken securityToken)
at Microsoft.IdentityServer.Web.FederationPassiveAuthentication.BuildSignInResponse(SecurityToken securityToken)
Oh sorry, crm version is 2013, and ADFS 2.0 🙂
Sorry, but I think I will find it hard to figure out your very specific error without knowing what you have configured and how, what steps you have taken to troubleshoot this, what you have checked etc.
This is my blog, not a support forum. You might be better off posting in one of the many forums available for such things that will have a much wider viewing audience and are designed for the back and forth that will almost certainly be required to fix this.
This is a hell of an impressive post. Thank you very much!
Not sure if you face similar situation, but from time to time ADFS restores the https://+:443/FederationMetadata/2007-06/ reservation breaking the Relying Party Monitoring between CRM and ADFS.
Is there any way to avoid this situation?
Regards,
Abreu.
@Daniel I have not seen that happen. I can’t see why it would do that unless you reinstall ADFS, or perhaps applying a windows update to it might have the same effect. Don’t forget, the best advice is NOT to run CRM and ADFS on the same port, but use eg port 444 or 4433 for ADFS to avoid all possible conflicts.