快速创建TLS证书并部署到Docker服务

将下方代码保存为certbot.sh,修改头部变量后,上传到装有openssl组件的linux服务器上运行即可。

#!/bin/sh
#

export PASSWORD="密码"

export COUNTRY="CN"
export STATE="省"
export CITY="市"
export ORGANIZATION="公司名称"
export ORGANIZATIONAL_UNIT="Dev"
export COMMON_NAME="域名"
export EMAIL="电子邮件地址"

export HOST_NAME="$COMMON_NAME"
export IP=`ping $HOST_NAME -c 1 | sed '1{s/[^(]*(//;s/).*//;q}'`

export DIR="cert-$HOST_NAME"

# Workspace

[ -d $DIR ] || mkdir -p $DIR

echo "PASSWORD: $PASSWORD" > $DIR/!nfo.txt
echo "HOST_NAME: $HOST_NAME" >> $DIR/!nfo.txt
echo "HOST_IP: $IP" >> $DIR/!nfo.txt

# Generate CA

openssl genrsa -aes256 -passout "pass:$PASSWORD" -out "$DIR/ca-key.pem" 4096

openssl req -new -x509 -days 3650 -key "$DIR/ca-key.pem" -sha256 -out "$DIR/ca.pem" -passin "pass:$PASSWORD" -subj "/C=$COUNTRY/ST=$STATE/L=$CITY/O=$ORGANIZATION/OU=$ORGANIZATIONAL_UNIT/CN=$COMMON_NAME/emailAddress=$EMAIL"

# Generate Server Certs

openssl genrsa -out "$DIR/server-key.pem" 4096

openssl req -subj "/CN=$HOST_NAME" -sha256 -new -key "$DIR/server-key.pem" -out $DIR/server.csr

echo "subjectAltName = DNS:$HOST_NAME,IP:$IP,IP:127.0.0.1" > $DIR/server.cnf
echo "extendedKeyUsage = serverAuth" >> $DIR/server.cnf

openssl x509 -req -days 3650 -sha256 -in $DIR/server.csr -passin "pass:$PASSWORD" -CA "$DIR/ca.pem" -CAkey "$DIR/ca-key.pem" -CAcreateserial -out "$DIR/server-cert.pem" -extfile $DIR/server.cnf

# Generate Client Certs

openssl genrsa -out "$DIR/client-key.pem" 4096

openssl req -subj '/CN=client' -new -key "$DIR/client-key.pem" -out $DIR/client.csr

echo "extendedKeyUsage = clientAuth" > $DIR/client.cnf

openssl x509 -req -days 3650 -sha256 -in $DIR/client.csr -passin "pass:$PASSWORD" -CA "$DIR/ca.pem" -CAkey "$DIR/ca-key.pem" -CAcreateserial -out "$DIR/client-cert.pem" -extfile $DIR/client.cnf

# Modify Certs Permission

