优化docker部署

publicsignpoll
youngS 3 years ago
parent 08c6b7b87f
commit 0e2578738f
  1. 13
      Docker/build.sh
  2. 6
      Docker/end.sh
  3. 58
      Docker/flyapps.conf
  4. 5
      Docker/init.sh
  5. 10
      Docker/start.sh
  6. 41
      Docker/uwsgi.conf
  7. 46
      Dockerfile
  8. 12
      build.sh
  9. 7
      build_client.sh
  10. 14
      docker.md
  11. 4
      fir_client/src/components/apps/FirApps.vue
  12. 41
      fir_ser/Dockerfile
  13. 5
      fir_ser/api/management/commands/services/services/base.py
  14. 3
      fir_ser/api/management/commands/services/utils.py
  15. 8
      fir_ser/api/utils/utils.py
  16. 30
      fir_ser/api/views/login.py
  17. 28
      fir_ser/api/views/order.py
  18. 1
      fir_ser/config.py
  19. 1
      fir_ser/fir_ser/settings.py
  20. 25
      fir_ser/flyapp.sh
  21. BIN
      fir_ser/sqlite-autoconf-3310100.tar.gz
  22. BIN
      fir_ser/zsign-1.1.2.tar.gz
  23. 0
      nginx.conf.d/app.hehelucky.cn.key
  24. 0
      nginx.conf.d/app.hehelucky.cn.pem
  25. 16
      nginx.conf.d/flyapps-vhost.conf
  26. 41
      start.sh

@ -1,13 +0,0 @@
#!/bin/bash
#
#
w_path=`pwd`
s_path=`dirname ${w_path}`
#first build fir_client
docker pull node:14.17.3
docker run --rm -v ${s_path}/fir_client:/fir_client -it node:14.17.3 sh /fir_client/build.sh
## secode build fir_ser
cd ../
docker build . -t flyapps

@ -1,6 +0,0 @@
#!/bin/bash
sed -i '/^\[program:init/,$d' /etc/supervisor/conf.d/flyapps.conf
supervisorctl stop init &>/dev/null
supervisorctl stop end &>/dev/null
echo 'init end------------------------------------------'
exit 0

@ -1,58 +0,0 @@
[program:nginx]
command=/usr/sbin/nginx -g 'daemon off;'
stdout_logfile=/data/logs/nginx.log
stderr_logfile=/data/logs/nginx.err
#user=nginx
autostart=true
autorestart=true
startsecs=1
[program:redis]
command=/usr/bin/redis-server /etc/redis/redis.conf
stdout_logfile=/data/logs/redis.log
stderr_logfile=/data/logs/redis.err
autostart=true
autorestart=true
startsecs=3
daemonize=no
[program:flyapps]
directory=/data/flyapps/fir_ser/
command=/usr/local/bin/uwsgi --ini uwsgi.conf
user=www-data
stdout_logfile=/data/logs/flyapps.log
stderr_logfile=/data/logs/flyapps.err
autostart=true
autorestart=true
startsecs=3
daemonize=no
[program:celery]
directory=/data/flyapps/fir_ser/
command=/usr/local/bin/celery -A fir_ser worker --beat --scheduler django --loglevel=debug
user=www-data
stdout_logfile=/data/logs/celery.log
stderr_logfile=/data/logs/celery.err
autostart=true
autorestart=true
startsecs=3
daemonize=no
[program:init]
startsecs=1
stdout_logfile=/data/logs/init.log
stderr_logfile=/data/logs/init.err
command=/data/flyapps/init.sh
user=www-data
autostart=true
autorestart=false
daemonize=no
[program:end]
startsecs=1
stdout_logfile=/data/logs/init.log
stderr_logfile=/data/logs/init.err
command=/data/flyapps/end.sh
autostart=true
autorestart=false
daemonize=no

@ -1,5 +0,0 @@
#!/bin/bash
cd /data/flyapps/fir_ser/
python manage.py makemigrations && python manage.py migrate
python manage.py loaddata dumpdata.json
exit 0

