架构第二周作业
第二周作业
单报架构班的小伙伴本周学习内容
第四天:
1.实现GTID复制和主从复制常见问题及MySQL中间件介绍
2.MyCAT中间件服务实现读写分离
3.MHA实现MySQL的高可用性
4.MySQL的PXC和压力测试
第五天:
1.运维自动化和ansible简介
2.ansible的安装和基本使用
3.ansible的常用模块
4.ansible常用模块和实现playbook
5.ansible的playbook实现
第六天:
1.ansible的playbook的模版和条件循环技术实现
2.ansible的角色实现大型项目管理
3.缓存技术应用
4.redis的安装和优化
5.redis的编译安装多实例及客户端连接和访问
完成作业:
第二周
1、MyCAT中间件服务实现读写分离
2、ansible常用模块总结
3、ansible-playbook批量安装httpd,按主机名提供不同的index.html(如node1的index.html欢迎页面为welcome node1)
4、编译安装redis
1、mycat 中间件服务实现读写分离
1.1MyCat 简介
Mycat 是一个开源的分布式数据库系统,但是由于真正的数据库需要存储引擎,而 Mycat 并没有存 储引擎,所以并不是完全意义的分布式数据库系统
mycat是一个数据库中间件,也可以理解为是数据库代理。在架构体系中是位于数据库和应用层之间的一个组件,并且对于应用层是透明的,即数据库 感受不到mycat的存在,认为是直接连接的mysql数据库(实际上是连接的mycat,mycat实现了mysql的原生协议)
mycat的三大功能:
- 分表
对于数据量很大的表(千万级以上),mysql性能会有很大下降,因此尽量控制在每张表的大小在百万级别。对于数据量很大的一张表,可以考虑将这 些记录按照一定的规则放到不同的数据库里面。这样每个数据库的数据量不是太大,性能也不会有太大损失。
mycat分表的实现:首先在mycat的scheme.xml中配置逻辑表,并且在配置中说明此表在哪几个物理库上。此逻辑表的名字与真实数据库中的名字一致!然后需要配置分片规则,即按照什么逻辑分库!
- 读写分离
经过统计发现,对数据库的大量操作是读操作,一般占到所有操作70%以上。所以做读写分离还是很有必要的,如果不做读写分离,那么从库也是一种很大的浪费。
- 主从切换
mycat 的高可用集群方式:
- keepalived+mycat+mysql
- keepalived+lvs+mycat +mysql
- keepalived+haproxy+mycat+mysql
1.2 mycat 基本元素
1.逻辑库,mycat中存在,对应用来说相当于mysql数据库,后端可能对应了多个物理数据库,逻辑库中不保存数据
2.逻辑表,逻辑库中的表,对应用来说相当于mysql的数据表,后端可能对应多个物理数据库中的表,也不保存数据
逻辑表分类
1.分片表,进行了水平切分的表,具有相同表结构但存储在不同数据库中的表,所有分片表的集合才是一张完整的表
2.非分片表,垂直切分的表,一个数据库中就保存了一张完整的表
3.全局表,所有分片数据库中都存在的表,如字典表,数量少,由mycat来进行维护更新
4.ER关系表,mycat独有,子表依赖父表,保证在同一个数据库中
1.3 mycat 安装
安装jdk
yum install java -y
java -version
下载安装mycat
wget http://dl.mycat.org.cn/1.6.7.4/Mycat-server-1.6.7.4-release/Mycat-server-1.6.7.4-release-20200105164103-linux.tar.gz
mkdir /app
tar -zxf ~/Mycat-server-1.6.7.4-release-20200105164103-linux.tar.gz -C /app
ls /app/mycat/
bin catlet conf lib logs tmlogs version.txt
#环境变量
cat >> /etc/profile.d/mycat.sh << EOF
PATH=/app/mycat/bin:$PATH
EOF
source /etc/profile.d/mycat.sh
# 启动
mycat start
#启动日志
tailf -n 20 /app/mycat/logs/wrapper.log
#详细运行日志
tailf -n 20 /app/mycat/logs/mycat.log
#连接mycat
yum install mysql
mysql -uroot -p123456 -h 127.0.0.1 -P 8066
mycat 安装目录结构
bin mycat 命令。启动,重启停止
catlet 是mycat一个扩展功能
conf mycat 配置文件信息
schema.xml mycat对应的物理数据库和数据库表的配置,读写分离,高可用、分布式策略定制、节点控制
rule.xml mycat 分片(分库分表)规则配置文件,记录分片规则列表、使用方法等
lib mysql引用jar包,Java开发
logs 日志文件,包括启动和运行日志
versrion.txt mycat 版本说明
1.4 mycat 主要配置文件说明
server.xml
<user name="user">
<property name="password">user</property>
<property name="schemas">TESTDB</property>
<property name="readOnly">true</property>
<property name="defaultSchema">TESTDB</property>
<!-- 表级 DML 权限设置 -->
<!--
<privileges check="false">
<schema name="TESTDB" dml="0110" >
<table name="tb01" dml="0000"></table>
<table name="tb02" dml="1111"></table>
</schema>
</privileges>
-->
</user>
mysql软件本身相关配置,设置账号参数,数据库名称等
| 参数 | 说明 |
|---|---|
| user | 用户配置 |
| name | 客户端登录mycat用户名 |
| password | 客户端登录密码 |
| schemas | 数据库名和schema.xml配置关联 |
| privileges | 配置用户针对表的增删改查权限 |
| readOnly | mycat 逻辑库所具有的权限,true为只读,false为读写都有,默认false |
sckema.xml
<?xml version="1.0"?>
<!DOCTYPE mycat:schema SYSTEM "schema.dtd">
<mycat:schema xmlns:mycat="http://io.mycat/">
<schema name="TESTDB" checkSQLschema="false" sqlMaxLimit="100" randomDataNode="dn1">
<table name="test" dataNode="dn1" />
</schema>
<dataNode name="dn1" dataHost="localhost1" database="testdb" />
<dataHost name="localhost1" maxCon="1000" minCon="10" balance="1"
writeType="0" dbType="mysql" dbDriver="native" switchType="1" slaveThreshold="100">
<heartbeat>select user()</heartbeat>
<!-- can have multi write hosts -->
<writeHost host="hostM1" url="192.168.67.134:3306" user="scm"
password="Magedu123!">
<readHost host="hostM2" url="192.168.67.135:3306" user="scm"
password="Magedu123!"/>
</writeHost>
</dataHost>
</mycat:schema>
~
| 参数 | 说明 |
|---|---|
| schema属性 | 数据库设置/ |
| name | 逻辑数据库名,与server.xml中sckema对应 |
| checkSQLschema | 数据库前缀相关配置 |
| sqlMaxLimir | select时默认的limit,避免查询全表 |
| table 属性 | 说明 |
| name | 表名,与table中的dataNode对应 |
| dataNode | 表存储在哪些节点,多节点都好分割 |
| dataNode属性 | 分片信息,分库相关配置 |
| name | 节点名称,与table中datanode对应 |
| datahost | 物理数据库名,与 datahost中name对应 |
| database | 物理数据库中数据库名 |
| dataHost属性 | 物理数据库,真正存储数据的数据库 |
| name | 物理数据库名与 datande中datahost对应 |
| balanece | 负载均衡方式,0:不开启读写分离,1:读写分离,读请求随机分发到当前可用writehost对应的readhost和standby的writehost上 :2:读请求随机分发到当前datahost内所有的writehost和readhost 3:读请求分发到writehost 对应的readhost上,1.4版本后可用 |
| writeType | 写入方式 |
| dbType | 数据库类型 |
| hearbeat | 心跳检测语句,语句结尾要加分号 |
| 实例化后端连接池 | |
| writehost | 指定写实例 |
| readhost | 指定读实例 |
说明: |
一个datahost可以定义多个读写实例,但是写实例宕机,这个实例绑定的所有readhost也将不可用。另外:writehost宕机系统会自动检测到,并切换到备用的writehost上去 |
注意: |
mycat 主从分离只是在读的时候做了处理,写入数据的时候,只会写入writehost,需要通过mysql的主从复制将数据复制到readhost |
2、ansible常用模块总结
2.1 ansible常用模块
模块文档:https://docs.ansible.com/ansible/latest/modules/modules_by_category.htmlCommand:在远程主机执行命令,默认模块,可忽略-m选项 > ansible srvs -m command -a 'service vsftpd start' > ansible srvs -m command -a 'echo adong |passwd --stdin 123456'此命令不支持 $VARNAME < > | ; & 等,用shell模块实现 chdir: 进入到被管理主机目录 creates: 如果有一个目录是存在的,步骤将不会运行Command命令 ansible websrvs -a 'chdir=/data/ ls'Shell:和command相似,用shell执行命令 > ansible all -m shell -a 'getenforce' 查看SELINUX状态 > ansible all -m shell -a "sed -i 's/SELINUX=.*/SELINUX=disabled' /etc/selinux/config" > ansible srv -m shell -a 'echo magedu |passwd –stdin wang' 调用bash执行命令 类似 cat /tmp/stanley.md | awk -F'|' '{print $1,$2}' &> /tmp/example.txt 这些复杂命令,即使使用shell也可能会失败, 解决办法:写到脚本时,copy到远程执行,再把需要的结果拉回执行命令的机器 修改配置文件,使shell作为默认模块 vim /etc/ansible/ansible.cfg module_name = shellScript:在远程主机上运行ansible服务器上的脚本 > -a "/PATH/TO/SCRIPT_FILE" > ansible websrvs -m script -a /data/test.shCopy:从主控端复制文件到远程主机 src : 源文件 指定拷贝文件的本地路径 (如果有/ 则拷贝目录内容,比拷贝目录本身) dest: 指定目标路径 mode: 设置权限 backup: 备份源文件 content: 代替src 指定本机文件内容,生成目标主机文件 > ansible websrvs -m copy -a "src=/root/test1.sh dest=/tmp/test2.showner=wang mode=600 backup=yes" 如果目标存在,默认覆盖,此处指定先备份 > ansible websrvs -m copy -a "content='test content\nxxx' dest=/tmp/test.txt" 指定内容,直接生成目标文件Fetch:从远程主机提取文件至主控端,copy相反,目前不支持目录,可以先打包,再提取文件 > ansible websrvs -m fetch -a 'src=/root/test.sh dest=/data/scripts' 会生成每个被管理主机不同编号的目录,不会发生文件名冲突 > ansible all -m shell -a 'tar jxvf test.tar.gz /root/test.sh' > ansible all -m fetch -a 'src=/root/test.tar.gz dest=/data/'File:设置文件属性 path: 要管理的文件路径 (强制添加) recurse: 递归,文件夹要用递归 src: 创建硬链接,软链接时,指定源目标,配合'state=link' 'state=hard' 设置软链接,硬链接 state: 状态 absent 缺席,删除 > ansible websrvs -m file -a 'path=/app/test.txt state=touch' 创建文件 > ansible websrvs -m file -a "path=/data/testdir state=directory" 创建目录 > ansible websrvs -m file -a "path=/root/test.sh owner=wang mode=755" 设置权限755 > ansible websrvs -m file -a 'src=/data/testfile dest=/data/testfile-link state=link' 创建软链接 unarchive:解包解压缩,有两种用法: 1、将ansible主机上的压缩包传到远程主机后解压缩至特定目录,设置copy=yes. 2、将远程主机上的某个压缩包解压缩到指定路径下,设置copy=no 常见参数: copy:默认为yes,当copy=yes,拷贝的文件是从ansible主机复制到远程主机上, 如果设置为copy=no,会在远程主机上寻找src源文件 src: 源路径,可以是ansible主机上的路径,也可以是远程主机上的路径, 如果是远程主机上的路径,则需要设置copy=no dest:远程主机上的目标路径 mode:设置解压缩后的文件权限 示例: ansible websrvs -m unarchive -a 'src=foo.tgz dest=/var/lib/foo' #默认copy为yes ,将本机目录文件解压到目标主机对应目录下 ansible websrvs -m unarchive -a 'src=/tmp/foo.zip dest=/data copy=no mode=0777' # 解压被管理主机的foo.zip到data目录下, 并设置权限777 ansible websrvs -m unarchive -a 'src=https://example.com/example.zip dest=/data copy=no'Archive:打包压缩 > ansible all -m archive -a 'path=/etc/sysconfig dest=/data/sysconfig.tar.bz2 format=bz2 owner=wang mode=0777' 将远程主机目录打包 path: 指定路径 dest: 指定目标文件 format: 指定打包格式 owner: 指定所属者 mode: 设置权限Hostname:管理主机名 ansible appsrvs -m hostname -a "name=app.adong.com" 更改一组的主机名 ansible 192.168.38.103 -m hostname -a "name=app2.adong.com" 更改单个主机名Cron:计划任务 支持时间:minute,hour,day,month,weekday > ansible websrvs -m cron -a "minute=*/5 job='/usr/sbin/ntpdate 172.16.0.1 &>/dev/null' name=Synctime" 创建任务 > ansible websrvs -m cron -a 'state=absent name=Synctime' 删除任务 > ansible websrvs -m cron -a 'minute=*/10 job='/usr/sbin/ntpdate 172.30.0.100" name=synctime disabled=yes' 注释任务,不在生效Yum:管理包 ansible websrvs -m yum -a 'list=httpd' 查看程序列表 ansible websrvs -m yum -a 'name=httpd state=present' 安装 ansible websrvs -m yum -a 'name=httpd state=absent' 删除 可以同时安装多个程序包 Service:管理服务 ansible srv -m service -a 'name=httpd state=stopped' 停止服务 ansible srv -m service -a 'name=httpd state=started enabled=yes' 启动服务,并设为开机自启 ansible srv -m service -a 'name=httpd state=reloaded' 重新加载 ansible srv -m service -a 'name=httpd state=restarted' 重启服务User:管理用户 home 指定家目录路径 system 指定系统账号 group 指定组 remove 清除账户 shell 指定shell类型 ansible websrvs -m user -a 'name=user1 comment="test user" uid=2048 home=/app/user1 group=root' ansible websrvs -m user -a 'name=sysuser1 system=yes home=/app/sysuser1' ansible websrvs -m user -a 'name=user1 state=absent remove=yes' 清空用户所有数据 ansible websrvs -m user -a 'name=app uid=88 system=yes home=/app groups=root shell=/sbin/nologin password="$1$zfVojmPy$ZILcvxnXljvTI2PhP2Iqv1"' 创建用户 ansible websrvs -m user -a 'name=app state=absent' 不会删除家目录 安装mkpasswd yum insatll expect mkpasswd 生成口令 openssl passwd -1 生成加密口令 删除用户及家目录等数据 Group:管理组 ansible srv -m group -a "name=testgroup system=yes" 创建组 ansible srv -m group -a "name=testgroup state=absent" 删除组
3、playbook
> playbook是由一个或多个"play"组成的列表
> play的主要功能在于将预定义的一组主机,装扮成事先通过ansible中的task定义好的角色。
Task实际是调用ansible的一个module,将多个play组织在一个playbook中,
即可以让它们联合起来,按事先编排的机制执行预定义的动作
> Playbook采用YAML语言编写
3.1 Playbook核心元素
Hosts 执行的远程主机列表(应用在哪些主机上)
Tasks 任务集
Variables 内置变量或自定义变量在playbook中调用
Templates模板 可替换模板文件中的变量并实现一些简单逻辑的文件
Handlers和notify结合使用,由特定条件触发的操作,满足条件方才执行,否则不执行
tags标签 指定某条任务执行,用于选择运行playbook中的部分代码。
ansible具有幂等性,因此会自动跳过没有变化的部分,
即便如此,有些代码为测试其确实没有发生变化的时间依然会非常地长。
此时,如果确信其没有变化,就可以通过tags跳过此些代码片断
ansible-playbook -t tagsname useradd.yml
3.2 playbook基础组件
Hosts:
> playbook中的每一个play的目的都是为了让特定主机以某个指定的用户身份执行任务。
hosts用于指定要执行指定任务的主机,须事先定义在主机清单中
> 可以是如下形式:
one.example.com
one.example.com:two.example.com
192.168.1.50
192.168.1.*
> Websrvs:dbsrvs 或者,两个组的并集
> Websrvs:&dbsrvs 与,两个组的交集
> webservers:!phoenix 在websrvs组,但不在dbsrvs组
示例: - hosts: websrvs:dbsrvs
remote_user:
可用于Host和task中。
也可以通过指定其通过sudo的方式在远程主机上执行任务,其可用于play全局或某任务;
此外,甚至可以在sudo时使用sudo_user指定sudo时切换的用户
- hosts: websrvs
remote_user: root (可省略,默认为root) 以root身份连接
tasks: 指定任务
- name: test connection
ping:
remote_user: magedu
sudo: yes 默认sudo为root
sudo_user:wang sudo为wang
task列表和action
任务列表task:由多个动作,多个任务组合起来的,每个任务都调用的模块,一个模块一个模块执行
1> play的主体部分是task list,task list中的各任务按次序逐个在hosts中指定的所有主机上执行,
即在所有主机上完成第一个任务后,再开始第二个任务
2> task的目的是使用指定的参数执行模块,而在模块参数中可以使用变量。
模块执行是幂等的,这意味着多次执行是安全的,因为其结果均一致
3> 每个task都应该有其name,用于playbook的执行结果输出,建议其内容能清晰地描述任务执行步骤。
如果未提供name,则action的结果将用于输出
tasks:任务列表
两种格式:
(1) action: module arguments
(2) module: arguments 建议使用 模块: 参数
注意:shell和command模块后面跟命令,而非key=value
某任务的状态在运行后为changed时,可通过"notify"通知给相应的handlers
任务可以通过"tags"打标签,可在ansible-playbook命令上使用-t指定进行调用
示例:
tasks:
- name: disable selinux 描述
command: /sbin/setenforce 0 模块名: 模块对应的参数
如果命令或脚本的退出码不为零,可以使用如下方式替代
tasks:
- name: run this command and ignore the result
shell: /usr/bin/somecommand || /bin/true
转错为正 如果命令失败则执行 true
或者使用ignore_errors来忽略错误信息
tasks:
- name: run this command and ignore the result
shell: /usr/bin/somecommand
ignore_errors: True 忽略错误
3.3 运行playbook
运行playbook的方式
ansible-playbook <filename.yml> ... [options]
常见选项
--check -C 只检测可能会发生的改变,但不真正执行操作
(只检查语法,如果执行过程中出现问题,-C无法检测出来)
(执行playbook生成的文件不存在,后面的程序如果依赖这些文件,也会导致检测失败)
--list-hosts 列出运行任务的主机
--list-tags 列出tag (列出标签)
--list-tasks 列出task (列出任务)
--limit 主机列表 只针对主机列表中的主机执行
-v -vv -vvv 显示过程
示例
ansible-playbook hello.yml --check 只检测
ansible-playbook hello.yml --list-hosts 显示运行任务的主机
ansible-playbook hello.yml --limit websrvs 限制主机
3.4 批量安装httpd示例
- hosts: websrvs
remote_user: root
tasks:
- name: Install httpd
yum: name=httpd state=present
- name: Install configure file
copy: src=files/httpd.conf dest=/etc/httpd/conf/
- name: Install configure file
copy: content="wellcome {{ ansible_nodename }} \n" dest=/var/www/html/index.html
- name: start service
service: name=httpd state=started enabled=yes
4、redis
4.1 redis 简介
- Redis是一个开源的使用ANSI C语言编写、支持网络、可基于内存亦可持久化的日志型、Key-Value数据库,并提供多种语言的API。从2010年3月15日起,Redis的开发工作由VMware主持。从2013年5月开始,Redis的开发由Pivotal赞助。
- Redis是 NoSQL技术阵营中的一员,它通过多种键值数据类型来适应不同场景下的存储需求,借助一些高层级的接口使用其可以胜任,如缓存、队列系统的不同角色
4.2 Redis特性
- Redis 与其他 key - value 缓存产品有以下三个特点:
- Redis支持数据的持久化,可以将内存中的数据保存在磁盘中,重启的时候可以再次加载进行使用。
- Redis不仅仅支持简单的key-value类型的数据,同时还提供list,set,zset,hash等数据结构的存储。
- Redis支持数据的备份,即master-slave模式的数据备份。
4.3 Redis 优势
- 性能极高 – Redis能读的速度是110000次/s,写的速度是81000次/s 。
- 丰富的数据类型 – Redis支持二进制案例的 Strings, Lists, Hashes, Sets 及 Ordered Sets 数据类型操作。
- 原子 – Redis的所有操作都是原子性的,同时Redis还支持对几个操作全并后的原子性执行。
- 丰富的特性 – Redis还支持 publish/subscribe, 通知, key 过期等等特性。
4.4 Redis应用场景
- 用来做缓存(ehcache/memcached)——redis的所有数据是放在内存中的(内存数据库)
- 可以在某些特定应用场景下替代传统数据库——比如社交类的应用
- 在一些大型系统中,巧妙地实现一些特定的功能:session共享、购物车
- 只要你有丰富的想象力,redis可以用在可以给你无限的惊喜…….
4.5 编译安装redis
redis 下载地址:http://download.redis.io/releases/
编译安装:https://blog.csdn.net/edgar_t/article/details/119515615

浙公网安备 33010602011771号