Why has Apple’s integrated architecture kept winning – and will it continue?

There’s a question I’ve never been able to answer about Clayton Christensen’s theory of disruption and Apple’s iPhone, which seems to be an anomaly to which the theory doesn’t apply. But recently, I’ve had some ideas that may explain why Christensen’s brilliantly successful theory fails to explain the iPhone’s continued success.

In a recent podcast, Benedict Evans, a partner at Andreessen Horowitz, mentioned the iPhone’s integrated architecture in a reference to two new features in iPhone 6s – 1) new 3D touch feature announced for coming iPhone 6s, which allows the phone to respond differently depending on how hard the user presses on the touchscreen, and 2) the way the screen lights up to act as a flash if the user is taking a selfie with the front-facing camera in the dark.

After discussing the difficult engineering involved in making these capabilities possible, Evans made the following comments: “that’s much more difficult for an Android OEM to do because Apple controls the operating system and all the apps as well … that’s just a structural advantage Apple has” (3:00). “it is about that integration as well, it’s about the making the whole thing, and it’s really hard to do that when you’re not in that position. (5:44). “So Apple made a chip to give you a better flash to take better selfies. Think about the kind of hardware/software integration that’s involved to do that. (6:08).

The iPhone has an integrated architecture

It’s common knowledge that Apple doesn’t make its own parts for the iPhone (for example, see this teardown report on an earlier model). However, the product’s architecture is still what Christensen would refer to as “integrated”, as opposed to “modular”. The critical difference is in whether the specifications for the parts and the interfaces between parts (including the operating system) are proprietary or broadly standardized. Imagine a phone that is designed to utilize a standard 4-inch touchscreen that could come from any number of manufacturers who produce this stock part. The 4-inch screens from these manufacturers are built with a standardized interface that allows their screens to work with any phone that adheres to the interface specifications. This is called a modular architecture – the product is designed in a way that allows any screen that meets the standard specifications to be plugged into the phone.

The iPhone is not like this – although Apple doesn’t make the components for the iPhone itself, it requires many of the parts to be manufactured to a proprietary specification, and works with its manufacturing partners to design those specifications specifically to give the iPhone the best possible performance.

It’s worth noting that the distinction between “integrated/proprietary” and “modular” is not always clean-cut. Phones that would be considered modular, on the one hand, may contain some parts that are specifically designed for that phone, while its operating system is an open standard that any hardware maker can build phones around and the bulk of its parts are commodity parts designed to that standard. Conversely, I believe that there are a handful of commodity components included in the iPhone’s build as well. The iPhone has a proprietary architecture, though, inasmuch as its operating system is a proprietary standard, and the key components in the phone are designed and built specifically to meet the specifications in that standard.

Disruption theory says integrated architectures should fail

In their book The Innovator’s Solution, Clayton Christensen and Michael E. Raynor describe the way market forces can shape a market’s value chain, determining the types of firms that can prosper in the market. I’ll give a [sort of] quick summary of their argument. Christensen and Raynor assert that as markets mature, the basis of competition changes. [1] A firm that was successful in obtaining customers and earning attractive profits in the past may find that it can no longer do so, and wonder what changed. That firm may feel that it has somehow lost its competitive edge, it may talk about refocusing on its “core competency”, or pursue any number of other misguided strategies to right its course, but if it doesn’t understand the change in the basis of competition in the market(s) in which it operates, none of these things will fix the problems.

Christensen & Raynor argue that in a market’s early days, the basis of competition is almost always functionality and reliability (which they refer to as the product’s “performance” – an abbreviation we’ll continue to use here). They offer the personal computer as a simple example. [2] In the early days of the personal computer market, functionality and reliability were inferior to customer expectations. Sitting at a computer and trying to do something was frustrating, because the computer was slow and hard to use. Notwithstanding its superior ability to do the things that it could do, a typical customer found the performance of the product to be “not good enough”. [3] Therefore, in this phase of the market’s maturity, the dominant firms were those who could make the computers with the best performance in functionality and reliability. This is the pattern of any emerging market space – the products are not yet good enough to meet the basic expectations of the users, and so, assuming all other parts of their business are managed well, those who can get the closest to performance expectations can obtain market share and demand attractive profits in the market.

How does a firm create a product with superior performance? Christensen & Raynor argue that, for a number of reasons, an integrated architecture is essential for a product to perform better than its competitors in these early days of a new market. By managing the entire end to end production of the product and all of its components and subsystems, a company can ensure that its product achieves the best possible performance. In the early days of the personal computer market, this integrated player was Apple Computer, which made computers that “were easier to use and crashed much less often” than computers made by firms with less integrated architectures for their products. [4]

Disruption theory says products with modular architectures should eventually overtake those with integrated architectures

The other choice, instead of having an integrated architecture, is to have a modular architecture – where the design and manufacturing of a product’s subsystems are outsourced to other firms who specialize in producing that one component. The subsystems from these different firms are then built into the final product. In the early market days when no product in the market has performance that is good enough, these firms cannot deliver a product that is competitive with the integrated product. Interfaces between subsystems are not yet standardized, and more importantly, the non-integrated product doesn’t have the integrated product’s ability to milk performance out of every subsystem through its proprietary architecture.

However, there comes a time when the market matures so that the functionality and reliability of the products are more than good enough to meet the expectations of customers – or in other words, there is a “performance surplus”. In this stage of the market, “customers are happy to accept [performance improvements], but they are unwilling to pay a premium price to get them”. [5] At this point, the basis of competition changes. Since any firm in the market can make a product with performance that is good enough to meet the expectations of customers, performance is no longer the essential thing that a firm must do to obtain customers and earn attractive profits.

Christensen and Raynor argue that, at this stage, the new basis for competition becomes the ability to give the customer what they want, when they want it – in other words, speed to market and the ability to customize the products for customers. Microsoft, Intel, Dell, Gateway, Word Perfect, Lotus, and others were the victors in this stage of the personal computer market. By developing a product with a modular architecture, these specialized firms were able to offer a greater spread of product configuration choices for customers, and could even offer computers built according to customer specifications. Upgrades could happen more quickly, because subsystems could be upgraded without necessitating change in other subsystems. In this stage of the market, Apple’s integrated architecture meant slower upgrades and fewer choices. It “became a competitive liability”. [6]

This shift in the basis of competition can happen more than once. It can shift from functionality and reliability (i.e. “performance”) to speed to market and customization, and then back to functionality and reliability, or to something else. With these thoughts in mind, let’s look now at the iPhone.

The iPhone keeps winning with an integrated architecture

It would appear that the iPhone has exposed a gap in Christensen’s theory – something that the theory does not completely explain. Christensen himself felt that the iPhone’s integrated architecture would lead to its marginalization in the market. [7] Some commentators latch onto this statement as an error, considering the iPhones continued visibility and its wildly successful contribution to Apple’s bottom line.

