设为首页 收藏本站
查看: 1767|回复: 0

[经验分享] Apache Ranger对HDFS的访问权限控制的原理分析(一)

[复制链接]

尚未签到

发表于 2017-12-24 07:52:47 | 显示全部楼层 |阅读模式
介绍
  Aapche Ranger是以插件的形式集成到HDFS中,由Ranger Admin管理访问策略,Ranger插件定期轮询Admin更新策略到本地,并根据策略信息进行用户访问权限的判定。其中提供管理员管理策略、插件的Ranger web和Ranger Plugin,与Admin之间的通信是基于HTTP的RESTful架构。Ranger集成HDFS的架构图如下:

DSC0000.png

Ranger对HDFS访问控制的实现原理
  HDFS本身是有访问控制机制的,即在身份认证机制之后通过查询ACLs来对用户的权限检查,该权限检查的实现代码是INodeAttributeProvider抽象类中接口AccessControlEnforcer的checkPermission方法。Ranger将HDFS NameNode 的Inode attribute的提供类即INodeAttributeProvider抽象类修改为Ranger自己写的类,该类继承了INodeAttributeProvider抽象类。即在hdfs-site.xml文件中修改如下配置项。
  

<name>dfs.namenode.inode.attributes.provider.class</name>  
<value>org.apache.ranger.authorization.hadoop.RangerHdfsAuthorizer</value>
  


Ranger 插件的初始化过程

动态加载类
  在Namenode启动过程中编译RangerHdfsAuthorizerorizer类(包名为ranger-hdfs-plugin-shim),将RangerHdfs的相关类动态加载进虚拟机,并实例化具体实现类RangerHdfsAuthorizerorizer(包名为ranger-hdfs-plugin)。
  

rangerPluginClassLoader = RangerPluginClassLoader.getInstance(RANGER_PLUGIN_TYPE, this.getClass());  

    @SuppressWarnings("unchecked")  

   >
    activatePluginClassLoader();  

    rangerHdfsAuthorizerImpl = cls.newInstance();       


插件初始化
DSC0001.png

  初始化RangerPlugin,如上面的类图可知,RangerHdfsPlugin是RangerBasePlugin类的子类,其具体的初始化是由父类的初始化方法来实现的。该方法主要完成了以下几个功能:
  (1)调用cleanup()方法,主要完成清空了refresher、serviceName、policyEngine这三个变量的值。
  (2)读取配置文件,并设置以下变量的初始值。


  • serviceType:Ranger提供访问控制服务的类型。
  • serviceName:Ranger提供访问控制服务的名称。
  • appId:由Ranger提供服务的组件ID。
  • propertyPrefix:Ranger插件的属性前缀。
  • pollingIntervalMs:刷新器定期更新策略的轮询间隔时间。Ranger 插件会定期从Ranger Admin拉取新的策略信息,并保存在Hdfs缓存中。
  • cacheDir:从Ranger Admin拉取策略到Hdfs插件的临时存放目录。
  (3)设置PangerPolicyEngineOptions类的成员变量值。


  • evaluatorType:评估器的类型。在Ranger对Hdfs的访问权限的鉴权阶段需要策略评估器根据策略判断是否具有访问权限。
  • cacheAuditResults:是否缓存审计。
  • disableContextEnrichers:是否使用上下文增强器。
  • disableCustomConditions:是否使用自定义条件。在Ranger0.5版本之后加入上下文增强器和用户自定义条件这样的“钩子”函数以增加授权策略的可扩展性。
  • disableTagPolicyEvaluation:是否使用基于标签的策略评估。在Ranger0.6版本以后,Ranger不仅仅支持基于资源的策略,还支持基于标签的策略,该策略的优点是资源分类与访问授权的分离,标记的单个授权策略可用于授权跨各种Hadoop组件访问资源。
  (4)调用createAdminClient(),创建RangerAdmin与RangerPlugin通信的客户端。这里使用的基于RESTful的通信风格,所以创建RangerAdminClient类的实例对象。
  (5)创建PolicyRefresher类的对象,调用startRefresher()开启策略刷新器,根据轮询间隔时间定期从Ranger Admin 拉取更新的策略。

策略更新
  Ranger插件更新策略的流程图如下:
DSC0002.png

  这部分主要讲Ranger插件如何通过调用Ranger定义好的API获取策略。这里使用了jersey来构建RESTful服务。

(1)Jersey客户端的实现
  RangerAdminRESTClient # getServicePoliciesIfUpdated()
  

if (isSecureMode) {  

    PrivilegedAction<ClientResponse> action = new PrivilegedAction<ClientResponse>() {  

       public ClientResponse run() {  

// 创建WebResource实例,并根据URI和查询参数(lastKnownVersion、pluginId)构建URL  
          WebResource secureWebResource = createWebResource(RangerRESTUtils.REST_URL_POLICY_GET_FOR_SECURE_SERVICE_IF_UPDATED + serviceName)
  
                               .queryParam(RangerRESTUtils.REST_PARAM_LAST_KNOWN_POLICY_VERSION, Long.toString(lastKnownVersion))
  
                               .queryParam(RangerRESTUtils.REST_PARAM_PLUGIN_ID, pluginId);
  
// 发送GET请求,并且mime类型为Json
  
          return secureWebResource.accept(RangerRESTUtils.REST_MIME_TYPE_JSON).get(ClientResponse.class);
  
       };
  
    };         
  
    response = user.doAs(action);
  
}else{
  
    WebResource webResource = createWebResource(RangerRESTUtils.REST_URL_POLICY_GET_FOR_SERVICE_IF_UPDATED + serviceName)
  
                                                                               .queryParam(RangerRESTUtils.REST_PARAM_LAST_KNOWN_POLICY_VERSION, Long.toString(lastKnownVersion))
  
                                                                               .queryParam(RangerRESTUtils.REST_PARAM_PLUGIN_ID, pluginId);
  
    response = webResource.accept(RangerRESTUtils.REST_MIME_TYPE_JSON).get(ClientResponse.class);
  
}
  
if(response != null && response.getStatus() == 200) {  //200:请求成功
  
    ret = response.getEntity(ServicePolicies.class);
  
} else if(response != null && response.getStatus() == 304) { // 304:未修正
  
    // no change
  
}
  

  在RangerRESTUtils类中定义了参数的值:
  

public static final String REST_URL_POLICY_GET_FOR_SERVICE_IF_UPDATED = "/service/plugins/policies/download/";  

public static final String SERVICE_NAME_PARAM = "serviceName";  

public static final String LAST_KNOWN_TAG_VERSION_PARAM = "lastKnownVersion";  

public static final String REST_MIME_TYPE_JSON     = "application/json" ;  


(2)服务端的实现
  ServiceREST # getServicePolicesIfUpdate()
  

@GET  

@Path("/policies/download/{serviceName}")  

@Produces({ "application/json", "application/xml" })  

public ServicePolicies getServicePoliciesIfUpdated(@PathParam("serviceName") String serviceName, @QueryParam("lastKnownVersion") Long lastKnownVersion, @QueryParam("pluginId") String pluginId, @Context HttpServletRequest request) throws Exception {  

    ServicePolicies ret      = null;  

    int             httpCode = HttpServletResponse.SC_OK;  

    String          logMsg   = null;  

    RangerPerfTracer perf    = null;  

  
    if (serviceUtil.isValidateHttpsAuthentication(serviceName, request)) {
  
       if(lastKnownVersion == null) {
  
          lastKnownVersion = Long.valueOf(-1);
  
       }
  
       try {
  
          ServicePolicies servicePolicies = svcStore.getServicePoliciesIfUpdated(serviceName, lastKnownVersion); // 从数据库获取更新策略的过程
  
          if(servicePolicies == null) {
  
             httpCode = HttpServletResponse.SC_NOT_MODIFIED;
  
             logMsg   = "No change since last update";
  
          } else {
  
             ret = filterServicePolicies(servicePolicies);
  
             httpCode = HttpServletResponse.SC_OK;
  
             logMsg   = "Returning " + (ret.getPolicies() != null ? ret.getPolicies().size() : 0) + " policies. Policy version=" + ret.getPolicyVersion();
  
          }
  
       }
  
     }
  
    return ret;
  
}
  

运维网声明 1、欢迎大家加入本站运维交流群:群②:261659950 群⑤:202807635 群⑦870801961 群⑧679858003
2、本站所有主题由该帖子作者发表,该帖子作者与运维网享有帖子相关版权
3、所有作品的著作权均归原作者享有,请您和我们一样尊重他人的著作权等合法权益。如果您对作品感到满意,请购买正版
4、禁止制作、复制、发布和传播具有反动、淫秽、色情、暴力、凶杀等内容的信息,一经发现立即删除。若您因此触犯法律,一切后果自负,我们对此不承担任何责任
5、所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其内容的准确性、可靠性、正当性、安全性、合法性等负责,亦不承担任何法律责任
6、所有作品仅供您个人学习、研究或欣赏,不得用于商业或者其他用途,否则,一切后果均由您自己承担,我们对此不承担任何法律责任
7、如涉及侵犯版权等问题,请您及时通知我们,我们将立即采取措施予以解决
8、联系人Email:admin@iyunv.com 网址:www.yunweiku.com

所有资源均系网友上传或者通过网络收集,我们仅提供一个展示、介绍、观摩学习的平台,我们不对其承担任何法律责任,如涉及侵犯版权等问题,请您及时通知我们,我们将立即处理,联系人Email:kefu@iyunv.com,QQ:1061981298 本贴地址:https://www.yunweiku.com/thread-427429-1-1.html 上篇帖子: Apache CXF 入门详解 下篇帖子: python配置apache的web服务器方法(python的CGI配置)
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

扫码加入运维网微信交流群X

扫码加入运维网微信交流群

扫描二维码加入运维网微信交流群,最新一手资源尽在官方微信交流群!快快加入我们吧...

扫描微信二维码查看详情

客服E-mail:kefu@iyunv.com 客服QQ:1061981298


QQ群⑦:运维网交流群⑦ QQ群⑧:运维网交流群⑧ k8s群:运维网kubernetes交流群


提醒:禁止发布任何违反国家法律、法规的言论与图片等内容;本站内容均来自个人观点与网络等信息,非本站认同之观点.


本站大部分资源是网友从网上搜集分享而来,其版权均归原作者及其网站所有,我们尊重他人的合法权益,如有内容侵犯您的合法权益,请及时与我们联系进行核实删除!



合作伙伴: 青云cloud

快速回复 返回顶部 返回列表