Sonoma Partners Microsoft CRM and Salesforce Blog

Simple Dynamics CRM Lookup using Kendo UI

Using third party libraries is a great way to speed up development and save some money by not having to reinvent the wheel. If you are a developer and haven’t checked out Telerik’s suite of controls, I definitely recommend it. They have a great set of javascript widgets and frameworks called Kendo UI which works very well with Dynamics CRM.  In this post I will show how easy it is to make your own custom CRM Lookup in just a few lines of code thanks to Telerik’s AutoComplete control.

First, we need the Kendo libraries. If you haven’t purchased the Kendo controls, you can download them for a trial here.  Then you can add the references to the header of your html page. This example will also require jQuery so be sure to include it as well.

<head>
    <title></title>
    <link href="kendo.common.min.css" rel="stylesheet" />
    <link href="kendo.default.min.css" rel="stylesheet" />
    
    <script src="jquery.js"></script>
    <script src="kendo.web.min.js"></script>
</head>
 

Next, add a simple input tag to the page and give it an ID. This will become the Lookup control.

<body>    
    <input id="accounts" />
</body>
 

Then add some script as well to execute a function on document ready. To keep it simple, this example uses an inline script tag.

<script>
    $(document).ready(function () {
    
    });
</script>
 
 

Now, inside the ‘ready’ callback, we can setup the Kendo AutoComplete control. First define the Schema Name of the entity you want the Lookup to point to and then define the Schema Name of the attribute that you would like to display in the Lookup dropdown.

var entityName = "Account";
var primaryAttribute = "Name";
 

 

Now you can create the Kendo AutoComplete control using the ID of the input element you added in the second step. The Kendo data source supports OData so we can easily set it up to hook up to CRM’s OData endpoint. Since OData is case sensitive, make sure your entityName and primaryAttribute are set correctly.

$('#accounts').kendoAutoComplete({
                dataSource: {
                    type: "odata",
                    serverFiltering: true,
                    transport: {
                        read: {
                            url: window.parent.Xrm.Page.context.getClientUrl() + 
                                 "/XRMServices/2011/OrganizationData.svc/" + entityName + "Set",
                            dataType: "json"
                        }
                    }
                },
                dataTextField: primaryAttribute,
                animation: {
                    open: {
                        duration: 0
                    },
                    close: {
                        duration: 0
                    }
                }
            });
 

If you attempt to test your page now with just the code so far, you will notice that it won’t quite work just yet.  Kendo by default will try to use some OData parameters that the CRM OData endpoint doesn’t support. Therefore we have to setup a parameterMap function on the transport object so we can remove some of the unsupported filters.

Below is the updated transport object with the new parameterMap function. This function will set ignoreCase to false on any filters passed in.  If ignoreCase is set to true then Kendo will use the ‘tolower’ OData filter which CRM doesn’t support.  Kendo will also use the unsupported $inlinecount and $format filters as well so we need to remove them from the list.

transport: {
    read: {
        url: window.parent.Xrm.Page.context.getClientUrl() + "/XRMServices/2011/OrganizationData.svc/" + entityName + "Set",
        dataType: "json"
    },
    parameterMap: function (options, operation) {
        if (options.filter && options.filter.filters) {
            for (var i = 0; i < options.filter.filters.length; i++) {
                // CRM odata doesn't support 'tolower'
                options.filter.filters[i].ignoreCase = false;                       
            }
        }

        // CRM odata doesn't support $inlinecount or $format
        var paramMap = kendo.data.transports.odata.parameterMap(options);
        delete paramMap.$inlinecount;
        delete paramMap.$format;

        return paramMap;
    }
}
 

Now your page is ready to go and you can upload all the necessary files (kendo.common.min.css, kendo.default.min.css, jquery.js, kendo.web.min.js and your html page) to a CRM solution. Then embed your html web resource to a form and you should see a text box like so:

image

As you start typing into the box, it will make a CRM OData call filtering by the characters you typed. By default, each character pressed will hit the OData endpoint but you can set ‘minLength’ on the AutoComplete control to limit the number of characters required before a search is performed. All the matches found will be displayed in a nice dropdown shown below.

image

There you have it, a simple custom Lookup control for CRM! A couple things that could be done to expand this control even more, would be to add custom styling to make it look more like the Lookup control in CRM as well as the ability to filter the records even more, by active records for example.

For the full source code, check out the code sample on MSDN here.

Topics: Microsoft Dynamics CRM Microsoft Dynamics CRM 2011 Microsoft Dynamics CRM 2013