However, these commentators seem to forget that in some ways, Christensen is right. As of Q2 2015, research from IDC concludes that the iOS operating system (which only runs in the iPhone) owns about 14% of the worldwide market, while Android owns about 83%. The market is strongly consolidated around these two players. [8] Interestingly, if you look at the numbers by phone manufacturer instead of operating system, Apple’s share floats around in the same range, between 10 and 20%. From this phone manufacturer share chart, the market appears more fragmented – probably because the Android operating system’s modular architecture enables many phone makers to enter the market. Looking at the data in this way, the conclusion of those commentators that the iPhone is untouched by the market forces around the shift from integrated to modular architectures appears to be inaccurate.

However, if we take the point of view that the iPhone’s incredible profitability means that it has not failed in the face of modularization from its competitors, then the question remains. Why hasn’t the iPhone been crippled by the modularized competitors who can move faster and offer a greater range of options? This is a very valid question given the iPhone’s long and continuing status as the premier smartphone on the market, and its ability to command huge margins. However, we should remember that we have also allowed a subtle compromise in our thinking – because it could be argued that the iPhone would be much more successful today had its competitors with their modular architectures not arisen to take so much market share for themselves.

Explaining the iPhone’s longevity

Remember, the reason an integrated architecture is successful in the beginning of a market is because the performance of the products in that market is not good enough. In like manner, the reason the integrated architecture loses market share and ceases to command attractive margins is because the performance of the products in the market all become good enough, at which point the buyer’s willingness to pay a premium for the unnecessary performance surplus of the integrated player goes away.

So why does the iPhone continue to command outsized margins and maintain a steady market share when, to a casual observer, it would appear that performance from many players in the market is good enough, or even equivalent with the iPhone? Commentators have offered different explanations. Ben Thompson, author of the Stratechery blog, for example, claims that disruption theory doesn’t apply to consumer markets. [9] However, despite the Thompson’s strong grasp of the theory, his conclusion is somewhat broad, and ignores the fact that certain of the cases upon which Christensen’s theory is formed come from the consumer market.

So what can explain the iPhone’s exceptional status to a theory that has proven to be correct so many other times? I will offer several potential explanations, which are not mutually exclusive. Reality may lie somewhere between two or more of these explanations. Each is a potential avenue for further thought and analysis. I may find time personally to explore some of these avenues in future articles – I invite others to do so as well.

I should note that, although I ultimately reject Ben Thompson’s conclusion, I do think he is right that the consumer market may require a slightly different approach. In the smartphone market, in any case, good enough is a concept that operates on a host of dimensions – not just technical performance. My thoughts on this will become evident shortly.

Performance of products in the market is not yet good enough

We should keep in mind the fact that good enough is a relative term. What does it mean, and who decides where that line should be drawn? Each of the following explanations is actually, to one degree or another, a variation on this theme – because the definition of good enough is at the crux of the theory that says a market turns toward modularization when some critical mass of products achieve good enough status. It’s possible that the smartphone market is not yet at the stage where performance is good enough. I offer this here more as an introduction to the following explanations than an explanation that can stand on its own. By itself, this explanation lacks the necessary nuance to allow one to draw any meaningful insights or conclusions.

There are market segments for whom only the iPhone is good enough

It’s very possible that our error lies in our attempt to treat the entire smartphone market as one unit of analysis. There are almost certainly a numerous host of distinct market segments that may deserve to be treated independently. Perhaps by analyzing them independently, it would become surprisingly clear as to how the theory of modularization is operating in each segment.

Eric K. Clemons and Rick Spitler, in an unpublished draft of a book I studied in business school, argue that there is a change in the basis of competition in the consumer market that will require market players to differentiate more specifically for targeted segments of customers, rather than attempting to address a larger, less specific market segment at scale: “…success today and in the future will increasingly be related to skill-based competition, knowing what to offer, and to whom, and knowing what to charge, and to whom. That is, hyperdifferentiation is part of the transition in strategy, away from seeking advantage and higher margins solely through scale and lower expenses.” [10]

Clemons and Spitler argue that, with this new basis of competition, companies must:

[move] from a focus on large market segments with huge numbers of customers to a focus on numerous market niches with satisfied and profitable customers. The move to sweet spots requires better understanding of the customer. It also requires better understanding of competitors’ offerings and carefully staying away from already cluttered product “regions” in which there are numerous near substitute products already available. By avoiding cluttered areas with numerous product offerings – the firm is able to avoid the paradox of extremely differentiated products that are similar to other extremely differentiated offerings, and thus to avoid the resulting price wars that this could create. [11]

Clemons and Spitler suggest that a strong brand will be less critical in the transformed market they describe, and also argue that modular product design will be critical to simultaneously addressing the niche markets successful companies will target. While these aspects of their theory do not contribute to understanding the longevity of the iPhone’s success, the idea that companies should focus on “numerous market niches with satisfied and profitable customers” does seem to describe the iPhone’s history rather well. Think of the customers who would never use any other smartphone, and who line up outside stores on launch day. This is not every customer in the market – but it’s a steady segment of the market. As the IDC report shows, the iPhone market share viewed by both OS and phone manufacturer has hovered between 10 and 20% for the last 3 years, with some of that fluctuation appearing to result from variations in quarterly buying trends. This group of iPhone buyers has proven to be unswerving in their loyalty.

I just posed the question “what does good enough mean, and who decides where that line should be drawn?” Realistically, every buyer makes the decision of what is good enough for himself/herself, and it seems obvious that for a very stubborn market segment, only the iPhone is good enough. While the theory from Clemons and Spitler might suggest that Christensen’s disruption theory could benefit from more nuance in the definition of what is good enough based on customer segmentation, it does not fundamentally challenge disruption theory.

With the rapid pace of change and creation, the line for good enough performance doesn’t stay put

While each of my other suggested explanations operate with a very broad definition of “good enough performance”, including the phone’s performance on dimensions such as display quality, processor speed, network speed, physical attractiveness, social prestige, etc, this explanation focuses more on the hardware’s computing performance.

One could argue that the definition of good enough performance is almost impossible to nail down in a market where change is so constant. The requirements for good enough may increase with a new app that’s heavy on resource requirements (and it’s interesting to consider whether this is what Apple is intentionally doing with the 3D touch and selfie flash features mentioned at the beginning of this article). In other words, it may be more difficult to make a good enough phone when this happens, resulting in a smaller percentage of phones on the market that are good enough. The requirements may be relaxed when some platform improvement changes the way things get done or lowers the resource requirements for apps to run or for certain operations to be performed.

With a line for good enough that moves around so frequently, the tendency for the market to shift toward modular architectures may be hindered. And with moves such as the introduction of 3D touch and selfie flash, Apple may actually be turning the sword in the opposite direction – if it can introduce features such as these that are successful enough that the bar for good enough is effectively raised for some significant portion of the market, modular providers will actually struggle to surpass that bar, as they have to work together at a slower pace to introduce the features in their own phones.

