Wednesday, February 11, 2015

Find All References to a Custom Workflow Activity in Dynamics CRM 2013

If you ever need to find all the workflows that have references to a custom workflow assembly, you can query the Xaml column on the Workflow entity.  Using ODate is the fastest way:


If you are on-prem, then you can also do this via SQL:

FROM   workflow wf 
WHERE  xaml LIKE '%MyCustomWorkflowActivityClassName%' 

Tuesday, February 10, 2015

Stuck Dynamics CRM ImportJob importing a Solution

Did you know that you can view the progress of your import by using Advanced Find to query Import Jobs?  If you ever "lost touch" with the progress bar window, this can be very useful.  I have a saved view that displays the imports from the last 7 days in descending order.

Unfortunately, jobs can get stuck during import and prevent you from importing your solution again.  In that situation, you need to manually delete the stuck job.  Fortunately this is super easy with the Advanced Find you created above.  There is a special Delete button on this view.

You can also do it programmatically with the early-bound classes and a Linq query in the Service Context:

var xrm = new XrmServiceContext("Xrm");
var deadJobs = xrm.ImportJobSet.Where(x => x.CompletedOn.Equals(null));

foreach (var job in deadJobs)
    Console.WriteLine("Deleting Job Created On: " +job.CreatedOn);
    xrm.Delete(ImportJob.EntityLogicalName, job.Id);

Monday, November 17, 2014

CRM 2013 Invalid Argument FetchXML Report Errors on Premise

I love it when my former-self comes to the rescue of my present self.  I have been wrestling with an SSRS error that I knew I had seen before.  In searching for an answer, I ran across this blog post I wrote a couple years back.  I'm going to copy it here, just in case my former employer decides to take it down:

Even though the Report Wizard has some inherent limitations, it is still a useful tool for end-users that want ad-hoc reporting, or if you want to see beyond the 10,000 record limit when exporting to Excel.  You may find however that reports created by the Report Wizard return an "Invalid Argument" error. 
This happened to me recently so I followed my usual debugging steps but that did not help because the browser didn't return an error.  I checked the CRM and SSRS event logs, but there wasn't any helpful information in the errors that were logged.  Next I checked the SSRS HTTP Log and found some interesting information.  Note, the default location for the log is:
\Microsoft SQL Server\\Reporting Services\LogFiles
In the log I saw that I was getting a security error:
System.ServiceModel.Security.SecurityNegotiationException: A call to SSPI failed
When I looked up this error, I ran across KB2590774 which described the exact issue I was facing...unfortunately it involved SPNs; probably my least favorite administrative topic.
The instructions are a little contradictory.  It says that all you need to do is setup an SPN for the CRMAppPool...unless you are running IIS in Kernel Mode (generally the recommended configuration).  If running Kernel mode, you are supposed to review the information in the article about SPNs and IIS 7 Kernel Mode.
I read and confirmed that for my configuration (Scenario 2b - Custom app-pool and host header)the recommendation was to register an SPN for my custom URL on the NetBios name (aka, the computer name).  Unfortunately this did not resolve my issue, even after adding "trust for delegation" in AD.  So I tried the KB's recommendation which was an SPN for NetBios name on the CRMAppPool account:
setspn -s HTTP/my_server_name my_domain\my_CRM_app_pool_identity
After that SPN was applied (always using -S to check for duplicates) the FetchXML reports instantly started working!

Friday, November 14, 2014

Easy way to enable DevErrors for Dynamics CRM using IIS Manager

Windows Access Control prevents you from directly editing the Web.Config file for IIS site, so rather than copy/paste, you can use IIS Manager to edit keys via GUI.  To turn the DevErrors key to On you need to change the Section selector to appSettings and click the “…” button in the (Collection) property.  Make sure you click the Apply button (Action menu on right) after making a change:

Wednesday, November 12, 2014

How to Hide Alerts in CRM 2013 Sitemap Menu

Alerts appeared in 2013 to display server-side synchronization.  The information in the alerts can get pretty technical so they may not be appropriate for end-users.  In order to hide them from the menu, you can remove read permissions on the Trace entity (under Core Records).

Tuesday, November 11, 2014

Tricks for working with SetState and SetStateDynamic plugins

There are a couple of tricks to working with SetState and SetState Dynamic plugins.  To get the State that the record is "becoming" you can check the InputParameter "State":

var state = (OptionSetValue) context.InputParameters["State"];
localContext.Trace("Contact State: " + state.Value);

if (state.Value == (int)ContactState.Inactive) return;

To get the Guid of the record, check the PrimaryEntityId property:

Guid targetId = context.PrimaryEntityId;

Monday, November 3, 2014

Using PowerShell Get-ADPrincipalGroupMembership to find a user's groups

I needed to find a good AD group to grant organization wide permissions to an SSRS report and found the Get-ADPrincipalGroupMembership was really useful for querying AD.  The server needs to have the "Active Directory modul for Window PowerShell" feature enabled to allow import-module activedirectory to work:

import-module activedirectory
Get-ADPrincipalGroupMembership [username without domain prefeix] | Get-ADGroup -Properties * | select name, description
Get-ADGroup [group name]