0

I have a django 1.9 project and am using mongoengine to connect to mongodb instance.

I have a model as follows:

from django.db import models
from mongoengine import * 
class Employee(Document):
    email = StringField(required=True, unique=True)
    first_name = StringField(max_length=50)
    last_name = StringField(max_length=50)

A test class:

import web.models as models
class test:

    '''Test the accessibility of the business class'''
    def testBusiness():
        employee = models.Employee.objects.create(
            email="pedro.kong@company.com",
            first_name="Pedro",
            last_name="Kong"
        )
        try:
            employee.save()
        except pymongo.errors.DuplicateKeyError as e:
            return "Error"
        return "Business Tested"

The problem is that i cannot catch the DuplicateKeyError execption:

pymongo.errors.DuplicateKeyError: E11000 duplicate key error index: rockynode.employee.$email_1  dup key: { : "pedro.kong@company.com" }

I tried with global try except but it still crashes the code with a DuplicateKeyError exception:

try:
    employee.save()
except:
    return "Error"
return "Business Tested"

For info am using the following dependencies:

Django==1.9.7
mongoengine==0.10.6
pymongo==3.2.2

Reff:get-the-duplicate-value-on-duplicatekeyerror

Any help would be highly appreciable.Thx.

Community
  • 1
  • 1
Kheshav Sewnundun
  • 1,236
  • 15
  • 37

2 Answers2

2

I got to solve the issue.

The try except was not working since the DuplicateKeyError exception was not being triggered from the save() method but instead from the create() method.

Quoting from the documentation:create() :

Create new object. Returns the saved object instance.

The code section in the def create() in the mongoengine code: Reff: Monogoengine code shows clearly that the create() function calls the save() function:

Extract from mongoengine code:

def create(self, **kwargs):
        """Create new object. Returns the saved object instance.
        .. versionadded:: 0.4
        """
        return self._document(**kwargs).save()

Hence my try blocks must be enclose the create() method like follows:

 try:
            employee = models.Employee.objects.create(
                email="pedro.kong@company.com",
                first_name="Pedro",
                last_name="Kong"
            )
            employee.save()
        except Exception as e:
            return "Error \n %s" % (e)
        return "Business Tested"
Community
  • 1
  • 1
Kheshav Sewnundun
  • 1,236
  • 15
  • 37
2

As you saw yourself in the docs, create returns a saved document, so if you use it

  • you don't have to save it a second time
  • you must catch save exceptions in there

    try:
        employee = models.Employee.objects.create(
            email="pedro.kong@company.com",
            first_name="Pedro",
            last_name="Kong"
        )
    except Exception as e:
        return "Error \n %s" % (e)
    return "Business Tested"
    

or if you don't use create but save in a separate statement:

    employee = models.Employee(
        email="pedro.kong@company.com",
        first_name="Pedro",
        last_name="Kong"
    )
    try:
        employee.save()
    except Exception as e:
        return "Error \n %s" % (e)
    return "Business Tested"
Jérôme
  • 13,328
  • 7
  • 56
  • 106