The complexity of the product defies any good enough analysis

What is a smartphone? It’s simultaneously a phone, a computer, an app store, a personal assistant, a GPS device, a fashion statement, and more – it’s each of these things, and it’s all of these things. Can any product ever be good enough on all of these dimensions individually, and good enough on all of these dimensions holistically? It’s possible that no working definition of good enough is achievable with our current tools and understanding.

In a market where “performance” is an open-ended set of possibilities, perhaps the description good enough may not apply

The smartphone market is characterized by frequent product launches, each pushing the envelope as far as possible. While the improvements in recent time have become less radical and more incremental, the attitude of consumers toward phone launches (who ultimately are the only ones who can determine where the bar for good enough is located) is still one of anticipation. When expectations for infinite improvement underlie the market’s relationship with the product, including expectations for innovation never before seen, perhaps the usage of the measure good enough should be re-evaluated for use in this market.


My attempt in this article has been to explain why Clayton Christensen’s remarkable theory of disruptive innovation has, to this point, failed to completely describe the performance of the iPhone in the smartphone market. I hope this analysis is helpful. Comments are welcome.


1. Basis of Competition: the thing that a company must do better than competitors to obtain and retain customers and earn attractive profits in a given market. Put another way, it is the thing for which customers will pay a premium and offer their loyalty.

2. Please note that this simplistic example of the personal computer market is not offered as proof that the concepts put forward here are valid, but as an example to aid the reader’s understanding of the concepts. The research done by Christensen and Raynor applies broadly and stems from broad research.

3. Christensen, Clayton & Michael E. Raynor, The Innovator’s Solution, 133.

4. Ibid, 133.

5. Ibid, 130.

6. Ibid, 133.

7. Critical Path podcast, episode 36, May 2, 2012. 42:55.

8. see IDC report

9. see blog post September 22, 2013

10. Clemons, Eric K & Spitler, Rick, 2003, unpublished draft. I’m Entitled: Profiting from Customer Preferences in a Resonance Economy.

11. ibid

Update 9/29 – minor corrections to grammar and clarifications made to arguments.

How to authorize an Azure app to use CRM Online web services without asking the user to authenticate

Disclosure: I work for Microsoft. The views in this post are my own and not those of Microsoft.

