URL Rewriting for user-friendly URLs with Dynamics CRM 2011

Anyone who has attempted to configure Dynamics CRM 2011 with an Internet-Facing Deployment (IFD) knows that it is no trivial task. Where there are blog posts that discuss setting up an IFD, and Microsoft documentation for configuring the IFD, they often assume that ADFS and Dynamics CRM are installed on the same server, and that there is only one Dynamics CRM front-end server. Unfortunately, real-world implementations don’t always follow that.

For example, take the following configuration:

  • a Dynamics CRM front-end server on the internal network, providing services to internal clients
  • a Dynamics CRM front-end server in an Internet-facing zone, providing services to external clients
  • a separate ADFS server accessible to internal and external clients

Dynamics CRM with IFD requires a combination of ADFS relaying party trusts and DNS configuration to get things working. One caveat with IFDs is that the internal and external host names for the Dynamics CRM front-end servers must be different because, externally, the host name includes the CRM organization name. Where, internally, you may have https://icrm.contoso.com/crm, externally you would have https://crm.contoso.com.

Let’s flesh out our sample implementation and requirements:

  • icrm.contoso.com is our internal Dynamics CRM front-end server, accessible only on the internal network
  • ecrm.contoso.com is our external Dynamics CRM front-end server, accessible to our internal network and the public Internet
  • adfs.contoso.com is our ADFS server, accessible to our internal network and the public Internet
  • We have two Dynamics CRM organizations: CRM and CRM-Test.
  • We want our internal and external (public Internet) clients to access CRM using the same URLs: crm.contoso.com and crm-test.contoso.com. In other words, we don’t want the two-URL problem outlined above.

The last bit has nothing to do with Dynamics CRM: it is all done in IIS. Let me explain how.

IFD Host Names and DNS Configuration

In order to get Dynamics CRM configured for the IFD, your internal DNS and external DNS must be set as needed to allow internal and external clients to resolve to all Dynamics CRM and ADFS host names.

One poorly-documented part of the IFD setup is what the host names should point to in the Internet Facing Deployment Configuration Wizard. The Discovery Web Service Domain (something like dev.contoso.com) and the “external domain where your Internet-facing servers are located” (something like auth.contoso.com) must both resolve to a Dynamics CRM front-end server, not the ADFS server. Be sure to set up these host names to resolve to your internal/external Dynamics CRM servers.

So, in our sample environment, our internal and external DNS has the following entries:

  • contoso.com zone:
    • icrm (internal DNS only)
    • ecrm (internal and external DNS)
    • adfs (internal and external DNS)
    • auth (internal and external DNS, points to icrm internally and ecrm externally)
    • dev (internal and external DNS, points to icrm internally and ecrm externally)
    • crm (internal and external DNS, points to ecrm internally and externally)
    • crm-test (internal and external DNS, points to ecrm internally and externally)

The DNS configuration, if wrong, at best, will break your IFD, and at worst break all access to Dynamics CRM, so be sure to get it right. If you get it right, and you configure the IFD right, your setup would work as follows:

This unfortunately is not what we want. Instead, we want our users to use the external client domains whether they are internal or external. To do this requires no change to Dynamics CRM; rather, the solution is through Internet Information Services (IIS).

Rewriting URLs with IIS

Here’s what happens with the above configuration:

  1. User enters https://crm.contoso.com or https://crm-test.contoso.com in their browser.
  2. The request is sent to the internal Dynamics CRM server, icrm.contoso.com.
  3. Dynamics CRM calls ADFS to get credentials for the user.
  4. ADFS can’t resolve the user’s credentials, because the host name is not known to ADFS.
  5. User can’t access Dynamics CRM.

Here’s what needs to happen:

  1. User enters https://crm.contoso.com or https://crm-test.contoso.com in their browser.
  2. The request is sent to the internal Dynamics CRM server, ecrm.contoso.com.
  3. IIS and the URL Rewrite module running on ecrm.contoso.com examine the request and identifies it as coming from an internal client (by IP address).
  4. If the request is coming from an internal client, IIS redirects the client to https://icrm.contoso.com/crm or https://icrm.contoso.com/crm-test.
  5. Everything else works as expected.

URL Rewriting rules live in the web.config file in the Dynamics CRM installation directory (by default, C:\Program Files\Microsoft Dynamics CRM\CRMWeb). Open this file and add the following to the <rules> section.

<rule name="Redirect Internal Connections" stopProcessing="true">
<match url="(.*)" />
<conditions trackAllCaptures="true">
<add input="{REMOTE_ADDR}" pattern="192\.168\.&#91;0-9&#93;{1,3}\.&#91;0-9&#93;{1,3}" />
<add input="{HTTP_HOST}" pattern="(&#91;^\.&#93;*)\.(.*)" />
</conditions>
<action type="Redirect" url="https://icrm.contoso.com/{C:1}/{R:1}" appendQueryString="true" redirectType="Found" />
</rule>

