利用docker-compose和nginx搭建高可用負載均衡
前言
實驗環境
Ubuntu16.04
Docker
Nginx
https://github.com/CTFd/CTFd
ps: 並未實現跨域部署
服務文件以及思路展現
初始的docker-compose.yml裏面有一個主服務,一個數據庫。
version: '2'
services:
ctfd:
build: .
user: root
restart: always
ports:
- "81:8000"
environment:
- UPLOAD_FOLDER=/var/uploads
- DATABASE_URL=mysql+pymysql://root:ctfd@db/ctfd
- REDIS_URL=redis://cache:6379
- WORKERS=1
- LOG_FOLDER=/var/log/CTFd
- ACCESS_LOG=-
- ERROR_LOG=-
volumes:
- .data/CTFd/logs:/var/log/CTFd
- .data/CTFd/uploads:/var/uploads
- .:/opt/CTFd:ro
depends_on:
- db
networks:
default:
internal:
db:
image: mariadb:10.4
restart: always
environment:
- MYSQL_ROOT_PASSWORD=ctfd
- MYSQL_USER=ctfd
- MYSQL_PASSWORD=ctfd
- MYSQL_DATABASE=ctfd
volumes:
- .data/mysql:/var/lib/mysql
networks:
internal:
# This command is required to set important mariadb defaults
command: [mysqld, --character-set-server=utf8mb4, --collation-server=utf8mb4_unicode_ci, --wait_timeout=28800, --log-warnings=0]
cache:
image: redis:4
restart: always
volumes:
- .data/redis:/data
networks:
internal:
networks:
default:
internal:
internal: true
思路就是添加主服務的容器數量並且link同一個數據庫容器,通過不同的端口運行主服務,提供機器的高可用性。如果需要使用跨域搭建請參考(openvswitch網橋)
所以現在只需要添加主服務ctf的數量,且分配不同的ip即可。
version: '2'
services:
ctfd1:
build: .
user: root
restart: always
# expose:
# - 8000
ports:
- "81:8000"
environment:
- UPLOAD_FOLDER=/var/uploads
- DATABASE_URL=mysql+pymysql://root:ctfd@db/ctfd
- REDIS_URL=redis://cache:6379
- WORKERS=1
- LOG_FOLDER=/var/log/CTFd
- ACCESS_LOG=-
- ERROR_LOG=-
volumes:
- .data/CTFd/logs:/var/log/CTFd
- .data/CTFd/uploads:/var/uploads
- .:/opt/CTFd:ro
depends_on:
- db
networks:
default:
internal:
ctfd2:
build: .
user: root
restart: always
# expose:
# - 8000
ports:
- "82:8000"
environment:
- UPLOAD_FOLDER=/var/uploads
- DATABASE_URL=mysql+pymysql://root:ctfd@db/ctfd
- REDIS_URL=redis://cache:6379
- WORKERS=1
- LOG_FOLDER=/var/log/CTFd
- ACCESS_LOG=-
- ERROR_LOG=-
volumes:
- .data/CTFd/logs:/var/log/CTFd
- .data/CTFd/uploads:/var/uploads
- .:/opt/CTFd:ro
depends_on:
- db
networks:
default:
internal:
ctfd3:
build: .
user: root
restart: always
# expose:
# - 8000
ports:
- "83:8000"
environment:
- UPLOAD_FOLDER=/var/uploads
- DATABASE_URL=mysql+pymysql://root:ctfd@db/ctfd
- REDIS_URL=redis://cache:6379
- WORKERS=1
- LOG_FOLDER=/var/log/CTFd
- ACCESS_LOG=-
- ERROR_LOG=-
volumes:
- .data/CTFd/logs:/var/log/CTFd
- .data/CTFd/uploads:/var/uploads
- .:/opt/CTFd:ro
depends_on:
- db
networks:
default:
internal:
ctfd4:
build: .
user: root
restart: always
# expose:
# - 8000
ports:
- "84:8000"
environment:
- UPLOAD_FOLDER=/var/uploads
- DATABASE_URL=mysql+pymysql://root:ctfd@db/ctfd
- REDIS_URL=redis://cache:6379
- WORKERS=1
- LOG_FOLDER=/var/log/CTFd
- ACCESS_LOG=-
- ERROR_LOG=-
volumes:
- .data/CTFd/logs:/var/log/CTFd
- .data/CTFd/uploads:/var/uploads
- .:/opt/CTFd:ro
depends_on:
- db
networks:
default:
internal:
ctfd5:
build: .
user: root
restart: always
# expose:
# - 8000
ports:
- "85:8000"
environment:
- UPLOAD_FOLDER=/var/uploads
- DATABASE_URL=mysql+pymysql://root:ctfd@db/ctfd
- REDIS_URL=redis://cache:6379
- WORKERS=1
- LOG_FOLDER=/var/log/CTFd
- ACCESS_LOG=-
- ERROR_LOG=-
volumes:
- .data/CTFd/logs:/var/log/CTFd
- .data/CTFd/uploads:/var/uploads
- .:/opt/CTFd:ro
depends_on:
- db
networks:
default:
internal:
ctfd6:
build: .
user: root
restart: always
# expose:
# - 8000
ports:
- "86:8000"
environment:
- UPLOAD_FOLDER=/var/uploads
- DATABASE_URL=mysql+pymysql://root:ctfd@db/ctfd
- REDIS_URL=redis://cache:6379
- WORKERS=1
- LOG_FOLDER=/var/log/CTFd
- ACCESS_LOG=-
- ERROR_LOG=-
volumes:
- .data/CTFd/logs:/var/log/CTFd
- .data/CTFd/uploads:/var/uploads
- .:/opt/CTFd:ro
depends_on:
- db
networks:
default:
internal:
db:
image: mariadb:10.4
restart: always
environment:
- MYSQL_ROOT_PASSWORD=ctfd
- MYSQL_USER=ctfd
- MYSQL_PASSWORD=ctfd
- MYSQL_DATABASE=ctfd
volumes:
- .data/mysql:/var/lib/mysql
networks:
internal:
# This command is required to set important mariadb defaults
command: [mysqld, --character-set-server=utf8mb4, --collation-server=utf8mb4_unicode_ci, --wait_timeout=28800, --log-warnings=0]
cache:
image: redis:4
restart: always
volumes:
- .data/redis:/data
networks:
internal:
networks:
default:
internal:
internal: true
在這裏我封裝成了6個容器,因爲這樣子編寫需要重新build 6個主服務容器的鏡像,所以最好是根據原來一個的鏡像,執行docker tag命令,因爲主服務都是相同的,只要有一個鏡像搭建成功就可以了。
這樣我們就可以通過6個端口來訪問主服務了。(僅僅實現了端口分發)
配置Nginx實現負載均衡
主要的nginx配置內容爲
upstream myserver{
server 127.0.0.1:81;
server 127.0.0.1:82;
server 127.0.0.1:83;
server 127.0.0.1:84;
server 127.0.0.1:85;
server 127.0.0.1:86;
}
server {
listen 80;
server_name www.myserver.org;
location / {
proxy_pass http://myserver;
}
}
執行 ./nginx -s reload 或者 重啓服務即可實現負載均衡。因爲條件有限,如果還需要提高用戶的訪問速度,可以考慮添加動靜分離以及cdn分發,將網頁中的js文件或者css文件採用cdn外鏈。
關於作者
聯繫方式 - [email protected]
你也可以通過 github | csdn | @新浪微博 關注我的動態
歡迎點贊👍評論喲~