Thursday, 9 January 2020

What happens when a user is Assigned Multiple Security Roles in Microsoft Dynamics 365 CRM

What happens when a user is assigned multiple security roles in Microsoft Dynamics CRM?

In smaller organizations, you may find situations when a Manager would like to have access to both a Sales Profile and a Service Profile in Microsoft Dynamics CRM.
You may wonder what exactly happens when a user is assigned multiple security roles.
Assume that a user is assigned the profiles shown below in the screenshot. You see that there are different access levels set for each profile. 

You will that when the user gets assigned to both ‘Baseline for all users’ and ‘Sales Person’ profiles, the access levels get combined, and the user then has permissions as shown in the ‘Effective Permissions’ section.

So you see that when a user is assigned multiple roles, the user gains the permissions associated with each role.

Thursday, 2 January 2020

How to Filter Sub-Grid in Dynamics 365

In this example, I've added an "Accounts" sub-grid to my Account, configured to show "All Record Types" rather than "Only Related Records". The using this JavaScript we're filtering the sub-grid to display all the Accounts that the Primary Contact is a Primary Contact of (which will obviously include the current account). This function can be added to the form OnLoad and Primary Contact field OnChange to ensure the sub-grid is updated when the Primary Contact changes as well.
NOTE: I've found it best to create a custom view to be used as the default sub-grid view, and to customize this view to display no results by default (using a filter such as: Name equals "X" and Name does not equal "X" – which will always return no results), this way you won't see incorrect data initially on load before the JavaScript kicks in.
// Generic function to perform the filtering - this function shouldn't need to change
function filterSubGrid(subgridName, fetchXml, attempts) {
    // Try 10 times, then stop
    if (attempts < 0) { return; }

    var crmWindow = Xrm.Internal.isTurboForm() ? parent.window : window;

    // Get the subgrid element to filter
    var subgrid = crmWindow.document.getElementById(subgridName);
    if (subgrid == null || subgrid.control == null) {
        // If the subgrid hasn't loaded yet, keep trying
        setTimeout(function () { filterSubGrid(subgridName, fetchXml, (attempts || 10) - 1); }, 500);
        return;
    }

    // Update the fetchXml on the subgrid and refresh the grid
    subgrid.control.SetParameter("fetchXml", fetchXml);
    subgrid.control.refresh();
}

// Filters an accounts subgrid by the primary contact ID - this function is unique for your requirements
function filterAccountGrid() {
    // Get the dynamic contactId to filter on
    var contactValue = Xrm.Page.getAttribute("primarycontactid").getValue();

    // If the contact is null display nothing 
    var contactId = "00000000-0000-0000-0000-000000000000";
    if (contactValue != null) {
        contactId = contactValue[0].id;
    }

    // Fetch xml code which will retrieve all the accounts related to the contact 
    var fetchXml = "<fetch version='1.0' output-format='xml-platform' mapping='logical' distinct='false'>" +
    "  <entity name='account'>" +
    "    <attribute name='name' />" +
    "    <attribute name='address1_city' />" +
    "    <attribute name='primarycontactid' />" +
    "    <attribute name='telephone1' />" +
    "    <attribute name='accountid' />" +
    "    <order attribute='name' descending='false' />" +
    "    <filter type='and'>" +
    "      <condition attribute='primarycontactid' operator='eq' uitype='contact' value='" + contactId + "' />" +
    "    </filter>" +
    "    <link-entity name='contact' from='contactid' to='primarycontactid' visible='false' link-type='outer' alias='accountprimarycontactidcontactcontactid'>" +
    "      <attribute name='emailaddress1' />" +
    "    </link-entity>" +
    "  </entity>" +
    "</fetch>";

    filterSubGrid("Accounts", fetchXml);
}
Note: This code is unsupported, and is likely to break in any major releases (as it has in the past). The idea of sourcing this project on GitHub is that if/when it does break again, it can be updated here rather than having to release new blog posts and hoping people who have previously used it see it. Also if it breaks in an update and I don't get a chance to fix it, someone else can fix it :)

How to use Form Component Control to Edit Related Entity Information in Dynamics 365 CRM

In the recent release of the Dynamics 365 CRM, new features have been added. One of the most important and useful features among these is th...