2010-11-22 2 views
3

저는 GAE의 데이터 저장소에서 유익한 엔티티를 만드는 가장 효율적인 방법을 결정하려고합니다. 이 엔티티에 대해 투표 할 컨트롤이나 이미 투표 한 것을 나타내는 아이콘을 사용자에게 보여주고 싶습니다. 즉, "사용자가이 엔티티에 투표 했습니까?"라고 묻습니다. 사용자가 투표 할 수있는 질문 엔티티가 있다고 가정 해 보겠습니다. 다음은 내가하고 싶은 생각입니다.GAE의 투표 모델링

  1. 내 질문 엔티티에 대한 질의. 이 질문에는 이미 미리 정렬 된 순위가 있습니다.
  2. Question 엔터티의 하위 인 관계 인덱스 엔터티를 사용하십시오. 내 사용자가이 관계 색인 엔티티의 구성원 인 # 1과 동일한 필터를 사용하여 모든 질문을 쿼리합니다.
  3. 발견 된 각 집합 구성원에 대해 hasVoted 속성을 true로 설정하여 # 2에 # 1의 결과를 병합합니다.

이것은 내가 생각할 수있는 가장 깨끗한 방법이지만 여전히 두 가지 쿼리가 필요합니다. 너무 많은 데이터 중복을 초래할 수 있으므로 각 사용자가 소유 할 중복 Question 엔터티를 만들지 않았습니다. 이 솔루션은 투표와 질문 사이의 m2m 관계를 효과적으로 결합시키는 것을 처리하는 좋은 방법입니까 아니면 너무 관계 적으로 생각하고 있습니까?

답변

0

두 번째 쿼리가 발생하지 않도록하려면 모두의 질문을 사용자가 단일 항목에 저장할 수 있습니다. 이 엔티티는 사용자 모델의 일부이거나 사용자 엔티티와 일대일 관계로 존재할 수 있습니다.

그런 다음 필요에 따라이 정보를로드하여 (데이터 저장소가로드되지 않도록 memcache에 저장) 사용자가 이미 두 번째 쿼리를 수행하지 않고도 질문에 대해 투표를했는지 빠르게 확인할 수 있습니다.

사용자가 정말로 많은 수의 질문에 투표 할 수있는 경우이 아이디어를 연장해야 할 수 있습니다. 다음은 간단한 구조에 대해 이동하는 방법의 개요 (기능적으로 완전하지 않음)입니다 :

class UserVotes(db.Model): 
    # key = key_name or ID of the corresponding user entity 

    # if all of your question entities have IDs, then voted_on can be a list of 
    # integers; otherwise it can be a list of strings (key_name values) 
    voted_on = db.ListProperty(int, indexed=False) 

# in your request handler ... 
questions = ... 
voted_on = memcache.get('voted-on:%s' % user_id) 
if voted_on is None: 
    voted_on = UserVotes.get_by_id(user_id) # should do get_or_insert() instead 
    memcache.set(...) 
for q in questions: 
    q.has_voted = q.key().id() in voted_on 
+1

만약 voted_on = []이 아닌 경우'coted_on :'이 True이면'voted_on이 None :'으로'voted_on :'을 대체 할 것입니다. –

+0

좋은 지적 블라디미르; 코드를 수정했습니다 - 감사합니다! –

+0

@ David- 사용자가 투표 한 질문의 키를 포함하는 user_votes라는 사용자에 대해'db.ListProperty (db.Key) '를 만드는 것이 더 간단하지 않습니까? – Yarin

3

대신 관계 인덱스를 사용하는 단지 문제에 선정 된 각 사용자에 대한 자식 개체가 있습니다. 하위 엔티티의 key_name을 사용자의 ID로 만듭니다. 그런 다음 사용자 y가 ID x의 질문에 투표했는지 확인하려면 간단히 키 (질문 : x/투표 : y)를 가져옵니다. 여러 질문이나 사용자에 대해 여러 항목을 가져 오도록 일괄 처리 할 수도 있습니다.

+0

왜 사용자 측이 아닌 질문 측에 하위 항목을 보관하도록 제안하셨습니까? 질문이 인기있는 경우 질문 엔티티 그룹의 최대 쓰기 제한을 초과하지 않습니까? 사용자 측에서 투표를 유지하는 데 따른 단점은 무엇입니까? – ali

+0

@ali 질문의 하위 엔티티를 갖는 투표를하면 모든 득표에 대해 단일 원자 반입을 수행하여 정확한 개수를 얻을 수 있습니다. –

+0

득표 수를 질문 엔티티의 속성으로 저장하면 안됩니까? – ali

2

Overheard Google App Engine 샘플 애플리케이션을 살펴 보겠습니다.

우리의 기본 모델은 특정 사용자에 대한 사용자 이름과 투표를 포함 견적 문자열을 포함하는 지수, 및 투표를해야하는 것입니다.

여기에 Google article이 있고 소스는 here입니다.