In this post I will give an example in a real life scenario when this feature will be used. That is the scenario when a field in an entity needs to be numerically auto-generated with a particular pattern.
Auto number in Salesforce vs Dynamics 365
In Salesforce, auto-number is an out of the box feature when defining an object, as in the image below.Meanwhile in Dynamics 365 this feature is not there out of the box in Version 8 and before. This was only introduced in Version 9, but it is not part of the entity definition user interface. You need to add it programmatically via Web API or using SDK. More details can be found here: https://docs.microsoft.com/en-us/dynamics365/customer-engagement/developer/create-auto-number-attributes.
Another approach, which is the purpose of this post, is to build a custom plugin that will generate the next sequence number for the field in question.
Auto number custom plugin
In this approach we will create an entity, named as autonumber_config, that will centrally manage the sequence number and number format for a list of several fields in one or more entities. That is also the advantage of this approach over the built-in one where the auto number is configured individually in each field/entity.The autonumber_config entity will have following fields.
- entity_name
- field_name
- field_format
- next_number
The logic for this plugin is that, whenever a record is created in the target entity that the plugin is registered to, the plugin will query the respective record in autonumber_config entity to obtain the current value of next_number field, then increase it by 1 and update back to the autonumber_config entity. The value of next_number field, together with field_format field, will be used to generate the actual auto-number for the target field in target entity.
Now comes the issue. When multi users try to create a new record of the same entity at the same time, there will be chance that the same next_number value will be obtained for multiple records.
That is when optimistic concurrency comes into play. The idea is that, after the plugin has obtained a next_number value, when updating the new value back to the record it will use the UpdateRequest with the ConcurrencyBehavior set to ConcurrencyBehavior.IfRowVersionMatches. If request is successful, the next_number value can be used as a valid number.
If a FaultException exception thrown back from service with ConcurrencyVersionMismatch (code=-2147088254) then it means that the record has been updated by another user. In that case the plugin will try to increase next_number value by 1 and update again. This can be repeated until a new next_number value can be updated.
Enough talk, time for code. Below is the main part in the Execute method of the plugin.