The only changes you need to make to the above are:

  1. Change the regular expression pattern in the REMOTE_ADDR line to match your internal IP addresses. (Google has a nice tool to help with this.)
  2. Change the url in the Redirect line to match the host name of your internal Dynamics CRM server.

Do that, test it extensively (internally and externally), and then tell your users that the one URL they use to access Dynamics CRM is the only one they need to remember.

0 thoughts on “URL Rewriting for user-friendly URLs with Dynamics CRM 2011

  • This is a brilliant way to understand and learn more about the awesome list of features and functions of Dynamics CRM. Now it is much easier to configure, extend and implement the product according to your needs and specifications for an easy crm management.

  • Thanks for this great article, very useful. I am just wondering does that redirect rule should be prior the other 3 ADFS default rules? I guess so but that’s new for me.

    Regards,
    Christian

  • Sorry for the last post. It turned out to be a regexp issue. Now the issue is that child links are not being resolved for some reason. RequestURL = “” in the failed request log. Page appears blank.

  • There is a little bug with this, which you may want to look out for. Our organization name is “CRM”. Our Regex detected URLs starting with CRM, and redirected them. On the external server, this broke reporting, because reports call a URL “crmreports.aspx”. Tweaking the regex fixed it.

    In other words: be sure to test everything! 🙂

  • Phil Farnsworth says:

    trackallcaptures above requires url rewrite 2.0.

    Under Server 2008 R2, url rewrite 2.0 breaks dyanmics completely. Subsequently you’ll get a 403/404 or 500 error. Uninstalling url rewrite 2.0 doesn’t solve the problem, subsequent to removal of urlrewrite 2.0 you’ll get an error “The requested page cannot be accessed because the related configuration data for the page is invalid.” out of the original web.config file.

    There appears to be something else that you are doing to get this to work.

  • Phil Farnsworth says:

    I’m sure that you do, but it appears you did something else in your configuration to get it to work. If I take a clean IFD install of dynamics and apply URL Rewrite 2.0 to it, and change nothing else, dynamics breaks.

    Just FYI.

    Thanks.

  • ChristianV says:

    Why not use multiple ADFS relaying parties?
    That is one for the internal (icrm.domain.com) and one for the organization (external: org.domain.com)?

    The ADFS form will only be provided for the external org.domain.com while AD SSO is used on the internal.

  • Andreas Meyer says:

    Hi,
    this seems to be an interesting post.
    However, we face a more difficult situation. The environment and also the DNS is divided in Intranet (.xxx) and Internet (.yyy), let’s say .net and .com. Certificates govern these Zones. We cannot call .net-URLs from .com, neither .com-URLs from .net.
    The CRM-Server must reside somewhere and naturally lies in the .net (the internal) zone.
    Consequently from inside we cannot use IFD at all. Since any call – coming from a .net-place – to a .com-URL is blocked by the certificate which is an internal policy which I cannot overrule.
    The only thing we could do is two bindings to the CRM-site, one with https (for .com) and one with http for .net.
    This would work if it weren’t for the E-Mail-Router. The E-Mail-Router of course is on the CRM internal server, so coming from .net. Since IFD is configured it tries to authenticate as it must do and then tries to call the .com-configuration (for https is configured for the outside internet). This naturally is blocked by the certificate again.
    I do not see any way around this. Do you?
    With your example domain every host comes from the same domain name (contoso.com), so there is no such problem.
    We have ReverseProxies which could tunnel the traffic. But this doesn’t work either because the crucial URLs for the discovery web service (web) and also for auth cannot be routed since the CRM-Server tells the client these URLs on application level upon first contact. The ReverseProxy cannot touch and reroute application level information (osi-7) but only information from the transportation level (Osi-3). So the client gets the URL and then unpacks it and shouts it into the net from whereever it is at.
    We are here at our wits end and Microsoft most likely won’t budge.
    Are separate DNS-zones for Intranet and Internet so uncommon?
    I just wonder.
    Do you have any ideas?

    Regards
    Andreas

  • Andreas — not sure how to advise. As it is, I think Microsoft did a poor job of engineering this part of CRM; the fact that everything is so dependent on URLs, and the URLs differ based on configuration (IFD or internal), and you can’t have both, and the simple process of configuring an IFD is complicated, makes me cringe. It could have been so much easier.

    My suggestion would be to open a ticket with Microsoft and see what can be done. I was lucky to have gotten a very good ADFS engineer who helped me set up the IFD. As good as he was, he did say that some things simply can’t be done. It may be that the only “easy” way to handle on-premises CRM is to assume 100% internal or 100% external access, and configure accordingly.

  • Sudhanshu Sahoo says:

    Hi,

    thanks for posting such designed descriptions.
    just need to ask one things, when you have installed MS CRM in internet and intranet side, you must have used the same DB. so here have you used the SPN to manage the URLs for CRM for the different App serevres for CRM.

    i mean i can have 2 CRM servers(iCRM01 and iCRM02) with NLB in Intranet and also 2(eCRM01,eCRM02) on internet as NLB.
    So i ll install crm in iCRM01 1st with new instance. then i ll install in iCRM02 with considering existing instance.
    Also i ll do the same things for eCRM01 and eCRM02 with existing instance.
    but my question is, how the webservices URL and CRM URL will be managed for the iCRM02 and eCRM01/02? is it by using SPN or how?

    Your inputs will be really helpful.

    Tons of thanks in advance.

    Regards,
    Sudhanshu

  • Thanks, Brian.
    So is your scenario covers the Internet and Intranet scenario as described in the MS Planning Doc?
    if anytime is come your way as my scenario, plz post here. many ppl are looking for it..

    regards,
    sudhanshu

  • Hi Brian,

    I tried what you listed in the post, but no luck.
    When I make the above changes to the web.config neither my internal nor my external addresses work. I get 500 – Internal server error. Our internal network is 10.10.1.1-254 so I used: pattern=”\b(?:10)\.(?:10)\.([?:10])\.([0-9]{1,3})\b”
    We have crm.domain.com:444 and internalcrm.domain.com:444 and I would love to use just crm.domain.com:444

    Any help or insight would be greatly appreciated.
    Dede

  • Hi Brian,

    We have a similar problem, but we have only one CRM server for internal and external access and one ADFS Server.

    What change we have to make to the configuration explained here?

    Best Regards
    Rodrigo

  • It should work the same even if you have one CRM server, assuming your internal users can access it using both the “internal format” URL (org name after the slash) and the “external format” URL (org name as a subdomain). Just put the rules on the one server.

  • Hi Brian,

    I took you example and extended it to also redirect internal URLs to external URLs when a users try to access an internal URL from outside the network.

    Thanks for your very informative post.

    Regards,
    Alan.

  • @alano, thanks for extending this solution and covering those use cases — there is definitely a need to ensure internal URLs work externally, as well!

  • We run with crm 2015 and i also wanted to use our external url available as the internal used url.
    I added the rewrite rule, but it just gives an error 500 internal server error.

    We have an internal address of 192.168.14.32 – 192.168.14.192, but to test i used the following pattern rule: pattern=”192\.168\.14\.[0-9]{1,3}
    and as rewrite, https://crmi.internal.domain/crmrbcgroup/{C:1}/{R:1}

    I need to add the extra groupname otherwise the redirect will go to the wrong organisation name

    What else can i do ?

    Also, i believe the eventual pattern should be something like: 192\.168\.14\.(19[0-2]|1[0-8][0-9]|[4-9][0-9]|3[2-9])

    Is this correct to cover our internal addresses ?

  • I managed to get things running.

    The complete rewrite rule must be added as first option, also if you have an url like groupname.domain.com this is split up by the {HTTP_HOST} pattern into parts {C:0}, {C:1} and {C:2} where c:0 is the complete url, c:1 is the first name before the first ‘.’, e.g groupname and c:2 is the rest after the first ‘.’ e.g domain.com.

    so my problem where i nedded to add my groupname was allready resolved in the rewrite rule by the option {C:1} added after the internal url.

    I also had the problem when running this rule that there was around 8 times my groupname was added (in an loop i think) to the eventual rewritten url. e.g https://internal.url/groupname/groupname/groupname etc.
    I resolved this by changing the match url into “https://(.*)”

    To make thing easier to understand i installed the following add-on into IIS (on my windows 2012 server where CRM was installed) http://www.iis.net/downloads/microsoft/url-rewrite

    This adds the option in IIS manager to have an gui to the rewrite rules and also an option to test the various match conditions where an internal url must comply to before the rewrite rule kicks in.
    For the remote address pattern (regex) i found an tool at the following link: http://www.regexmagic.com/manual/xmppatternipv4.html which helps to calculate the needed rules.

    Hope this helps more people in the rewrite rules 🙂

  • We recently run into url problem on our CRM 2013 on premise with Windows server 2012 and ADFS 3

    We had to do the same thing, IT stakeholders were concerned about any kind of overload on server due to the redirect.

    Can you suggest if this issue has been solved in a better way with CRM 2013 or can we explain what implications this rewrite can cause and shall we be cautious about any performance or connectivity issues ?

  • The rewrite should not cause any overload. Consider this:

    * A redirect one request to a different URL results in one extra request to the server (i.e. the request to the new URL).
    * A request to a typical CRM page results in about 150 requests to the server (for HTML, JavaScripts, images, etc.).

    So, the overhead of a redirect is nothing compared to the overhead of Dynamics CRM in general.

Leave a Reply to brian Cancel Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes:

<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

This site uses Akismet to reduce spam. Learn how your comment data is processed.