系统环境

  • 系统版本:CentOS-7-x86_64-Minimal-1908
  • 内核版本:3.10.0-1062.el7.x86_64 #1 SMP Wed Aug 7 18:08:02 UTC 2019 x86_64 x86_64 x86_64 GNU/Linux
  • Tengine 版本:2.2.1

脚本内容

该脚本是本人 2017 年服务厦门紫京阁网络科技有限公司的一个最外层 tengine 代理安装脚本,脚本具体内容如下:

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
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
#!/usr/bin/env bash

set -e

# 软件包下载地址
SRC='/usr/local/src'

# 安装扩展源
[ -z "$(rpm -qa epel-release)" ] && yum install -y epel-release

# 安装必要的工具包
yum install -y readline-devel lua-devel openssl-devel geoip-devel gperftools-devel libatomic_ops-devel jemalloc-devel libmaxminddb-devel libxslt-devel gd-devel lrzsz wget git

#LUA='http://www.lua.org/ftp/lua-5.3.4.tar.gz'
#LUA_VERSION="$(echo ${LUA##*/} |sed -e 's/.tar.gz//')"
#[ ! -f "${SRC}/${LUA_VERSION}.tar.gz" ] && wget -O ${SRC}/${LUA_VERSION}.tar.gz ${LUA}
#[ ! -d "${SRC}/${LUA_VERSION}" ] && tar zxf ${SRC}/${LUA_VERSION}.tar.gz -C ${SRC}/
#cd ${SRC}/${LUA_VERSION} && make linux test


#下载解压 pcre
PCRE='https://ftp.pcre.org/pub/pcre/pcre-8.37.tar.gz'
PCRE_VERSION="$(echo ${PCRE##*/} |sed -e 's/.tar.gz//')"
[ ! -f "${SRC}/${PCRE_VERSION}.tar.gz" ] && wget -O ${SRC}/${PCRE_VERSION}.tar.gz $PCRE
[ ! -d "${SRC}/${PCRE_VERSION}" ] && tar zxf ${SRC}/${PCRE_VERSION}.tar.gz -C ${SRC}/

#下载加压zlib
#ZLIB='http://www.zlib.net/zlib-1.2.11.tar.gz'
#ZLIB_VERSION="$(echo ${ZLIB##*/} |sed -e 's/.tar.gz//')"
#[ ! -f "${SRC}/${ZLIB_VERSION}.tar.gz" ] && wget -O ${SRC}/${ZLIB_VERSION}.tar.gz $ZLIB
#[ ! -d "${SRC}/${ZLIB_VERSION}" ] && tar zxf ${SRC}/${ZLIB_VERSION}.tar.gz -C ${SRC}/

#GEOIP2 所支持的数据文件http://geolite.maxmind.com/download/geoip/database/GeoLite2-Country.tar.gz
#[ ! -f "${SRC}/GeoLite2-Country.tar.gz" ] && wget -O ${SRC}/GeoLite2-Country.tar.gz http://geolite.maxmind.com/download/geoip/database/GeoLite2-Country.tar.gz
[ ! -f "${SRC}/GeoLite2-Country.mmdb.gz" ] && wget -O ${SRC}/GeoLite2-Country.mmdb.gz http://geolite.maxmind.com/download/geoip/database/GeoLite2-Country.mmdb.gz
#[ ! -f "${SRC}/GeoLite2-City.tar.gz" ] && wget -O ${SRC}/GeoLite2-City.tar.gz http://geolite.maxmind.com/download/geoip/database/GeoLite2-City.tar.gz
[ ! -f "${SRC}/GeoLite2-City.mmdb.gz" ] && wget -O ${SRC}/GeoLite2-City.mmdb.gz http://geolite.maxmind.com/download/geoip/database/GeoLite2-City.mmdb.gz

#解压数据文件
[ ! -f "${SRC}/GeoLite2-Country.mmdb" ] && gunzip -q ${SRC}/GeoLite2-Country.mmdb.gz -d ${SRC}/ && echo $?
[ ! -f "${SRC}/GeoLite2-City.mmdb" ] && gunzip -q ${SRC}/GeoLite2-City.mmdb.gz -d ${SRC}/ && echo $?