The content in this post was developed in a joint effort between Marc Schweigert (http://blogs.msdn.com/b/devkeydet/, @devkeydet) and myself – mostly Marc. Thanks Marc! This post describes 2 distinct but related subjects:

  1. how to configure an app you’ve built and deployed to Azure to perform Single Sign-on (SSO) with CRM Online. Your app will not have to handle authentication, but will instead outsource this responsibility to Azure Active Directory, which is the identity provider for CRM Online. In other words, users will sign in to CRM Online in order to access your app.
  2. how to authorize this app to call the CRM Online web services without requiring a separate authentication.


Before we start the tutorial, you need to get the tools to follow along. I’ve provided two sets of Visual Studio 2013 solution files here in this repository: https://github.com/andisimo/AzureSsoSamples.

  • Starter Solution: The solution you can use to follow along with the tutorial and create an MVC or Web Forms project that’s registered in Azure Active Directory, configured for Single Sign On using the same directory as your CRM Online instance, and that allows your application to call the CRM web services via its registration in CRM Online.
  • Complete Sample: The finished solution that you should have at the end of the tutorial. Browse the completed code if you want to see what the end result should look like. Because of the steps requiring you to register your web project with Azure Active Directory when you create it, you will not be able to get this solution working without manually registering the web project in Azure Active Directory and changing a bunch of stuff in the web.config. You’re better off just using the Starter Solution for the purpose of getting a working sample.

This project was developed in Visual Studio 2013. Other versions will not follow exactly the same steps, because these instruction utilize some tools built into Visual Studio 2013 that do some of the work of connecting the web app to Azure for us.


Open the starter solution

This solution contains only a few publish scripts and a class library project called Devkeydet.OAuthHelper. As the name suggests, Devkeydet.OAuthHelper is a helper class that makes it easy to call the CRM web services via Azure Active Directory authentication once your app has been properly configured to do so. The starter solution also contains references to Microsoft.IdentityModel.Clients.ActiveDirectory and Microsoft.IdentityModel.Clients.ActiveDirectory.WindowsForms. These libraries are part of the Active Directory Authentication Library, available via NuGet. They are already referenced in the project, but will need to be installed when you open the solution in your Visual Studio. This will happen automatically the first time you build. You may actually need to uninstall and reinstall them to get them to work – but more on that when it becomes relevant.

Understand how you configure your web app to do SSO with Azure Active Directory

Before you create your project, you need to understand how to configure it to use Azure Active Directory for its authentication, because that configuration now happens during project creation. See the following video to get started: http://azure.microsoft.com/en-us/documentation/videos/azure-identity-application-to-authenticate/

Prepare Azure Active Directory to do SSO with CRM Online

With that background, you need to understand that there are 2 ways to associate your web app, to be deployed to Azure, with the instance of Azure Active Directory that CRM Online is using for Authentication. Once you have made this association, your app can be configured to do Single Sign On with CRM Online, and it can also be given permission to call the web services for your CRM Online organization. The first way is to use an Azure subscription administered by your CRM Administrator’s account (usually one that has an onmicrosoft.com domain). In other words, if you log into your Azure admin portal with the same Microsoft account you use to log in to CRM, you can use this option. To check, authenticate to CRM, and in the same browser instance, go to azure.microsoft.com. If you don’t have an Azure subscription for this account, you won’t be able to get in. If you’d like, you can create a trial subscription to be administered by your CRM Online admin user. By deploying your web app to this Azure subscription, it will be easy to register it in the same directory which stores the user information for your CRM Online instance, because your Azure admin already administers that directory. The second way is to give the administrator of a separate Azure subscription, who has an account with a different domain, permission to access the Azure Active Directory store where the CRM Online users live. This is the method to use if all of the following 3 statements are true:

  1. you already have an Azure subscription
  2. it’s administered with a Microsoft account on a different domain than the one you use to log in to CRM Online. The most common scenario is that you have accounts that look like this:
    1. Azure subscription – you login with Microsoft Account (formerly known as Windows Live ID) – an outlook.com, hotmail.com, msn.com address, or even an email address from a different company that you registered as a Live ID.
    2. CRM Online – you login with an account that has a *.onmicrosoft.com domain, or your own company domain like contoso.com.
  3. you want to use this existing Azure subscription rather than an Azure trial created for an account on your CRM Online domain

Give your Azure administrator access to your CRM Online Azure Active Directory

Allowing your Azure subscription admin to access and administer your separate CRM Online directory (a process called directory reuse) used to be a confusing process of logging into both services, creating accounts for the external user of the other directory, and giving that user admin privileges. Now, there is a very simple way to allow your Azure administrator to administer your CRM Online directory that exists in a different domain:

  • Browse to Active Directory in your Azure admin portal:


  • If your CRM Online tenant’s directory is not in the list of directories displayed on the page (and if you followed the proper branch of instructions to get to this point, it should NOT be listed), click “Add” at the bottom of the page.
  • In the “Add directory” dialog that appears, choose “Use Existing Directory”. As the dialog explains, you will be signed out and asked to sign in as a user with global administrator privileges for that directory (your CRM Online directory). After signing in, you will receive the instructions to give your Azure administrator the privilege of administering your CRM Online directory.


  • Once you’ve followed the instructions in the dialog, you’re ready to create your web project. You can log back in to your Azure admin portal, and you should see your CRM Online directory in the list. Now that it’s there, you can register your web app in that directory, and give it permission to use the directory for Single Sign On and to call the web services.

Create your web app and configure SSO in the process

  • Create a new MVC or Web Forms application in the “Starter Solution” sample solution. During the creation dialog, make sure you follow the instructions from the video referenced at the beginning of this walkthrough. Specifically, you’ll need to click the “Change Authentication” button on the right of the dialog:


And then choose “Organizational Accounts”. You’ll enter the domain for your CRM Online directory in the Domain field. I like to choose “Single Sign On, Read directory data” for the Access Level field.


Once you hit OK, you’ll be prompted to sign in to your CRM Online directory. Use your CRM Online credentials to do this. When you’re done, it will kick you back to the “New ASP.NET Project” dialog, and you can finish creating the project.

  • You have just configured your app to run SSO with CRM Online (or, more accurately, with the Azure Active Directory instance that CRM Online uses as its identity provider). When you run your web app now, it will redirect you (the user) to a Microsoft authentication page, which will then authenticate you and redirect you back to your web app with a token containing some info about you that tells your web app that you are in the directory. (Try it – run your web project in debug mode. When you’re finally redirected back to your application after signing in, you’ll see your email address in the header of the web page).

Give Consent for your web app to access the CRM Online web services

You’re probably familiar with the consent-based authentication flow, where one app or service wants to talk to another. App 1 redirects you to App 2, where you log into App 2 and it asks you if you want to let App 1 access your info on App 2. Facebook or Twitter are the most common examples of App 2. When you allow your web application to call the CRM Online web services, you’re essentially doing the same thing – you’re giving consent for your web app (App 1) to access your info in CRM Online (App 2). However, you won’t ever experience the redirection and request for consent as an end user. The reason for this is that you’re working with an organizational directory in CRM Online, which has an administrator. In the steps that follow, the administrator will effectively give consent on behalf of all users in the CRM Online directory for the web app to access CRM Online info. To give this consent, navigate to your app in the CRM Online directory by going to your Azure admin portal, going to Active Directory, selecting your CRM Online directory, and clicking on “Applications” at the top of the page. RegisteredAppsList There’s your application! Click the arrow in the NAME column to get to the configuration info for your application, and then click on CONFIGURE at the top of the page that appears. At the bottom of the CONFIGURE page, you’ll see a section titled “permissions to other applications” with a series of drop-down boxes. Choose “CRM Online” in the empty dropdown box, and then in the “Delegated Permissions” dropdown box, choose “Access CRM Online as organization users.” Permissions Make sure you save your changes (the save button is at the bottom of the page). You have just given your web app consent to access CRM Online’s web service. Note: Please recognize the distinction between these two tasks you’ve just completed (setting up SSO and giving your web app permission to call CRM Online web services) – they are not the same. SSO involves letting your app outsource identity management and authentication to the CRM Online directory in Microsoft Azure. This is telling your web app to trust the CRM Online directory. Giving your web application permission to call the CRM Online web services is a consent-based authentication flow that involves telling CRM Online to trust your web app. Making this happen is a separate step (although, as you just saw, Azure makes it so easy you might not realize it’s a separate step). You must complete the steps to configure SSO before you can tell CRM Online to let your app call its web services.

Configure your Web App

Now we need to configure our web app to access the CRM Online web services. Stay on your app’s configuration page in the Azure admin portal, because you’ll need some values from that page in a minute. First, build the project/solution to get the NuGet packages. Also, due to a strange glitch, you may have to use the Library Package Manager (Tools > Options > Library Package Manager > Package Manager Console) to uninstall and then reinstall the following library: Microsoft.IdentityModel.Clients.ActiveDirectory For both the DevKeyDet.OAuthHelper project and your own web app, run the following commands in the Package Manger Console in this sequence:

  • Uninstall-Package Microsoft.IdentityModel.Clients.ActiveDirectory
  • Install-Package Microsoft.IdentityModel.Clients.ActiveDirectory

Then, follow these steps to configure your app to call the CRM Online web services.

1. In your web app, add a project reference to the Devkeydet.OAuthHelper project.

2. In the web app project, add the following XML snippet to the <appSettings/> section of the web.config:

<add key="ida:ClientId" value="[CLIENT ID from the Azure portal here]" />

<add key="ida:AppKey" value="[KEY from the Azure portal here]" />

<add key="ida:AADInstance" value="https://login.windows.net/{0}" />

<add key="ida:ResourceId" value="https://[YOURORG].crm.dynamics.com" />

<add key="ida:OAuthRedirect" value="[url for your page/controller to handle OAuth redirect]" />

3. Put the proper values in each node:

  • ClientId: see step 4
  • AppKey: see step 4
  • AADInstance: do not modify this value
  • ResourceId: replace [YOURORG] with your CRM Online organization name. It should look like this when you’re done: https://awesomecompany.crm.dynamics.com.
  • OAuthRedirect: see steps 5 and 6

4. Get the ClientId and the AppKey values from the Azure admin portal. Navigate to your application’s Azure Active Directory configuration settings (hopefully you’re already there): AppConfigPage

The ClientId value is available in the page for you to copy. For the AppKey value, you’ll need to create a key in the keys section of the configuration settings:


Make sure you save the key value. Once you leave the configuration settings page, the key can no longer be seen. Copy it into OneNote or something like that.

5. Next, you will need to create a controller (if MVC) or a page (if Web Forms) to point Azure Active Directory to in order to process the returned access code and request a token that allows you to make requests to CRM web services using the logged in users identity.  The ida:OAuthRedirect value should be in the form of “/routetoyourcontroller” or “/urlofyourpage”. If you were to name your controller OAuthRedirectController, the value here would be “/OAuthRedirect” (just leave the word “Controller” off the end of the name).

6. Create the page or controller.  You can call it what you want, as long as you update the config file appropriately, but I prefer to call it OAuthRedirectController (MVC) or OAuthRedirect.aspx (Web Forms).

7. If you are using MVC, replace the code for the Index() action method with the following:

public ActionResult Index(string code, string error, string error_description, string resource, string state)
            var returnUrl = OAuthHelper.ProcessAccessTokenAndGetReturnUrl(code, error, error_description, state);
            return Redirect(returnUrl);

8. Fix using statements

9. If you are using Web Forms, replace the contents of the Page_Load event handler with the following code:

string code = Request.QueryString["code"];
            string error = Request.QueryString["error"];
            string error_description = Request.QueryString["error_description"];
            string state = Request.QueryString["state"];
            var returnUrl = OAuthHelper.ProcessAccessTokenAndGetReturnUrl(code, error, error_description, state);

10. Now go to the controller or page where you want to actually make web service calls that use the token.

11. For MVC, use the following code:

var accessToken = OAuthHelper.GetAccessTokenFromCacheOrRefreshToken();
            // If we don't have the access or refresh token cached, then we need to redirect to AAD to get a token THIS APP can use
            if (accessToken == null)
                return Redirect(OAuthHelper.GetAuthorizationUrl());
                   // Use token to make web service calls

12. For Web Forms, use the following code:

var accessToken = OAuthHelper.GetAccessTokenFromCacheOrRefreshToken();
            // If we don't have the access or refresh token cached, then we need to redirect to AAD to get a token THIS APP can use
            if (accessToken == null)
                   // Use token to make web service calls

13. The sample app has two examples of making OData calls.  The first is just raw http requests.  The second uses a LINQ to OData by way of a code generated OData context.  To create one of these contexts, see: http://blogs.msdn.com/b/devkeydet/archive/2012/06/10/using-the-crm-2011-odata-service-from-a-metro-style-app.aspx.  Start with the text Ok, now it’s time to “Add Service Reference” to the OData service.  You can ignore the rest of the blog post.

Windows Store Apps for Dynamics CRM – Best Practices as of 5/1/2013

Disclosure: I work for Microsoft. The views in this post are my own and not those of Microsoft.

The Problem: Authentication

When we’re discussing problems with writing a Windows Store app for CRM, the primary thing we need to talk about is authentication. After we discuss the problem, we’ll talk through 2 solutions for authenticating and writing code that communicates with CRM from a store app.

The Solutions: Sample SDK and Unsupported, Unsanctioned Goodness (for CRM Online on O365 Only)

  1. First we’ll walk through using the CRM Product Team’s sample SDK for Windows Store Apps. You may have used this already (I hope you have), but stay tuned, because there are some tricks that we can use to improve the developer experience, and we’ll identify those.
  2. Then, we’ll talk about using the Organization Service Odata endpoint directly from our Windows 8 Store App. Why, you might ask, am I talking about option 1 first if I have a solution that will let you call the Odata service directly? Because, young Jedi, this approach is non-sanctioned, has no path for official support, and if it breaks your apps, you’re on your own. But it’s still awesome. And I’m doing it last because I like suspense.

Why is there an authentication problem?

So why is there a problem authenticating with CRM from Windows Store apps?

When we’re building apps for CRM on other platforms, where we have access to the full .NET library, we use the Microsoft.Xrm.Sdk.dll library to connect to CRM. This library does quite a bit for us. Perhaps most importantly, it manages authentication for us. It has all the code in there that navigates through the steps the CRM web service exposes in compliance with the WS-Trust protocol. However, Microsoft.Xrm.Sdk.dll is dependent upon .NET 4.0 and WIF (Windows Identity Foundation). When we’re building Windows Store Apps, we have a lighter .NET profile that doesn’t include these resources.

There are 2 endpoints for the Organization Web Service that we use to access CRM data.

  • The Odata endpoint is not available to external callers (for now – read on for solution 2 :) ).
  • The SOAP endpoint uses the WS-Trust protocol to authenticate callers. WS-Trust itself doesn’t require .NET 4.0 or WIF, and for that matter, neither does the CRM SOAP endpoint. It just so happens that the code in Microsoft.Xrm.Sdk.dll uses those two resources for its own WS-Trust authentication. Without this library, we have to write our own WS-Trust implementation using the slimmed-down .NET profile available to us (hard), or we can use the sample SDK provided by the product team (easy).

