FetchXML is a style of late bound queries that provides a similar experience to using SQL in an application. The convenience of it lends itself to being used in your code base. Developers will often copy and past FetchXML into their methods from blog posts online or even examples out of the Dynamics CRM SDK. The challenge is that the convenience of FetchXML comes at a cost that is not only insidious, but I consider a form of hidden technical debt in Dynamics code bases.You can look at FetchXML as an equivalent subset of a SQL statement minus all the wonderful options you get when using SQL Server directly. It’s often times much faster to find a nice fetch statement from either online or even building your own using the advanced find dialog and then getting the fetch statement that was generated. It is often times more tedious to create the same query using the QueryExpression object in the CRM SDK. I’ve often had to fiddle with these code expressions to get them right and it can certainly take up a lot more lines of code then slapping a fetch statement in and formatting it to take up less space.
Create the Query String
As a technical lead on my projects I routinely scan the code base to make sure everyone is on the same page as far as development style, agreements we’ve made as a team on code structure and design patterns. One thing I routinely will bring up in code reviews is the use of FetchXML. While I won’t go so far as to say FetchXML is banned in backend code bases on my projects it requires a really good reason because of the challenges I’ve found it presents later down the road in projects.
Limited Visibility of Broken Queries
My preferred style when constructing a code base is to create something that will quickly break during development. What I mean by this is I want to know something is wrong very quickly as the architecture and system model are evolving over time. This is one of the reasons I believe it is very valuable to create or generate a system model within your code base that the business logic relies on to know what objects are in the system. If for example, we decide to remove a field on an entity that is tied to a piece of code team should see code compilation errors because something is wrong. This allows us to easily see and fix issues. When it comes to FetchXML however this doesn’t happen.
I see FetchXML more like a type of hard coding of logic. Many developers have a tendency to hard code entity and attribute names. This code pattern that is usually one the first things we address when I have a new developer who hasn’t worked with me before. Many developers have become used to hard coding for speed, but the fact is plugins with hard coded strings become an absolute nightmare to fix after months of development. When things change it will never break the code base because Visual Studio doesn’t see anything wrong. There’s no way for it natively check that the fetch statement is still valid or not based on the current system schema. When we code our business logic this way we typically have to rely on the testers to find the problem and let us know. In my experience it’s more rare that developers will find a newly invalid fetch statement before testers in a large code base. I would much rather the team find and correct these issues proactively rather than let it end up in the test cycle and let the testers feel like they scored points on us by finding a bug.
Exposure to Future Breakage (Hidden Bugs)
When building a system it’s best to think of it’s architecture in terms of supportability and maintainability. If the system truly adds business value and achieves the outcomes it’s meant to then the initial development cycle is very brief in the lifespan of a system. The reality is man decisions we make during greenfield project development will remain in that system until it dies. If we can do things that make maintainability easier we ideally should take those steps. Fetch statements are hidden time bombs in Dynamics code bases because even if everything goes well during the initial development phase at any time in the future it could break. I personally feel like I’m doing a customer a disservice if I allow something like this to persist in the system knowing that it very well may cause problems even after I’ve left. You simply can’t predict when a hard coded fetch statement will break. In my opinion, it’s a risk factor that we can proactively avoid up front.
My default method of creating queries in Dynamics is using the QueryExpression object. It allows you to do everything you can in fetch and since it’s compiled code it will break when things go wrong. If you want to save yourself the pain of hunting down hidden bugs it’s usually easier when you use complied code so that you can see issues as soon as they happen. The more hard coded strings you have in your code base including entity and attribute names the more pain you’ll feel later down the road when bug arise. Software systems that last are always evolving and adapting to the needs of the business. One of the attributes of a good code base is one that is structured so that it can more easily be changed in the future and doesn’t hide bugs as those changes occur.