docker 部署 apisix 网关

规划

服务 路径 ip:port
etcd /data/docker/etcd 192.123.2.1:2379、2380
etcd /data/docker/etcd 192.123.2.2:2379、2380
etcd /data/docker/etcd 192.123.2.3:2379、2380
keepalived /etc/keepalived 主机IP:192.123.2.1,浮动IP:192.123.2.100
keepalived /etc/keepalived 主机IP:192.123.2.2,浮动IP:192.123.2.100
keepalived /etc/keepalived 主机IP:192.123.2.3,浮动IP:192.123.2.100
apisix /data/docker/apisix 192.123.2.1:9080、9443、3305
apisix /data/docker/apisix 192.123.2.1:9080、9443、3305
apisix /data/docker/apisix 192.123.2.1:9080、9443、3305
apisix-dashboard /data/docker/apisix-dashboard 192.123.2.1:9000

部署 etcd

单机

/data/docker/etcd/docker-compose.yml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
version: "3.8"

services:
etcd:
image: quay.io/coreos/etcd:v3.5.0
container_name: etcd
ports:
- "2379:2379"
volumes:
- ./data:/etcd_data
environment:
- ETCD_ENABLE_V2=true
- ALLOW_NONE_AUTHENTICATION=yes
- ETCD_DATA_DIR=/etcd_data
- ETCD_LISTEN_CLIENT_URLS=http://0.0.0.0:2379
- ETCD_ADVERTISE_CLIENT_URLS=http://0.0.0.0:2379
restart: always

集群

192.123.2.1

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
version: "3.8"

services:
etcd:
image: quay.io/coreos/etcd:v3.5.0
container_name: etcd
volumes:
- ./data:/etcd_data
environment:
- ETCD_ENABLE_V2=true
- ETCD_ROOT_PASSWORD=etcd-cluster@2021
- ETCD_NAME=etcd-01
- ETCD_DATA_DIR=/etcd_data
- ETCD_LISTEN_PEER_URLS=http://0.0.0.0:2380
- ETCD_LISTEN_CLIENT_URLS=http://0.0.0.0:2379
- ETCD_ADVERTISE_CLIENT_URLS=http://192.123.2.1:2379
- ETCD_INITIAL_ADVERTISE_PEER_URLS=http://192.123.2.1:2380
- ETCD_INITIAL_CLUSTER_TOKEN=etcd-cluster
- ETCD_INITIAL_CLUSTER=etcd-01=http://192.123.2.1:2380,etcd-02=http://192.123.2.2:2380,etcd-03=http://192.123.2.3:2380
# 如果是第一次初始化集群,需要使用new,否则使用existing
- ETCD_INITIAL_CLUSTER_STATE=new
# - ETCD_INITIAL_CLUSTER_STATE=existing
ports:
- "2379:2379"
- "2380:2380"
restart: always

192.123.2.2

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
version: "3.8"

services:
etcd:
image: quay.io/coreos/etcd:v3.5.0
container_name: etcd
volumes:
- ./data:/etcd_data
environment:
- ETCD_ENABLE_V2=true
- ETCD_ROOT_PASSWORD=etcd-cluster@2021
- ETCD_NAME=etcd-02
- ETCD_DATA_DIR=/etcd_data
- ETCD_LISTEN_PEER_URLS=http://0.0.0.0:2380
- ETCD_LISTEN_CLIENT_URLS=http://0.0.0.0:2379
- ETCD_ADVERTISE_CLIENT_URLS=http://192.123.2.2:2379
- ETCD_INITIAL_ADVERTISE_PEER_URLS=http://192.123.2.2:2380
- ETCD_INITIAL_CLUSTER_TOKEN=etcd-cluster
- ETCD_INITIAL_CLUSTER=etcd-01=http://192.123.2.1:2380,etcd-02=http://192.123.2.2:2380,etcd-03=http://192.123.2.3:2380
# 如果是第一次初始化集群,需要使用new,否则使用existing
- ETCD_INITIAL_CLUSTER_STATE=new
# - ETCD_INITIAL_CLUSTER_STATE=existing
ports:
- "2379:2379"
- "2380:2380"
restart: always

192.123.2.3

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
version: "3.8"

