Tuesday 2 August 2016

CRM 2015 - Window OnLoad Unable to get property 'value' of undefined or null reference

We recently had a problem where we were receiving the following error in a single environment only.


Due to it only occurring in one environment I presumed it was a deployment issue.  However I was incorrect.

We were receiving the above error because we restored a full database from one environment to another.  We had some JavaScript which was checking the owner of a record.  The owner was displayed on the record however it was from an external domain.

Because of this it threw an error right down in the CRM depths at:-

function crmForm_window_onload_handler(eventObj,eventArgs){

  try{

    var eContext=Mscrm.FormUtility.constructExecutionObject(eventObj,0,null,null);

    eContext=Mscrm.FormUtility.constructExecutionObject(eventObj,0,null,eContext)

    loadInsideView();

    eContext=Mscrm.FormUtility.constructExecutionObject(eventObj,1,null,eContext)

    CEI.Initialize();

  } catch(e) {

    displayError('window', 'onload', e.description);

  }


}

So if you see an error occurring like this that did not appear in other environments make sure you confirm that the record you are looking at is correctly mapped to the new domain.

Tuesday 31 May 2016

CRM 2015 - Filtered View using a Lookup in the Criteria

Consider you want to use a lookup as part of your filter criteria.  You would presumably use "Where lookup Equals mylookup" however when doing this the following fetch XML is returned.



When exporting to another environment it appears that it is looking at the GUID and not the name.  The short term fix I'm using is to instead use Contains.

Wednesday 13 May 2015

CRM 2015 - Microsoft.Crm.Setup.Server.GrantAspNetServiceAccountAccessAction failed.: The parameter is incorrect

Came across this error when doing an install of CRM 2015.

Microsoft.Crm.Setup.Server.GrantAspNetServiceAccountAccessAction failed.: The parameter is incorrect


We looked into the Active Directory and in the OU found some entries "Account Unknown".  We deleted these items and then the installation worked.

Thursday 4 December 2014

CRM 2015 Review

CRM 2015 Review

Microsoft have released CRM 2015 which rather than being a complete look and feel update that we saw with CRM 4, CRM 2011, and CRM 2013 is instead an update on the changes that were included in 2013.

The release is more focused on functionality updates rather than the design updates many CRM users are useful.  This is obviously some good news as there is nothing more annoying than training business users in one look and feel only to have it completely change every 12-24 months.

This article is my observations of the differences between two vanilla instances of CRM (One 2013, one 2015).  There is probably a fair bit of information I have missed which can be discovered via Microsoft’s documentation.  However onto the article!

CRM Ribbon

The first difference when logging into 2015 is there is a new search box and icon clearly visible on the ribbon.
CRM 2013 - Ribbon

CRM 2015 - Ribbon

Entering a keyword(s) into the search box returns the results found by the query.  Currently it appears to be limited to Account, Contact, Lead, Opportunity, User, Competitor, Activity, and Case entities.  This is a bit of an issue if you have a CRM implementation with a lot of custom entities however for now I’m presuming it might be a configuration I haven’t found yet.

The icon beside it is the Advanced Find icon which pops up the standard Advanced Find window.  Advanced Find could often get lost in CRM2013 and having it in such and easy to find place will definitely help regular business

Colours and Theming

The colours of some of the OOB entities have changed which seems like a slightly odd decision (I don’t recall anyone really complaining about it) however the standard ribbon functionality seems to be the same.

CRM 2013 - Entities Menu


CRM 2015 - Entities Menu

The forms also appear to have had minor changes to colours however if you have clients using CRM 2013 then they should be able to continue navigating around the system easy enough.

CRM 2013 - Account Form


CRM 2015 - Account Form


Navigation Changes

The areas are generally the same as CRM 2013 however some slight changes include the splitting of the old Administration area within Settings.
CRM 2013 - Administration


CRM 2015 - Administration


CRM 2015 - Security

The new setup is probably a more logical design as the Security items now have their own area including the new Positions and Hierarchy Security items.  Hierarchy Security seems like it needs its own post so I won’t go into any detail here.
The Administration area also has the Microsoft Social Listening Configuration which allows you to use Microsoft’s Social Listening solution to track Facebook, Twitter, YouTube etc. information which can then be linked back into Accounts and Contacts so you can see how clients and the public are relating to your company.

Business Rules

