这个文章时2016年组内分享时写的,在此做个备份

常见web应用的部署

Title: uwsgi应用(django)

nginx->uwsgi: uwsgi_pass(uwsgi-protol)
uwsgi->django: call
django->uwsgi: resp
Title: 代理方式(tornado)

nginx->app: proxy_pass(http)
app->nginx: resp(http)

应用内生成缓存指令

api要有缓存,要根据api的具体情况定制缓存策略,下面给一种简单的缓存架构

在api server端,对于不同的接口,声明合适的http头,如Cache-control, expires等,缓存本身由中间层来做,如nginx、varnish等来负责。

last_modified = time.strftime("%a, %d %b %Y %H:%M:%S GMT", time.gmtime(time.time()))
web.header('Last-Modified',last_modified)
web.header('Cache-Control', 'max-age=86400')

nginx配置缓存

uwsgi-cache

Title: uwsgi应用(django)

nginx->uwsgi_cache: cache lookup
uwsgi_cache->nginx: hit/miss/updating?
nginx->uwsgi: cache miss?
uwsgi->django: call
django->uwsgi: resp
uwsgi->nginx: resp
nginx->uwsgi_cache: update cache
        location = / {
                include uwsgi_params;
                uwsgi_pass ui;
                uwsgi_cache ui-uwsgi-cache;
                uwsgi_next_upstream error timeout invalid_header http_500 http_503;
                uwsgi_cache_key "$request_method$scheme$host$request_uri";
                uwsgi_cache_valid 200 10m;
                uwsgi_ignore_headers Set-Cookie Vary;
                uwsgi_cache_use_stale error timeout invalid_header updating http_500 http_503;
        }

        location ~ ^/(open|terms|privacy)/ {
                include uwsgi_params;
                uwsgi_pass ui;
                uwsgi_cache ui-uwsgi-cache;
                uwsgi_next_upstream error timeout invalid_header http_500 http_503;
                uwsgi_cache_key "$request_method$scheme$host$request_uri";
                uwsgi_cache_valid 200 10m;
                uwsgi_ignore_headers Set-Cookie Vary;
                uwsgi_cache_use_stale error timeout invalid_header updating http_500 http_503;
        }
        
        location / {
                include uwsgi_params;
                uwsgi_pass ui;
                uwsgi_read_timeout 300;

                uwsgi_cache ui-uwsgi-cache;
                uwsgi_cache_key $host$request_uri;
                uwsgi_cache_valid 404 1h;
                uwsgi_ignore_headers Set-Cookie Vary;
                uwsgi_cache_use_stale error timeout invalid_header updating http_500 http_503;
        }

需要注意的地方:

  1. uwsgi_cache_key要谨慎指定,它是缓存资源的标识,要避免冲突
  2. uwsgi_cache_methods默认值是GET HEAD(!!!),因此缓存key必须包含$request_method, 否则会造成缓存混乱
  3. 源站的响应头中Set-Cookie Vary会影响缓存,需要忽略掉

proxy_cache

proxy_cache的配置项与uwsgi_cache几乎一样。

下面的配置中,未指定uwsgi_cache_valid,它会根据响应头中的相关缓存指令执行缓存策略

Title: 代理应用(tornado)

nginx->proxy_cache: cache lookup
proxy_cache->nginx: hit/miss/updating?
nginx->app: cache miss? proxy_pass
app->nginx: resp(http)
nginx->proxy_cache: update cache
server {
        listen 8200;
        
        location /v1 {
			proxy_cache ui-proxy-cache;
			proxy_cache_key "$scheme://$host$request_uri|$http_authorization";
			proxy_cache_use_stale error timeout invalid_header updating http_500 http_502;
			proxy_set_header Host "yyyyyyy";
			proxy_pass http://xxxxxxxx;
        }
        location /v2 {
        	proxy_cache ui-proxy-cache;
	        proxy_cache_key "$scheme://$host$request_uri|$request_body";
	        proxy_cache_valid  200 3d;
	        proxy_cache_methods POST;
	        proxy_pass http://yyyyyy;
        }
}

缓存清理

https://github.com/FRiCKLE/ngx_cache_purge

ngx_cache_purge模块,可以清除FastCGI, proxy, SCGI , uWSGI的缓存。