@ -1,10 +0,0 @@
#!/bin/bash
#
#
docker network create flyapps
docker run --net flyapps --name mariadb -e MARIADB_ROOT_PASSWORD=root -d mariadb:10.5
docker exec -it mariadb mysql -proot -e 'create database flyapp default character set utf8 COLLATE utf8_general_ci;'
docker exec -it mariadb mysql -proot -e "grant all on flyapp.* to flyuser@'%' identified by 'KGzKjZpWBp4R4RSa';"
docker run --net flyapps --link mariadb:mariadb -p 443:443 --name flyapps -d flyapps

@ -1,41 +0,0 @@
[uwsgi]
# 对外提供 http 服务的端口
#http = 127.0.0.1:8899
#listen = 512 # set max connections to 1024 in uWSGI
#the local unix socket file than commnuincate to Nginx 用于和 nginx 进行数据交互的端口
socket = 127.0.0.1:8899
# the base directory (full path) django 程序的主目录
chdir = /data/flyapps/fir_ser
# Django's wsgi file
wsgi-file = fir_ser/wsgi.py
touch-reload = fir_ser
#uwsgi 内部解析数据包大小为4K ,自己可以增加64k
buffer-size = 65536
# maximum number of worker processes
processes = 8
#thread numbers startched in each worker process
threads = 4
#monitor uwsgi status 通过该端口可以监控 uwsgi 的负载情况
stats = 127.0.0.1:9191
# 如果以nginx用户运行,则需要授权 ruby 权限 chmod ug+s /usr/local/rvm/rubies/ruby-2.7.0/bin/ruby /usr/bin/isign 否则,会导致登录信息保存失败
uid=www-data
gid=www-data
# clear environment on exit
vacuum = true
enable-threads = true
# 后台运行,并输出日志
#daemonize = ./flyapp.log
# 为了让阿里云cdn可以缓存数据
del-header=cache-control