An interesting addition to CRM 2013 was Business Rules.  The concept was fantastic as it in theory reduced the JavaScript required, however in practise the reality was a two basic limitations made them almost unusable.
Consider these scenarios:-

Scenario One

So you have a client whose preferred method of contact is Email.  Then logically they need to provide an email address.  However what if there preferred method is Phone, Fax, or Mail?  Programmatically you want the following:-
·         If Preferred Method of Contact is Email Then
o    Make Email Mandatory
·         Else If Preferred Method of Contact is Phone Then
o    Make Phone Mandatory
·         Else If Preferred Method of Contact is Fax Then
o    Make Fax Mandatory
·         Else If Preferred Method of Contact is Main Then
o    Make Address 1: Street 1 Mandatory

In CRM 2013 you could not do If/Else so the above required four separate Business Rules which becomes difficult when you have to start doing this for multiple fields.

Scenario Two


If you want to ensure you capture either a Home or Mobile phone for a client then you would like something like:-
·         If Home Phone or Mobile Phone do not contain Data Then
o    Home Phone or Mobile Phone are mandatory
·         Else
o    Home Phone or Mobile Phone are not mandatory
In CRM 2013 all conditions were “and” so the above wouldn’t work.  We could reverse it and say where Home Phone and Mobile Phone don’t contain data however what if we want something more complex? CRM 2015 opens up this functionality by allowing and/or.

CRM 2015 - Business Rule

Combining the If/Else and And/Or allows for a lot more customizability for the Business Rules which should greatly reduce the need for a programmer to develop JavaScript solutions leaving them to worry about more critical functionality.

Calculated and Rollup fields

CRM 2015 allows for fields to be of three types:-
·         Simple
The standard type from previous versions of CRM for data entry.
·         Calculated
Allows for Conditions if required (similar setup to Business Rules) and then allows actions using either a current field or one of the following formulas:-
       ADDDAYS
       ADDHOURS
       ADDMONTHS
ADDWEEKS
       ADDYEARS
       CONCAT
       SUBTRACTDAYS
       SUBTRACTHOURS
       SUBTRACTMONTHS
       SUBTRACTWEEKS
       SUBTRACTYEARS
       TRIMLEFT
       TRIMRIGHT
This is useful if you want to create a description for a record for example by combining multiple existing fields.
CRM 2015 - Calculated Field


·         Rollup
Rollup uses a related entity to do one of the following functions:-
       SUM
       MAX
       MIN
       COUNT
This is good to see how many contacts an Account has, or the total of child currency fields.
CRM 2015 - Roll up Field



Wednesday 26 November 2014

No response and catching errors cURL PHP

I covered this in another post however I thought it deserved its own "snippet". I use cURL when connecting to CRM's SOAP service as I found it easy to use almost right away.

Because I could use it right away I didn't really spend anytime thinking about it. That was until code that had been working for months suddenly stopped. I received no response from the service but I couldn't figure out why.

