【英文原文:https://arxiv.org/ftp/arxiv/papers/1702/1702.01715.pdf】
【译文转发:https://mp.weixin.qq.com/s?__biz=MzA4NTc3NzE5OQ==&mid=2652726103&idx=1&sn=66c2c341dd73eb38f256e30dd530e747】

1. 介绍

Google已经是一个非常成功的公司。正如在搜索和竞价广告方面的成功一样,Google也提供了许多其他突出产品,包括Google地图,Google新闻,Google翻译,Google语音识别,Chrome和Android。Google还通过购买小公司大大增强和扩展了许多产品,例如YouTube,并对多种多样的开源项目做出了重大贡献。Google也展示了一些尚未投入市场的惊人产品,如自动驾驶汽车。

Google的成功有很多原因,包括开明的领导力,技术牛人,高标准招聘,以及成功带来的经济实力,可以在非常迅速增长的市场早期进行介入。但其中一个原因是谷歌开发出的优秀软件工程实践,这帮助谷歌走向成功。这些实践基于全球最有才华的软件工程师的大量积累和提取的智慧,随着时间的推移而不断演化。我们想跟全球各地的人们分享我们的知识与实践以及我们从中学到的一些教训。

本文的目的是记载并简要介绍Google的关键软件工程实践。其他组织和个人可以进行比较和对比,并考虑是否应用一些做法。

许多作者(例如[9],[10],[11])都有书籍或文章来分析Google的成功历史。但大多数主要涉及商业,管理和文化;只有一小部分(例如[1,2,3,4,5,6,7,13,14,16,21])谈到了软件工程方面的内容,大多数只探讨一个方面;并且没有从整体上提供一个简短的、书面的关于谷歌软件工程实践的概述,本文目的正在于此。

继续阅读

有些时候,由于各种历史原因,某些应用的服务之间耦合度非常高,具体表现为各种crontab+脚本的管理模型,且每个脚本的功能已经随着历史的车轮滚滚风化。

当然,资源(主要是时间)和收益(主要是还有多少人用)受到制约的情况下,把所有服务塞到一个容器里未必是一个坏选择(至少下次迁移的时候可以省心很多),这个时候docker容器默认监控CMD命令的进程就是出现一点小问题,也许可以这样处理(笔者随手写的,没有找过是否有更好的方案):

继续阅读

一个是清理过期的image,也就是将名字为的镜像快速清理掉:

# alias.zsh
alias 'dclean-none'='docker images|grep "^<none>"|awk '\''{print $3}'\''|xargs docker rmi -f'

另一个是清理docker build失败时产生的冗余image

# alias.zsh
alias 'dclean2'='docker ps -a|grep "^[a-f0-9]\{12\}[[:blank:]]\+[a-z0-9]\{12\}[[:blank:]]\+[[:print:]]\+[[:blank:]]\+[[:lower:]]\+_[[:lower:]]\+"|awk '\''{print $1}'\''|xargs docker rm'

因为严格来说没法绝对匹配,这个正则假设了IMAGE不是12位的小写+数字,但是有可能因为原来的镜像更新导致本来有名字的镜像,变成了sha编码,所以继续判定了末尾的NAMES是否是由#单词_单词#的结构组成的。

所以自己的镜像尽可能避免这个场景,或者有更好的方案欢迎留言~

CentOS

在崩溃地部署了n台服务器后终于大彻大悟…… 我特么早应该整一个这样的脚本…… 于是一台新服务器被我重置了又更新重置了又更新,测出了一下的东西^<^ # CentOS

set -e;
echo -e "请尽可能避免在有业务的机器上使用,避免影响已有业务;\n"
read -p "这个脚本只能给阿里云的CensOS7系统使用,是否继续?(y/n):" goon
if [ ! $goon == "y" ]; then
    exit 0
fi

read -p "设置hostname:" myhostname
if [[ ${myhostname} == "" ]];then
   echo "请不要设置为空的hostname";
else
   hostname ${myhostname};
fi

read -p "设置Docker镜像加速地址:" mirror

# ssh
sudo ssh-keygen
touch ~/.ssh/authorized_keys

