Ok. I'm working with GAE. And i want create something like this:
I have types "group" "topic" "tag":
each "group" can have as many "topics" as needed
each "topic" can have as many "tags" as needed
each "group" can have as many "tags" as needed
it's something like circle.
right now i have something like this:
class TopicGroup(db.Model):
value = db.StringProperty(required=True)
class Topic(db.Model):
title = db.StringProperty(required=True)
group = db.ReferenceProperty(TopicGroup, 'group', 'topics', required=True)
class TopicTag(db.Model):
topic = db.ReferenceProperty(Topic, 'topic', 'tags', required=True)
group = db.ReferenceProperty(TopicGroup, 'group', 'tags', required=True)
value = db.StringProperty(required=True)
but this is no good (in my model "topic" can have only one tag, but i nead "topic" to have as many tags as needed)
well i already have a crack in my head... is there someone who could help?
The solution is to use a db.ListProperty with a type of db.Key. see: http://code.google.com/appengine/articles/modeling.html (section many to many)
Many-to-many joins can be implemented as join tables (or Relationship Models). In the solution below, there is a model that holds all of the tags that are applied to individual
Groups
(GroupTags
) and a model that holds the tags that are applied toTopics
(TopicTags
).Decoupling the
Tag
itself from references to theTag
allows you to do things like change the spelling of a tag without needing to update everyGroup
orTopic
to which thatTag
is applied.Also, this model takes good advantage of the fact that AppEngine creates automatic backreferences on entities that have other entities referencing them. In the models below, a Group entity will have a property called
topics
that is a query that will fetch allTopic
entities who'sgroup
reference points to thatGroup
. Similarly, eachGroup
gets atags
property from theGroupsTags
model that gives it all of theTag
entities that belong to it. EveryTag
entity gets agroups
andtopics
property that is a query for all of the entities of those types that have the give Tag assigned, making searching by tag (a very typical operation) quite simple.It's a very powerful and flexible approach to modeling systems such as yours.