services:
etcd:
image: quay.io/coreos/etcd:v3.5.0
container_name: etcd
volumes:
- ./data:/etcd_data
environment:
- ETCD_ENABLE_V2=true
- ETCD_ROOT_PASSWORD=etcd-cluster@2021
- ETCD_NAME=etcd-03
- ETCD_DATA_DIR=/etcd_data
- ETCD_LISTEN_PEER_URLS=http://0.0.0.0:2380
- ETCD_LISTEN_CLIENT_URLS=http://0.0.0.0:2379
- ETCD_ADVERTISE_CLIENT_URLS=http://192.123.2.3:2379
- ETCD_INITIAL_ADVERTISE_PEER_URLS=http://192.123.2.3:2380
- ETCD_INITIAL_CLUSTER_TOKEN=etcd-cluster
- ETCD_INITIAL_CLUSTER=etcd-01=http://192.123.2.1:2380,etcd-02=http://192.123.2.2:2380,etcd-03=http://192.123.2.3:2380
# 如果是第一次初始化集群,需要使用new,否则使用existing
- ETCD_INITIAL_CLUSTER_STATE=new
# - ETCD_INITIAL_CLUSTER_STATE=existing
ports:
- "2379:2379"
- "2380:2380"
restart: always

部署 keepalived

安装

1
2
3
4
5
6
7
8
9
10
11
12
13
14
# 安装
sudo yum install keepalived
# 开启开机启动
sudo systemctl enable keepalived
# 禁用开机启动
sudo systemctl disable keepalived
# 启动服务
sudo systemctl start keepalived
# 重启服务
sudo systemctl restart keepalived
# 查看状态
sudo systemctl status keepalived
# 停止服务
sudo systemctl stop keepalived

keepalived.conf 配置

路径:/etc/keepalived/keepalived.conf

配置说明

  • state 取值
    • MASTER:master 节点
    • BACKUP:backup节点
  • interface:宿主机的网卡名
  • mcast_src_ip:宿主机的 ip
  • priority:master 节点的 priority 值需要大于 backup 节点的值
  • virtual_ipaddress:浮动 IP

192.123.2.1

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
global_defs {
router_id LVS_DEVEL
}
vrrp_instance VI_1 {
state MASTER
interface eth0
mcast_src_ip 192.123.2.1
virtual_router_id 51
priority 101
nopreempt
advert_int 2
authentication {
auth_type PASS
auth_pass keepavlied_apisix
}
virtual_ipaddress {
192.123.2.100
}
}

192.123.2.2

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
global_defs {
router_id LVS_DEVEL
}
vrrp_instance VI_1 {
state BACKUP
interface eth0
mcast_src_ip 192.123.2.2
virtual_router_id 51
priority 100
nopreempt
advert_int 2
authentication {
auth_type PASS
auth_pass keepavlied_apisix
}
virtual_ipaddress {
192.123.2.100
}
}

192.123.2.3

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
global_defs {
router_id LVS_DEVEL
}
vrrp_instance VI_1 {
state BACKUP
interface eth0
mcast_src_ip 192.123.2.3
virtual_router_id 51
priority 100
nopreempt
advert_int 2
authentication {
auth_type PASS
auth_pass keepavlied_apisix
}
virtual_ipaddress {
192.123.2.100
}
}

检测脚本

/etc/keepalived/alive-check.sh

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
#!/usr/bin/env bash

# 定时检测服务是否启动来判断需要 start keepalived 还是 stop keepalived。
# 以此来预防服务出现异常,但是浮动 IP 漂移到了异常服务节点的问题。
#
# 配置 crontab 定时任务:
# * * * * * /etc/keepalived/alive-check.sh > /dev/null 2>&1
# * * * * * /etc/keepalived/alive-check.sh >> /etc/keepalived/stdout.log 2>&1

# 获取 openresty 服务第一个进程 Id
openresty_pid=`ps aux | grep /usr/local/openresty | grep -v grep | awk 'NR==1{print $2}'`

# 获取 keepalived 服务第一个进程 Id
keepalived_pid=`ps aux | grep /usr/sbin/keepalived | grep -v grep | awk 'NR==1{print $2}'`

