0

I'm writing a generic update method to simplify save an case class change to mongodb. my model T trait has the following function:

  def update(id: BSONObjectID, t: T)(implicit writer: OFormat[T]): Future[WriteResult] = {
    collection.update(Json.obj("_id" -> id), t)
  }

when i'm calling it, it fails with the following error:

Caused by: reactivemongo.api.commands.UpdateWriteResult: 
DatabaseException['The _id field cannot be changed from {_id: ObjectId('4ec58120cd6cad6afc000001')} to {_id: "4ec58120cd6cad6afc000001"}.' (code = 16837)]

Which makes sense cause MongoDB does not allow to update the document ID even though its the same value.

I'm wondering how i would remove the _id from my case-class instance to update it in mongodb. I guess I have to tuple the instance before it is converted to BSON, but i don't know how to do that. this is my example case class:

case class User(
  _id: BSONObjectID,
  email: String
}

thanks

cchantep
  • 9,118
  • 3
  • 30
  • 41
magegu
  • 530
  • 4
  • 18
  • I suggest you to use `findAndModify` instead of update. Removing fields from case classes and build new classes using reflection doesn't look good (and not thread-safe). – Nikita Jul 11 '15 at 10:11
  • You can provide a custom write, not ouputting the ID. – cchantep Jul 11 '15 at 10:55
  • Mongo has the concept of `upsert` (https://mongodb.github.io/casbah/tutorial.html#update) which might come handy for your case. – mfirry Jul 11 '15 at 12:18

1 Answers1

0

I agree with ipoteka. I would use the findAndModify command from reactive mongo. There is an example gist here that should help.

scarpacci
  • 8,957
  • 16
  • 79
  • 144