Skip to content

Commit 644ae50

Browse files
committed
add CDN caching to rustdoc redirects only
1 parent 9598ae7 commit 644ae50

File tree

2 files changed

+28
-22
lines changed

2 files changed

+28
-22
lines changed

src/web/mod.rs

+23-1
Original file line numberDiff line numberDiff line change
@@ -99,7 +99,7 @@ use extensions::InjectExtensions;
9999
use failure::Error;
100100
use iron::{
101101
self,
102-
headers::{Expires, HttpDate},
102+
headers::{CacheControl, CacheDirective, Expires, HttpDate},
103103
modifiers::Redirect,
104104
status,
105105
status::Status,
@@ -496,6 +496,28 @@ fn redirect(url: Url) -> Response {
496496
resp
497497
}
498498

499+
/// creates a redirect-response which is cached on the CDN level for
500+
/// the given amount of seconds. Browser-Local caching is deactivated.
501+
/// The used s-maxage is respected by CloudFront (which we can invalidate
502+
/// if we need to), and perhaps by other proxies in between.
503+
/// When the cache-seconds are reasonably small, this should be fine.
504+
///
505+
/// CloudFront doesn't have `surrogate-control` headers which would be only
506+
/// used by CloudFront and dropped (Fastly has them).
507+
///
508+
/// The `Expires` header from `redirect` is still kept to be safe,
509+
/// CloudFront ignores it when it gets `Cache-Control: max-age` or
510+
/// `s-maxage`.
511+
fn cached_redirect(url: Url, cache_seconds: u32) -> Response {
512+
let mut resp = redirect(url);
513+
resp.headers.set(CacheControl(vec![
514+
CacheDirective::MaxAge(0),
515+
CacheDirective::SMaxAge(cache_seconds),
516+
]));
517+
518+
resp
519+
}
520+
499521
fn redirect_base(req: &Request) -> String {
500522
// Try to get the scheme from CloudFront first, and then from iron
501523
let scheme = req

src/web/rustdoc.rs

+5-21
Original file line numberDiff line numberDiff line change
@@ -70,14 +70,8 @@ pub fn rustdoc_redirector_handler(req: &mut Request) -> IronResult<Response> {
7070
}
7171
let url = ctry!(req, Url::parse(&url_str));
7272
let config = extension!(req, Config);
73-
let mut resp = Response::with((status::Found, Redirect(url)));
74-
resp.headers.set(CacheControl(vec![
75-
CacheDirective::MaxAge(0),
76-
// s-maxage is only for the CDN.
77-
CacheDirective::SMaxAge(config.cache_rustdoc_redirects),
78-
]));
79-
80-
Ok(resp)
73+
74+
Ok(super::cached_redirect(url, config.cache_rustdoc_redirects))
8175
}
8276

8377
fn redirect_to_crate(req: &Request, name: &str, vers: &str) -> IronResult<Response> {
@@ -87,14 +81,7 @@ pub fn rustdoc_redirector_handler(req: &mut Request) -> IronResult<Response> {
8781
);
8882

8983
let config = extension!(req, Config);
90-
let mut resp = Response::with((status::Found, Redirect(url)));
91-
resp.headers.set(CacheControl(vec![
92-
CacheDirective::MaxAge(0),
93-
// s-maxage is only for the CDN.
94-
CacheDirective::SMaxAge(config.cache_rustdoc_redirects),
95-
]));
96-
97-
Ok(resp)
84+
Ok(super::cached_redirect(url, config.cache_rustdoc_redirects))
9885
}
9986

10087
let metrics = extension!(req, Metrics).clone();
@@ -292,7 +279,7 @@ pub fn rustdoc_html_server_handler(req: &mut Request) -> IronResult<Response> {
292279
);
293280
let url = ctry!(req, Url::parse(&redirect_path));
294281

295-
Ok(super::redirect(url))
282+
Ok(super::cached_redirect(url, config.cache_rustdoc_redirects))
296283
};
297284

298285
rendering_time.step("match version");
@@ -561,10 +548,7 @@ pub fn target_redirect_handler(req: &mut Request) -> IronResult<Response> {
561548
);
562549

563550
let url = ctry!(req, Url::parse(&url));
564-
let mut resp = Response::with((status::Found, Redirect(url)));
565-
resp.headers.set(Expires(HttpDate(time::now())));
566-
567-
Ok(resp)
551+
Ok(super::cached_redirect(url, config.cache_rustdoc_redirects))
568552
}
569553

570554
pub fn badge_handler(req: &mut Request) -> IronResult<Response> {

0 commit comments

Comments
 (0)