if [[ "$openresty_pid" == "" ]]; then
# 如果 openresty 服务未启动,stop keepalived 服务
echo "[$(date '+%Y-%m-%d %H:%M:%S')] stop keepalived ---> openresty_pid: $openresty_pid, keepalived_pid: $keepalived_pid"
/usr/bin/systemctl stop keepalived
else
# 如果 openresty 已启动,且 keepalived 服务未启动,则 start keepalived 服务
if [[ "$keepalived_pid" == "" ]]; then
echo "[$(date '+%Y-%m-%d %H:%M:%S')] start keepalived ---> openresty_pid: $openresty_pid, keepalived_pid: $keepalived_pid"
/usr/bin/systemctl start keepalived
fi
fi

配置定时任务

1
* * * * * /etc/keepalived/alive-check.sh >> /etc/keepalived/stdout.log 2>&1

部署 apisix

docker-compose.yml

/data/docker/apisix/docker-compose.yml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
version: "3.8"

services:
apisix:
image: apache/apisix:2.9-alpine
container_name: apisix
ports:
- "9080:9080"
- "9443:9443"
- "3305:3305"
volumes:
- ./conf/config.yaml:/usr/local/apisix/conf/config.yaml
- ./logs:/usr/local/apisix/logs
environment:
- "TZ=Asia/Shanghai"
restart: always

config.yaml

/data/docker/apisix/conf/config.yaml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
apisix:
# 这里改成对应宿主机的 IP 即可,也可以不配置,集群中的节点 Id 不能重复
id: "192_123_2_1"
node_listen: 9080
enable_ipv6: false

stream_proxy:
only: false
tcp:
- 9200

nginx_config:
stream_configuration_snippet: |
upstream mysqld {
hash $remote_addr consistent;
server 192.123.2.1:9003 weight=5 max_fails=1 fail_timeout=30s max_conns=1000;
server 192.123.2.2:9001 weight=5 max_fails=1 fail_timeout=30s max_conns=1000;
server 192.123.2.3:9002 weight=5 max_fails=1 fail_timeout=30s max_conns=1000;
}
server {
listen 3305;
proxy_connect_timeout 15s;
proxy_pass mysqld;
}

etcd:
host:
- "http://192.123.2.1:2379"
- "http://192.123.2.2:2379"
- "http://192.123.2.3:2379"
prefix: "/apisix"
timeout: 30

# 这里的 plugins 配置会覆盖 config-default.yml 的 plugins 配置,所以如果在这里配置
# 最好确定使用到的插件都配置了,最好把 default 配置拷贝过来,然后再追加自己需要开启的插件
plugins:
- real-ip
- client-control
- ext-plugin-pre-req
- zipkin
- request-id
- fault-injection
- serverless-pre-function
- batch-requests
- cors
- ip-restriction
- ua-restriction
- referer-restriction
- uri-blocker
- request-validation
- openid-connect
- authz-casbin
- wolf-rbac
- hmac-auth
- basic-auth
- jwt-auth
- key-auth
- consumer-restriction
- authz-keycloak
- error-log-logger
- proxy-mirror
- proxy-cache
- proxy-rewrite
- api-breaker
- limit-conn
- limit-count
- limit-req
- node-status
- gzip
- server-info
- traffic-split
- redirect
- response-rewrite
# - dubbo-proxy
- grpc-transcode
- prometheus
- echo
- http-logger
- sls-logger
- tcp-logger
- kafka-logger
- syslog
- udp-logger
- log-rotate
- example-plugin
# - skywalking
- serverless-post-function
- ext-plugin-post-req

plugin_attr:
server-info:
report_interval: 600
report_ttl: 3600
log-rotate:
interval: 86400
max_kept: 7
enable_compression: false

部署 apisix-dashboard

docker-compose.yml

/data/docker/apisix-dashboard/docker-compose.yml

1
2
3
4
5
6
7
8
9
10
11
12
version: "3.8"

services:
apisix-dashboard:
image: apache/apisix-dashboard:2.8
container_name: apisix-dashboard
volumes:
- ./conf/conf.yaml:/usr/local/apisix-dashboard/conf/conf.yaml
- ./logs:/usr/local/apisix-dashboard/logs
ports:
- "9000:9000"
restart: always

conf.yml

/data/docker/apisix-dashboard/conf/conf.yml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
#
# 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.
#

# yamllint disable rule:comments-indentation
conf:
listen:
# host: 127.0.0.1 # the address on which the `Manager API` should listen.
# The default value is 0.0.0.0, if want to specify, please enable it.
# This value accepts IPv4, IPv6, and hostname.
port: 9000 # The port on which the `Manager API` should listen.