The investigation led me to the following function:
 public static function GetSOAPResponse($url, $request) {
    // Set up headers.
    $headers = array(
      "POST " . "/Organization.svc" . " HTTP/1.1",
      "Host: yourorganisation.api.crm5.dynamics.com",
      'Connection: Keep-Alive',
      "Content-type: application/soap+xml; charset=UTF-8",
      "Content-length: " . strlen($request),
    );
 
    $cURLHandle = curl_init();
    curl_setopt($cURLHandle, CURLOPT_URL, $url);
    curl_setopt($cURLHandle, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($cURLHandle, CURLOPT_TIMEOUT, 60);
    curl_setopt($cURLHandle, CURLOPT_SSL_VERIFYPEER, FALSE);
    curl_setopt($cURLHandle, CURLOPT_FOLLOWLOCATION, TRUE);
    curl_setopt($cURLHandle, CURLOPT_SSLVERSION, 3);
    curl_setopt($cURLHandle, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1);
    curl_setopt($cURLHandle, CURLOPT_HTTPHEADER, $headers);
    curl_setopt($cURLHandle, CURLOPT_POST, 1);
    curl_setopt($cURLHandle, CURLOPT_POSTFIELDS, $request);
    $response = curl_exec($cURLHandle);
    curl_close($cURLHandle);
 
    return $response;
  }

In such a small project such as this when something stops working the question is usually what dependencies have changed? I presumed something at the Microsoft end (I was using CRM Online) had changed but the question was what.

A quick Google search on curl_exec shows that it does not throw exceptions due to it being a C library all wrapped up. So in order to get an exception you need to instead use the following:
if( ! $response = curl_exec($cURLHandle)) 
   { 
       trigger_error(curl_error($cURLHandle)); 
   }

This will fire off a PHP exception for the cURL error. Which led me to my real issue!

Microsoft due to the 'poodle' vulnerability in SSL updated to SSL version 4. The code I had above (grabbed from some other persons post presumably!) has the SSL Version explicitly stated. By changing this to 4 the issue went away. However I thought it was easier to just remove that setting and this seemed to do the trick (and hopefully makes it a bit more robust for future use!). So the updated code is below.

public static function GetSOAPResponse($url, $request) {
   // Set up headers.
   $headers = array(
     "POST " . "/Organization.svc" . " HTTP/1.1",
     "Host: yourorganisation.api.crm5.dynamics.com",
     'Connection: Keep-Alive',
     "Content-type: application/soap+xml; charset=UTF-8",
     "Content-length: " . strlen($request),
   );
 
   $cURLHandle = curl_init();
   curl_setopt($cURLHandle, CURLOPT_URL, $url);
   curl_setopt($cURLHandle, CURLOPT_RETURNTRANSFER, 1);
   curl_setopt($cURLHandle, CURLOPT_TIMEOUT, 60);
   curl_setopt($cURLHandle, CURLOPT_SSL_VERIFYPEER, FALSE);
   curl_setopt($cURLHandle, CURLOPT_FOLLOWLOCATION, TRUE);
   curl_setopt($cURLHandle, CURLOPT_HTTP_VERSION, CURL_HTTP_VERSION_1_1);
   curl_setopt($cURLHandle, CURLOPT_HTTPHEADER, $headers);
   curl_setopt($cURLHandle, CURLOPT_POST, 1);
   curl_setopt($cURLHandle, CURLOPT_POSTFIELDS, $request);
   if( ! $response = curl_exec($cURLHandle)) 
   { 
       trigger_error(curl_error($cURLHandle)); 
   }
   curl_close($cURLHandle);
 
   return $response;
 }

Wednesday 12 November 2014

CRM 2011 Workflow execution

As newer versions of CRM are released I find myself wondering when we might reach a point where plugin code might not be required. Between Workflows, JavaScript, and Business Rules CRM it is getting easier to customize in more and more powerful ways.

Every time I think of this though I find a "gotcha" which makes me realise plugin code will still be required for a while yet.

We had an issue where the client told us that there was a bug with auditing in CRM 2011. The problem was two different sets of audit changes were listed.

The problem ended up being not with the auditing but with the workflows. Workflows do not capture data at the time of change rather they run against the data at time of workflow execution. This is a rather obvious but interesting difference.

In our case the record needed to be recommended and then approved. We had a workflow which was created and run on "Status" change that on Approval would push data to a new entity . In a real world scenario we would presume that no one would recommend and immediately approve however there would be many cases I’m sure where a fast change such as this is completely possible.

Where a fast change like this occurs chances are that 1) the workflow has not yet been created by CRM yet or 2) the workflow has been created and not run. The issue of course is the workflow will look at the Status and see "Approved" both times it runs!

So if you have a field that is updated multiple times in quick succession I suggest having a plugin (which snapshots that data) rather than relying on a workflow.

NOTE: I haven't confirmed this in 2013 or 2015 so they might actually handle snapshots in workflows? The above talks about CRM 2011 specifically.

Sunday 7 September 2014

CRM 2011 - JavaScript - Access Is Denied

While testing a CRM 2011 instance we ran into a issue where the JavaScript kept throwing an "Access is Denied" message. This only occurred on one system and no others. What we discovered was the user was looked in using the fully qualified URL ie:- http://crmtroubleshoot.blogspot.com.au While everone else was using the short URL something like the following http://crmtroubleshoot When calling the service through JavaScript we use the following getClientUrl() + "/XRMServices/2011/Organization.svc/web"; This was returning the short URL which the server thought was a different server to the long name. The user re logged in with the Short URL and the problem went away. If you have DNS suffixes set then you need to log in to CRM using the short name. I suspect (unconfirmed) if you don't have the DNS suffixes set then using the long URL should be fine.