2013-02-27 29 views
5


Trong Django (và nói chung), là một cookie cũng là một tiêu đề, giống như, ví dụ: User-Agent?
Tức là, hai phương pháp này có tương đương với Django không?

Sử dụng set_cookie:
Cookie và tiêu đề Django

response.set_cookie('food', 'bread') 
response.set_cookie('drink', 'water') 

sử dụng cài đặt tiêu đề:

response['Cookie'] = ('food=bread; drink=water') 
# I'm not sure whether 'Cookie' should be capitalized or not 


Ngoài ra, nếu chúng ta có thể thiết lập một cookie bằng cách sử dụng cách thứ hai, làm thế nào chúng ta có thể bao gồm thông tin bổ sung,
như path, max_age, v.v. trong chuỗi? Chúng ta chỉ cần tách riêng chúng với một số đặc biệt
ký tự?

Trả lời

3

Sẽ dễ dàng hơn nhiều nếu bạn sử dụng set_cookie. Nhưng có, bạn có thể đặt cookie của thiết lập các tiêu đề phản ứng:

response['Set-Cookie'] = ('food=bread; drink=water; Path=/; max_age=10') 

Tuy nhiên, kể từ khi thiết lập lại Set-Cookie trong response đối tượng sẽ rõ ràng ra trước một, bạn không thể có nhiều hơn một Set-Cookie tiêu đề trong Django. Hãy xem lý do.

Quan sát trong response.py, set_cookie method:

class HttpResponseBase: 

    def __init__(self, content_type=None, status=None, mimetype=None): 
     # _headers is a mapping of the lower-case name to the original case of 
     # the header (required for working with legacy systems) and the header 
     # value. Both the name of the header and its value are ASCII strings. 
     self._headers = {} 
     self._charset = settings.DEFAULT_CHARSET 
     self._closable_objects = [] 
     # This parameter is set by the handler. It's necessary to preserve the 
     # historical behavior of request_finished. 
     self._handler_class = None 
     if mimetype: 
      warnings.warn("Using mimetype keyword argument is deprecated, use" 
          " content_type instead", 
          DeprecationWarning, stacklevel=2) 
      content_type = mimetype 
     if not content_type: 
      content_type = "%s; charset=%s" % (settings.DEFAULT_CONTENT_TYPE, 
        self._charset) 
     self.cookies = SimpleCookie() 
     if status: 
      self.status_code = status 

     self['Content-Type'] = content_type 

    ... 

    def set_cookie(self, key, value='', max_age=None, expires=None, path='/', 
        domain=None, secure=False, httponly=False): 
     """ 
     Sets a cookie. 

     ``expires`` can be: 
     - a string in the correct format, 
     - a naive ``datetime.datetime`` object in UTC, 
     - an aware ``datetime.datetime`` object in any time zone. 
     If it is a ``datetime.datetime`` object then ``max_age`` will be calculated. 

     """ 
     self.cookies[key] = value 
     if expires is not None: 
      if isinstance(expires, datetime.datetime): 
       if timezone.is_aware(expires): 
        expires = timezone.make_naive(expires, timezone.utc) 
       delta = expires - expires.utcnow() 
       # Add one second so the date matches exactly (a fraction of 
       # time gets lost between converting to a timedelta and 
       # then the date string). 
       delta = delta + datetime.timedelta(seconds=1) 
       # Just set max_age - the max_age logic will set expires. 
       expires = None 
       max_age = max(0, delta.days * 86400 + delta.seconds) 
      else: 
       self.cookies[key]['expires'] = expires 
     if max_age is not None: 
      self.cookies[key]['max-age'] = max_age 
      # IE requires expires, so set it if hasn't been already. 
      if not expires: 
       self.cookies[key]['expires'] = cookie_date(time.time() + 
                  max_age) 
     if path is not None: 
      self.cookies[key]['path'] = path 
     if domain is not None: 
      self.cookies[key]['domain'] = domain 
     if secure: 
      self.cookies[key]['secure'] = True 
     if httponly: 
      self.cookies[key]['httponly'] = True 

