Go Mongodb Error Cannot create field X in element {Y: null}
Today we had a MongoDB 3.6 collection with the following documents:
db.getCollection('person').insertMany([
    {"name": "Odyseas", "surname": "Androutsos", "profilePicture": null},
    {"name": "Theodoros", "surname": "Kolokotronis", "profilePicture": null},
    {"name": "Ioannis", "surname": "Makrygiannis", "profilePicture": null},
    {"name": "Ioannis", "surname": "Kapodistrias", "profilePicture": null},
    {"name": "Emanouil", "surname": "Pappas", "profilePicture": null}
])
and we wanted to update them with Go using mongodb/mongo-go-driver in order to become like this:
[{
    "name": "Ioannis",
    "surname": "Kapodistrias",
    "profilePicture": {
        "image":{
            "iconUrl":null,
            "retrievalStatus": "NOT_FOUND",
            "lastSuccessfulRetrieval": ISODate("2021-07-13T10:00:00.000Z")
        }
    }
},
{
    "name": "Ioannis",
    "surname": "Makrygiannis",
    "profilePicture": {
        "image":{
            "iconUrl":null,
            "retrievalStatus": "NOT_FOUND",
            "lastSuccessfulRetrieval": ISODate("2021-07-13T10:00:00.000Z")
        }
    }
}]
. We were using the following update statement:
db.getCollection('person').update(
    { "name": "Ioannis" },
    {
        "$set": {
            "profilePicture.image.iconUrl": null,
            "profilePicture.image.retrievalStatus": "NOT_FOUND",
            "profilePicture.image.lastSuccessfulRetrieval":   ISODate("2021-07-13T10:00:00.000Z"),
        }
    },
    {multi:true})
however the MongoDB driver was returning this error:
Cannot create field 'image' in element {profilePicture: null}
Initially we thought that something is wrong with the single update() command and we tried in mongo shell the updateMany():
db.getCollection('person').updateMany(
    { "name": "Ioannis" },
    {
        "$set": {
            "profilePicture.image.iconUrl": null,
            "profilePicture.image.retrievalStatus": "NOT_FOUND",
            "profilePicture.image.lastSuccessfulRetrieval":   ISODate("2021-07-13T10:00:00.000Z"),
        }
    })
However it returned a quite similar error:
Failed to execute script.
Error:
WriteError({
	"index" : 0,
	"code" : 28,
	"errmsg" : "Cannot create field 'image' in element {profilePicture: null}",
	"op" : {
		"q" : {
			"surname" : "Manios"
		},
		"u" : {
			"$set" : {
				"profilePicture.image.iconUrl" : null,
				"profilePicture.image.retrievalStatus" : "NOT_FOUND",
				"profilePicture.image.lastSuccessfulRetrieval" : ISODate("2021-07-13T10:00:00Z")
			}
		},
		"multi" : true,
		"upsert" : false
	}
}) :
WriteError({
	"index" : 0,
	"code" : 28,
	"errmsg" : "Cannot create field 'image' in element {profilePicture: null}",
	"op" : {
		"q" : {
			"surname" : "Manios"
		},
		"u" : {
			"$set" : {
				"profilePicture.image.iconUrl" : null,
				"profilePicture.image.retrievalStatus" : "NOT_FOUND",
				"profilePicture.image.lastSuccessfulRetrieval" : ISODate("2021-07-13T10:00:00Z")
			}
		},
		"multi" : true,
		"upsert" : false
	}
})
WriteError@src/mongo/shell/bulk_api.js:458:48
mergeBatchResults@src/mongo/shell/bulk_api.js:855:49
executeBatch@src/mongo/shell/bulk_api.js:919:13
Bulk/this.execute@src/mongo/shell/bulk_api.js:1163:21
DBCollection.prototype.updateMany@src/mongo/shell/crud_api.js:690:17
@(shell):1:1
We searched for the error in the internet but we could not understand where we are wrong:
- Google: code: 28, “errmsg” : “Cannot create element in Null”,
 - Mongodb “Cannot create field ‘x’ in element” [duplicate]
 - NULL data type in MongoDB
 
After some time and numerous attempts, we realised that MongoDB was trying to tell us that it cannot create the subdocument:
"image":{
    "iconUrl":null,
    "retrievalStatus": "NOT_FOUND",
    "lastSuccessfulRetrieval": ISODate("2021-07-13T10:00:00.000Z")
}
inside a field which is alread assigned to null:
"profilePicture": null
So with a small change, the update statement works:
// ------
// BEFORE
// ------
// THIS DOES NOT WORK AND CONFUSES MONGODB. 
db.getCollection('person').update(
    { "name": "Ioannis" },
    {
        "$set": {
            "profilePicture.image.iconUrl": null,
            "profilePicture.image.retrievalStatus": "NOT_FOUND",
            "profilePicture.image.lastSuccessfulRetrieval":   ISODate("2021-07-13T10:00:00.000Z"),
        }
    },
    {multi:true}
)
// ------
// AFTER
// ------
// THIS WORKS
db.getCollection('person').update(
    { "name": "Ioannis" },
    {
        "$set": {
            "profilePicture": {
                "image": {
                    "iconUrl": null,
                    "retrievalStatus": "NOT_FOUND",
                    "lastSuccessfulRetrieval":   ISODate("2021-07-13T10:00:00.000Z"),
                }
            }
        }
    },
    {multi:true}
)
We tested the example in the following versions (running db.version() in Mongo shell):
- CosmosDB for MongoDB 3.6.0
 - MongoDB 3.6.22
 - MongoDB 4.4.0
 
and all behave identically.
We hope this helped you and you gain some minutes instead of searching in the web to find a solution! Greetings from our hot Greece with 40 °C!
Comments