1

One can read about sporadic DUPLICATE_VALUE errors during Upsert in many forums. They mostly occur in Dataloader scenarios with a root cause being Oracle race conditions. But what I have here is not sporadic, but occurs every single time in a specific customer org running our managed app.


The error occurs in a custom save action called on the EDIT page of a custom object. Clicking "Save" also update the child records using this method. I use upsert as the page needs to work for New and Edit scenarios (Should I replace it with insert / upsert?)

public PageReference doSave() {

    // Note: Required as below try/catch would prevent the platforms default behaviour to rollback on error
    Savepoint toBeforeState = Database.setSavepoint();

    // Note: Without try/catch DML errors would be shown as ugly white error page
    try {
        upsert parent;

        for(Child__c child : children) {
            if(child.Id == null) {
                child.mdr_Parent__c = parent.Id;
            }
        }

        upsert children;
    }
    catch(Exception ex) {
        ApexPages.addMessages(ex);
        Database.rollback(toBeforeState);

        // Note: Workaround for Ref.1

        removeInvalidIds();
    }

    PageReference result = (ApexPages.hasMessages()) ? null : new PageReference('/' + parent.Id);
    return result;
}

Ref.1: "Data not available" when using Database.rollback() in custom save action

This how we reproduce this error in a single customer org:

  1. Save and provoke an custom (unpackaged) validation error on the packaged Child__c
  2. Validation Error is displayed
  3. Correct error and click save again
  4. DUPLICATE_VALUE is displayed as follows

System.DmlException: Upsert failed. First exception on row 1; first error: DUPLICATE_VALUE, duplicate value found: unknown duplicates value on record with id: a0IZ0000003WUaY: []

The record of the provided Id does NOT exist after that. I guess the error comes from a Unique field on the child record which is set by a WF rule:

OR( ISNEW(), ISCHANGED( Field1__c ), ISCHANGED( Field2__c ))

Maybe ISNEW() is triggered even by an Upsert on an existing record?!

We are unable to reproduce this in our DE org (even with validation rules) BUT I can stop this error in the customer org when I turn off a workflow rule that is performing a Field Update on the same object.

4
  • Can you provide the part of the code where "children" list is been populated?
    – snehakem
    Apr 8, 2015 at 8:45
  • Sure. But what do you mean by "populated"? Apr 8, 2015 at 8:50
  • To be precise: There are two different child record types. The one has the validation rule that fails and then the workflow rule on the other provokes the described problem. Apr 8, 2015 at 8:52
  • i mean how does children list gets filled. I want the part of code where you must have done children.add(new child()); because there might be chances that child with same id is been added twice in children list.
    – snehakem
    Apr 8, 2015 at 9:18

1 Answer 1

2

Check how you populate the children collection. It sounds like you are adding the same object to it multiple times. Make sure you use the new keyword (as in new Child__c()) for the new items being added, and not just changing some fields on an existing object and re-adding it to the collection.

3
  • I handle the collection and adding item right, but...there is a Unique field on the child object which value is set on Insert by a WF rule: OR( ISNEW(), ISCHANGED(field1 ), ISCHANGED( field2 )). Maybe the ISNEW is triggered by an Upsert?? Apr 8, 2015 at 10:48
  • 1
    ISNEW() wouldn't be triggered by update. What could be happening, is that since your workflow is populating this unique field, it might be populating it incorrectly with the same value on multiple records. That would in turn trigger the Duplication warning. Apr 8, 2015 at 10:53
  • Update doesn't trigger ISNEW() but maybe Upsert?! Apr 8, 2015 at 10:54

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .