为了从独立的Flink安装访问安全的HDFS或HBase安装,您必须执行以下操作:
我有一个独立的Flink安装,在上面要运行将数据写入HDFS安装的流作业。 HDFS安装是Cloudera部署的一部分,并且需要Kerberos身份验证才能读取和写入HDFS。由于我没有找到有关如何使Flink与受Kerberos保护的HDFS连接的文档,因此我不得不对该过程进行一些有根据的猜测。这是我到目前为止所做的:
在我的Flink工作中,添加了以下代码:
UserGroupInformation.loginUserFromKeytab("myusername", "/path/to/keytab");
最后我正在使用TextOutputFormat
将数据写入HDFS。
[当我执行工作时,出现以下错误:
org.apache.hadoop.security.AccessControlException: SIMPLE authentication is not enabled. Available:[TOKEN, KERBE
ROS]
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:422)
at org.apache.hadoop.ipc.RemoteException.instantiateException(RemoteException.java:106)
at org.apache.hadoop.ipc.RemoteException.unwrapRemoteException(RemoteException.java:73)
at org.apache.hadoop.hdfs.DFSOutputStream.newStreamForCreate(DFSOutputStream.java:1730)
at org.apache.hadoop.hdfs.DFSClient.create(DFSClient.java:1668)
at org.apache.hadoop.hdfs.DFSClient.create(DFSClient.java:1593)
at org.apache.hadoop.hdfs.DistributedFileSystem$6.doCall(DistributedFileSystem.java:397)
at org.apache.hadoop.hdfs.DistributedFileSystem$6.doCall(DistributedFileSystem.java:393)
at org.apache.hadoop.fs.FileSystemLinkResolver.resolve(FileSystemLinkResolver.java:81)
at org.apache.hadoop.hdfs.DistributedFileSystem.create(DistributedFileSystem.java:393)
at org.apache.hadoop.hdfs.DistributedFileSystem.create(DistributedFileSystem.java:337)
at org.apache.hadoop.fs.FileSystem.create(FileSystem.java:908)
at org.apache.hadoop.fs.FileSystem.create(FileSystem.java:889)
at org.apache.hadoop.fs.FileSystem.create(FileSystem.java:786)
at org.apache.flink.runtime.fs.hdfs.HadoopFileSystem.create(HadoopFileSystem.java:405)
[出于某种奇怪的原因,即使我叫loginUserFromKeytab
,Flink似乎也尝试使用简单身份验证。我在Stackoverflow(Error with Kerberos authentication when executing Flink example code on YARN cluster (Cloudera))上发现了另一个类似的问题,该问题的答案解释为:
独立Flink当前仅在所有工作节点上都通过了用户验证时才支持访问受Kerberos保护的HDFS。
这可能意味着我必须在操作系统级别进行一些身份验证,例如用kinit
。由于我对Kerberos的了解非常有限,所以我不知道该怎么做。我也想了解在没有任何配置的情况下,kinit
之后运行的程序实际上如何知道从本地缓存中选择哪个Kerberos票证。
我不是Flink用户,但根据我在Spark和朋友中看到的情况,我的猜测是“在所有工作程序节点上均经过身份验证]表示每个工作程序进程具有
a core-site.xml
配置在本地fs上可用hadoop.security.authentication
设置为kerberos
(以及其他事物]
包含core-site.xml
的本地目录添加到CLASSPATH中,以便由Hadoop Configuration
对象自动找到它。[它将以静默方式恢复为默认的硬编码值,否则,duh]
kinit
的隐式身份验证和默认缓存[为Linux帐户全局设置的TGT,会影响所有进程,du]kinit
的##或##隐式身份验证以及通过设置的“专用”缓存KRB5CCNAME环境变量(Hadoop仅支持通过UserGroupInformation.loginUserFromKeytab()
和本地fs上可用的密钥表进行的##或##显式身份验证)>该UGI“登录”方法非常冗长,因此,如果在Flink尝试从Configuration
启动HDFS客户端之前确实调用了该方法,您会注意到。另一方面,如果看不到冗长的内容,则Flink会绕过创建私有Kerberos TGT的尝试,您必须找到一种绕过Flink :-/
为了从独立的Flink安装访问安全的HDFS或HBase安装,您必须执行以下操作:
kinit
针对Kerberos进行身份验证,然后启动JobManager(无需注销或在两者之间切换用户。)>kinit
进行身份验证并启动TaskManager(同样,使用同一用户)。kinit
登录到Kerberos,然后以/bin/flink run
启动您的作业。据我所知,kinit
正在登录当前用户,并在/tmp
中的某个位置创建带有一些登录数据的文件。首次登录时,大多数静态类UserGroupInformation
正在使用登录数据查找该文件。如果当前用户已通过Kerberos认证,则该信息将用于根据HDFS进行认证。
您还可以将独立群集配置为自己进行身份验证,而无需在作业中添加其他代码。
HADOOP_CONF_DIR
并将其指向core-site.xml
和hdfs-site.xml
所在的目录flink-conf.yml
security.kerberos.login.use-ticket-cache: false security.kerberos.login.keytab: <path to keytab> security.kerberos.login.principal: <principal> env.java.opts: -Djava.security.krb5.conf=<path to krb5 conf>
- 将预先捆绑的Hadoop添加到群集
lib
的https://flink.apache.org/downloads.html目录中>您在工作中唯一需要的依赖项是:
compile "org.apache.flink:flink-java:$flinkVersion" compile "org.apache.flink:flink-clients_2.11:$flinkVersion" compile 'org.apache.hadoop:hadoop-hdfs:$hadoopVersion' compile 'org.apache.hadoop:hadoop-client:$hadoopVersion'
为了从独立的Flink安装访问安全的HDFS或HBase安装,您必须执行以下操作:
您还可以将独立群集配置为自己进行身份验证,而无需在作业中添加其他代码。
HADOOP_CONF_DIR
并将其指向core-site.xml
和hdfs-site.xml
所在的目录