@ -1,46 +0,0 @@
FROM python:3.6.14-slim
# Fixes some weird terminal issues such as broken clear / CTRL+L
ARG PIP_MIRROR=https://mirrors.aliyun.com/pypi/simple
RUN sed -i 's/deb.debian.org/mirrors.aliyun.com/g' /etc/apt/sources.list \
&& sed -i 's/security.debian.org/mirrors.aliyun.com/g' /etc/apt/sources.list \
&& apt update
RUN apt-get install g++ wget nginx redis supervisor -y
RUN apt-get install libssl-dev openssl libmariadb-dev sqlite -y
RUN rm -rf /var/lib/apt/lists/*
RUN mkdir -pv /data/flyapps
RUN mkdir -pv /data/logs/
COPY fir_client/dist /data/flyapps/fir_client
RUN cd /opt/ && wget https://github.com/nineaiyu/zsign/archive/refs/tags/v1.1.1.tar.gz
RUN cd /opt/ && tar xvf v1.1.1.tar.gz && cd zsign-1.1.1/ && g++ *.cpp common/*.cpp -lcrypto -O3 -std=c++11 -o zsign && cp zsign /usr/bin/
# install pip
COPY fir_ser /data/flyapps/fir_ser
RUN cd /data/flyapps/fir_ser/ && pip install -U setuptools pip -i ${PIP_MIRROR} --ignore-installed && pip install --no-cache-dir -r requirements.txt -i ${PIP_MIRROR} && pip install --no-cache-dir uwsgi -i ${PIP_MIRROR}
RUN rm -rf /var/cache/yum/
COPY Docker/flyapps.conf /etc/supervisor/conf.d/flyapps.conf
COPY Docker/uwsgi.conf /data/flyapps/fir_ser/uwsgi.conf
COPY Docker/flyapps-vhost.conf /etc/nginx/conf.d/flyapps-vhost.conf
COPY Docker/app.hehelucky.cn.pem /data/flyapps/app.hehelucky.cn.pem
COPY Docker/app.hehelucky.cn.key /data/flyapps/app.hehelucky.cn.key
RUN chown -R www-data:www-data /data/flyapps/fir_ser/
RUN sed -i "/^daemonize/s@yes@no@" /etc/redis/redis.conf
#RUN cd /data/flyapps/&& source py3/bin/activate && cd fir_ser/ && python manage.py makemigrations && python manage.py migrate
COPY Docker/init.sh /data/flyapps/init.sh
COPY Docker/end.sh /data/flyapps/end.sh
EXPOSE 443
#ENTRYPOINT ["/data/flyapps/init.sh"]
#ENTRYPOINT ["/usr/bin/supervisord", "-c", "/etc/supervisor/supervisord.conf", "-n"]
CMD ["/usr/bin/supervisord", "-c", "/etc/supervisor/supervisord.conf", "-n"]

@ -0,0 +1,12 @@
#!/bin/bash
#
#
# shellcheck disable=SC2006
s_path=`pwd`
#first build fir_client
docker pull node:14.17.3
\cp -a build_client.sh fir_client/
docker run --rm -v "${s_path}"/fir_client:/fir_client -it node:14.17.3 sh /fir_client/build_client.sh
cd "${s_path}"/fir_ser/ && docker build . -t flyapps

@ -0,0 +1,7 @@
#!/bin/bash
#
#
cd /fir_client/ && yarn config set registry https://registry.npm.taobao.org && yarn install && yarn build

@ -13,9 +13,9 @@ yum install docker -y
```
#### 配置域名和证书,如果有cdn或者oss,也要进行配置
```shell script
Docker/app.hehelucky.cn.key
Docker/app.hehelucky.cn.pem
Docker/flyapps-vhost.conf
nginx.conf.d/app.hehelucky.cn.key
nginx.conf.d/app.hehelucky.cn.pem
nginx.conf.d/flyapps-vhost.conf
```
### api服务需要修改api和web域名,短信,邮箱,geetest,存储等信息
```shell script
@ -40,6 +40,12 @@ const pro_base_env = {
##### 构建静态资源和api服务
```
cd Docker && sh build.sh
sh build.sh
```
##### 启动所有服务
```
sh start.sh
```

@ -712,6 +712,10 @@
if (this.data_package_prices && this.data_package_prices.length > 0) {
this.default_price_radio = this.data_package_prices[parseInt(this.data_package_prices.length / 2)].name;
}
if (this.pay_choices.length === 0) {
this.$message.warning("暂不支持下载次数购买,请联系管理员");
this.show_buy_download_times = false;
}
} else {
this.$message.error("获取价格异常");
this.show_buy_download_times = false;

@ -0,0 +1,41 @@
FROM python:3.6.14-slim
# Fixes some weird terminal issues such as broken clear / CTRL+L
ARG PIP_MIRROR=https://mirrors.aliyun.com/pypi/simple
RUN sed -i 's/deb.debian.org/mirrors.aliyun.com/g' /etc/apt/sources.list \
&& sed -i 's/security.debian.org/mirrors.aliyun.com/g' /etc/apt/sources.list \
&& apt update
RUN apt-get install g++ wget -y
RUN apt-get install libssl-dev openssl libmariadb-dev -y
RUN rm -rf /var/lib/apt/lists/*
#COPY fir_client/dist /data/flyapps/fir_client
#RUN cd /opt/ && wget https://github.com/nineaiyu/zsign/archive/refs/tags/v1.1.2.tar.gz
COPY zsign-1.1.2.tar.gz /opt/zsign-1.1.2.tar.gz
RUN cd /opt/ && tar xvf zsign-1.1.2.tar.gz && cd zsign-1.1.2/ && g++ *.cpp common/*.cpp -lcrypto -O3 -std=c++11 -o zsign && cp zsign /usr/bin/
# install pip
COPY requirements.txt /opt/requirements.txt
RUN cd /opt/ && pip install -U setuptools pip -i ${PIP_MIRROR} --ignore-installed && pip install --no-cache-dir -r requirements.txt -i ${PIP_MIRROR} && pip install --no-cache-dir uwsgi -i ${PIP_MIRROR}
RUN rm -rf /var/cache/yum/
#COPY Docker/flyapps.conf /etc/supervisor/conf.d/flyapps.conf
#COPY Docker/uwsgi.conf /data/flyapps/fir_ser/uwsgi.conf
#COPY Docker/flyapps-vhost.conf /etc/nginx/conf.d/flyapps-vhost.conf
#COPY Docker/app.hehelucky.cn.pem /data/flyapps/app.hehelucky.cn.pem
#COPY Docker/app.hehelucky.cn.key /data/flyapps/app.hehelucky.cn.key
WORKDIR /data/fir_ser/
RUN addgroup --system --gid 101 nginx \
&& adduser --system --disabled-login --ingroup nginx --no-create-home --home /nonexistent --gecos "nginx user" --shell /bin/false --uid 101 nginx
#EXPOSE 443
#ENTRYPOINT ["./entrypoint.sh"]
#ENTRYPOINT ["/usr/bin/supervisord", "-c", "/etc/supervisor/supervisord.conf", "-n"]
CMD ["python", "manage.py", "start", "all","-u","nginx","-usm","1"]

@ -121,8 +121,6 @@ class BaseService(object):
# -- action --
def open_subprocess(self):
self.set_work_dir_owner()
if self.name in ['uwsgi']:
prepare()
kwargs = {'cwd': self.cwd, 'stderr': self.log_file, 'stdout': self.log_file}
self._process = subprocess.Popen(self.cmd, **kwargs)
@ -146,6 +144,9 @@ class BaseService(object):
for (dir_path, dir_names, filenames) in os.walk(LOG_DIR):
for filename in filenames + dir_names:
os.chown(uid=u_gid, gid=u_gid, path=os.path.join(dir_path, filename))
if self.name == 'uwsgi':
for dirs in ['files', 'supersign']:
os.chown(uid=u_gid, gid=u_gid, path=os.path.join(BASE_DIR, dirs))
else:
logging.error(f'uid: {self.uid} gid:{self.gid} is not exists')

@ -35,6 +35,9 @@ class ServicesUtil(object):
self.watch()
def start(self):
if 'uwsgi' in [service.name for service in self._services]:
prepare()
for service in self._services:
service: BaseService
service.start()

@ -113,7 +113,9 @@ def get_sender_token(sender, user_id, target, action, msg=None):
def get_sender_sms_token(key, phone, action, msg=None):
sender = SendMessage('sms')
return get_sender_token(sender, key, phone, action, msg)
if sender.sender:
return get_sender_token(sender, key, phone, action, msg)
return False, False
def is_valid_sender_code(key, token, code):
@ -122,7 +124,9 @@ def is_valid_sender_code(key, token, code):
def get_sender_email_token(key, email, action, msg=None):
sender = SendMessage('email')
return get_sender_token(sender, key, email, action, msg)
if sender.sender:
return get_sender_token(sender, key, email, action, msg)
return False, False
def check_username_exists(username):

@ -77,7 +77,11 @@ def check_register_userinfo(target, act, key, ftype=None):
res.msg = "手机号已经存在"
else:
token, code = get_sender_sms_token(act, target, 'register')
res.data["auth_token"] = token
if token:
res.data["auth_token"] = token
else:
res.code = 1009
res.msg = "短信服务异常,请联系管理员"
else:
res.code = 1009
res.msg = "该手机号今日使用次数已经达到上限"
@ -94,7 +98,11 @@ def check_register_userinfo(target, act, key, ftype=None):
res.msg = "邮箱已经存在"
else:
token, code = get_sender_email_token(act, target, 'register')
res.data["auth_token"] = token
if token:
res.data["auth_token"] = token
else:
res.code = 1009
res.msg = "邮件服务异常,请联系管理员"
else:
res.code = 1009
res.msg = "该邮箱今日注册次数已经达到上限"
@ -109,7 +117,11 @@ def check_register_userinfo(target, act, key, ftype=None):
res.msg = "用户名已经存在"
else:
token, code = get_sender_email_token(act, target, 'register')
res.data["auth_token"] = token
if token:
res.data["auth_token"] = token
else:
res.code = 1009
res.msg = "未知错误"
else:
res.code = 1009
res.msg = "用户名已经存在"
@ -139,7 +151,11 @@ def check_change_userinfo(target, act, key, user, ftype=None):
res.msg = "手机号已经存在"
else:
token, code = get_sender_sms_token(act, target, 'change')
res.data["auth_token"] = token
if token:
res.data["auth_token"] = token
else:
res.code = 1009
res.msg = "短信服务异常,请联系管理员"
else:
res.code = 1009
res.msg = "该手机号今日使用次数已经达到上限"
@ -156,7 +172,11 @@ def check_change_userinfo(target, act, key, user, ftype=None):
res.msg = "邮箱已经存在"
else:
token, code = get_sender_email_token(act, target, 'change')
res.data["auth_token"] = token
if token:
res.data["auth_token"] = token
else:
res.code = 1009
res.msg = "邮件服务异常,请联系管理员"
else:
res.code = 1009
res.msg = "该邮箱今日使用次数已经达到上限"

@ -59,24 +59,26 @@ class OrderView(APIView):
order_obj = Order.objects.filter(user_id=request.user, order_number=order_number).first()
if order_obj and order_obj.status in [1, 2] and order_obj.payment_name:
pay_obj = get_pay_obj_form_name(order_obj.payment_name)
pay_url = pay_obj.get_pay_pc_url(order_number, int(order_obj.actual_amount),
{'user_id': request.user.id})
res.data = pay_url
logger.info(f"{request.user} 下单成功 {res.dict}")
return Response(res.dict)
if pay_obj:
pay_url = pay_obj.get_pay_pc_url(order_number, int(order_obj.actual_amount),
{'user_id': request.user.id})
res.data = pay_url
logger.info(f"{request.user} 下单成功 {res.dict}")
return Response(res.dict)
if price_obj:
try:
order_number = get_order_num()
actual_amount = price_obj.price
pay_obj = get_pay_obj_form_name(pay_id)
pay_url = pay_obj.get_pay_pc_url(order_number, int(actual_amount), {'user_id': request.user.id})
Order.objects.create(payment_type=get_payment_type(pay_obj.p_type), order_number=order_number,
user_id=request.user, status=1, order_type=0, actual_amount=actual_amount,
actual_download_times=price_obj.package_size, payment_name=pay_obj.name,
actual_download_gift_times=price_obj.download_count_gift)
res.data = pay_url
logger.info(f"{request.user} 下单成功 {res.dict}")
return Response(res.dict)
if pay_obj:
pay_url = pay_obj.get_pay_pc_url(order_number, int(actual_amount), {'user_id': request.user.id})
Order.objects.create(payment_type=get_payment_type(pay_obj.p_type), order_number=order_number,
user_id=request.user, status=1, order_type=0, actual_amount=actual_amount,
actual_download_times=price_obj.package_size, payment_name=pay_obj.name,
actual_download_gift_times=price_obj.download_count_gift)
res.data = pay_url
logger.info(f"{request.user} 下单成功 {res.dict}")
return Response(res.dict)
except Exception as e:
logger.error(f"{request.user} 订单 {price_id} 保存失败 Exception:{e}")
res.code = 1003

@ -37,7 +37,6 @@ class BASECONF(object):
'is_https': True if API_DOMAIN.split("://")[0] == "https" else False,
}, # 验证码,ios 描述文件和plist文件下载域名,该域名用于后端,一般为api访问域名
'POST_UDID_DOMAIN': API_DOMAIN, # 超级签名 安装签名时 向该域名 发送udid数据,该域名用于后端,一般为 api 访问域名
# 'REDIRECT_UDID_DOMAIN': 'https://app.hehelucky.cn', # 超级签名 安装完成之后,跳转域名,该域名为前端web访问域名,如果用户定义了自己的域名,则跳转用户域名
'FILE_UPLOAD_DOMAIN': API_DOMAIN, # 本地文件上传域名,使用本地存储必须配置
}

@ -334,7 +334,6 @@ LOGGING = {
},
}
PAY_SUCCESS_URL = PAYCONF.PAY_SUCCESS_URL
PAY_CONFIG_KEY_INFO = PAYCONF.PAY_CONFIG_KEY_INFO
# 结果存放到Django|redis

@ -1,25 +0,0 @@
#!/bin/bash
#
source /www/flyapps/py3/bin/activate && cd /www/flyapps/fir_ser/
chown www.www -R /www/flyapps/fir_ser/
stop(){
pgrep -f uwsgi |xargs -i kill {}
sleep 1
pgrep -f celery |xargs -i kill {}
}
start(){
uwsgi --ini uwsgi.conf
sleep 1
celery multi start 4 -A fir_ser -l INFO -c4 --pidfile=/var/run/celery/%n.pid --logfile=logs/%p.log
sleep 1
nohup celery -A fir_ser beat --uid=1000 --pidfile=logs/beat.pid --scheduler django -l INFO --logfile=logs/beat.log &
}
restart(){
stop
sleep 1
start
}
$@

Binary file not shown.

@ -8,14 +8,14 @@ server
listen 443 ssl http2;
server_name app.hehelucky.cn;
index index.html index.htm default.htm default.html;
root /data/flyapps/fir_client;
root /data/fir_client;
if ($server_port !~ 443){
rewrite ^(/.*)$ https://$host$1 permanent;
}
ssl_certificate /data/flyapps/app.hehelucky.cn.pem;
ssl_certificate_key /data/flyapps/app.hehelucky.cn.key;
ssl_certificate /etc/nginx/conf.d/app.hehelucky.cn.pem;
ssl_certificate_key /etc/nginx/conf.d/app.hehelucky.cn.key;
ssl_protocols TLSv1.1 TLSv1.2 TLSv1.3;
ssl_ciphers ECDHE-RSA-AES128-GCM-SHA256:HIGH:!aNULL:!MD5:!RC4:!DHE;
ssl_prefer_server_ciphers on;
@ -29,15 +29,15 @@ server
# rewrite ^/download/(.*) /files/$1 break;
# }
# 如果使用cdn,需要配置该选项
set_real_ip_from 0.0.0.0/0;
real_ip_header X-Forwarded-For;
#set_real_ip_from 0.0.0.0/0;
#real_ip_header X-Forwarded-For;
location ~ ^/(download|api|files|udid|captcha) {
location ~ ^/(download|api|files|udid|captcha|show_udid|flower) {
uwsgi_send_timeout 300; # 指定向uWSGI传送请求的超时时间,完成握手后向uWSGI传送请求的超时时间。
uwsgi_connect_timeout 300; # 指定连接到后端uWSGI的超时时间。
uwsgi_read_timeout 300; # 指定接收uWSGI应答的超时时间,完成握手后接收uWSGI应答的超时时间。
include uwsgi_params;
uwsgi_pass 127.0.0.1:8899;
uwsgi_pass flyapps:8898;
uwsgi_param UWSGI_SCRIPT wsgi;
}
@ -71,6 +71,4 @@ server
error_log off;
access_log /dev/null;
}
access_log /data/logs/flyapps.access.log;
error_log /data/logs/flyapps.error.log;
}

@ -0,0 +1,41 @@
#!/bin/bash
#
#
# shellcheck disable=SC2006
s_path=`pwd`
docker network create flyapps
docker run --net flyapps --name redis -d redis:6.2.5 redis-server --requirepass nineven --bind '0.0.0.0'
docker run --net flyapps --name mariadb -e MARIADB_ROOT_PASSWORD=root -v "${s_path}"/data/mysql:/var/lib/mysql -d mariadb:10.5
sleep 3
code=1
count=1
while [ ${code} -ne 0 ];do
docker exec -it mariadb mysql -proot -e 'show databases;'
code=$?
((count+=1))
if [ "$count" -gt 30 ];then
echo "30s away, but mysql service is not available"
exit 1
fi
sleep 2
echo "check whether mysql service is ready..."
done
docker exec -it mariadb mysql -proot -e 'create database flyapp default character set utf8 COLLATE utf8_general_ci;'
docker exec -it mariadb mysql -proot -e "grant all on flyapp.* to flyuser@'%' identified by 'KGzKjZpWBp4R4RSa';"
docker run --sysctl net.core.somaxconn=4096 --net flyapps \
-v "${s_path}"/fir_ser:/data/fir_ser \
-v "${s_path}"/data/files:/data/fir_ser/files \
-v "${s_path}"/data/supersign:/data/fir_ser/supersign \
--name flyapps -d flyapps
docker run --net flyapps --name nginx -d -p 80:80 -p 443:443 \
-v "${s_path}"/fir_client/dist:/data/fir_client \
-v "${s_path}"/nginx.conf.d:/etc/nginx/conf.d nginx:1.21.3
Loading…
Cancel
Save