2009-02-10 20 views
6

Tôi cần thực hiện truy vấn phân biệt chữ hoa chữ thường theo số username theo mặc định khi sử dụng khung công tác Auth Django.Django: Thực hiện tra cứu phân biệt dạng chữ theo mặc định

tôi đã cố gắng khắc phục vấn đề bằng cách viết một phân lớp tùy chỉnh của Queryset và trọng phương pháp _filter_or_exclude và sau đó sử dụng mà phân lớp trong một nhà quản lý tùy chỉnh cho người dùng model-

from django.db.models import Manager 
from django.db.models.query import QuerySet 
from django.contrib.auth.models import UserManager 

class MyQuerySet(QuerySet): 
    def _filter_or_exclude(self, negate, *args, **kwargs): 
     if 'username' in kwargs: 
      kwargs['username__iexact'] = kwargs['username'] 
      del kwargs['username'] 
     return super(MyQuerySet, self)._filter_or_exclude(negate, *args, **kwargs) 

class MyUserManager(UserManager): 
    def get_query_set(self): 
     return MyQuerySet(self.model) 

User.objects = MyUserManager() 

Nhưng phương pháp này không công việc và tôi gặp lỗi lạ khi tôi thử làm User.objects.get(username='Foo').

Mọi trợ giúp sẽ được đánh giá cao.

Cập nhật: Tôi bao gồm lỗi chính xác mà tôi nhận được.

/usr/lib/python2.5/site-packages/django/db/models/query.py in get(self, *args, **kwargs) 
    295   keyword arguments. 
    296   """ 
--> 297   clone = self.filter(*args, **kwargs) 
    298   num = len(clone) 
    299   if num == 1: 

/usr/lib/python2.5/site-packages/django/db/models/query.py in filter(self, *args, **kwargs) 
    481   set. 
    482   """ 
--> 483   return self._filter_or_exclude(False, *args, **kwargs) 
    484 
    485  def exclude(self, *args, **kwargs): 

/home/ghoseb/src/git/ocricket.git/ocricket/user/models.py in _filter_or_exclude(self, negate, *args, **kwargs) 
    38    kwargs['username__iexact'] = kwargs['username'] 
    39    del kwargs['username'] 
---> 40   return super(MyQuerySet, self)._filter_or_exclude(negate, *args, **kwargs) 
    41 
    42 class MyUserManager(UserManager): 

/usr/lib/python2.5/site-packages/django/db/models/query.py in _filter_or_exclude(self, negate, *args, **kwargs) 
    499    clone.query.add_q(~Q(*args, **kwargs)) 
    500   else: 
--> 501    clone.query.add_q(Q(*args, **kwargs)) 
    502   return clone 
    503 

/usr/lib/python2.5/django/db/models/sql/query.py in add_q(self, q_object, used_aliases) 

/usr/lib/python2.5/django/db/models/sql/query.py in add_filter(self, filter_expr, connector, negate, trim, can_reuse, process_extras) 

/usr/lib/python2.5/django/db/models/sql/query.py in get_meta(self) 

<type 'exceptions.AttributeError'>: 'NoneType' object has no attribute '_meta' 

Cập nhật: Bằng cách này, tôi chỉ muốn đề cập rằng khi tôi copy logic bên trong phương pháp _filter_or_exclude tôi vào lớp học thực tế QuerySet, nó hoạt động hoàn hảo.

+0

cũng có thể đăng lỗi đó? –

+0

Đã thêm. Cảm ơn vì đã nhắc nhở. –

+0

Lỗi lạ. Bạn có thể xác minh rằng bạn nhận được lỗi này trên mã chính xác này không? Không có phương pháp bổ sung nào trên QuerySet hoặc Manager bị ghi đè, và không có lớp con bổ sung can thiệp nào trong hệ thống phân cấp thừa kế, không có thêm các mixin? –

Trả lời

4

Không thể thêm người quản lý vào các lớp học với phân bổ thuộc tính đơn giản (User.objects = MyManager()). Nhìn vào metaclass ModelBase (db/models/base.py) để xem tất cả những gì được thực hiện cho bạn đằng sau hậu trường khi bạn phân lớp Model.

Bạn sẽ có thể làm cho nó hoạt động với User.add_to_class('objects', MyManager()). Ngoài ra, bạn có thể tạo proxy subclass người dùng và thêm người quản lý ở đó.

+0

Tôi không chắc chắn rằng một lớp con trừu tượng của một lớp cụ thể được cho phép hoặc có ý nghĩa, nhưng mô hình proxy sẽ hoạt động tốt trong tình huống này. –

+0

@rz Mô hình proxy không tồn tại khi câu trả lời này được viết :-) Tôi sẽ cập nhật nó. –

+0

tuyệt! tôi đoán tôi nên đã sử dụng các siêu cường chỉnh sửa mới của tôi và chỉ cần thực hiện điều đó cho bạn. Nhân tiện, Carl, ngoài cách anh ta thêm người quản lý, là cách tiếp cận này để có được một cửa hàng phân biệt chữ hoa chữ thường với tra cứu phân biệt chữ hoa chữ thường không? –

5

Bạn không muốn gây rối với các tính năng nội bộ của các lớp Django. Bằng cách đó, bạn gặp khó khăn với mọi nâng cấp trong tương lai.

Nếu bạn muốn thay đổi cách mọi người xác thực, hãy viết chương trình phụ trợ xác thực tùy chỉnh.

Dưới đây là hai công thức nấu ăn.

http://www.davidcramer.net/code/224/logging-in-with-email-addresses-in-django.html

http://www.djangosnippets.org/snippets/577/

Cả hai chúng tôi gửi email thay vì tên người dùng. Không khó sử dụng truy vấn phân biệt chữ hoa chữ thường thay vì truy vấn email.

+0

Vâng, tôi biết rõ về các chương trình phụ trợ auth tùy chỉnh nhưng tôi không không cần điều này cho (chỉ) auth, nhưng đối với những thứ khác, như tên người dùng được sử dụng trong URL, v.v. –

Các vấn đề liên quan