Hai điều cần lưu ý ở đây:

  1. set_cookie phương pháp sẽ chăm sóc xử lý datetime trong expires cho bạn, và bạn sẽ phải cài đặt nó cho mình nếu bạn tự đặt nó.
  2. self.cookie là từ điển của dictionaies. Vì vậy, mỗi key sẽ thêm ["Set-Cookie"] vào tiêu đề, như bạn sẽ thấy ngay.

Đối tượng cookies bên HttpResponse sau đó sẽ được thông qua để WSGIHandler, và được nối vào tiêu đề phản ứng:

response_headers = [(str(k), str(v)) for k, v in response.items()] 
for c in response.cookies.values(): 
    response_headers.append((str('Set-Cookie'), str(c.output(header='')))) 

Đoạn mã trên cũng là lý do tại sao chỉ set_cookie() phép nhiều Set-Cookie trong tiêu đề phản ứng, và cài đặt cookie đó trực tiếp đến đối tượng Response sẽ chỉ trả lại một Set-Cookie.

0

Chắc chắn, nhưng thay đổi “Cookie” thành “Set-Cookie” và thêm “Path = /” để làm cho trang web rộng.

response["Set-Cookie"] = "food=bread; drink=water; Path=/" 

Edit:

Sau khi cố gắng này ra bản thân mình Tôi tìm thấy một đứa thú vị, set_cookie không nhóm lại với nhau cookie tương tự (cùng đường, hết hạn, miền, vv) trong cùng một tiêu đề. Nó chỉ thêm một "Set-Cookie" vào phản ứng. Có thể hiểu được, khi kiểm tra và xáo trộn các chuỗi có thể mất nhiều thời gian hơn là có thêm một vài byte trong tiêu đề HTTP (và sẽ là tối ưu hóa vi mô ở mức tốt nhất).

response.set_cookie("food", "kabanosy") 
response.set_cookie("drink", "ardbeg") 
response.set_cookie("state", "awesome") 

# result in these headers 
# Set-Cookie: food=kabonosy; Path=/ 
# Set-Cookie: drink=ardbeg; Path=/ 
# Set-Cookie: state=awesome; Path=/ 

# not this 
# Set-Cookie:food=kabanosy; drink=ardbeg; state=awesome; Path=/ 
+0

Vì vậy, nếu tôi đặt hai cookie khác nhau, với các tham số 'đường dẫn' và' max_age' khác nhau; nhưng sử dụng cú pháp 'response [" Set-Cookie "] = ...'? –

+0

Thành thật mà nói, bạn nên sử dụng 'set_cookie' vì không có lợi ích thực sự nào từ việc tự đặt tiêu đề. Nó sẽ giống như thế này: 'response [" Set-Cookie "] =" food = kabanosy; Max-Age = 86400; Path =/"'. – Matt

+0

Tôi biết về cơ bản thuận tiện hơn khi sử dụng 'set_cookie', nhưng tôi muốn hiểu mối quan hệ của nó với đối tượng' HttpResponse' và với tiêu đề. –

1

Một đoạn từ mã của HttpResponse lớp:

class HttpResponse(object): 

    #... 

    def __init__(self, content='', mimetype=None, status=None, 

     #... 

     self.cookies = SimpleCookie() 

    #... 

    def set_cookie(self, key, value='', max_age=None, expires=None, path='/', 
        domain=None, secure=False, httponly=False): 

     self.cookies[key] = value 

     #... 


Đó là, bất cứ khi nào response.set_cookie() được gọi, nó hoặc đặt một cookie mới
value tại response.cookies[key] hoặc thay đổi hiện giá trị nếu có một tại khóa đó.
Nó giải thích lý do tại sao nó đặt nhiều tiêu đề Set-Cookie.
Tôi tự hỏi làm thế nào chúng ta có thể làm điều tương tự với response['Set-Cookie'].

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