# [ ! -d "/usr/local/GeoLite2" ] && mkdir -p /usr/local/GeoLite2
# mv ${SRC}/GeoLite2-C* /usr/local/GeoLite2/

# 从github 上下载geoip2 模块和 cache_purge 模块
[ ! -d "${SRC}/ngx_http_geoip2_module" ] && git clone https://github.com/leev/ngx_http_geoip2_module ${SRC}/ngx_http_geoip2_module
[ ! -d "${SRC}/ngx_cache_purge" ] && git clone https://github.com/FRiCKLE/ngx_cache_purge.git ${SRC}/ngx_cache_purge

# 下载安装tengine
TENGINE='http://tengine.taobao.org/download/tengine-2.2.1.tar.gz'
TENGINE_VERSION="$(echo ${TENGINE##*/} |sed -e 's/.tar.gz//')"
[ ! -f "${SRC}/${TENGINE_VERSION}.tar.gz" ] && wget -O ${SRC}/${TENGINE_VERSION}.tar.gz ${TENGINE}
[ ! -d "${SRC}/${TENGINE_VERSION}" ] && tar zxf ${SRC}/${TENGINE_VERSION}.tar.gz -C ${SRC}

cd ${SRC}/${TENGINE_VERSION}

./configure --prefix=/usr/local/nginx --user=nginx --group=nginx --enable-mods-shared=all --with-rtsig_module --with-select_module --with-force-exit --with-http_v2_module --with-http_realip_module --with-http_addition_module --with-http_xslt_module --with-http_dav_module --with-http_gunzip_module --with-http_gzip_static_module --with-http_auth_request_module --with-http_degradation_module --with-google_perftools_module --with-libatomic --with-jemalloc --add-module=${SRC}/ngx_http_geoip2_module --add-module=${SRC}/ngx_cache_purge

make -j $(awk '/processor/{i++}END{print i}' /proc/cpuinfo) && make install

# 添加nginx 用户
[ -z "$(egrep nginx /etc/passwd)" ] && useradd -s /sbin/nologin nginx

# 将 nginx 加入到系统命令下:
ln -sf /usr/local/nginx/sbin/nginx /usr/bin/

# 重新配置tengine
cat << 'eof' > /usr/local/nginx/conf/nginx.conf
user nginx nginx;

worker_processes auto;
worker_cpu_affinity auto;

error_log logs/error.log info;
pid logs/nginx.pid;
google_perftools_profiles /var/tmp/tcmalloc;

worker_rlimit_nofile 65535;

dso {
load ngx_http_rewrite_module.so;
load ngx_http_access_module.so;
load ngx_http_concat_module.so;
load ngx_http_limit_conn_module.so;
load ngx_http_limit_req_module.so;
load ngx_http_sysguard_module.so;
load ngx_http_upstream_session_sticky_module.so;
load ngx_http_autoindex_module.so;
load ngx_http_charset_filter_module.so;
load ngx_http_trim_filter_module.so;
load ngx_http_fastcgi_module.so;
load ngx_http_sub_filter_module.so;
}

events {
use epoll;
worker_connections 10240;
}

