Hadoop浅解Centralized Cache Management(集中式缓存管理)

来源:互联网 发布:union类似软件 编辑:程序博客网 时间:2024/05/24 01:43

HDFS集中式缓存管理

概观

HDFS的集中化缓存管理是一个明确的缓存机制,它可以将用户指定的HDFS路径进行缓存。NameNode会和保存着所需快数据的所有DataNode进行通信,并指导他们把块数据缓存在off-heap缓存中。

HDFS上的集中式缓存管理具有明显的优势:
1. 明确的锁定可以阻止频繁使用的数据被从内存中清除。当数据集的大小超过了主内存大小(这种情况对于许多HDFS负载都是司空见惯的)时,这一点尤为重要。
2. 由于DataNode缓存是由NameNode管理的,所以,在确定任务分发位置时,应用程序可以快速查询所需数据缓存块位置。把任务和缓存块副本放在一个位置上可以提高读操作的性能。
3. 当块已经被DataNode缓存时,客户端就可以使用一个新的更高效的零拷贝读操作API。因为缓存数据的checksum校验只需由DataNode执行一次,所以,使用这种新API时,客户端基本上不会有开销。
4. 集中缓存可以提高整个集群的内存使用率。当依赖于每个DataNode上操作系统的缓存时,重复读取一个块数据会导致该块的N个副本全部被送入buffer缓存。使用集中化缓存管理,用户就能明确地只锁定这N个副本中的M个了,从而节省了N-M的内存量。

使用场景

集中化缓存管理对于重复访问的文件很有用。例如,Hive中的一个较小的fact表(常常用于joins操作)就是一个很好的缓存对象。另一方面,对于一个全年报表查询的输入数据做缓存很可能就没有多大作用了,因为,历史数据只会读取一次。

集中化缓存管理对于带有性能SLA的混合负载也很有用。缓存正在使用的高优先级负载可以保证它不会和低优先级负载竞争磁盘I/O。

架构

这里写图片描述

在这个架构中,NameNode负责协调集群中所有DataNode的off-heap缓存。NameNode周期性地接收来自每个DataNode上的缓存报告(其中记录DataNode的所有的缓存块的信息)。NameNode通过借助DataNode心跳上的缓存和非缓存命令来管理DataNode缓存。

NameNode查询自身的缓存指令集来确定应该缓存那个路径。缓存指令永远存储在fsimage和edit日志中,而且可以通过Java和命令行API被添加、移除或修改。NameNode还存储了一组缓存池,它们是用于把资源管理类和强制权限类的缓存指令进行分组的管理实体。

NameNode周期性地重复扫描命名空间和活跃的缓存指定以确定需要缓存或不缓存哪个块,并向DataNode分配缓存任务。重复扫描也可以又用户动作来触发,比如,添加或删除一条缓存指令,或者删除一个缓存池。

当前,我们不支持缓存construction、corrupt下的块数据,或者别的不完整的块。如果一条缓存指令包含一个symlink,那么该symlink目标不会被缓存。

当前,我们只实现了文件或目录级的缓存。块和子块缓存是未来的目标。

概念

缓存指令

一条缓存指令定义了一个要被缓存的路径(path)。这些路径(path)可以是文件夹或文件。文件夹是以非迭代方式缓存的,只有在文件夹顶层列出的文件才会被缓存。

文件夹也可以指定额外的参数,比如缓存副本因子,有效期等。副本因子指定了要缓存的块副本数。如果多个缓存指令指向同一个文件,那么就用最大缓存副本因子。

有效期是在命令行指定的,就像TTL一样,相对有效期会在未来版本引入。缓存指令过期之后,在决定缓存时,它就不再被NameNode考虑了。

缓存池

缓存池是一个管理实体,用于管理缓存指令分组。缓存池拥有类UNIX的权限,可以限制哪个用户和组可以访问该缓存池。写权限允许用户向缓存池添加或从中删除缓存指令 。读权限允许用户列出缓存池内的缓存指令和其他元数据。执行权限并没有什么作用。

缓存池也可以用于资源管理。它可以强加一个最大限制值,可以限制通过缓存池中的指令缓存的字节数。通常,缓存池限制值之和约等于为HDFS在集群中做缓存而保留的总内存量。缓存池也可以追踪许多统计信息以便于集群用户决定哪一个目录应该缓存。

缓存池也可以强加一个TTL最大值。该值限制了被添加到缓存池的指令的最大有效期。

缓存管理命令接口

在命令行上,管理员和用户可以使用过hdfs cacheadmin子命令借助缓存池来交互。

缓存指令由一个唯一的无重复的64位整数ID来标识。即使缓存指令后来被删除了,ID也不会重复使用。

缓存池由一个唯一的字符串名称来标识。

缓存管理命令

addDirective

hdfs cacheadmin -addDirective -path -pool [-force] [-replication ] [-ttl ]

参数 意义 要缓存的路径,该路径可以是文件夹或文件。 要加入缓存指令的缓存池。你必须对改缓存池有写权限以便添加新的缓存指令。 要使用的缓存副本因子,默认为1 缓存指令可以保持有效多长时间。可以按照分钟,小时,天来指定,如30m,4h,2d。有效单位为[smhd]。“never”表示永不过期的指令。如果未指定该值,那么,缓存指令就不会过期。 -force 不检查缓存池的资源限制

