2010-11-25 3 views
5

私は1つまたは複数のタグでマークされたたくさんの(例えば)投稿を持っています。投稿を作成または削除することができます。また、ユーザーは1つまたは複数のタグ(論理ANDと組み合わせて)の検索要求を行うことができます。私の心に来た 最初のアイデアは、作成および削除操作の簡単なモデルGoogle App Engine(Python)の高度にスケーラブルなタグ

class Post(db.Model): 
    #blahblah 
    tags = db.StringListProperty() 

実装が明らかであるでした。検索はより複雑です。 N個のタグを検索するには、 "SELECT * FROM投稿WHEREタグ=:1"のようなN個のGQLクエリを実行し、カーソルを使用して結果をマージします。

セカンドアイデアはそれがキーによってデシベルからタグを取る(GQLでそれを取るよりもはるかに高速)、メモリにそれをマージ異なるエンティティに

class Post(db.Model): 
    #blahblah 
    tags = db.ListProperty(db.Key) # For fast access 

class Tag(db.Model): 
    name = db.StringProperty(name="key") 
    posts = db.ListProperty(db.Key) # List of posts that marked with tag 

をタグを分離することで、私はこの実装は、より良い性能を持っていると思います非常に頻繁に使用できるタグは、単一のデータストアオブジェクトを許可する最大サイズを超えることができます。また、もう1つの問題があります。データストアは1つのオブジェクトを〜1 /秒しか変更できないため、頻繁に使用できるタグでは変更待ち時間のボトルネックもあります。

提案がありますか?

答えて

0

おそらく考えられる解決策は、2番目の例をとり、より大きなセットで効率的なクエリを可能にする方法で修正することです。心に浮かぶ1つの方法は、単一のタグに複数のデータベースエンティティを使用し、少数のグループ以上を取得する必要がほとんどないようにグループ化することです。デフォルトのソート順(唯一許可されているものだけを呼び出すことができます)がポスト・デートである場合は、その順序でタグ・グループ・エンティティを入力します。

class Tag(db.Model): 
    name = db.StringProperty(name="key") 
    posts = db.ListProperty(db.Key) # List of posts that marked with tag 
    firstpost = db.DateTimeProperty() 

追加しているポストはポストを作るならば、そのグループ内にあるどのように多くの記事を確認し、グループにタグを追加または削除100件の記事を言う、より多くを持って、2つのタグに分割グループ。グループの投稿数が50未満になるように投稿を削除する場合は、前のグループまたは次のグループの投稿を盗みます。隣接するグループのいずれかに50個の投稿がある場合は、それらを一緒にマージしてください。タグで投稿を一覧表示すると(日付順に)、少数のグループしか取得できません。

これは、高需要タグの問題を実際に解決するものではありません。

これについて考えてみると、挿入がもう少し投機的であれば大丈夫かもしれません。最新のタググループエントリを取得し、それらをマージして新しいタググループを配置します。取引の遅れは実際には本当の問題ではないかもしれません。

+1

投稿の追加に関するジャーナルを実装することで、トランザクションの遅延を解決できます。ポストが追加のためにキューに入れられると、Memcacheのコピーが期限切れになった場合は、ジャーナルの後に、それが持つ各タグの "Look!そのタグはそのタグに属している"(タグエンティティのmemcacheコピーも変更する)アプライアーはすべてのジャーナルエントリを収集し、それをデータストア内のタグエンティティに適用します(また、memcacheにコピーします)。 –