最近做QoS报告,数据来源于Impala,客户端认证采用的是Kerberos。
Impala是Cloudera公司开发并开源的一款基于HDFS/Hbase的MPP SQL引擎,它提供SQL语义,能够查询存储在Hadoop的HDFS和HBase中的PB级大数据。Kerberous本身是一个网络认证授权协议,借由中心服务器认证,对通信双方的客户端/服务端进行授权而不需要传递双方的密码。Kerberos的认证流程比较有意思,分为三个阶段:
- 客户端认证
- 1 客户端发送自己用户名
- 2 认证服务器返回使用客户端密钥加密的Client/TGS会话密钥和使用票据授权服务器密钥加密的TGT, 包括sessions key,用户信息及有效期
- 3 客户端使用自己的密钥解密出Client/TGS会话密钥
- 服务授权
- 1 客户端发送两条消息:接收到的TGT和所请求的服务ID;使用Client/TGS会话密钥加密的用户ID和时间戳
- 2 票据授权服务器使用自己的密钥解密TGT得到客户端的Client/TGS会话密钥,然后使用它解密出用户ID并进行认证。返回使用所请求服务端密钥加密的client-server票据和使用Client/TGS会话密钥加密的Client/Server会话密钥
- 3 客户端使用Client/TGS会话密钥(Client/TGS Session Key)解密出Client/Server会话密钥
- 服务请求
- 1 客户端发送两条消息:使用所请求服务端密钥加密的client-server票据及使用Client/Server会话密钥加密的用户ID和时间戳
- 2 服务端使用自己的密钥解密client-server票据从而得到Client/Server会话密钥,使用该密钥解密获得用户信息并认证。返回使用Client/Server会话密钥的新时间戳
- 3 客户端使用Client/Server会话密钥解密该消息,认证结束并请求服务
- 4 服务端提供服务
在CentOS上安装Kerberos
1 | yum install krb5-devel pam_krb5 krb5-libs krb5-workstation |
编辑配置
1 | vim /etc/krb5 .conf |
配置KDC,认证服务器
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 | [logging] default = FILE: /var/log/krb5libs .log kdc = FILE: /var/log/krb5kdc .log admin_server = FILE: /var/log/kadmind .log [libdefaults] default_realm = EXAMPLE.COM dns_lookup_realm = false dns_lookup_kdc = true ticket_lifetime = 24h renew_lifetime = 7d forwardable = true default_tkt_enctypes = rc4-hmac default_tgs_enctypes = rc4-hmac permitted_enctypes = rc4-hmac [realms] EXAMPLE.COM = { default_domain = example.com kdc = kdc01.example.com kdc = kdc02.example.com admin_server = adc01.example.com admin_server = adc02.example.com } [domain_realm] .example.com = EXAMPLE.COM example.com = EXAMPLE.COM |
测试一下
1 2 | [root@localhost rc] # kinit abc.xyz@EXAMPLE.COM Password for abc.xyz@EXAMPLE.COM: |
注意这个配置文件每行前面的空格被删掉,是因为在VirtualBox里面每行开头有莫名其妙的乱码,Linux下并不可见,在EditPlus下面才发现,否则会乱报错
1 2 | kinit: Improper format of Kerberos configuration file while initializing Kerberos 5 library kinit: Cannot find KDC for realm "EXAMPLE.COM" while getting initial credentials |
查看一下认证的ticket
1 2 3 4 5 6 7 | [root@localhost vagrant] # klist Ticket cache: FILE: /tmp/krb5cc_0 Default principal: abc.xyz@EXAMPLE.COM Valid starting Expires Service principal 09 /21/2017 08:30:50 09 /21/2017 18:30:50 krbtgt /EXAMPLE .COM@EXAMPLE.COM renew until 09 /28/2017 08:30:42 |
这个ticket在28号就会过期了,到时候又要输入密码,这样也不便于自动化程序使用。可以使用ktutil创建keytab文件
1 2 3 4 5 6 7 | $ ktutil ktutil: addent -password -p abc.xyz@EXAMPLE.COM -k 1 -e RC4-HMAC Password for abc.xyz@EXAMPLE.COM: ktutil: wkt abc.xyz.keytab ktutil: q $ ls abc.xyz.keytab |
测试一下
1 2 3 4 5 6 | $ kinit -kt abc.xyz.keytab abc.xyz@EXAMPLE.COM $ klist -k abc.xyz.keytab Keytab name: FILE:abc.xyz.keytab KVNO Principal ---- -------------------------------------------------------------------------- 1 abc.xyz@EXAMPLE.COM |
之后便可以使用kinit自动更新ticket了。注意,如果更换了密码,需要重新生成新的keytab。
另外,相同用户生成的授权ticket在任意一台机器上都是相同的, kinit时会自动同步回来的。
公司的大数据平台使用Hue来提供基于web界面的查询,Impala也支持使用ODBC方式查询。在Python里使用的是impyla来查询,首先安装sasl的依赖
1 2 | yum install libgsasl-devel cyrus-sasl-devel cyrus-sasl-gssapi pip install impyla thrift_sasl |
测试脚本
1 2 3 4 5 | from impala.dbapi import connect conn = connect(host = "impalad.example.com" , port = 21050 , auth_mechanism = 'GSSAPI' , kerberos_service_name = 'impala' , database = 'acme' ) cur = conn.cursor() cur.execute(r 'SELECT * FROM acme WHERE dt="2017-09-12" LIMIT 5' ) print (cur.fetchall()) |
运行下
1 | python test .py |
如下报错,则是服务器不能连接,检查一下网络,DNS/hosts及VPN
1 | thriftpy.transport.TTransportException: TTransportException( type =1, message= "Could not connect to ('impalad.example.com', 21050)" ) |
如下报错,CentOS则是需要cyrus-sasl-gssapi模块
1 | thriftpy.transport.TTransportException: TTransportException( type =1, message= "Could not start SASL: b'Error in sasl_client_start (-4) SASL(-4): no mechanism available: No worthy mechs found'" ) |
参考链接:
Impala:新一代开源大数据分析引擎
大数据时代快速SQL引擎-Impala
CDH 5.2中Impala认证集成LDAP和Kerberos
Kerberos
Configuring Kerberos Authentication for Windows
Speaking Kerberos with KNIME Big Data Extensions