谈到线上环境, 一般开发同学, 不太容易接触到. 即使接触到, 也只是其中的冰山一角!
所以, 其实说起线上环境的部署, 咱们好像都有点懂, 但是又都不一定完全懂! 网上的知识无穷无尽, 但往往都是各司一职, 对于普通同学, 很难窥其全貌!
所以, 我今天就来说说, 一些普通的线上环境的部署步骤, 和一些脚本小技巧吧. 只希望通过这篇文章, 能够让大家有一个运维的全局!
我将会分几条线来整理咱们的运维思路!
一, 从理论上讲, 我们应该怎么做?
1. 针对的是什么样的用户群体, 体量大量会有多少?
这是一个部署规划的前题. 为啥呢?
一, 如果你针对的是后台管理员, 人数也不多, 那么你可能只需要一个服务器就可以了, 前后端也都可以部署在同一台服务器上; 如果稍微考虑下单点故障问题, 则顶多两台服务器搞定!
二, 如果针对的是前端普通用户, 那么, 往往就会考虑多机部署, 前后端分离, 单点问题, 负载均衡了; 至于具体要部署多少台, 则要根据你的用户情况来定了, 当然, 前期一般水需要多少台! 只要能持横向扩展, 则短期内, 往往不太关心性能和架构问题!
2. 为支持预估的用户量, 大概需要多少的带宽?
有访问就会有流量产生, 而预估的用户量, 则是一个带宽资源需求的一个决断依据!
一般针对前期用户不太确定的场景, 可以先买个 10M 左右的共享带宽, 基本能够应付; 经过一段时间的观察后, 再进行带宽的变更也可以;
当然, 考虑带宽, 自然也会存在一个公网 IP 的问题, 因为流量是从 IP 进来的.
而在 IP 之前, 则是域名的访问.
公网 IP 可以是直接指向机器的, 也可以是指向负载均衡器的. 如果想要支持横向扩展, 则 IP 的指向一定是一个负载均衡器. 因为只有这样, 当遇到流量突增, 或者做活动的时候, 才能更快速的进行扩容!
3. 数据库规划如何?
数据在当下时代, 算是重中之重了. 机器没了可以再买, 代码没了可以再写, 但是数据没了就完蛋了!
数据库一般要新人两个基本原则: 一, 带宽要大; 二, 运算速度要快; 三, 要能承受足够大的运算空间;
所以, 一般不要在数据库上省钱, 能多点就多点!
另外, 也不要什么样的数据都往数据库 (关系型数据库) 存, 搞清楚各类型数据库的强项与弱项, 做出明智的选择. 否则会带来很多不必要的麻烦!
4. 应用要基于系统来部署还是基于容器来部署?
这是个决策性的问题! 基于系统的部署, 是一种比较传统和常见的部署方式. 优点是, 很多系统工具都是完善的, 只要你大概知道要部署什么, 部署下来一般不会有太多问题, 因为这是个完整的系统.
但是, 由于系统与系统之间可能不能完全一致, 有各种各样的差异, 所以, 你在这个机器上运行成功的东西, 在另外的机器上则不一定能成功. 因此, 基于系统的部署将会使我人们的问题排查难度大大增加, 而且移值性会很差. 比如你在机器 A 上安装了 10 个软件, 你可能配置了 n 个选项, 但是, 你在安装 B 机器的时候, 你并不能很好的利用原有的配置, 你还得从头一个个地来!
因此, 有另一个部署方案, 基于容器的部署(我这里是基于 docker 容器的部署).docker 就类似于一个个的虚拟机, 但是它更加轻量级, 当一个 docker 部署好后, 你可以任意复制到其他机器上运行, 看起来很诱人吧. 不过, docker 只是入门级容器, 对于大量集群容器的管理, 还是显得力不从心, 当然你很容易找到另一个方案: Kubernetes (K8s); 你只要花上少许的时间了解下, 你就可以应用了! 当然了, 使用容器的方案, 有没有什么缺点呢? 应该是有的, 比如本来可以基于系统的监控方案, 因为接入容器后, 监控指标则不一定适用了, 当然现成的方案还是有的, 不过得另外再花点时间研究了. 再比如: 如果容器出了问题, 是否能排查出来, 这也是另一个问题!
5. 都有些什么样的基础设施或者中间件?
想要运行应用程序, 自然是先考虑运行环境的. 比如: 应用需要 nginx 来做 http 服务器, 用 tomcat 来做 java web 应用服务器, 用 Redis 来做缓存中间件, 用 zk 来做应用协调中间件, 用 rabbitmq 来做消息中间件, 等等!
因此, 要在代码跑起来之前, 先要把这些环境给准备好咯.
准备这些中间件或基础设施之前, 也要问下当下的形势, 比如: 是否需要集群部署, 或者单机部署? 往往集群部署又会依赖其他的中间件! 也更复杂!
当然, 这些都不是事. 事儿是在出问题之后, 能够有意识, 能够猜测到问题发生的点!
6. 应用代码应该怎样部署?
当基础环境就绪后, 就应该让主角上场了. 应用代码怎么部署?
最简单的: 通过 ftp 上传代码到服务器上后, 一个个部署! 这种方案是最原始的, 也是在没有办法搞更好的方案的时候使用的, 不应长期使用;
稍微好点的: 使用集成工具 (如 jenkins) 进行打包, 然后上传一个私有 yum 镜像服务器(yum 源). 然后在线进行 yum 安装; 这种方式, 借助了集成工具, 三个好处:
1. 可以检测代码有改动做留档;
2. 减少了手动上传导致的包破坏的可能性;
3. 适合大规模应用;
再成熟点的: 再往后面, 手动 yum 安装也已经太累了, 所以急需一个部署平台, 实现自动化部署;(这里的自动化部署可能就是基于 CI 集成部署的一种升级版). 总之, 大大减小了人工参与程序, 提升了效率, 同时也保证了质量! 当然, 这种部署平台已经经过了严格的测试, 出错的可能性也比较小了!
8. 服务器的安全性?
不考虑服务器的安全性的应用, 无异于自暴自弃. 黑客无处不在, 不过幸好现在系统也是越来越完善, 只要稍加控制, 即不那么容易被攻破了. 但是如果放弃安全防护, 则随便来一个菜鸟程序员就把你搞死了, 那时的损失就大了.
网络安全是个很专业的领域, 不过我们可以简单的做下防护: 如防火墙, 授权操作, 病毒库等等. 当然, 如果使用 xx 云服务, 则轻松方便多了, 在后台点点设置几下搞定!
9. 服务的可监控性?
无监控, 不上线!
这是一个警示, 如果线上服务没有监控, 则所有线上的东西, 都成了盲区, 这对程序员 GG 们来说, 简直太糟糕了, 虽然他们很自信!
监控分两个方面: 一是系统级别的监控; 二是应用级别的监控;(一般忽略其他监控: 如网络)
系统级别的监控一般可以安装第三方的软件来解决: 如 zabbix, grafana ...
而应用级别的监控, 则需要自己拥有一套监控代码了, 而这对初期项目, 则往往比较吃力.
而如果使用 xx 云服务, 则往往都会自带服务器监控的, 可以很方便地查看到服务器情况, 站在高层次预估应用是否存在潜藏的问题!
如上, 就是一些个人觉得的在部署一整套线上环境的时候, 需要考虑的事项! 从理论上讲解了下个人见解, 不对之处, 请赐教!
二, 接下来, 我将给到一些实际的操作捷径或提示?(Linux)
1. 免密登录服务器?
在 n 服务器之间跳转, 如果每次都要求输入密码, 那确实太烦了. 尤其在密码一般还很不容易记住的情况下!
所以, 可以将一台服务器作为跳板机, 在这台服务器上, 可以免密地登录到允许的 n 台子服务器;
操作步骤有二:
- # 1. 先使用 SSH-keygen 生成本机的 key
- SSH-keygen -t rsa # 如果已生成不要重复生成
- # 2. 使用 SSH-copy-id 将梧桐的 key 发送到需要免密登录的服务器, 首页 copy 时会要求输入密码, 后续则免密了
- SSH-copy-id -i ~/.SSH/id_rsa.pub root@172.1.2.111
2. 服务器之间文件 (夹) 拷贝?
拷贝文件的目的有很多, 比如: 代码同步, 文件同步...
- # 1. 使用 scp 拷贝文件
- scp /home/ol-Web.war root@xxx.com:/www/tomcat/wepapps/ # 从本机拷贝到远程
- scp /home/ol-Web.war root@xxx.com:/www/tomcat/wepapps/ # 从远程拷贝到本机
- scp -r /www/nginx/html/ root@$1.2.3.2:/www/nginx/HTML/ # 从本机拷贝文件夹到远程
- # 2. 使用 rsync 同步文件,(可能需要安装 rsync 服务)
- rsync -av --delete /www/nginx/HTML/ root@$1.2.3.1:/www/nginx/HTML/ # 同步所有属性, 本地删除的文件也同步远程删除
3. 快捷使用 SSH 等等命令, 使用 tab 键进行信息补全?
当使用 SSH / scp 等等命令操作的时候, 其操作对象往往 123 这样的 ip 显示, 如果不能友好点, 那确实太累了! 我们可以如下操作, 以实现 SSH 也能更好的记忆:
- # 在文件 /root/.bashrc 中, 添加脚本如下, 使自动补全添加 SSH
- # auto complete ...
- complete -W "$(echo $(grep -v'^$|#'.ssh/config | sort -u | sed's/^ssh //'))" SSH
- # 在文件 /root/.SSH/config 中, 添加需要自动补全的服务器,
- Host 172.2.3.5 server-API-01
- Host 172.2.3.6 server-API-02
- # 以上服务器名字需要在 /etc/hosts 文件中添加相应解析
- # 而登录 server 时, 只需, SSH server-API-01 即可
如上补全工作, 无需在所有服务器上进行操作, 只需在相应的跳板机上提供功能即可!
4. 简要 salt 搭建指南?
salt 是个方便易用的集群管理工具, 比如你可以用于批量重启服务, 全局搜索日志等等;
- # 1. 安装, 仅需到相应机器上安装即可
- yum install salt-master salt-minion
- # 2. 配置 /etc/salt/master /etc/salt/minion, 最简单的, 只需修改 minion 配置, 指向 master 的 ip 即可;
- #指定 master, 冒号后有一个空格, minion
- master: 172.1.2.22
- id: server-API-01
- user: root
- # 3. 启动所有节点, status, restart
- systemctl start salt-master # 162 机器可用
- systemctl start salt-minion
- /etc/init.d/salt-master start # 155 机器可用
- /etc/init.d/salt-minion start
- # 4. 将所有 salt-minion 添加到 master 集群管理
- salt-key -A
- # 5. 登录跳板机 api_01, 运行 salt 操作, 执行集群管理工作
- salt server-API-02 cmd.run 'lsof -i:80'
- salt '*' test.ping
5. 简要集群复制 shell 脚本?
有时, 你可能需要将你的应用发布到 n 台服务中, 你可以直接改如下 shell, 也可以依赖于 salt 这样的高级工具进行发布! shell 参考如下:
- #!/bin/bash
- # find out my ip to exclude...
- MY_MERCHINE_IP=`ifconfig eth0 |awk -F "[: ]+" '/inet addr/{print $4}'`;
- MERCHINE_IP_LIST="172.1.2.7 172.1.3.4";
- for m_ip in $MERCHINE_IP_LIST;
- do
- if [[ $m_ip != $MY_MERCHINE_IP ]]; then
- echo "- Installing apps to mechine@${m_ip} ...";
- # install API apps
- scp /www/test/hello-1.0.0-SNAPSHOT.jar root@${m_ip}:/www/test/
- rsync -av --delete /www/HTML/ root@${m_ip}:/www/HTML/
- echo "- Install apps to merchine@${m_ip} done.";
- fi;
- done;
6. 简要 docker 搭建指南?
docker 作为一个容器化的基石, 一出世就被追棒. 包括现在的 k8s , 也是基于 docker 的. docker 可以让你在一处搭建, 处处运行, 从而避免每次新买机器就要搞很久的尴尬局面; 其搭建也是很简单的(简单应用):
为方便任意发挥, 我们可以基于 CentOS 这种系统级别的镜像进行创建自己的 image;
- # docker 安装:
- yum install docker
- service docker start
- # 拉取 centos6 的 docker 镜像
- docker pull CentOS:6
- docker images
- # 构建一个 image, 创建空目录, 编辑 Dockerfile
- VIM Dockerfile # 内容可变
- FROM CentOS:6
- MAINTAINER oom <w@163.com>
- # move all configuration files into container
- # RUN yum install -y lsof
- # EXPOSE 80
- # CMD ["sh","-c","service httpd start;bash"]
- # 创建镜像
- docker build -t tmp_image:1.0 .
- # 创建并运行容器
- docker run -h tmp_container -itd --name tmp_container -v /opt/docker/webapps:/www/webapp tmp_image:1.0
- # 进入容器, 相当于进入 CentOS 操作系统
- docker exec -it tmp_container bash
- # 保存容器修改到 images
- docker commit -m 'web final.' 49d79fc19eaa tmp_image:1.2
- # 备份容器修改后的 docker 镜像
- docker save> /opt/images/images_final/tmp_image.final.tar tmp_image:1.2
- ...
来源: https://www.cnblogs.com/yougewe/p/10327217.html