首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >Riak客户端注释在Scala案例类中不被识别?

Riak客户端注释在Scala案例类中不被识别?
EN

Stack Overflow用户
提问于 2013-02-05 23:54:14
回答 2查看 406关注 0票数 1

在我们的应用程序中,我使用案例类来定义不同的数据“模型”。原因是为了方便地使用Jerkson (Scala接口到Jackson)。为了在Riak中将User转换为域对象,我在guid上使用了@RiakKey注释。我有以下几点:

代码语言:javascript
复制
case class User(
  @RiakKey val guid: String,

  @RiakIndex(name = "email") val email: String,

  val salt: String,

  val passwordHash: String,

  val emailHash: String,

  val firstName: String,

  val lastName: String,

  val suspended: Boolean=false,

  val created: Timestamp=now

)

当我对case类执行域转换时,无法识别@RiakKey。它抛出一个NoKeySpecifedException。这是我的转换器:

代码语言:javascript
复制
class UserConverter(val bucket: String) extends Converter[User] {

  def fromDomain(domainObject: User, vclock: VClock) = {
    val key = getKey(domainObject)

    if(key == null) throw new NoKeySpecifedException(domainObject)

    val kryo = new Kryo()
    kryo.register(classOf[User])

    val ob = new ObjectBuffer(kryo)
    val value = ob.writeObject(domainObject)

    RiakObjectBuilder.newBuilder(bucket, key)
        .withValue(value)
        .withVClock(vclock)
        .withContentType(Constants.CTYPE_OCTET_STREAM)
        .build()
  }
}

这是Scala中带有Java注释的问题吗?有解决办法吗?

更新

下面是创建和存储用户对象以及引用转换器的位置:

1)

代码语言:javascript
复制
val user = parse[User](body) // jerkson parse, body is a string of JSON
User.store(user)

2)

代码语言:javascript
复制
object User {

  val bucketName = "accounts-users"
  val bucket = DB.client.createBucket(bucketName).execute()

  def fetch(id: String) = bucket.fetch(id).execute().getValueAsString()

  def store(o: User) = bucket.store( o ).withConverter(new UserConverter(bucketName)).execute()

}

Strack跟踪

代码语言:javascript
复制
com.basho.riak.client.convert.NoKeySpecifedException
        at com.basho.riak.client.bucket.DefaultBucket.store(DefaultBucket.java:455)
        at com.threetierlogic.AccountService.models.User$.store(User.scala:58)
        at com.threetierlogic.AccountService.controllers.Users$$anonfun$routes$3.apply(Users.scala:54)
        at com.threetierlogic.AccountService.controllers.Users$$anonfun$routes$3.apply(Users.scala:51)
EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2013-02-06 20:34:27

(对此之前的长谈,我深表歉意)

在深入了解了scala之后,我发现在使用case类时,您必须做一些不同的操作。

http://piotrbuda.eu/2012/10/scala-case-classes-and-annotations-part-1.html

如果你这样做了:

代码语言:javascript
复制
@(RiakKey@field) guid: String

它起作用了。

我用scala编写了一个小的测试程序,并且能够使用在返回null并导致抛出异常的getKey()中使用的静态DefaultBucket方法提取带注释的键。

代码语言:javascript
复制
import com.basho.riak.client.convert.KeyUtil.getKey;

object Main {

  def main(args: Array[String]): Unit = {
    val u = User("my_key")
    val k = getKey(u)
    System.out.println(k);

  }
}

User.scala

代码语言:javascript
复制
/* scala 2.9.1 would be scala.annotation.target.field */
import scala.annotation.meta.field
import com.basho.riak.client.convert.RiakKey;

case class User (@(RiakKey@field) guid: String)

输出:

my_key

(如果将注释更改为原来的方式,它将按预期返回null )

票数 2
EN

Stack Overflow用户

发布于 2013-02-06 18:05:11

这是我建议的解决这个问题的方法。我将使用DefaultBucket.store方法并手动指定一个键,而不是依赖注释。

我的用户同伴对象:

代码语言:javascript
复制
object User {

  val bucketName = "accounts-users"
  val bucket = DB.client.createBucket(bucketName).execute()

  def store(key: String, o: User) = bucket.store(key, o).withConverter(new UserConverter(bucketName)).execute()

}

并使用它:

代码语言:javascript
复制
val user = parse[User](body)
User.store(user.guid, user)
票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/14719166

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档