OBPROXY简介
背景
- obproxy核心功能就是路由以将客户端发起的数据访问请求转发到正确的OBServer上;
- 通过obproxy解决定位到数据所属的表或是分区的主副本位置;
核心功能(路由)
-
核心功能:路由转发;转发到最恰当的server上执行;
核心过程包括: * 简单的SQL Parser * LDC路由 * 读写分离 * 备优先读 * 黑名单机制
-
核心功能:连接管理
* 在observer宕机/升级/重启时,客户端与OBProxy的连接不会断开,OBProxy可以迅速切换到正常的server上,对应用透明 * OBProxy支持用户通过同一个OBProxy访问多个OB集群 * Server session对于每个client session独占 * 同一个client session对应server session状态保持相同(session 变量同步)
-
核心功能:监控&运维
* 周期性汇报统计项到OCP,实现了语句级别,事务级别,session级别,obproxy级别的各种统计 * Xflush日志监控(包括慢查询日志、error包监控等) * SQL Audit功能 * 实现了大量内部命令来实现远程监控,查询和运维
两种启动模式
- 测试模式:主要用于现阶段开发调试,无需依赖config server
- 生产模式:obp可以通过指定config server提供的config_url来启动,config server服务可以协助获取该集群的配置信息。同一个config server可以保存多个OB集群的RSList信息,使obproxy能为多个OB集群同时提供服务;
路由实现
obproxy执行流程
1、parse sql,通过简易parse,解析出sql涉及的table name、database name
2、fetch route entry,根据用户的tenant name,database name,table name,partition id向observer拉取该partition的路由表;
3、sort route entry,根据各种相关属性对路由表中ip进行排序
* read_consisitency:强一致性读或弱一致性读
* 目标server状态:正在合并or常态
* 路由精准度:PS or TS(PS即分区的路由信息,TS即租户的路由信息)
* LDC 匹配:本地、同城、异地
* Zone类型:读写型VS只读型
* 读写分离的ob_route_policy取值
4、filter by congestion,从路由表中依次尝试目标ip,通过黑名单进行过滤;
5、forward request,将用户请求发给目标server
IDC配置与查询
配置方式:
1、启动时通过启动参数:
./bin/obproxy -p2883 -e -o
obproxy_config_server_url='ocp_config_server_url',proxy_idc_name='hz001' -n trade
2、修改proxy配置项
mysql> alter proxyconfig set proxy_idc_name='hz001';
查看LDC部署情况
show proxyinfo idc
检查observer LDC设置内容是否生效
select * from __all_zone;
OBProxy使用限制
-
proxy parser在根据SQL选择server时,有以下特殊逻辑
- proxy parser只解析begin/start/transaction/set和其他DML,如遇到其他开头,parser会直接跳过,认为该语句不包含表名
- proxy parser会按照第一条包含实体表名的stmtement进行路由,如果整个stmtement都不包含表名,则将请求发送至上一条SQL所发送的server;
-
observer会根据执行计划的类型,来告诉proxy是否将请求路由至正确的server,如果路由失败,proxy会更新location
- server返回第一条DML的命中情况;
OBProxy使用和运维
守护进程
-
obproxy无状态,即使宕机重启,也不会影响数据一致性,所以OBProxy在部署时都带有一个守护进程,周期性检查OBProxy的健康程度,一旦发现宕机就立即重启OBProxy;
-
OBProxy手动启动和检查过程
-
登录OBProxy所在的宿主主机,使用admin用户在命令行工具中运行以下启动守护进程,守护进程会自动拉起OBProxy进程
启动守护启动 /opt/taobao/install/<obproxy目录>/bin/obproxyd.sh -c start -e private -n <obproxy名称> 检查进程状态 ps -ef | grep obproxy|grep '^admin'
-
OBProxy配置项
分三种类型
-
第一种时proxy写到本地etc文件夹中配置文件的配置项,这些配置项可供用户根据使用场景进行配置和更新
-
第二种时proxy内部自己使用,对一般用户不可见的配置项,不会注册到内部表中
-
第三种是proxy从config server中获取到的配置信息(包括版本号、meta table信息、cluster信息、bin url和更新时间)
这些信息只用来展示config server的配置,不会注册到内部表或者dump到本地配置文件中,并且它们全部以字符串“json_config”开头,查询时可以使用like进行过滤;
常见配置项
xflush_log_level:监控用的xflush的日志级别
syslog_level:OBProxy自己的应用日志的日志级别
observer_query_timeout_delta:关系到网络断开连接,到认为OBserver不可用的delta时间
log_cleanup_interval:清理OBProxy自身应用日志的间隔时间
log_dir_size_threshold:proxy日志大小阈值,超过阈值即可进行日志清理
inter_cmd_mem_limited:会话较多,导致buffer内存不足时需要调大
慢查询配置项
OBProxy 有自己的慢查询日志打印功能
配置项:
slow_transaction_time_threshold:指慢查询或事务整个生命周期的时间阈值,超过了该时间,就会打印;
slow_proxy_process_time_threshold:在发往Server前Proxy本身的处理时间。包括获取集群信息、路由信息、黑名单信息等;
slow_query_time_threshold:指从OBProxy获取SQL直到返回客户端之前的这段时间的法制。超过该事件,则打印;
配置项 slow_proxy_process_time_threshold默认值为 2ms
ALTER PROXYCONFIG SET slow_transaction_time_threshold='100ms';
ALTER PROXYCONFIG SET slow_proxy_process_time_threshold='5ms';
慢查询举例分析
[2016-05-24 22:39:00.824392] WARN [PROXY.SM] update_cmd_stats (ob_mysql_sm.cpp:4357) [28044][Y0-7F70BE3853F0] [14]
Slow query:
client_ip=127.0.0.1:17403 // 执行SQL client IP
server_ip=100.81.152.109:45785 // SQL被路由到的observer
conn_id=2147549270
cs_id=1
sm_id=8
cmd_size_stats=
client_request_bytes:26 // 客户端请求 SQL大小
server_request_bytes:26 // 路由到observer SQL大小
server_response_bytes:1998889110 // observer转发给obproxy数据大小
client_response_bytes:1998889110 // obproxy转发给client数据大小
cmd_time_stats=
client_transaction_idle_time_us=0 // 在事务中该条SQL与上一条SQL执行结束之间的间隔时间, 即客户端事务中SQL间隔时间
client_request_read_time_us=0 // obproxy读取客户端SQL耗时
server_request_write_time_us=0 // obproxy将客户端SQL转发给observer耗时
client_request_analyze_time_us=15 // obproxy 解析本条SQL消耗时间
cluster_resource_create_time_us=0 // 如果执行该条SQL, 需要收集OB cluster相关信息(一般发生在第一次连接到该集群的时候),建立集群相关信息耗时
pl_lookup_time_us=3158 // 查询partition location耗时
prepare_send_request_to_server_time_us=3196 // 从obproxy接受到客户端请求,到转发到observer执行前总计时间,正常应该是前面所有时间之和
server_process_request_time_us=955 // observer处理请求的时间,对于流式请求就是从observer处理数据,到第一次转发数据的时间
server_response_read_time_us=26067801 // observer转发数据到obproxy耗时,对于流式请求observer是一边处理请求,一边转发数据(包含网络上的等待时间)
client_response_write_time_us=716825 // obproxy将数据写到客户端耗时
request_total_time_us=26788969 // 处理该请求总时间
sql=select * from sbtest1 // 请求SQL
SQL相关timeout设置
ob_query_timeout(默认10s) //查询超时
ob_trx_timeout(默认100s) //事务未提交超时
ob_trx_idle_timeout(默认120s) //事务空闲超时
启动失败
- 机器是否存在hostname:输入hostname -i,确认host ip是否存在
- 目录是否存在,权限是否正确;确保当目录下有读、写、执行的权限
- 端口是否被占用:使用obproxy.sh启动OBProxy,使用端口2883
- 启动环境是否指定正确:如果通过obproxy.sh启动,需要使用-e参数指定OBProxy运行环境