# ssl:
# host: 127.0.0.1 # the address on which the `Manager API` should listen for HTTPS.
# The default value is 0.0.0.0, if want to specify, please enable it.
# port: 9001 # The port on which the `Manager API` should listen for HTTPS.
# cert: "/tmp/cert/example.crt" # Path of your SSL cert.
# key: "/tmp/cert/example.key" # Path of your SSL key.

#allow_list: # If we don't set any IP list, then any IP access is allowed by default.
# - 127.0.0.1 # The rules are checked in sequence until the first match is found.
# - ::1 # In this example, access is allowed only for IPv4 network 127.0.0.1, and for IPv6 network ::1.
# It also support CIDR like 192.168.1.0/24 and 2001:0db8::/32
etcd:
endpoints: # supports defining multiple etcd host addresses for an etcd cluster
- http://192.123.2.1:2379
- http://192.123.2.2:2379
- http://192.123.2.3:2379
# yamllint disable rule:comments-indentation
# etcd basic auth info
# username: "root" # ignore etcd username if not enable etcd auth
# password: "123456" # ignore etcd password if not enable etcd auth
mtls:
key_file: "" # Path of your self-signed client side key
cert_file: "" # Path of your self-signed client side cert
ca_file: "" # Path of your self-signed ca cert, the CA is used to sign callers' certificates
# prefix: /apisix # apisix config's prefix in etcd, /apisix by default
log:
error_log:
level: warn # supports levels, lower to higher: debug, info, warn, error, panic, fatal
file_path:
logs/error.log # supports relative path, absolute path, standard output
# such as: logs/error.log, /tmp/logs/error.log, /dev/stdout, /dev/stderr
# such as absolute path on Windows: winfile:///C:\error.log
access_log:
file_path:
logs/access.log # supports relative path, absolute path, standard output
# such as: logs/access.log, /tmp/logs/access.log, /dev/stdout, /dev/stderr
# such as absolute path on Windows: winfile:///C:\access.log
# log example: 2020-12-09T16:38:09.039+0800 INFO filter/logging.go:46 /apisix/admin/routes/r1 {"status": 401, "host": "127.0.0.1:9000", "query": "asdfsafd=adf&a=a", "requestId": "3d50ecb8-758c-46d1-af5b-cd9d1c820156", "latency": 0, "remoteIP": "127.0.0.1", "method": "PUT", "errs": []}
max_cpu: 0 # supports tweaking with the number of OS threads are going to be used for parallelism. Default value: 0 [will use max number of available cpu cores considering hyperthreading (if any)]. If the value is negative, is will not touch the existing parallelism profile.

authentication:
secret:
secret # secret for jwt token generation.
# NOTE: Highly recommended to modify this value to protect `manager api`.
# if it's default value, when `manager api` start, it will generate a random string to replace it.
expire_time: 3600 # jwt token expire time, in second
users: # yamllint enable rule:comments-indentation
- username: admin # username and password for login `manager api`
password: admin
- username: user
password: user

plugins: # plugin list (sorted in alphabetical order)
- api-breaker
- authz-keycloak
- basic-auth
- batch-requests
- consumer-restriction
- cors
# - dubbo-proxy
- echo
# - error-log-logger
# - example-plugin
- fault-injection
- grpc-transcode
- hmac-auth
- http-logger
- ip-restriction
- jwt-auth
- kafka-logger
- key-auth
- limit-conn
- limit-count
- limit-req
# - log-rotate
# - node-status
- openid-connect
- prometheus
- proxy-cache
- proxy-mirror
- proxy-rewrite
- redirect
- referer-restriction
- request-id
- request-validation
- response-rewrite
- serverless-post-function
- serverless-pre-function
# - skywalking
- sls-logger
- syslog
- tcp-logger
- udp-logger
- uri-blocker
- wolf-rbac
- zipkin
- server-info
- traffic-split
  • 本文作者: forever杨
  • 本文链接: https://blog.yl-online.top/posts/1666f2bf.html
  • 版权声明: 本博客所有文章除特别声明外,均采用 BY-NC-SA 许可协议。如果文章内容对你有用,请记录到你的笔记中。本博客站点随时会停止服务,请不要收藏、转载!