removeDirective

hdfs cacheadmin -removeDirective

参数 意义 要删除的缓存指令的ID。你必须对该指令的缓存池拥有写权限,以便删除它。要查看详细的缓存指令ID列表,可以使用-listDirectives命令。

removeDirectives

hdfs cacheadmin -removeDirectives

要删除的缓存指令的路径。你必须对该指令的缓存池拥有写权限,以便删除它。要查看详细的缓存指令列表,可以使用-listDirectives命令

listDirectives

hdfs cacheadmin -listDirectives [-stats] [-path ] [-pool ]

参数 意义 只列出带有该路径的缓存指令。注意,如果路径path在缓存池中有一条我们没有读权限的缓存指令,那么它就不会被列出来。 只列出该缓存池内的缓存指令。 -stats 列出基于path的缓存指令统计信息

缓存池命令

addPool

hdfs cacheadmin -addPool [-owner ] [-group ] [-mode ] [-limit ] [-maxTtl ]

参数 意义 新缓存池的名称。 该缓存池所有者的名称。默认为当前用户。 缓存池所属的组。默认为当前用户的主要组名。 以UNIX风格表示的该缓存池的权限。权限以八进制数表示,如0755.默认值为0755. 在该缓存池内由指令总计缓存的最大字节数。默认不设限制。 添加到该缓存池的指令的最大生存时间。该值以秒,分,时,天的格式来表示,如120s,30m,4h,2d。有效单位为[smhd]。默认不设最大值。“never”表示没有限制。

modifyPool

hdfs cacheadmin -modifyPool [-owner ] [-group ] [-mode ] [-limit ] [-maxTtl ]

参数 意义 要修改的缓存池的名称。 该缓存池所有者的名称。 缓存池所属的组。 以UNIX风格表示的该缓存池的权限。权限以八进制数表示,如0755.默认值为0755. 在该缓存池内由指令总计缓存的最大字节数。 添加到该缓存池的指令的最大生存时间。

removePool

hdfs cacheadmin -removePool

参数 意义 要删除的缓存池的名称。

listPools

hdfs cacheadmin -listPools [-stats] []

参数 意义 若指定,则仅列出该缓存池的信息 -stats 显示额外的缓存池统计信息

help

hdfs cacheadmin -help

参数 意义 要获得详细帮助信息的命令。如果没有指定命令,则打印所有命令的帮助信息。

配置

本地库

为了把块文件锁定在内存,DataNode需要依赖本地JNI代码(Linux系统为libhadoop.so,Windows系统为hadoop.dll)。如果你正在使用HDFS集中化缓存管理,请确保JNI可以使用。

配置属性

必选属性

参数 默认值 意义 dfs.datanode.max.locked.memory 0 这个属性决定了DataNode用于缓存的最大内存。在类UNIX系统中, the “locked-in-memory size” ulimit (ulimit -l) of the DataNode user also needs to be increased to match this parameter (see below section on OS Limits).设置这个值的时候,注意考虑DataNode和应用程序JVM堆内存、以及操作系统的页缓存。This setting is shared with the Lazy Persist Writes feature. The Data Node will ensure that the combined memory used by Lazy Persist Writes and Centralized Cache Management does not exceed the amount configured in dfs.datanode.max.locked.memory.

可选属性

参数 默认值 意义 dfs.namenode.path.based.cache.refresh.interval.ms 3000 NameNode使用该参数作为两次子路径缓存重复扫描的动作之间的时间间隔,单位为毫秒。该参数计算要缓存的块和每个DataNode包含一个该块应当缓存的副本。 dfs.datanode.fsdatasetcache.max.threads.per.volume 4 DataNode使用该参数作为缓存新数据时每个卷要用的最大线程数。 dfs.cachereport.intervalMsec 10000 DataNode使用该参数作为两次发送缓存状态报告给NameNode的动作之间的时间 dfs.namenode.path.based.cache.block.map.allocation.percent 0.25 分配给已缓存块映射的Java堆内存的百分比。它是hash map,使用链式hash。如果缓存块的数目很大,那么map越小,访问速度越慢;map越大,消耗的内存越多。

系统设置

如果你遇到错误“Cannot start datanode because the configured max locked memory size… is more than the datanode’s available RLIMIT_MEMLOCK ulimit,”,就意味着操作系统对用户可以锁定的内存使用量强加了一个限制,该限制值比用户设置的值更低一些。要修复这个问题,必须使用“ulimit -l”命令来调整DataNode运行需要锁定的内存值。通常,该值是在/etc/security/limits.conf文件中配置的。然而,它也会因用户所用的操心系统和分发版的不同而变化。

当你从shell中运行“ulimit -l”并得到一个比你用属性dfs.datanode.max.locked.memory设置的值更高的值,或者字符串“ulimited”(表示没有限制)时,你就会明白你已经正确配置了该值。值得注意的是,ulimit -l命令通常以KB为单位输出内存锁定限制值,但是dfs.datanode.max.locked.memory的值必须以字节为单位。

这些信息不适用于Windows环境部署。Windows没有和“ulimit -l”相对应的命令。

官方原文

0 0
原创粉丝点击