sudo rpm --import https://www.elrepo.org/RPM-GPG-KEY-elrepo.org
sudo rpm -Uvh http://www.elrepo.org/elrepo-release-7.0-2.el7.elrepo.noarch.rpm
yum install -y https://centos7.iuscommunity.org/ius-release.rpm
wget -O /etc/yum.repos.d/CentOS-Base.repo http://mirrors.aliyun.com/repo/Centos-7.repo
yum makecache

# 基础配置
sudo yum update -y
sudo yum upgrade -y

# 安装常用工具
sudo yum install -y git vim lrzsz htop zsh sudo autojump-zsh psmisc lsof pass bzip2 linux-firmware perl python3 python3-pip python3-devel

# ZSH配置
chsh -s /bin/zsh
wget https://github.com/robbyrussell/oh-my-zsh/raw/master/tools/install.sh -O - | sh
echo '[[ -s ~/.autojump/etc/profile.d/autojump.sh ]] && . ~/.autojump/etc/profile.d/autojump.sh' >> ~/.zshrc
sed -i 's/plugins=(git)/plugins=(git autojump extract)/' ~/.zshrc
sed -i 's/ZSH_THEME="robbyrussell"/ZSH_THEME="back"/' ~/.zshrc

cat <<-'EOF' >> ~/.oh-my-zsh/custom/themes/back.zsh-theme
local ret_status="%(?:%{$fg_bold[green]%}➜ :%{$fg_bold[red]%}➜ )"
PROMPT='${ret_status}%{$fg[yellow]%}[%M]%{$reset_color%}%{$fg[cyan]%}%c%{$reset_color%} $(git_prompt_info)'

ZSH_THEME_GIT_PROMPT_PREFIX="%{$fg_bold[blue]%}git:(%{$fg[red]%}"
ZSH_THEME_GIT_PROMPT_SUFFIX="%{$reset_color%} "
ZSH_THEME_GIT_PROMPT_DIRTY="%{$fg[blue]%}) %{$fg[yellow]%}✗"
ZSH_THEME_GIT_PROMPT_CLEAN="%{$fg[blue]%})"
EOF

# 最近github特别卡,另外处理
#wget https://github.com/bcicen/ctop/releases/download/v0.7.2/ctop-0.7.2-linux-amd64 -O /usr/local/bin/ctop
#chmod +x /usr/local/bin/ctop

cd /usr/bin;
mv pip pip.bak
ln -s pip3.6 pip
cd ~;

# 安装docker
# step 1: 安装必要的一些系统工具
yum install -y yum-utils  device-mapper-persistent-data  lvm2
# Step 2: 添加软件源信息
sudo yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
# Step 3: 更新并安装 Docker-CE
sudo yum makecache fast
sudo yum install -y docker-ce docker-ce-cli containerd.io
# Step 4: 开启Docker服务
sudo systemctl start docker

# 开始配置
sudo mkdir -p /etc/docker
## 这段有点恶心但没找到好方法
sudo cat <<-'EOF' > /etc/docker/daemon.json
{
    "registry-mirrors": [
EOF

sudo echo "        \"${mirror}\"" >> /etc/docker/daemon.json

sudo cat <<-'EOF' >> /etc/docker/daemon.json
    ],
  "exec-opts": ["native.cgroupdriver=systemd"],
  "log-driver": "json-file",
  "log-opts": {
    "max-size": "100m"
  },
  "storage-driver":"overlay2",
  "storage-opts": [
    "overlay2.override_kernel_check=true"
  ]
}
EOF

sudo cat <<-'EOF' >> /etc/sysctl.conf
# fix docker warning
net.bridge.bridge-nf-call-ip6tables = 1
net.bridge.bridge-nf-call-iptables = 1
net.bridge.bridge-nf-call-arptables = 1
EOF

# 优化网络服务

sudo cat <<-'EOF' >> /etc/security/limits.conf
* soft nofile 100000
* hard nofile 100000
root soft nofile 100000
root hard nofile 100000
* soft core unlimited
* hard core unlimited
root soft core unlimited
root hard core unlimited
EOF

