简体   繁体   中英

Scala toJson when using net.liftweb.mongodb.record.MongoRecord and Argonaut

I'm scala newbie and come from a Ruby background so and am having trouble rendering json response in my web service for which I use scalatra, mongodb with liftweb mongo record and argonaut for JSon serialisation and deserialisation.

However based on the examples given at http://argonaut.io/ I'm unable to figure out how this would work when using the net.liftweb.mongo.record library.

On compiling this i get a error which says a type mismatch . The error description follows the code snippet.

package firstscalatraapp

import org.scalatra
import net.liftweb.mongodb._
import net.liftweb.mongodb.record.MongoRecord
import net.liftweb.mongodb.record.field.ObjectIdPk

import net.liftweb.record.field.StringField
import net.liftweb.record.field.IntField
import net.liftweb.record.field.PasswordField
import net.liftweb.record.field.DateTimeField
import net.liftweb.mongodb.record.MongoMetaRecord
import argonaut._
import Argonaut._

case class Person private extends MongoRecord[Person] with ObjectIdPk[Person] {
    def meta = Person   
    object age extends IntField(this, 3)
    object name extends StringField(this, 29)
    object created_at extends DateTimeField(this)
    object password extends PasswordField(this)
}

object Person extends Person with MongoMetaRecord[Person] {
 implicit def PersonCodecJson: CodecJson[Person] =
  casecodec3(Person.apply, Person.unapply)("name", "age", "things")
}

The Error i get is


[error]  found   : () => firstscalatraapp.Person
[error]  required: (?, ?, ?) => ?
[error]   casecodec3(Person.apply, Person.unapply)("name", "age", "things")
[error]                     ^
[error] one error found
[error] (compile:compile) Compilation failed

which seems logical because the constructor does not accept any parameters and the mongo library seems to be generating the val for the fields that i need for the class (I still don't fully understand what the lift mongo wrapper does yet).

So how do i define the implicit to be able to find serialise an object of type person.

Also how do I define serialisation capabilities when i'm dealing with collections. For instance when I have a List[Person] .

Thanks in advance. I would really appreciate any help i can get on this.

I'm just about to start using Argonaut so I'm no expert on that but with that said your initial problem seems obvious.

casecodec3 needs a constructor and a deconstructor for the class you're defining the codec for. In the examples of Argonaut they're using case classes and these have automatically generated companion objects with apply/unapply for the fields defined. Which for casecodec3 needs to be 3. In your case, the case class is of zero-arity - you have no case class fields at all. The fields of the record are defined as inner objects with their own apply-methods (very imperative stuff). That's just the way lifts records are defined. So your apply method is just () => Person.

casecodec3 wants a function from a 3-tuple to Person and from Person to a 3-tuple. I would suggest skipping the case definition if you're going to use lift record. And create functions on the side instead. Something like:

object Person extends Person with MongoMetaRecord[Person] {
 implicit def PersonCodecJson: CodecJson[Person] =
  casecodec3(parse, serialize)("name", "age", "things")

  // Something like
  def parse(name: String, age: Int, things: Something) = {
    val p = Person.createRecord
    p.name(name)
    ...
  }

  def serialize(p: Person) = (p.name.get, p.age.get, p.things.get)

} 

As for your other questions I think you can head back to argonaut.io again. Their documentation seems quite alright - maybe it was worse when you posted this question as it is kind of old?

I'm going to try to replace all my serialization from lift-json to argonaut right now so if you're still stuck (probably not) I might be able to answer better in a bit.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM