2011-12-30 5 views
3

안녕 유래 사람들과 SQL 쿼리 내 현재 프로젝트장고 : 모델 기능에 뚜렷한

, 나는 다음과 같은 모델 구조를 가지고 :

class Project(models.Model): 
    student_id = models.ForeignKey(User) 
    class_a = models.ForeignKey(ClassA) 
    class_b = models.ForeignKey(ClassB) 
    ... 

class ClassA(models.Model): 
    teacher_name = models.CharField(...) 

class ClassB(models.Model): 
    teacher_name = models.CharField(...) 
는 를 ClassA와 ClassB가 매우 다르고

만 그들은 단지 은 teacher_name을 공통으로 사용하므로 별도의 클래스로 유지합니다. 또한 각 프로젝트에서 class_a 또는 class_b에만 ForeignKey를 포함 할 수 있습니다 (두 클래스에 할당 할 수 없음). 나는 모든 프로젝트를 표시하고 나는 선생님의 이름을 나열 할 때

따라서 나는 교사의 이름을 반환하는 작은 모델 함수를 생성 :

def get_teacher_name(self): 
    if self.class_a: 
     return self.class_a.teacher_name 
    if self.class_b: 
     return self.class_b.teacher_name 

지금, 나는 쿼리를 작성하려는 student_id에 대한 교사의 이름을 반환 만 교사가 한 번 이름을 반환 예 : 학생 X 프로젝트 교사 생물학 부인 X 물리 씨 Y 를 들어 (-> 수학 씨 Y는 무시한다)

장고 쿼리는 어떻게 구성해야합니까? 내가하고 싶습니다 Project.objects.filter (student_id = user.pk) .values ​​('get_teacher_name'). distinct(),하지만 이것은 불가능합니다. 그것을위한 해결책이 있습니까?

의견을 보내 주셔서 감사합니다. 가치관 전화 당신에게 고유 한 값을 줄 것이다 valueshttps://docs.djangoproject.com/en/dev/topics/db/aggregation/#order-of-annotate-and-values-clauses

annotate을 찾고

답변

3

You'er.

import itertools 

class_a_names = user.project_set.values_list('class_a__teacher_name', flat=True).annotate() 
class_b_names = user.project_set.values_list('class_b__teacher_name', flat=True).annotate() 
unique_teachers = set(itertools.chain(class_a_names, class_b_names)) 
+0

답장을 보내 주셔서 감사합니다. project_set이 어디에서 왔는지 설명해 주시겠습니까? 고맙습니다! – neurix

+0

@neurix - 프로젝트에서'User'까지'ForeignKey'를 가지고 있다면 django는'ForeignKey' 필드에'related_name' 인자를 지정하지 않으면'class_set' 형식으로 역방향 관련 모델 관리자를 추가합니다. https://docs.djangoproject.com/en/dev/topics/db/queries/#following-relationships-backward –

+0

선생님의 pk를 목록에 보관하는 방법이 있습니까? 나는 ('class_a_teacher__name', 'class_a_teacher__pk') 시도했지만, pk를 찾을 수 없습니다. 도와 줘서 고마워! – neurix