简体   繁体   English

在带有MongoDB的Lift中,存储异构数据列表

[英]In Lift with MongoDB, storing lists of heterogeneous data

I need to make a web service that can will contain lists of objects. 我需要制作一个可以包含对象列表的Web服务。 One list can contain objects of many types. 一个列表可以包含许多类型的对象。 Here, for example, I have a library of media items. 例如,在这里,我有一个媒体项目库。 Each item can be either a link or a video, each with their own metadata. 每个项目都可以是链接或视频,每个都有自己的元数据。

I want to do this with the Lift web framework, because I need something that compiles to WAR and I've used Lift before. 我想使用Lift Web框架来完成此操作,因为我需要将其编译为WAR,并且以前使用过Lift。

I thought that using MongoDB for this sort of storage would work as, by definition, it's supposed to be able to handle collections of heterogeneous items. 我认为使用MongoDB进行这种存储将有效,因为按照定义,它应该能够处理异构项目的集合。

I can define types of BSON objects to be stored in Lift records, but I can't seem to stick away from creating only one type of object in one record/collection. 我可以定义要存储在Lift记录中的BSON对象的类型,但似乎不能不放弃在一个记录/集合中仅创建一种类型的对象。 Ideally, I'd like each "thing" (for lack of a better word) in my Library to be either a video or a link. 理想情况下,我希望库中的每个“事物”(因为缺少更好的词)都可以是视频或链接。 For example: 例如:

[
  {
    "type"       : "Video",
    "title"      : "Story",
    "videoID"    : "123ab4",
    "description": "Feature-length epic",
    "time"       : 12.6
  },
  {
    "type" : "link",
    "url"  : "http://www.google.com",
    "title": "Search for stuff"
  }
]

I should be able to do it with the right type of inheritance, but the way all of the record objects's parents inherit from the object throws me off. 我应该能够使用正确的继承类型来做到这一点,但是所有记录对象的父对象从该对象继承的方式都会使我失望。 Can I get this to work? 我可以让它工作吗? Having a collection of different things that Lift can use as such? 有Lift可以使用的不同东西的集合吗?

Here's what I have so far. 到目前为止,这就是我所拥有的。 I haven't tested it, but even if it works what it does is NOT what I want. 我没有测试过,但即使它的工作原理是什么它是不是我想要的。

import net.liftweb.record._
import net.liftweb.record.field._

import net.liftweb.mongodb._
import net.liftweb.mongodb.record._
import net.liftweb.mongodb.record.field._


class VideoShelf private () extends BsonRecord[VideoShelf] {
  def meta = VideoShelf

  object title       extends StringField (this, 256)
  object videoID     extends StringField (this, 32 )
  object description extends StringField (this, 256)
  object time        extends DecimalField(this, 0  )
}

object VideoShelf extends VideoShelf with BsonMetaRecord[VideoShelf]


class LinkShelf private () extends BsonRecord[LinkShelf] {
  def meta = LinkShelf

  object url   extends StringField(this, 128)
  object title extends StringField(this, 256)
}

object LinkShelf extends LinkShelf with BsonMetaRecord[LinkShelf]


class MediaLibrary private () extends MongoRecord[MediaLibrary] with ObjectIdPk[MediaLibrary] {
  def meta = MediaLibrary

  ///////////////////////////////////////
  ///////////////////////////////////////
  // What I want is this record type to
  // contain either of these:
  ///////////////////////////////////////      
  object videoshelf extends BsonRecordField(this, VideoShelf)
  object linkshelf  extends BsonRecordField(this, LinkShelf )
}

object MediaLibrary extends MediaLibrary with MongoMetaRecord[MediaLibrary]

How can I get this? 我怎么能得到这个?

After seeking more, I found this post: https://groups.google.com/forum/#!topic/liftweb/LmkhvDgrgrI 寻找更多信息后,我发现了这篇文章: https : //groups.google.com/forum/#!topic/liftweb/LmkhvDgrgrI

That led me to this conclusion, which I think is correct, though it has not been tested yet. 这使我得出了这个结论,我认为它是正确的,尽管尚未经过检验。 I may be missing some pieces for it to fully work. 我可能会缺少一些东西,以使其无法正常工作。

import net.liftweb.record._
import net.liftweb.record.field._

import net.liftweb.mongodb._
import net.liftweb.mongodb.record._
import net.liftweb.mongodb.record.field._


/**
 * The base record type for library objects.
 */
trait MediaLibrary[T <: MediaLibrary[T]] extends MongoRecord[T] with ObjectIdPk[T] {
  self: T =>
}

/**
 * Items in the library that are videos.
 */
class VideoItem extends MediaLibrary[VideoItem] {

  def meta = VideoItem

  object title       extends StringField (this, 256)
  object videoID     extends StringField (this, 32 )
  object description extends StringField (this, 256)
  object time        extends DecimalField(this, 0  )
}

object VideoItem extends VideoItem with MongoMetaRecord[VideoItem]

/**
 * Items in the library that are links.
 */
class LinkItem extends MediaLibrary[LinkItem] {

  def meta = LinkItem

  object url         extends StringField (this, 256)
  object title       extends StringField (this, 256)    
}

object LinkItem extends LinkItem with MongoMetaRecord[LinkItem]


UPDATE UPDATE

I've also just found out that there is a MongoDB-specific record that's a list of case classes. 我还刚刚发现,有一个MongoDB特定的记录,其中包含案例类的列表。 That seems to be exactly what I need! 那似乎正是我所需要的! It's the power of Scala and Mongo being used hand in hand! 这是Scala和Mongo携手使用的强大功能! That's what I wanted from the start. 那就是我从一开始就想要的。 I'll have to try that tomorrow. 我明天必须尝试。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

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