def _handle_old_since_redirect()

in kinto-remote-settings/src/kinto_remote_settings/changes/views.py [0:0]


def _handle_old_since_redirect(request):
    """
    In order to limit the number of possible combinations
    of `_since` and `_expected` querystring parameters,
    and thus maximize the effect of caching, we redirect the clients
    that arrive here with a very old `_since` value.

    This simply means that these clients will have to iterate
    and compare the local timestamps of the whole list of changes
    instead of a filtered subset.

    https://searchfox.org/mozilla-central/rev/b58ca450/services/settings/remote-settings.js#299

    See https://bugzilla.mozilla.org/show_bug.cgi?id=1529685
    and https://bugzilla.mozilla.org/show_bug.cgi?id=1665319#c2
    """
    try:
        # request.validated is not populated yet (resource was not instantiated yet,
        # we want to bypass storage).
        qs_since_str = request.GET.get("_since", "")
        qs_since = int(qs_since_str.strip('"'))
    except ValueError:
        # Will fail later during resource querystring validation.
        return

    settings = request.registry.settings
    max_age_since = int(settings.get("changes.since_max_age_days", 21))
    if max_age_since < 0:
        # Redirect is disabled.
        return

    min_since_dt = datetime.now() - timedelta(days=max_age_since)
    min_since = min_since_dt.timestamp() * 1000

    if qs_since >= min_since:
        # Since value is recent. No redirect.
        return

    http_scheme = settings.get("http_scheme") or "https"
    http_host = settings.get(
        "changes.http_host", request.registry.settings.get("http_host")
    )
    host_uri = f"{http_scheme}://{http_host}"
    redirect = host_uri + request.matched_route.generate(request.matchdict)

    queryparams = request.GET.copy()
    del queryparams["_since"]
    if queryparams:
        redirect += "?" + urlencode(queryparams)

    # Serve a redirection, with optional cache control headers.
    response = httpexceptions.HTTPTemporaryRedirect(redirect)
    cache_seconds = int(
        settings.get("changes.since_max_age_redirect_ttl_seconds", 86400)
    )
    if cache_seconds >= 0:
        response.cache_expires(cache_seconds)
    raise response