http {
server_tokens off;
server_tag off;
include mime.types;
default_type application/octet-stream;

autoindex off;
charset utf-8;
sendfile on;
tcp_nopush on;
keepalive_timeout 60;
tcp_nodelay on;

#日志格式配置
log_format main '$remote_addr - $remote_user [$time_local] "$request_method $scheme://$host$request_uri $server_protocol" '
'"$upstream_addr" "$upstream_cache_status"'
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for" $request_time $upstream_response_time $geoip2_data_city_names $geoip2_data_country_code';

#访问日志:
access_log /usr/local/nginx/logs/access.log main;

limit_req_zone $binary_remote_addr zone=perip:10m rate=10r/s;
limit_req_status 444;
limit_conn_zone $binary_remote_addr zone=addr:5m;
#limit_conn addr 20;

server_names_hash_bucket_size 128;
client_header_buffer_size 32k;
large_client_header_buffers 4 32k;
client_max_body_size 10m;
client_body_buffer_size 256k;

gzip on;
gzip_min_length 1k;
gzip_buffers 4 16k;
gzip_comp_level 2;
gzip_http_version 1.1;
gzip_types text/plain application/x-javascript text/css application/xml image/gif image/jpeg image/png;
gzip_proxied any;
gzip_vary on;
gzip_disable "MSIE [1-6].";

proxy_connect_timeout 300s;
proxy_read_timeout 300s;
proxy_send_timeout 300s;
proxy_buffer_size 128k;
proxy_buffers 4 128k;
proxy_busy_buffers_size 256k;
proxy_temp_file_write_size 256k;
proxy_headers_hash_max_size 1024;
proxy_headers_hash_bucket_size 128;

proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;

proxy_temp_path /dev/shm/temp;
proxy_cache_path /dev/shm/cache levels=1:2 keys_zone=cache_one:2048m inactive=30m max_size=60g;


#GEOIP2 国家:
geoip2 /usr/local/src/GeoLite2-Country.mmdb {
$geoip2_data_continent_code default=AS continent code;
$geoip2_data_continent_names continent names en;
$geoip2_data_country_code default=CN country iso_code;
$geoip2_data_country_name country names en;
}
fastcgi_param CONTINENT_CODE $geoip2_data_continent_code;
fastcgi_param CONTINENT_NAMES $geoip2_data_continent_names;
fastcgi_param COUNTRY_CODE $geoip2_data_country_code;
fastcgi_param COUNTRY_NAME $geoip2_data_country_name;

#GEOIP2 城市:
geoip2 /usr/local/src/GeoLite2-City.mmdb {
$geoip2_data_subdivisions_names subdivisions names en;
$geoip2_data_city_names default=Xiamen city names en;
}
fastcgi_param SUBDIVISIONS_NAMES $geoip2_data_subdivisions_names;
fastcgi_param CITY_NAMES $geoip2_data_city_names;

include /usr/local/nginx/conf.d/*.conf;
}
eof

#创建目录:
mkdir -p /usr/local/nginx/conf.d

# 创建反向代理配置
cat << 'eof' > /usr/local/nginx/conf.d/default.conf
upstream tomcat-game {
server 52.128.239.226:6834 max_fails=1 fail_timeout=10s weight=1;
server 182.16.45.90:6834 max_fails=1 fail_timeout=10s weight=1;

#ip_hash;
#session_sticky;
check interval=3000 rise=2 fall=5 timeout=1000 type=http;
check_http_send "GET / HTTP/1.0\r\n\r\n";
check_http_expect_alive http_2xx http_3xx;
}

server {
listen 80 default;
server_name _;

access_log /usr/local/nginx/logs/access.log main;

if ( $host ~* "\d+\.\d+\.\d+\.\d+" ) {
return 444;
}

if ($host ~ "^(a|b|d|x)[0-9]{1,6}.xinboht.com"){
return 444;
}

if ($http_user_agent ~* "ab|wget|MJ12bot|qihoobot|Baiduspider|Googlebot|Googlebot-Mobile|YandexBot|Googlebot-Image|Mediapartners-Google|Adsbot-Google|Feedfetcher-Google|Yahoo! Slurp|Yahoo! Slurp China|YoudaoBot|Sosospider|Sogou spider|Sogou web spider|MSNBot|ia_archiver|Tomato Bot") {
return 403;
}

if ($request_method !~ (POST|GET)) {
return 444;
}
location / {
#trim on;
#trim_js on;
#trim_css on;
#下面这项配置不要忘记,否则用https 代理后端tomcat 会出现静态文件(样式)显示问题
#proxy_set_header X-Forwarded-Proto $scheme;
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
#proxy_set_header X-Forwarded-For $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
#proxy_set_header X-Forwarded-Proto $scheme;
proxy_pass http://tomcat-game;

#单个IP同一时间内的请求限制;zone=perip:对应上面配置的zone;burst=5:允许超过频率限制的请求数不多于5个;
#nodelay 不等待客户端响应(不进入响应队列),直接返回错误状态
limit_req zone=perip burst=5 nodelay;
proxy_next_upstream http_500 http_502 http_503 http_504 error timeout invalid_header;
}

#缓存设置
location ~ .*\.(htm|html|css|gif|jpg|jpeg|png|bmp|ico|swf|flv)$ {
proxy_next_upstream http_500 http_502 http_503 http_504 error timeout invalid_header;
proxy_cache cache_one;
proxy_cache_valid 200 304 15m;
proxy_cache_valid 301 302 10m;
proxy_cache_valid any 1m;
proxy_cache_key $host$uri$is_args$args;
add_header Ten-webcache '$upstream_cache_status from $host';
if ( !-e $request_filename ) {
proxy_pass http://tomcat-game;
}
#expires 30m;
}

error_page 404 500 502 503 504 /50x.html;
location = /50x.html {
root html;
}

}
eof

cat << eof > /usr/local/nginx/html/50x.html
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Error</title>
</head>
<body style="text-align: center;color: red;line-height: center;">

<h1>If you see this page, mains the server network problems, please contact our customer service staff!</h1>
</body>
</html>
eof

#防止time_wait 过高
echo 'net.ipv4.tcp_tw_reuse = 1' >> /etc/sysctl.conf
echo 'net.ipv4.tcp_fin_timeout = 30' >> /etc/sysctl.conf
echo 'net.ipv4.tcp_tw_recycle = 1' >> /etc/sysctl.conf
echo 'net.ipv4.tcp_syncookies = 1' >> /etc/sysctl.conf

sysctl -p


#创建Tengine 的启动脚本:
echo '[Unit]' > /usr/lib/systemd/system/nginx.service
echo ' ' >> /usr/lib/systemd/system/nginx.service
echo 'Description=Nginx' >> /usr/lib/systemd/system/nginx.service
echo 'After=syslog.target network.target' >> /usr/lib/systemd/system/nginx.service
echo ' ' >> /usr/lib/systemd/system/nginx.service
echo '[Service]' >> /usr/lib/systemd/system/nginx.service
echo 'Type=forking' >> /usr/lib/systemd/system/nginx.service
echo 'ExecStart=/usr/local/nginx/sbin/nginx' >> /usr/lib/systemd/system/nginx.service
echo 'ExecReload=/usr/local/nginx/sbin/nginx -s reload' >> /usr/lib/systemd/system/nginx.service
echo 'ExecStop=/usr/local/nginx/sbin/nginx -s quit' >> /usr/lib/systemd/system/nginx.service
echo ' ' >> /usr/lib/systemd/system/nginx.service
echo '[Install]' >> /usr/lib/systemd/system/nginx.service
echo 'WantedBy=multi-user.target' >> /usr/lib/systemd/system/nginx.service

#启动Tengine
systemctl start nginx && systemctl enable nginx

#NGINX 日志切割:
cat << 'eof' > /etc/logrotate.d/nginx
#日志文件,可以是一组 ,用空格隔开
/usr/local/nginx/logs/*.log {
#daily:日志文件将按天轮循。其它可用值为‘weekly’,‘monthly’或者‘yearly’
daily
#一次将存储15个归档日志。对于第16个归档,时间最久的归档将被删除
rotate 15
#在日志轮循期间,任何错误将被忽略,例如“文件无法找到”之类的错误。
missingok
#如果日志文件为空,轮循不会进行。
notifempty
#使用日期作为命名格式
dateext
#在轮循任务完成后,已轮循的归档将使用gzip进行压缩。
compress
#总是与compress选项一起用,delaycompress选项指示logrotate不要将最近的归档压缩,压缩将在下一次轮循周期进行。
#这在你或任何软件仍然需要读取最新归档时很有用
delaycompress
#指定的权限创建全新的日志文件,同时logrotate也会重命名原始日志文件
create 600 nginx nginx
#只为整个日志组运行一次的脚本
sharedscripts
#在截断转储以后需要执行的命令
postrotate
if [ -f /usr/local/nginx/logs/nginx.pid ]; then
kill -USR1 `cat /usr/local/nginx/logs/nginx.pid`
fi
endscript
}
eof

logrotate -f -d -v /etc/logrotate.conf

#开启防火墙的80 端口:
firewall-cmd --add-service={http,https} --permanent --zone=public && firewall-cmd --reload

#删除脚本自身:
rm -rf $0