chmod 0400 $DIR/*-key.pem
chmod 0444 $DIR/ca.pem $DIR/*-cert.pem

# Remove Temporary Files

rm -f $DIR/*.csr $DIR/*.cnf

如果需要部署到Docker服务,请继续

# Install To Docker Daemon

mkdir -p /etc/docker/certs.d
cp $DIR/ca.pem /etc/docker/certs.d/
cp $DIR/server-*.pem /etc/docker/certs.d/

cat <<EOF >/etc/docker/daemon.json
{
    "tlsverify": true,
    "tlscacert": "/etc/docker/certs.d/ca.pem",
    "tlscert": "/etc/docker/certs.d/server-cert.pem",
    "tlskey": "/etc/docker/certs.d/server-key.pem",
    "hosts": ["tcp://0.0.0.0:2376", "unix:///var/run/docker.sock"]
}
EOF

# Modify Systemd Service

if [ -f /lib/systemd/system/docker.service ]; then
    sed -i '/"hosts"/d' /etc/docker/daemon.json
    sed -i 's#server-key.pem",#server-key.pem"#' /etc/docker/daemon.json
    sed -i 's#-H fd://#-H fd:// -H tcp://0.0.0.0:2376#' /lib/systemd/system/docker.service
    systemctl daemon-reload
fi

特别注意

在systemd系统上-H已设置,因此无法使用hosts键来添加侦听地址,请参阅 https://docs.docker.com/install/linux/linux-postinstall/#configuring-remote-access-with-systemd-unit-file

Debian9/10 启用 Google BBR 加速

一、加载BBR内核模块

lsmod | grep bbr

如果回显tcp_bbr 20480 14则表示已加载,否则请使用如下命令加载BBR内核模块

modprobe tcp_bbr
echo "tcp_bbr" | tee -a /etc/modules-load.d/modules.conf

二、启用BBR网络优化

sysctl net.ipv4.tcp_available_congestion_control

如果回显net.ipv4.tcp_available_congestion_control = bbr cubic reno则表示已启用优化,否则请使用如下命令启用BBR网络优化

echo "net.core.default_qdisc=fq" >> /etc/sysctl.conf
echo "net.ipv4.tcp_congestion_control=bbr" >> /etc/sysctl.conf
sysctl -p

Ubuntu下刷极路由不死uboot

今天帮朋友刷2个极路由的uboot,但他那边只有一台Ubuntu-Server可远程登陆。
悲剧的我,只好SSH连接他本地的Ubuntu,然后再连接极路由刷写固件:

极路由1s

wget https://breed.hackpascal.net/breed-mt7620-hiwifi-hc5761.bin

scp -P 1022 root@192.168.199.1:/tmp/
ssh -p 1022 root@192.168.199.1

输入密码,登陆系统后,执行刷写命令

mtd write /tmp/breed-mt7620-hiwifi-mt7620.bin u-boot

极路由3

wget https://breed.hackpascal.net/breed-mt7620-hiwifi-hc5861.bin

scp -P 1022 root@192.168.199.1:/tmp/
ssh -p 1022 root@192.168.199.1

输入密码,登陆系统后,执行刷写命令

mtd write /tmp/breed-mt7620-hiwifi-hc5861.bin u-boot

Ubuntu安装Docker/Redmine/GitLab教程

兴趣所致,使用Docker部署下Redmine和GitLab,体验下Docker的魅力。

一、安装Docker

二、安装Redmie

地址 http://172.20.1.15
账号 admin
密码 admin

三、安装Gitlab

地址 http://172.20.1.16
账号 root
密码 5iveL!fe

集成安装脚本

PS1:安全起见,以下绑定的地址均为本地IP,无法对外提供服务,如需部署到服务器请酌情修改。
PS2:也可以安装 rinetd 软件包,实现任意端口转发。

请下载下面的集成安装脚本,修改password和email参数后,一键安装Redmine/GitLab吧~

#!/bin/bash
#
# Author  Anrip <mail@anrip.com>
# Website http://www.anrip.com/post/1811
# Refs https://github.com/sameersbn/docker-gitlab
# Refs https://github.com/sameersbn/docker-redmine
#

if [ ! `which docker` ]; then
    wget -qO- https://get.docker.com/ | sh
fi

docker network create --subnet=172.20.1.0/24 docker1

docker pull sameersbn/redis:latest
docker pull sameersbn/mysql:latest
docker pull sameersbn/gitlab:latest
docker pull sameersbn/redmine:latest

docker run --name app-redis -d \
    --net docker1 --ip 172.20.1.11 \
    --volume /srv/app-redis:/var/lib/redis \
    sameersbn/redis:latest

docker run --name app-mysql -d \
    --net docker1 --ip 172.20.1.12 \
    --env 'MYSQL_CHARSET=utf8' \
    --env 'MYSQL_COLLATION=utf8_general_ci' \
    --env 'DB_REMOTE_ROOT_NAME=root' \
    --env 'DB_REMOTE_ROOT_PASS=password' \
    --volume /srv/app-mysql:/var/lib/mysql \
    sameersbn/mysql:latest

MYSQL_CHARSET="DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci"
cat > /opt/app-mysql/init.sql <<EOF
    CREATE USER 'gitlab'@'%.%.%.%' IDENTIFIED BY 'password';
    CREATE DATABASE IF NOT EXISTS gitlabhq_production ${MYSQL_CHARSET};
    GRANT ALL PRIVILEGES ON \`gitlabhq_production\`.* TO 'gitlab'@'%.%.%.%';
    CREATE USER 'redmine'@'%.%.%.%' IDENTIFIED BY 'password';
    CREATE DATABASE IF NOT EXISTS redmine_production ${MYSQL_CHARSET};
    GRANT ALL PRIVILEGES ON \`redmine_production\`.* TO 'redmine'@'%.%.%.%';
EOF

sleep 30
docker exec -it app-mysql mysql "-e source /var/lib/mysql/init.sql"
rm -rf /opt/app-mysql/init.sql

docker run --name app-redmine -d \
    --net docker1 --ip 172.20.1.15 \
    --env 'REDMINE_PORT=80' \
    --env 'REDMINE_RELATIVE_URL_ROOT=/redmine' \
    --env 'SMTP_DOMAIN=anrip.com' \
    --env 'SMTP_HOST=smtp.exmail.qq.com' \
    --env 'SMTP_PORT=587' \
    --env 'SMTP_USER=team@anrip.com' \
    --env 'SMTP_PASS=anrip.2010' \
    --env='DB_ADAPTER=mysql2' \
    --env 'DB_HOST=172.20.1.12' \
    --env='DB_NAME=redmine_production' \
    --env 'DB_USER=redmine' \
    --env 'DB_PASS=password' \
    --volume /opt/app-redmine:/home/redmine/data \
    sameersbn/redmine:latest

docker run --name app-gitlab -d \
    --net docker1 --ip 172.20.1.16 \
    --env 'GITLAB_SSH_PORT=22' \
    --env 'GITLAB_PORT=80' \
    --env 'GITLAB_HOST=team.vmlu.com' \
    --env 'GITLAB_RELATIVE_URL_ROOT=/gitlab' \
    --env 'GITLAB_EMAIL=team@anrip.com' \
    --env 'GITLAB_EMAIL_DISPLAY_NAME=Vmlu Team' \
    --env 'GITLAB_SECRETS_DB_KEY_BASE=your-db-key-base' \
    --env 'GITLAB_SECRETS_SECRET_KEY_BASE=your-secert-key-base' \
    --env 'GITLAB_SECRETS_OTP_KEY_BASE=your-opt-key-base' \
    --env 'GITLAB_USERNAME_CHANGE=false' \
    --env 'UNICORN_TIMEOUT=120' \
    --env 'SMTP_DOMAIN=anrip.com' \
    --env 'SMTP_HOST=smtp.exmail.qq.com' \
    --env 'SMTP_PORT=587' \
    --env 'SMTP_USER=your@anrip.com' \
    --env 'SMTP_PASS=your-mail-pasowrd' \
    --env 'REDIS_HOST=172.20.1.11' \
    --env 'REDIS_PORT=6379' \
    --env 'DB_ADAPTER=mysql2' \
    --env 'DB_HOST=172.20.1.12' \
    --env 'DB_NAME=gitlabhq_production' \
    --env 'DB_USER=gitlab' \
    --env 'DB_PASS=password' \
    --volume /opt/app-gitlab:/home/git/data \
    sameersbn/gitlab:latest

#sudo aptitude install -y rinetd
#sudo echo "12.34.56.78 22 172.20.1.16 22" >>/etc/rinetd.conf

Ubuntu/Linux 配置 Vlan

很久以前配置过,后来都是基于管理交换机配置;今天被逼无奈,又一次必须使用,怎么也弄不好,原来配置方式变了,郁闷!!

#开启内核支持
modprobe 8021q
echo "8021q" >>/etc/modules

#安装配置工具
aptitude install vlan

#增加虚拟接口
vconfig add eth1 30

以下内容添加到 /etc/network/interfaces

auto eth1

auto eth1.30
iface eth1.30 inet static
    address 10.20.30.19
    netmask 255.255.255.0
    network 10.20.30.0
    broadcast 10.20.30.255

Linux磁盘莫名其妙占满(No space left on device)

今天朋友跟我讲:好奇怪的现象,磁盘明明没有满,使用 df -h 查看,显示剩余80G,但是却无法创建或者写入文件,总提示 No space left on device

其实出现磁盘空间不足的提示,有两种原因,一种是我们通常认为的空间不足了,另外就是inode用完了。此时可以使用 df -li 命令看下,是不是inode使用过多造成的。

如果是由于inode占满造成,那怎么解决呢,最简单的:增加inode数量。但是可能你会不放心,因为inode被占满很可能是存在什么隐患的。。。

好吧,我们用下面的命令来看下一个目录中的文件总数好了,不过,你需要一个目录一个目录的耐心找下去喽!

#查看某文件夹下文件的个数,包括子文件夹
ls -lR | grep "^-" | wc -l
#查看某文件夹下文件夹的个数,包括子文件夹
ls -lR | grep "^d" | wc -l

找到后怎么办,不用我说了吧?

使用ab进行压力测试遇到”Connection reset by peer”

Nginx作为前端服务器,当使用 ab 进行压力测试的时候遇到
apr_socket_recv: Connection reset by peer

由于linux内核已经是3.x,基本网上各种方法已经不再适用,现给出2.6.x以上内核的解决方案

#按需加载内核模块
modprobe nf_conntrack_ipv4
modprobe nf_conntrack_ipv6

#按需修改网络参数
sysctl net.nf_conntrack_max=655360
sysctl net.netfilter.nf_conntrack_tcp_timeout_established=1200

注:
1、重启后网络参数会还原,若需永久保存该参数请使用: sysctl -w
2、Debian/Ubuntu下单独安装ab测试工具: apt install apache2-utils

查看Web服务器并发请求连接数

查看服务器TCP连接状态

netstat -n | awk '/^tcp/ {++S[$NF]} END {for(k in S) print k,S[k]}'

得到的结果一般如下:
ESTABLISHED 1597 正常数据传输状态
TIME_WAIT 1057 等待超时结束的请求数

附一、netstat常见参数

-a (all)显示所有选项,默认不显示LISTEN相关
-t (tcp)仅显示tcp相关选项
-u (udp)仅显示udp相关选项
-n 拒绝显示别名,能显示数字的全部转化成数字。
-l 仅列出有在 Listen (监听) 的服務状态
-p 显示建立相关链接的程序名
-r 显示路由信息,路由表
-e 显示扩展信息,例如uid等
-s 按各个协议进行统计
-c 每隔一个固定时间,执行该netstat命令。

附二、awk常用内置变量

ARGC 命令行参数个数
ARGV 命令行参数排列
ENVIRON 支持队列中系统环境变量的使用
FILENAME 浏览的文件名
FNR 浏览文件的记录数
FS 设置输入域分隔符,等价于命令行 -F选项
NF 浏览记录的域的个数
NR 已读的记录数
OFS 输出域分隔符
ORS 输出记录分隔符
RS 控制记录分隔符

附三、TCP状态转换图

TCP状态转换图

CLOSED 无连接是活动的或正在进行
LISTEN 服务器在等待进入呼叫
SYN_RECV 一个连接请求已经到达,等待确认
SYN_SENT 应用已经开始,打开一个连接
ESTABLISHED 正常数据传输状态
FIN_WAIT1 应用说它已经完成
FIN_WAIT2 另一边已同意释放
ITMED_WAIT 等待所有分组死掉
CLOSING 两边同时尝试关闭
TIME_WAIT 另一边已初始化一个释放
LAST_ACK 等待所有分组死掉

Linux中的$符号 — 读取命令行参数

在Ubuntu中一些经常使用的参数操作方法,脚本环境为 sh / bash

#最后一个守护进程pid
echo " last daemon process id : $! "

#exit退出状态
echo " exit status : $? "

#当前脚本进程
echo " process id of this script : $$ "

#脚本名
echo " script name : `basename $0` "

#第一个参数
echo " first param : $1 "

#所有参数
echo " all params : $* "

#所有参数
echo " all params : '$@' "

#参数长度
echo " params length : $# "

以下一些扩展方法,需要 bash 环境


#倒数第一个参数
#或 ${$#}, 但由于大括号中不能嵌套$符号, 要用!代替
echo " last param : ${!#} "
echo " last param : ${@:${#@}} "

#倒数第二个参数
echo " last 2nd param : ${@:${#@}-1:1} "

#最后两个参数
echo " last 2 param : ${@:${#@}-1} "

#从第二个到最后一个参数
echo " from 2nd to last param : ${@:2} "

#从第2个参数开始,连续2个参数
echo " from 2nd, count 2 : ${@:2:2} "