Mongoengine和add_to_set似乎没有工作

问题描述:

我试图保存对数据库的MP3引用。我将艺术家,歌曲和专辑保存到各自的模式中,并通过ReferenceFields在它们之间引用。Mongoengine和add_to_set似乎没有工作

我使用eyeD3解析id3数据,如果有的话,并将其保存到数据库。我的问题是,我想同时保存所有三种模式类型,但我可能会以错误的方式处理它。我使用python 2.7.10。

示例模式:

class Artist(db.Document): 
    """Schema for Artist""" 
    name = db.StringField(max_length=255, required=True, unique=True) 
    albums = db.ListField(db.ReferenceField('Album')) 
    songs = db.ListField(db.ReferenceField('Song')) 

    def __unicode__(self): 
     return self.name 

class Album(db.Document): 
    """Schema for albums""" 
    title = db.StringField(max_length=255, required=True, unique=True) 
    artist = db.ReferenceField(Artist) 
    songs = db.ListField(db.ReferenceField('Song')) 

    def __unicode__(self): 
     return self.title 

class Song(db.Document): 
    """Schema for songs""" 
    title = db.StringField(max_length=255, required=True, unique=True) 
    artist = db.ReferenceField(Artist) 
    album = db.ReferenceField(Album) 
    path = db.StringField(max_length=255, required=True) 

    def __unicode__(self): 
     return self.title 

以及码保存到DB:

for root, dirs, files in os.walk(dir): 
    for f in files: 
     if '.mp3' in f: 
      id3 = eyed3.load(os.path.join(root, f)) 
      song = Song(title=id3.tag.title, path=os.path.join(root, f)) 
      album = Album(title=id3.tag.album) 
      artist = Artist(name=id3.tag.artist) 

      song.save() 
      album.save() 
      artist.save() 
      Artist.objects(id=artist.id).update(add_to_set__albums=album, add_to_set__songs=song) 
      Album.objects(id=album.id).update(artist=artist, add_to_set__songs=song) 
      Song.objects(id=song.id).update(artist=artist, album=album) 

保存后,add_to_set仅保存一个目的是每ListField代替推到端。

我很难搞清楚如何正确地做到这一点。任何帮助,将不胜感激。谢谢

好吧,所以我找到了罪魁祸首。由于架构的一些属性是独特的,当我分配一个对象到已经插入到数据库变量:

artist = Artist(name=id3.artist) 

它返回一个dulpicate错误。然后,我尝试使用该变量推到另一个对象:

Album.objects(title=id3.album).update(artist=artist) 

但变量未设置由于重复的错误。

这里使用upserts我重构的代码:

Song.objects(title=song.tag.title).update(path=path, upsert=True) 
so = Song.objects.get(title=song.tag.title) 
Album.objects(title=song.tag.album).update(add_to_set__songs=so, upsert=True) 
al = Album.objects.get(title=song.tag.album) 
Artist.objects(name=song.tag.artist).update(add_to_set__songs=so, add_to_set__albums=al, upsert=True) 
ar = Artist.objects.get(name=song.tag.artist) 
so.update(artist=ar, album=al) 
al.update(artist=ar, add_to_set__songs=so)