Sample Windows Store App Project: Take Notes on Contacts

This sample project gives you a list of Contacts and lets you create a Note for each one:

Untitled picture

Untitled picture

Solution 1: The Sample SDK


  • Authentication = Easy
  • You’re building Win8 apps for CRM right away


  • No LINQ
  • No await/async – have to use EAP
  • No early binding
  • No support for Windows authentication – only IFD and CRM Online

Is the 4th bullet really a drawback? Not really, but I thought I’d note it here. If you really wanted to build an app that only can be used inside your company’s firewalls, you could write your own Windows Authentication mechanism.

Of the 3 drawbacks, the last 2 are actually easily rectified – but I won’t detail them here, because Marc Schweigert has already created a great video that walks through the steps you can take to get early bound entities and await/async methods:


Unfortunately, there’s no LINQ support; you’re stuck with FetchXML. Put it in a static class like I do in my sample app, and use the LINQPad solution Marc recommends if you want to.

Solution 2 (Unsupported): Call the Odata endpoint from the outside

  • To install the Nuget package, run commandlet: Install-Package FedId.WinRT.Project.Scaffolding -Version
  • My Sample Project Code: https://github.com/andisimo/CrmFedId (see the instructions on how to get the code working below)

Yes, this is groundbreaking. You’ve never been able to do this before, and you aren’t misunderstanding me. There is a way now to call the CRM Odata endpoint from a Windows Store app. It’s unsupported – and I’ll explain what that means below. This only works for CRM Online tenants running on the Office 365 cloud, not to LiveId tenants or to on-premise installations. You’ll also want to keep in mind that this approach has all of the limitations of the Odata endpoint (it only does CRUD operations over entities), so there are some scenarios where you may need to access the SOAP endpoint via the Sample SDK anyway. However, for most Windows Store Apps, CRUD over entities will probably be all you’ll ever need.

You can get the package by running the above commandlet from the Package Manager Console in Visual Studio with your Windows Store app project open.

The benefits of this approach are that you can use the modern code conventions we’ve been used to using since CRM 2011 was released. This is like writing a web resource that runs inside of CRM, because we’re using the same Odata endpoint! The authentication part is relatively easy. Let me correct myself – it is easy for US because a very smart programmer has done a substantial amount of work to build the assets that make this possible.

The drawbacks are that this approach is not supported. What does this mean? As CRM devs, when we hear “not supported”, we tend to think we’re talking about a forbidden no-no. That’s not the case with what I’m about to discuss. Remember, we’re building an app outside of CRM. How we authenticate from that app is not going to place our CRM deployment in an unsupported state. What unsupported means, in this instance, is that there is NO GUARANTEE that what we build using this approach won’t break in the future if something changes in CRM. This is not aligned with the CRM product group’s strategy and you should have no expectation that what I’m about to show you will merge with or become part of the officially recommended way of doing things in the future.

