Skip to content

Commit

Permalink
feature: support for proxy caching plugin based on disk. (#1153)
Browse files Browse the repository at this point in the history
  • Loading branch information
agile6v authored Mar 15, 2020
1 parent c1df18f commit 864aa16
Show file tree
Hide file tree
Showing 12 changed files with 1,287 additions and 7 deletions.
47 changes: 46 additions & 1 deletion bin/apisix
Original file line number Diff line number Diff line change
Expand Up @@ -182,6 +182,22 @@ http {
lua_shared_dict jwks 1m; # cache for JWKs
lua_shared_dict introspection 10m; # cache for JWT verification results
{% if proxy_cache then %}
# for proxy cache
{% for _, cache in ipairs(proxy_cache.zones) do %}
proxy_cache_path {* cache.disk_path *} levels={* cache.cache_levels *} keys_zone={* cache.name *}:{* cache.memory_size *} inactive=1d max_size={* cache.disk_size *};
{% end %}
{% end %}
{% if proxy_cache then %}
# for proxy cache
map $upstream_cache_zone $upstream_cache_zone_info {
{% for _, cache in ipairs(proxy_cache.zones) do %}
{* cache.name *} {* cache.disk_path *},{* cache.cache_levels *};
{% end %}
}
{% end %}
lua_ssl_verify_depth 5;
ssl_session_timeout 86400;
Expand Down Expand Up @@ -375,6 +391,8 @@ http {
proxy_pass_header Server;
proxy_pass_header Date;
### the following x-forwarded-* headers is to send to upstream server
set $var_x_forwarded_for $remote_addr;
set $var_x_forwarded_proto $scheme;
set $var_x_forwarded_host $host;
Expand All @@ -398,7 +416,34 @@ http {
proxy_set_header X-Forwarded-Host $var_x_forwarded_host;
proxy_set_header X-Forwarded-Port $var_x_forwarded_port;
proxy_pass $upstream_scheme://apisix_backend$upstream_uri;
{% if proxy_cache then %}
### the following configuration is to cache response content from upstream server
set $upstream_cache_zone off;
set $upstream_cache_key '';
set $upstream_cache_bypass '';
set $upstream_no_cache '';
set $upstream_hdr_expires '';
set $upstream_hdr_cache_control '';
proxy_cache $upstream_cache_zone;
proxy_cache_valid any {% if proxy_cache and proxy_cache.cache_ttl then %} {* proxy_cache.cache_ttl *} {% else %} 5s {% end %};
proxy_cache_min_uses 1;
proxy_cache_methods GET HEAD;
proxy_cache_lock_timeout 5s;
proxy_cache_use_stale off;
proxy_cache_key $upstream_cache_key;
proxy_no_cache $upstream_no_cache;
proxy_cache_bypass $upstream_cache_bypass;
proxy_hide_header Cache-Control;
proxy_hide_header Expires;
add_header Cache-Control $upstream_hdr_cache_control;
add_header Expires $upstream_hdr_expires;
add_header Apisix-Cache-Status $upstream_cache_status always;
{% end %}
proxy_pass $upstream_scheme://apisix_backend$upstream_uri;
header_filter_by_lua_block {
apisix.http_header_filter_phase()
Expand Down
16 changes: 16 additions & 0 deletions conf/config.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,21 @@ apisix:
# enable_tcp_pp: true # Enable the proxy protocol for tcp proxy, it works for stream_proxy.tcp option
# enable_tcp_pp_to_upstream: true # Enables the proxy protocol to the upstream server

proxy_cache: # Proxy Caching configuration
cache_ttl: 10s # The default caching time if the upstream does not specify the cache time
zones: # The parameters of a cache
- name: disk_cache_one # The name of the cache, administrator can be specify
# which cache to use by name in the admin api
memory_size: 50m # The size of shared memory, it's used to store the cache index
disk_size: 1G # The size of disk, it's used to store the cache data
disk_path: "/tmp/disk_cache_one" # The path to store the cache data
cache_levels: "1:2" # The hierarchy levels of a cache
# - name: disk_cache_two
# memory_size: 50m
# disk_size: 1G
# disk_path: "/tmp/disk_cache_two"
# cache_levels: "1:2"

# allow_admin: # http://nginx.org/en/docs/http/ngx_http_access_module.html#allow
# - 127.0.0.0/24 # If we don't set any IP list, then any IP access is allowed by default.
# - "::/64"
Expand Down Expand Up @@ -124,6 +139,7 @@ plugins: # plugin list
- fault-injection
- udp-logger
- wolf-rbac
- proxy-cache
- tcp-logger

stream_plugins:
Expand Down
1 change: 1 addition & 0 deletions doc/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ Plugins
* [redirect](plugins/redirect.md): URI redirect.
* [response-rewrite](plugins/response-rewrite.md): Set customized response status code, body and header to the client.
* [fault-injection](plugins/fault-injection.md): The specified response body, response code, and response time can be returned, which provides processing capabilities in different failure scenarios, such as service failure, service overload, and high service delay.
* [proxy-cache](plugins/proxy-cache.md): Provides the ability to cache upstream response data.
* [tcp-logger](plugins/tcp-logger.md): Log requests to TCP servers

Deploy to the Cloud
Expand Down
1 change: 1 addition & 0 deletions doc/README_CN.md
Original file line number Diff line number Diff line change
Expand Up @@ -59,4 +59,5 @@ Reference document
* [redirect](plugins/redirect-cn.md): URI 重定向。
* [response-rewrite](plugins/response-rewrite-cn.md): 支持自定义修改返回内容的 `status code``body``headers`
* [fault-injection](plugins/fault-injection-cn.md):故障注入,可以返回指定的响应体、响应码和响应时间,从而提供了不同的失败场景下处理的能力,例如服务失败、服务过载、服务高延时等。
* [proxy-cache](plugins/proxy-cache-cn.md):代理缓存插件提供缓存后端响应数据的能力。

146 changes: 146 additions & 0 deletions doc/plugins/proxy-cache-cn.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
<!--
#
# Licensed to the Apache Software Foundation (ASF) under one or more
# contributor license agreements. See the NOTICE file distributed with
# this work for additional information regarding copyright ownership.
# The ASF licenses this file to You under the Apache License, Version 2.0
# (the "License"); you may not use this file except in compliance with
# the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
-->

[English](proxy-cache.md)

# proxy-cache

代理缓存插件,该插件提供缓存后端响应数据的能力,它可以和其他插件一起使用。该插件支持基于磁盘的缓存,未来也会支持基于内存的缓存。目前可以根据响应码、请求 Method 来指定需要缓存的数据,另外也可以通过 no_cache 和 cache_bypass 配置更复杂的缓存策略。

基于磁盘的缓存需要注意:
1. 不能动态配置缓存的过期时间,只能通过后端服务响应头 Expires 或 Cache-Control 来设置过期时间,如果后端响应头中没有 Expires 或 Cache-Control,那么 APISIX 将默认只缓存10秒钟
2. 如果后端服务不可用, APISIX 将返回502或504,那么502或504将被缓存10秒钟

### 参数

|名称 |必须|类型|描述|
|------- |-----|------|------|
|cache_zone||string|指定使用哪个缓存区域,不同的缓存区域可以配置不同的路径,在conf/config.yaml文件中可以预定义使用的缓存区域|
|cache_key||array[string]|缓存key,可以使用变量。例如:["$host", "$uri", "-cache-id"]|
|cache_bypass||array[string]|是否跳过缓存检索,即不在缓存中查找数据,可以使用变量,需要注意当此参数的值不为空或非'0'时将会跳过缓存的检索。例如:["$arg_bypass"]|
|cache_method||array[string]|根据请求method决定是否需要缓存|
|cache_http_status||array[integer]|根据响应码决定是否需要缓存|
|hide_cache_headers||boolean|是否将 Expires 和 Cache-Control 响应头返回给客户端,默认为 false|
|no_cache||array[string]|是否缓存数据,可以使用变量,需要注意当此参数的值不为空或非'0'时将不会缓存数据。|

注:变量以$开头,也可以使用变量和字符串的结合,但是需要以数组的形式分开写,最终变量被解析后会和字符串拼接在一起。

### 示例

#### 启用插件

示例1:为特定路由启用 `proxy-cache` 插件:

```shell
curl http://127.0.0.1:9080/apisix/admin/routes/1 -X PUT -d '
{
"plugins": {
"proxy-cache": {
"cache_zone": "disk_cache_one",
"cache_key": ["$uri", "-cache-id"],
"cache_bypass": ["$arg_bypass"],
"cache_method": ["GET"],
"cache_http_status": [200],
"hide_cache_headers": true,
"no_cache": ["$arg_test"]
}
},
"upstream": {
"nodes": {
"127.0.0.1:1999": 1
},
"type": "roundrobin"
},
"uri": "/hello"
}'
```

测试:

```shell
$ curl http://127.0.0.1:9080/hello -i
HTTP/1.1 200 OK
Content-Type: application/octet-stream
Content-Length: 6
Connection: keep-alive
Server: APISIX web server
Date: Tue, 03 Mar 2020 10:45:36 GMT
Last-Modified: Tue, 03 Mar 2020 10:36:38 GMT
Apisix-Cache-Status: MISS

hello
```

> http status 返回`200`并且响应头中包含`Apisix-Cache-Status`,表示该插件已启用。
示例2:验证文件是否被缓存,再次请求上边的地址:

测试:

```shell
$ curl http://127.0.0.1:9080/hello -i
HTTP/1.1 200 OK
Content-Type: application/octet-stream
Content-Length: 6
Connection: keep-alive
Server: APISIX web server
Date: Tue, 03 Mar 2020 11:14:46 GMT
Last-Modified: Thu, 20 Feb 2020 14:21:41 GMT
Apisix-Cache-Status: HIT

hello
```

> 响应头 Apisix-Cache-Status 值变为了 HIT,说明文件已经被缓存
示例3:如何清理缓存的文件,只需要指定请求的 method 为 PURGE:

测试:

```shell
$ curl -i http://127.0.0.1:9080/hello -X PURGE
HTTP/1.1 200 OK
Date: Tue, 03 Mar 2020 11:17:35 GMT
Content-Type: text/plain
Transfer-Encoding: chunked
Connection: keep-alive
Server: APISIX web server
```

> 响应码为200即表示删除成功,如果文件未找到将返回404
#### 禁用插件

移除插件配置中相应的 JSON 配置可立即禁用该插件,无需重启服务:

```shell
curl http://127.0.0.1:9080/apisix/admin/routes/1 -X PUT -d '
{
"uri": "/hello",
"plugins": {},
"upstream": {
"type": "roundrobin",
"nodes": {
"127.0.0.1:1999": 1
}
}
}'
```

这时该插件已被禁用。
Loading

0 comments on commit 864aa16

Please sign in to comment.