Skip to main content

Notifications

Announcements

No record found.

Microsoft Dynamics 365 | Integration, Dataverse...
Suggested answer

How to use preImage and postImage in Plugins

(0) ShareShare
ReportReport
Posted on by 355

I created a Plugin which is triggered while updating a Movie and shows an error when the fields "Title" and "Year" are left empty. 

I also need to use PreImage to check whether the value is present in the pre-image but not in the target, i.e. if it was erased by the user.

I wrote the following code, but it doesn't work, can you please tell me if I'm using preImage and PostImage correctly?

public void Execute(IServiceProvider serviceProvider)
        {
            var context = new PluginContext(serviceProvider);
            var service = context.CrmServiceSystem;
            var trace = context.TracingService;
            var target = context.GetTarget();

            var preImage = context.GetPreImage();
            if (target == null)
                return;
            var postImage = preImage.Merge(target);
            
            // case 1: the field is left empty and it was empty before too: 

            if((!preImage.Attributes.Contains("title") && !postImage.Attributes.Contains("title"))
                ||
                
                // case 2: the field was not empty, but the user deleted the content:
                (preImage.Attributes.Contains("title") && !postImage.Attributes.Contains("title")))
            {
                throw new InvalidPluginExecutionException(OperationStatus.Failed, "Title can't be null");
            }

            if ((!preImage.Attributes.Contains("year") && !postImage.Attributes.Contains("year"))
                ||
                (preImage.Attributes.Contains("year") && !postImage.Attributes.Contains("year")))
            {
                throw new InvalidPluginExecutionException(OperationStatus.Failed, "Year is null!");
            }
           
        }

For instance, I have this issue: when the Year is already correct and I don't modify it, I get the error "Year can't be null". As I merged the PreImage with the target, why the value is not recognized?

  • Guido Preite Profile Picture
    Guido Preite 54,069 Super User 2024 Season 1 on at
    RE: How to use preImage and postImage in Plugins

    you need to make sure that this director field is inside the postimage, otherwise you can't get the correct value from it

    more than this I can't suggest as I don't have access to your instance, so if there are other parts of your code that may interfere with this logic

  • Joel D Profile Picture
    Joel D 355 on at
    RE: How to use preImage and postImage in Plugins

    I checked whether the lookup is empry but the plugin does not work for the director field: when I don't edit the text inside it throws the exception.

    My updated code is the following:

    EntityReference director = postImage.GetAttributeValue<EntityReference>("director");
    if (director == null)
    throw new InvalidPluginExecutionException(OperationStatus.Failed, "Director is empty!");

  • Guido Preite Profile Picture
    Guido Preite 54,069 Super User 2024 Season 1 on at
    RE: How to use preImage and postImage in Plugins

    EntityReference is null when is not set, when is set means is filled

    if (director == null) { /* lookup is empty */} else { /* lookup has value */ }

  • Joel D Profile Picture
    Joel D 355 on at
    RE: How to use preImage and postImage in Plugins

    Thanks.

    What if I wanted to do the same with a lookup field, e.g I want to check the filed "Director" which is a lookup named "director_id" ?

    I defined the variable as in the following:

    EntityReference director= postImage.GetAttributeValue("director_id");

  • Suggested answer
    Guido Preite Profile Picture
    Guido Preite 54,069 Super User 2024 Season 1 on at
    RE: How to use preImage and postImage in Plugins

    how the plugin is executed (pre, post, async, sync) and the registration of images (pre, post) and their attributes is done entirely with Plugin Registration Tool (by the executable from nuget or using the one inside XrmToolBox)

    in your code I don't think it's necessary that Merge operation that you are doing (because I don't know how it will merge the attributes) but if you are in a post sync, the attributes on the image will be the same as the attributes of the target/current entity.

    also in your check I would avoid the use of Contains, Contains returns if the attribute is present inside the collection of attributes or not (and you can have a case where the attribute is there but is null for example)

    I would use the GetAttributeValue, something like this

    string year = postImage.GetAttributeValue<string>("year");

    if (String.IsNullOrWhiteSpace(year)) { throw new InvalidPluginExecutionException(OperationStatus.Failed, "Year is empty!"); }

    in my code I assumed that year is a string, if is a whole number you should use an int?

    int? year = postImage.GetAttributeValue<int?>("year");

    if (!year.HasValue) { throw new InvalidPluginExecutionException(OperationStatus.Failed, "Year is empty!"); }

    to summarize:

    1) just use a post image with just these two attributes

    2) use GetAttributeValue instead of Contains to check if the value is actually null

  • Joel D Profile Picture
    Joel D 355 on at
    RE: How to use preImage and postImage in Plugins

    Thank you for replying.
    @Guido I wrote the following, is it correct? How can I trigger the plugin as post sync, do you mean that I should register it as post-operation?  

    var targetEntity = context.GetTarget();
    
    var preImage = context.GetPreImage();
    if (targetEntity == null)
        return;
    var postImage = preImage.Merge(target);
    
    if (!postImage.Contains("title"))
            throw new InvalidPluginExecutionException(OperationStatus.Failed, "Title is empty!");
    if (!postImage.Contains("year"))
            throw new InvalidPluginExecutionException(OperationStatus.Failed, "Year is empty!");
    

  • Suggested answer
    Guido Preite Profile Picture
    Guido Preite 54,069 Super User 2024 Season 1 on at
    RE: How to use preImage and postImage in Plugins

    for the requirement you wrote (shows an error when the fields "Title" and "Year" are left empty) you just need to trigger your plugin as post sync on both fields and use a single post image containing these two fields.

    in your plugin you get the fields from the post image and if one of them is empty then you show the error.

  • Suggested answer
    Community Member Profile Picture
    Community Member Microsoft Employee on at
    RE: How to use preImage and postImage in Plugins

    Here is how I have seen it used in plugins before:

    Entity preImage = (Entity)context.PreEntityImages["Image"];

    If not this, can you add any tracing just after you set the preImage variable to see whats in it?

Under review

Thank you for your reply! To ensure a great experience for everyone, your content is awaiting approval by our Community Managers. Please check back later.

Helpful resources

Quick Links

Congratulations 2024 Spotlight Honorees

Kudos to all of our 2024 community stars! 🎉

Meet the Top 10 leaders for December

Congratulations to our December super stars! 🥳

Start Your Super User Journey

Join the ranks of our community heros! 🦹

Leaderboard

#1
André Arnaud de Calavon Profile Picture

André Arnaud de Cal... 291,759 Super User 2024 Season 2

#2
Martin Dráb Profile Picture

Martin Dráb 230,468 Most Valuable Professional

#3
nmaenpaa Profile Picture

nmaenpaa 101,156

Leaderboard

Product updates

Dynamics 365 release plans