sudo cat <<-'EOF' >> /etc/sysctl.conf
# network improve
net.unix.max_dgram_qlen = 128
net.ipv4.tcp_mem = 98304 131072 229376
net.ipv4.tcp_wmem = 4096 16384 4194304
net.ipv4.tcp_rmem = 4096 87380 4194304
net.core.somaxconn = 4096
net.core.wmem_default = 8388608
net.core.rmem_default = 8388608
net.core.rmem_max = 16777216
net.core.wmem_max = 16777216
net.ipv4.tcp_tw_recycle = 1
net.ipv4.tcp_tw_reuse = 1
kernel.msgmnb = 4194304
kernel.msgmni = 128
kernel.msgmax = 8192
kernel.core_pattern = /data/core_files/core-%e-%p-%t
net.ipv4.tcp_max_syn_backlog = 8192
net.core.netdev_max_backlog = 1024
net.ipv4.ip_local_port_range = 20000 65535
net.ipv4.tcp_fin_timeout = 30

fx.file-max=100000
EOF

# 限制权限
chown root:root /etc/passwd /etc/shadow /etc/group /etc/gshadow
chmod 0644 /etc/group
chmod 0644 /etc/passwd
chmod 0400 /etc/shadow
chmod 0400 /etc/gshadow

echo "重载Docker"

sudo systemctl daemon-reload
sudo systemctl enable docker
sudo systemctl restart docker

# 随机内存地址
sysctl -w kernel.randomize_va_space=2

# 设置server端的ssh心跳帧
sudo cat <<-'EOF' >> /etc/ssh/sshd_config
ClientAliveInterval 30
ClientAliveCountMax 2
LogLevel INFO
Protocol 2
MaxAuthTries 4
Port 10022
EOF

# 安装docker-compose
sudo mkdir -p ~/.pip
sudo cat <<-'EOF' > ~/.pip/pip.conf
[global]
index-url = http://mirrors.aliyun.com/pypi/simple/
[install]
trusted-host=mirrors.aliyun.com
EOF

sudo pip3 install --upgrade pip
sudo pip3 uninstall urllib3 chardet requests
sudo pip3 install requests
sudo pip3 install docker-compose

# 常用别名
cat <<-'EOF' >> /root/.oh-my-zsh/custom/alias.zsh
alias 'pt'='pstree -ap|grep '
alias 'vi'='vim'
alias 'la'='ls -lah'
alias 'net'='netstat -nalp'
alias 'docker-rm-none'='docker images|grep "<none>"|awk '\''{print $3}'\''|xargs docker rmi -f'
EOF

# VIM配置
cat <<-'EOF' >> /etc/vimrc
set paste
set showmode
set encoding=utf-8
set t_Co=256
filetype indent on
set autoindent
set tabstop=2
set shiftwidth=2
set ruler
EOF

# 最后处理
sudo yum update -y
sudo yum upgrade -y
sudo yum autoremove -y

# 重启
read -p "是否立即重启计算机?(y/n):" goon
if [ $goon == "y" ]; then
    sudo reboot
fi

意外收到阿里云容器服务的溪恒的回复和详细说明,感谢,并附录在文章末尾。

想试用一下阿里云的容器服务,结果要求内核是3.18+,然后整出一堆事情,都跟内核有关。

我现在使用的几个服务器都是CentOS,没辙,之前升级php7的时候Ubuntu14给我留下的印象实在太渣了,这也促使我后来转投CentOS……

然后这次轮到了CentOS,果然坑是踩不完的,首先查看了自己的操作系统内核是3.10+,显然是不够的,然后阿里云容器的文档又说推荐CentOS或者Ubuntu的操作系统,因为阿里云对这两个系统进行了严格的验证巴拉巴拉,于是乎考虑是那台租了两年多的老服务器操作系统版本太旧了,于是执行了停机操作,并查看能不能升级系统盘,当然,我只是打算看看现在可选的操作系统有没有新的版本,并没有真的升级系统

于是坑出现了,重新启动服务器的时候,服务器无法启动,最后提交工单才解决……

继续阅读

前言

前文再续,就书接上一回,经过了各种突发事件的2016后,笔者终于苟延残喘到了传说中的2017,去年我们简单聊了Swoole的进程模型,这次俺们来聊聊热重载的问题。

在这个普天同庆的元旦里,祝愿大伙身体健康,平平安安~

继续阅读