Add cache control headers with respect to Snippet expire time.

This commit is contained in:
Martin Mahner 2019-12-08 09:07:23 +01:00
parent a8574613ab
commit 0c9b346c4d
6 changed files with 63 additions and 18 deletions

View File

@ -30,7 +30,7 @@ class dpasteAppConfig(AppConfig):
EXTRA_POST_ABOUT = ""
# HTML content injeted after the "New snippet" form
EXTRA_POST_NEW =""
EXTRA_POST_NEW = ""
# HTML content injected at the end of every form
EXTRA_POST_FORM = ""
@ -613,6 +613,14 @@ class dpasteAppConfig(AppConfig):
# ('zephir', 'Zephir')
]
# Whether to send out cache headers (Max-Age, Never-Cache, etc.).
CACHE_HEADER = True
# Defines how long pages are cached by upstream Proxies (Max-Age Header).
# This does not affect caching of snippets, their max-age limit is set
# to the expire date.
CACHE_TIMEOUT = 60 * 10
@staticmethod
def get_base_url(request=None):
"""

View File

@ -1,9 +1,8 @@
from datetime import timedelta
from django.apps import apps
from django.core.management.base import BaseCommand
from django.utils import timezone
from django.apps import apps
from dpaste.models import Snippet

View File

@ -30,7 +30,7 @@ ALLOWED_HOSTS = env("ALLOWED_HOSTS", "*").split(",")
TIME_ZONE = "UTC"
USE_I18N = True
USE_L10N = True
USE_TZ = True
USE_TZ = False
LANGUAGE_CODE = "en"
LANGUAGES = (("en", "English"),)

View File

@ -2,6 +2,7 @@
Settings for the testsuite runs.
"""
import django
from .base import * # noqa
SECRET_KEY = "test-key"

View File

@ -1,6 +1,7 @@
from django.apps import apps
from django.conf import settings
from django.conf.urls import url
from django.views.decorators.cache import cache_control
from django.views.decorators.clickjacking import xframe_options_exempt
from django.views.generic import TemplateView
@ -13,9 +14,11 @@ urlpatterns = [
url(r"^$", views.SnippetView.as_view(), name="snippet_new"),
url(
r"^about/$",
TemplateView.as_view(
template_name="dpaste/about.html",
extra_context=config.extra_template_context,
cache_control(max_age=config.CACHE_TIMEOUT)(
TemplateView.as_view(
template_name="dpaste/about.html",
extra_context=config.extra_template_context,
)
),
name="dpaste_about",
),

View File

@ -1,6 +1,7 @@
import datetime
import difflib
import json
import time
from django.apps import apps
from django.http import (
@ -10,12 +11,12 @@ from django.http import (
HttpResponseForbidden,
HttpResponseRedirect,
)
from django.shortcuts import get_object_or_404
from django.shortcuts import get_object_or_404, render
from django.urls import reverse
from django.utils import timezone
from django.utils.cache import add_never_cache_headers, patch_cache_control
from django.utils.http import http_date
from django.utils.translation import ugettext
from django.views.defaults import page_not_found as django_page_not_found
from django.views.defaults import server_error as django_server_error
from django.views.generic import FormView
from django.views.generic.base import TemplateView, View
from django.views.generic.detail import DetailView
@ -43,6 +44,12 @@ class SnippetView(FormView):
form_class = SnippetForm
template_name = "dpaste/new.html"
def get(self, request, *args, **kwargs):
response = super().get(request, *args, **kwargs)
if config.CACHE_HEADER:
patch_cache_control(response, max_age=config.CACHE_TIMEOUT)
return response
def get_form_kwargs(self):
kwargs = super(SnippetView, self).get_form_kwargs()
kwargs.update({"request": self.request})
@ -58,12 +65,13 @@ class SnippetView(FormView):
return ctx
class SnippetDetailView(SnippetView, DetailView):
class SnippetDetailView(DetailView):
"""
Details list view of a snippet. Handles the actual view, reply and
tree/diff view.
"""
form_class = SnippetForm
queryset = Snippet.objects.all()
template_name = "dpaste/details.html"
slug_url_kwarg = "snippet_id"
@ -106,7 +114,18 @@ class SnippetDetailView(SnippetView, DetailView):
snippet.view_count += 1
snippet.save(update_fields=["view_count"])
return super(SnippetDetailView, self).get(request, *args, **kwargs)
response = super(SnippetDetailView, self).get(request, *args, **kwargs)
# Set the Max-Age header up until the snippet would expire
if config.CACHE_HEADER:
if snippet.expire_type == Snippet.EXPIRE_KEEP:
patch_cache_control(response, max_age=config.CACHE_TIMEOUT)
if snippet.expire_type == Snippet.EXPIRE_ONETIME:
add_never_cache_headers(response)
if snippet.expire_type == Snippet.EXPIRE_TIME and snippet.expires:
response["Expires"] = http_date(snippet.expires.timestamp())
return response
def get_initial(self):
snippet = self.get_object()
@ -116,6 +135,11 @@ class SnippetDetailView(SnippetView, DetailView):
"rtl": snippet.rtl,
}
def get_form_kwargs(self):
kwargs = super().get_form_kwargs()
kwargs.update({"request": self.request})
return kwargs
def form_valid(self, form):
snippet = form.save(parent=self.get_object())
return HttpResponseRedirect(snippet.get_absolute_url())
@ -203,6 +227,11 @@ class SnippetHistory(TemplateView):
snippet_id_list = self.request.session.get("snippet_list", [])
return Snippet.objects.filter(pk__in=snippet_id_list)
def get(self, request, *args, **kwargs):
response = super().get(request, *args, **kwargs)
add_never_cache_headers(response)
return response
def post(self, request, *args, **kwargs):
"""
Delete all user snippets at once.
@ -332,12 +361,17 @@ class APIView(View):
def page_not_found(request, exception=None, template_name="dpaste/404.html"):
return django_page_not_found(
request, exception, template_name=template_name
)
context = {}
context.update(config.extra_template_context)
response = render(request, template_name, context, status=404)
if config.CACHE_HEADER:
patch_cache_control(response, max_age=config.CACHE_TIMEOUT)
return response
def server_error(request, template_name="dpaste/500.html"):
return django_server_error(
request, template_name=template_name
) # pragma: no cover
context = {}
context.update(config.extra_template_context)
response = render(request, template_name, context, status=500)
add_never_cache_headers(response)
return response