As a follow-up to last week’s post on conditional action buttons, I wanted to dive a bit deeper into a very cool, but completely undocumented, feature that exists in the Dynamics 365 Portal product: the Filter Criteria for action buttons.
In case you didn’t read last week’s post, I’ve copied and pasted the introduction to action buttons to save you a click:
If you’re not familiar with action buttons, they are a pretty powerful feature included in Entity Lists and Entity Forms allowing you to add buttons that perform actions (I know, they are well named!). For example, action buttons allow you to perform actions such as:
Within an Entity List, non-record-specific actions (like download or create) appear above the list, and the record-specific actions (like edit, delete, and run workflow) appear as options in a dropdown in an additional column in the grid. On an Entity Form, you have the choice of adding these buttons above or below the form itself. Of course, the necessary Entity Permissions are required for a user to perform these actions.
If you haven’t seen the Filter Criteria field in the action button configuration, then it’s probably because you’ve never turned on the Advanced Settings option available in the Action Button Configuration section on the Entity Form form, or the Grid Configuration section on the Entity List form:
Once you’ve checked that option, you should be able to see the Filter Criteria field within the configuration for action buttons.
Normally, when you create an action button, it’s always shown unless you use JavaScript, CSS or some other technique to hide them (again, see my previous post). Filter Criteria allows you to hide action buttons if the record doesn’t match a FetchXML query.
To hide an action button using
Let’s look at an example, which I’ve taken from an Edit button configured for the out-of-the-box Managed Opportunities Entity List in the Partner Portal:
<fetch version="1.0" output-format="xml-platform" mapping="logical" distinct="false"> <entity name="opportunity"> <attribute name="opportunityid" /> <order attribute="name" descending="false" /> <filter type="and"> <condition attribute="adx_partnercollaboration" operator="eq" value="0" /> </filter> </entity> </fetch>
As you can see, the Edit button in this case is only shown if the adx_partnercollaboration attribute equals 0.
Before the Portal code displays the action button, it executes a modified version of that FetchXML, and will only display the action button if the record is in the result set.
The query is modified for performance reasons – the code doesn’t want to have to go through all of the results of the query. This would be bad if there were a lot of records, especially if there were more than 5000 records in the result set, and then it had to start worrying about paging. So how is the query modified? The Portal code adds an IN condition on the Primary ID of the record to limit the result set. If the record in question is returned by the FetchXML query (meaning it matched all the other aspects of the FetchXML query), then the action button is shown; if not, it is hidden. In the case of the Entity List, all of the IDs of the records currently being shown in the list are included in the IN clause – this is done so that the visibility of a button for all currently shown records can be determined in a single query.
So now that we’ve seen how it works, why is this useful?
Microsoft has leveraged this functionality in the Partner Portal (and if I had to guess, it was probably added to the product because they wanted to build out some scenarios in the Partner Portal) to configure different Edit buttons for the same record type. So in the above example, there are actually multiple Edit buttons configured, so it is not necessarily about hiding an Edit button, but instead choosing which Edit button the user will see based on attributes of the opportunity. This allows you to point the user to different Entity Forms based on a value in the record itself.
As I mentioned, this feature only allows you to take into consideration a FetchXML query based on the record (and if you want to make a more complicated FetchXML query, you could do related records as well). However, you can’t take into account things like the current user’s permissions, as this type of information can’t be included in the FetchXML query.
There are certain action buttons that don’t apply to specific records, like Download or Create, yet the Filter Criteria field can still be configured for them. Since there is no record to query against, what does adding a Filter Criteria do for these buttons? In short, nothing. Feel free to put whatever you want in these fields, it won’t have any affect on the visibility of these buttons. As far as I can tell, the value in that field is never used by the Portal code. If I had to guess, the Portal product team implemented a reusable configuration module for the action buttons, and didn’t hide the ones for the buttons where that particular field doesn’t apply.
If you’re curious how I was able to determine how the functionality worked, it all goes back to one of my old blog posts. No, I don’t have special access to product team developers that tell me how it works. Instead, I have access to the full source code for the product – and so do you! At least, we all have access to v8.3 code, which for most features, hasn’t changed a whole lot.
I often find myself digging through the Portals Source Code Release, or more accurately, the xRM Portals Community Edition, to figure out how something works. It’s an extremely useful technique, and something I think you need to learn how to do if you want to get serious about Dynamics 365 Portal development.
I’d also to point out this Microsoft Dynamics 365 Community forum post that I found while researching for this post, which includes helpful information on this topic from Business Applications MVPs, and Portal Experts, Colin Vermander (@koolin_) and Nick Doelman (@readyxrm).
Hey Nick,
I have a prevailing issue as posted, came across your blog and need your help further on this one… https://community.dynamics.com/crm/f/117/t/358575
}}..
Help! Is it possible to hide/show Action Buttons on forms based on the logged user? I was thinking that injecting the {{user.id}} into the fetchxml entered within the Button’s Filter Criteria should work…. but it’s not working. It seems the Filter Criteria only accepts fetchxml. Is this correct? The fetchxml works with hard-coded GUID or without the logged user condition but this is needed because different users will have access to the same view. Splitting entity forms/views by user does not apply here. Example: A delegated user must be able to interact with all records but can ONLY SUBMIT his own record.
Here is my current fetchxml with hardcoded GUID:
Tried:
No luck!
Thanks in advance for your help!
Tim
Hey Tim – I’ve responded directly on your Dynamics 365 Community Forum post – long story short unfortunately I don’t think this is possible.
Hi Nicholas, thanks for this incredible post. Solved some riddles and saved much time. Regards, Niklas
This is brilliant Nick.
I am able to hide the Edit action button, but not the create action button.
what condition we need to use to hide the create button as for the edit one I used statuscode = 1
I don’t think the create would work – since the record doesn’t exist yet, it wouldn’t be possible to compare anything against the condition.
Nick
you can use something like this
$(“.entitylist.entity-grid”).on(“loaded”, function () {
//$(‘html[dir=ltr] .grid-actions a.btn.action’).show();
$(‘html[dir=ltr] .grid-actions a.btn.action’).remove();
});
What about having to filter for Associate? When I put in a Filter Criteria, nothing changes in the number of records displayed within the module.
The filter criteria affect the buttons only. The rows will still show.
Nick
Hello,
How would one add a custom button on the list/grid and do some custom logic for that record selected on the grid that cannot be done via configuration? And that is if I didn’t want to Edit and open a form for that selected record.
Great question! That is the topic for our next blog post actually, so stay tuned!
Nick
Do you happen to know if this functionality has been removed/deprecated? It isn’t working for me…
Nevermind, I solved it by using a simplified query (no attributes on the fetch element and no attribute or order elements):
$(‘html[dir=ltr] .grid-actions a.btn.action’).remove();
This removes both Download & Create button. Need to hide only Create button. How?
Try: $(‘html[dir=ltr] .grid-actions a.btn.create-action’).remove();
Or disable the ability to create via the list, if no one should see that button.
Nick
I cannot get the filter criteria to work with the link-entity with type “not any” added to a filter. Is this filter type not supported by this feature? I want to disable a “create related record button” if a related record has already been created. The filter seems to work in fetch builder as I expect but it doesn’t disable the action button. I can achieve this with JS but want to avoid using it as JS can be undone.
This is the filter I am using:
Hmm, that’s interesting. We were able to replicate your findings, so I guess it is not supported. Not sure why. I would recommend submitting a support ticket to Microsoft – my guess is that it isn’t intentional.
Nick