Now, why am I sharing it with you if I have to give such a stern disclaimer up front? Because what I’m about to show you is exciting, and at the very least, it’s a very compelling thing to test and try out. When you’ve carefully weighed your decision, some of you might decide to use it. Just know that any minor change in the CRM api could potentially cause this to stop working, and while that may be unlikely, it’s definitely possible. We have a major release coming out later this year, and you’ll want to keep your eye on that.

How Solution 2 Works

Solution 1 (The sample SDK from the CRM team) uses WS-Trust to authenticate via the SOAP endpoint, passing a request security token in the SOAP header. This is an established, solid approach to authentication, but there are problems. Since this all happens via the SOAP header, we are constrained to use the SOAP service, which introduces the developer productivity limitations we discussed earlier.

Authentication to the CRM endpoints is fundamentally nothing more than a requirement that a caller meet a certain criteria. The criteria the SOAP endpoint looks for is a valid token in the SOAP header. The criteria the OData endpoint looks for is a valid, encrypted cookie being passed in the request that identifies the caller.

The FedId WinRT Project Scaffolding collects the user’s credentials. It then walks through the steps a browser client goes through, inserting the credentials at the necessary places, to mimic the steps a browser takes in WS-Federation passive authentication. It collects the various tokens that are returned during the several required steps, in order to finally get a token that can be used to access the CRM Odata endpoint.

How to Use the FedId WinRT Project Scaffolding Package

  1. Download and install the WCF Data Services Tools for Windows Store Apps:
    1. http://www.microsoft.com/en-us/download/details.aspx?id=30714
  2. Download the CSDL from CRM > Settings > Customizations > Developer Resources
  3. Create an empty windows store app
  4. Install the Nuget package from package manager console:
    Install-Package FedId.WinRT.Project.Scaffolding -Version
  5. Add a Service Reference and point it to the location of the csdl file you downloaded. Name it OdataReference. It will have a context type to match your org name (like OdataReference.OrgNameContext). Giving your service reference a namespace other than “OdataReference” will require you to find and change a few using statements that are currently “using CrmFedId.OdataReference”.

What’s in the Sample Code

  • There are only a few main components at work here:
    • I’ve got a MainPage.xaml for signin, and a BasicPage1 and BasicPage2.xaml. Upon authentication, MainPage navigates to BasicPage1, which shows a gridview of Contacts. When you click (or tap – come on, this is Windows 8) on a Contact, BasicPage1 navigates to BasicPage2 and shows you a textbox that allows you to create a note for that contact.
    • I also have a ContactsNotesViewModel class that has a few properties to store the data I get from CRM so the xaml pages (views) can bind to it, and some methods to get that data. The context for the CRM tenant is also instantiated and stored in the ViewModel, as well as a few events that help me keep track of the authentication and data responses. I have a static property of type ContactsNotesViewModel defined in App.xaml.cs and instantiated in the OnLaunched method of that class.
    • Security.IdpCredentialsFlyout.xaml: this is the definition for the flyout. This “Security” folder is added when you install the Nuget package. You can look at the codebehind for this page to see the event handler for when the user pushes the “Sign In” button (called SignIn), how it handles the credentials, and ultimately calls the FedId.Instance.SignInAsync method and gets the token in the response.
    • A class called FedId that manages security tokens, settings, things like that. It has a static property of its own type (FedId) called Instance, that you will use to access the actual tokens you get from CRM from elsewhere in your project code.
    • You don’t need it, but I have an extension method, courtesy of Marc Schweigert again, that gives me an await/async-friendly ExecuteAsync<T> method with a generic type parameter. It’s definitely better to have it than not.
    • And, finally, your Service Reference, which gives you the entity context for your CRM organization. Your context is at “OdataReference.[OrgName]context”.

How to Get the Sample Code Working

  1. Follow the steps in the section above, “How to Use the FedId WinRT Project Scaffolding Package“, with the EXCEPTION OF steps 3 and 4, creating a new Windows Store App project and installing the Nuget package. You already have your project in the sample code, and it already has the Nuget package installed.
  2. Once you have your Service Reference added, open your Find dialogue (ctrl + f) and search the ContactsNotesViewModel for the text “psecdemoContext”. You should find 3 instances of it – in the type declaration for a private field, a public property, and in the HaveToken() method that sets the public property. Change the type of these items to match your own [orgname]Context. Orgname = the name of your CRM organization.
  3.  Use your find dialogue again to search for “psecdemo.” (psecdemo with a period). This is to find 2 URLs where you’ll need to insert your own organization name. One is in the ContactsNotesViewModel, and the other is in the MainPage.xaml.cs file.
  4. Build!

Code Flow

The main page loads (in the LoadState method). The first thing that happens there is that we subscribe to the following event:


The lengthy lambda expression that follows mostly makes sure that when the event is fired, the flyout where the user enters his/her credentials is displayed properly.

Next, we subscribe to the TokenReceived and ContactsLoaded events on the ContactsNotesViewModel. We’ll discuss these events in a moment when they actually get fired, in order to keep our walkthrough of the code chronologically sequenced.

So finally we get to the bottom of the LoadState method, where we find the first code that actually proactively does something:

if (!FedId.Instance.IsSecurityTokenValid())
   var result = await FedId.Instance.SignInAsync

This code is checking the FedId.Instance property to see if there is a valid security token there. Sometimes there will be – for example, if you’ve already authenticated and your computer has stored the authentication cookie. If you haven’t authenticated, or if your cookie is expired, then there won’t be a valid security token, and the code will invoke the SignInAsync method. You can’t see this method other than its signature in the metadata viewer, but we know that somewhere in this method or in other code called by this method, the ShowSettingsFlyout event is triggered (the one we subscribed to at the very top of our LoadState method on MainPage.xaml.cs).

The user then enters credentials and clicks the “Sign In” button, triggering the


method. When that method gets a token back successfully (i.e. if result == true in the following code), we call the ContactsNotesViewModel.HaveToken() method:

if (result == true)
   //The HaveToken method fires the TokenReceived event on our viewmodel 

As the comment there says, this HaveToken() method turns around and fires the TokenReceived event, after initializing the ViewModel’s context. There may or may not be a code smell here, calling a method on object1 to essentially trigger an event on object1 from object2, but it seemed like a solid way to get this sequence working properly in my sample.

public void HaveToken()
   Ctx = new psecdemoContext(new Uri(

Now, let’s go back to MainPage.xaml.cs. In our LoadState method, you should remember that we subscribed to the HaveToken() method. When this event is fired, we call the LoadContactsAsync method on our ViewModel:

App.ContactsNotesVM.TokenReceived += () =>

The LoadContactsAsync method is where we have the code that actually interacts with the Odata service.

public async void LoadContactsAsync()
if (FedId.Instance.IsSecurityTokenValid() == false)
   throw new InvalidOperationException(@"ContactsNotexViewModel.LoadContactsAsync cannot retrieve         
   contacts when the FedIde.Instance.IsSecurityTokenValid property is false. This property is set = true when the         
   security token is correctly received from the FedId.Instance.SignInAsync method call."); }            

   var query = from c in Ctx.ContactSet    
   select c;Ctx.SendingRequest += (sender, args) => 
      args.RequestHeaders[HttpRequestHeader.Cookie] = 

   var results = await ((DataServiceQuery<Contact>)query).ExecuteAsync();

   foreach (Contact c in results)

   this.IsDataLoaded = true;

The last thing this method does is trigger the ContactsNotesViewModel.Loaded event. We subscribed to this in our MainPage.LoadState method:

App.ContactsNotesVM.Loaded += async () =>
   await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>

As you can see, once we know the contacts have been loaded into our ViewModel, we are free to navigate to BasicPage1, where the databinding between the page and the ViewModel takes over and the contacts are displayed just like you saw in the picture at the top of the post.

Instead of using an event to tell us when the contacts were loaded, a better solution would be to make the ContactsNotesViewModel.Contacts property an ObservableCollection and implement the INotifyPropertyChanged interface on the ViewModel, which would allow us to navigate to BasicPage1 without worrying about whether we would get there before the contacts were loaded. The viewmodel would simply update the view with the data as it arrived.

But you’ll notice that there this isn’t the only less-than-optimal choice I’ve made for writing this Windows Store app. My goal was to show you two ways to access the CRM web services from the app, and I hope you’ve found at least one of them valuable!

New Role and Disclosure

As of Dec 10, 2012, I work at Microsoft as a CRM Technical Architect focused on Public Sector. The last 4 months have been really exciting for me. Because I’ve spent my career in the Microsoft partner channel, I have always had the ambition of working for Microsoft “one day”.

So, as a point of disclosure, future posts about technology should be read in the light of the fact that I now work at Microsoft. However, the views expressed here are my own and NOT those of Microsoft.

Simply Simplify

After an off-the-cuff remark I made the other day in my post on the CRM security model, I ran across this video post by James Governor. He’s driving at something bigger than an argument for general simplicity, but it was the comments he made on simple software design that caught my attention. He says the following:

Software had always thrived on complexity, on more configuration, on making things more and more complicated so that everything could be custom, so that the user could do things in a million different ways. But the problem is when you do that, they will do things in a million different ways, and that makes support much more expensive. It creates all these challenges … it turns out, the way to make things better is to make things simple, and to have an opinion.

I like Governor’s concept of having an opinion. In using that term, he is referring to stubborn people who build products in a simple way despite criticism that the product won’t do everything users might want it to do. For example, he tells the story of Ruby on Rails, created by a very opinionated person by the name of David Heinemeier Hansson. Hansson chose standardization over configurability, and thereby chose simplicity over complexity. Developers who use Rails have fewer choices. It turned out that options weren’t what developers were looking for – they responded very well to the simplicity of Rails, and it has become one of the most popular web development environments available.

On the flipside, he quickly demos a tablet running Windows 8 Pro. The interface is simple and lovely. App design focuses on content not chrome, and the interaction is intuitive. His praise turns sour, however, when he lands on the old Windows desktop. While Microsoft did a great job building a simple interface for Windows 8, they were not opinionated enough in telling people “this is how we’re going to interact with Windows from now on.” The result, in Governor’s analysis, is a disturbing dual-personality that jars the user experience and cheapens the otherwise tremendous accomplishment embodied in the new metro interface.

Governor isn’t the only one to level this criticism at Windows 8 – it’s actually a common complaint, and I think it’s a valid one, with qualifications, which I’ll discuss in a moment. The old face of Windows is still in Windows 8 because Microsoft thinks many people want more options, that many people don’t want to change, and yet they know they have to change for Windows to be relevant in the changing technology landscape. So they developed an operating system that tries to please everyone. I believe the size of Microsoft’s customer base makes it very difficult for the company to make the types of opinionated decisions that Governor favors. But personally, I’d like to see them take a bold move like that just to see what happens.

Taking a step back, though, one could argue that there’s another reason why the Windows 8 interface had to be the way it is. Today’s tablet technology simply doesn’t have the ability to run all the applications that people use. Windows 8 is the new version of Windows, period – not a new auxiliary category in the Windows family. It’s one operating system for tablets and PCs. This means a user could realistically use one device for all of their computing activities. Isn’t that a step toward simplification? One step toward reducing the current load of 3 personal devices to 1? (I would like to see a tablet that can, like the Windows 8 tablet, get carried around and also docked, allowing both mobile and desktop computing. But on top of that, my ideal device could be easily strapped to your back, your hip, or against your ribs under your arm, FBI gun-style, and it would have a little removable earpiece for phone calls).

Governor’s critique seems to limitits analysis to the experience of the single device, but I think it’s also valid to consider the consolidation of devices as a great step toward simplicity; and in that respect, I think Microsoft did exert a strong opinion. Whether or not that opinion gains the respect of the market remains to be seen.

Governor’s Opinionated Design concept isn’t the only approach to simplicity. A great book I read recently called Nail it then Scale it, by Nathan Furr and Paul Ahlstrom, advises entrepreneurs to build simple products with the following anecdote:

A number of recent books, such as The Paradox of Choice, summarize decades of social psychological research showing that even though it may appear that we crave more choices, in fact, we respond to simplicity. For example, in one well-known experiment at a Bay Area grocery store, two different jam exhibits were tested. In the first exhibit, six types of jam were put on display for customers to sample, and the resulting sales were robust (30% of customers bought a jam). In a second exhibit, customers were given far more choices; twenty-four different types of premium jam were put on display in the true spirit of customer choice. Shockingly, sales dropped over seven-fold to a meager 4% sales rate. In other words, despite the fact that modern capitalism has led to an explosion in choices, customers respond to simplicity more than complexity (58 – 59).

Furr and Ahlstrom also relate the story of two entrepreneurs who built an application prototype that had 20 major features. When researching the product’s feasibility with actual potential customers, they found that customers would only be willing to pay about $200 per month for the product. They also found, however, that most of the customers placed the most value on 3-4 of those 20 features. The entrepreneurs rebuilt the prototype with only 4 features, and did their analysis with real potential customers again. This time, they found that the customers would be willing to pay $1,000 per month for the product. By reducing the clutter and mess caused by a slew of unneeded features, these entrepreneurs saw the perceived value of their product skyrocket.

Contrary to Governor’s concept of opinionated design, however, Furr and Ahlstrom’s premise is that no company should ever build a product before having an assurance from customers that they will buy the product. In essence, while Governor advocates telling the customer what they want, Furr and Ahlstrom advocate getting more customer feedback, and letting that feedback drive the product development.

There are nuances in each theory that soften the conflict between them. For example, Furr and Ahlstrom are very clear that although customers know what their problems and desires are, customers do not know the solution to those problems and desires. Quoting Henry Ford, who said “If I had asked customers what they wanted, they would have said faster horses”, Furr and Ahlstrom argue that the product creator/designer’s innovative contribution is the essential core of successful product development – something Governor would clearly agree with. However, unlike Governor, Furr and Ahlstrom argue that early, focused, and continued attention to customer feedback is necessary for the productive direction of an innovator’s creative energy.

Likewise, I have to assume that Governor’s opinionated design concept doesn’t completely reject the idea of letting the market drive product design – it simply argues that the product creators must take a stand on principles of simplicity, which might require ignoring much of that feedback to focus on the core messages it conveys.


I’ve been plowing through more of Governor’s material and, as I come to a better understanding of his thought on this subject, I believe his opinionated design actually requires ignoring the conventional wisdom that presses in horizontally from non-customers (like analysts, competitors, etc.), rather than vertically from customers. The problem is, with the massive change in computing that we’re experiencing, customers often don’t know how to ask for the right things; and, according to Governor, vendors aren’t there yet either. It’s well worth a read (and a view – his posts often have videos also): http://redmonk.com/jgovernor/.

When the CRM Security Model Isn’t Enough

I myself am not an expert in organizational behavior or in structuring companies. So keep that in mind as you read my next statement, where I invoke the wisdom of these people anyway, without asking, based on my assumptions about things. I’ll let you work out the validity of my argument on your own.

I think large organizations that have complex chains of command where people (usually in sales) report to more than one lateral individual in the company have done a bad thing. I’m confident organizational experts would agree with me (experts.Invoke( ;-) ) ). Why would a salesperson span 2 regions and report to 2 bosses? How could this person possibly fulfill his accountability to both people?

I’ve worked with more than one large company with complex reporting structures full of exceptions. Some people may look at such a complex structure as a badge of honor that seems to say “here is something important enough to be complicated.”

But making CRM’s security model work with something like this is difficult, and it will cost extra money up front and over time. Imagine the money spent on this, and how much better it would be to simply … simplify. Alas, while B2C technology is focused on meeting the users’ demands for simplicity, B2B technology is forced to cater to demands for more complexity. It’s one of my greatest professional sorrows. Because deep down, I’m a minimalist. I believe clarity and simplicity are within our grasp anywhere, if we try. But unfortunately, in the case we’re describing today, that’s not your job.

The Problem in clearer terms

Let me give you the details in simplicity. A customer’s sales organization is split into regions. Each region has a leader that should be able to see all of the stuff for the people who work for him. Can we do this in Dynamics CRM?

YES. If only it were always this simple. You can create a business unit for each of the different regions. There can even be sub-regions if you need. The users go in the different business units, and they are given the proper security roles. The leaders of the regions go in the business unit for their region, and they have a security role which gives them privileges to interact with every record in that business unit (and possibly also with all of that business unit’s child business units).

This is the situation the CRM security model was designed for. And, to my point above, it should happen more often.

The Problem in slightly muddier terms

Now, in the situations I’ve been in where things got difficult, there were a lot of confusing exceptions to the rules I laid out above. But if I distill them into the simple principles, the main problem was this:

We have users who belong to more than one region.

Utterly crushed. Why? Because it probably didn’t have to be that way. In my experience, this situation can start with a well-intentioned effort to re-pick teams to address the market more effectively, and ended with politics (like salespeople refusing to let go of accounts) that confused the effort.

But you’re probably not here to rewrite an org-chart. So you think – TEAMS!! We’ll just put them on a team in the second business unit, so they can essentially exist in both places!

Don’t let me interrupt your high fiving and back patting. Carry on – you’re having fun. But as soon as you’re done, consider this – you still have the requirement for the leader of each region to see the stuff that belongs to users in his region. He WILL NOT see the stuff owned by the users who are part of his region by virtue of membership in a team. (Why not? See here). Remember, we decided above that the leader’s user record would reside in his business unit, and he would have privileges to all the records owned by people in his business unit.

There are enough possibilities here that you can work out the details yourself for this situation. It probably won’t be clean and pretty, but it can work. For example, teams can own records. Maybe the accounts in this CRM system are owned by the regional leader guy, or maybe they have a relationship with a piece of data that indicates the region. Since the accounts are the core of all the other data, you can create a rule through a plugin or workflow that looks at the related account record for created records (like an opportunity). If the opportunity is for an account that is in a different business unit than the salesperson who’s creating it, it gets assigned to the team for that business unit.

Or, you could modify the leader’s security role and give him access to see more, and then filter it down to what he wants to see using views. There are several ways of addressing this that could work. As a last resort, you could try something I’m going to describe in my next section, but it would be so anti-climactic for me to mention it here.

The Problem in dark obscurity

Now, imagine as you work through solving what you thought was a big problem, another little issue comes up. This one is mentioned off the cuff, almost as something taken for granted. Slid sideways into casual, non-charged conversation. You can save things right? And this program works with a mouse and keyboard? I assume it has colors? Oh good. Super. … And of course we’ll need to set up some security based on the type of sale we’re looking at.

Mushroom cloud. Let’s change the subject. Do you like politics? Let’s talk about those …

But it’s impossible to change the subject. Did you really think they didn’t see the mushroom cloud go off in your head? You know that Security in CRM is role-based. The lynchpin of this role-based security is record ownership. A record has an owner, and that owner resides in a business unit. The security role operates in the context of those 2 very simple pieces of data, and nothing else.

In other words, you can’t flag an opportunity as a “Corporate Sale” or a “Classified Sale” or as anything else and expect security to operate on those values. If this requirement didn’t exist in tandem with the last one I described above, you might be able to create business units for your regions as we discussed at first, and then create child business units underneath the regions, one for normal sales, and one for “Classified” sales. But this would assume that salespeople only work on one or the other, and that’s probably not true either. After all, you’ve had to come this far, why should something go your way now?

At this point, you might have to look at using the SDK. You could potentially write a plugin that executes on the pre-stage of the Retrieve and RetrieveMultiple platform methods. This would allow you to check out who the user is and whether he’s somebody who should be able to see “Classified” sales. If the user is NOT that sort of user, you can modify the request to filter out those records, so views and forms won’t load the “Classified” data.

The downside to this is the obvious concern of maintaining security in code that the administrator can’t see or interact with. It’s also true that the security behavior of the system with this plugin in place would seem to directly contradict, in some cases, the privileges described in the security roles. But, if we’re smart and set it up as transparently as possible, it could be a very good solution. For example, maybe we could create an empty security role that has the name “View Classified Sales”, and have our plugin check to see if the user has that role to determine whether it needs to modify the query for the Retrieve methods. That way, an administrator looking at a user’s security roles could at least see that something was happening outside of the ordinary security construct.

Out of time! But let me mention one more thing … if you’re interested, there’s one loophole that I’m aware of in CRM security. If everything lined up right for you, you might be able to use this loophole to address this last requirement we’ve been discussing. Read about it here.