RADOS插件¶
自uWSGI 1.9.16起可用,自uWSGI 2.0.6起稳定
官方modifier1: 28
作者:Javier Guerra, Marcin Deranek, Roberto De Ioris, Sokolov Yura 又名funny_falcon
‘rados’插件让你可以使用librados API,直接提供存储在一个Ceph集群中的对象。
注意,不是CephFS文件系统,也不是’radosgw’ S3/Swift兼容层;RADOS是裸对象存储层。
第1步:Ceph集群和内容¶
如果你想尝试最小Ceph安装,那么你可以遵循这个指导:http://ceph.com/docs/master/start/。注意,你只需要OSD和MON守护进程,MDS只在CephFS文件系统的时候是必须的。
一旦运行了它,你应该有一个配置文件 (默认在/etc/ceph/ceph.con上),并且应该能够使用 rados 功能。
rados lspools
默认情况下,你应该至少拥有’data’, ‘metadata’和’rbd’池。现在添加一些内容到’data’池。例如,如果你有一个’list.html’文件和子目录’imgs/’下的图片’first.jpeg’, ‘second.jpeg’:
rados -p data put list.html list.html
rados -p data put imgs/first.jpeg imgs/first.jpeg
rados -p data put imgs/second.jpeg imgs/second.jpeg
rados -p data ls -
注意,RADOS没有目录的概念,但是对象名可以包含斜线。
第2步:uWSGI¶
有一个名为’rados’的构建配置文件可以用,因此你可以简单这样做:
make PROFILE=rados
或者
python uwsgiconfig.py --build rados
或者使用安装程序
# this will create a binary called /tmp/radosuwsgi that you will use instead of 'uwsgi'
curl http://uwsgi.it/install | bash -s rados /tmp/radosuwsgi
显然,你可以将rados支持当成插件构建
uwsgi --build-plugin plugins/rados/
或者旧式的:
python uwsgiconfig.py --plugin plugins/rados/
现在,你可以启动一个HTTP服务器来提供RADOS对象服务了:
[uwsgi]
; bind on port 9090
http-socket = :9090
; set the default modifier1 to the rados one
http-socket-modifier1 = 28
; mount our rados pool
rados-mount = mountpoint=/rad/,pool=data,config=/etc/ceph/ceph.conf
; spawn 30 threads
threads = 30
‘rados-mount’参数接收多个子参数:
- mountpoint: 必需,RADOS对象将会出现的URL前缀。
- pool: 必需,提供服务的RADOS池。
- config: 可选,ceph配置文件的路径。
- timeout: 可选,设置操作的超时时间,以秒为单位
- allow_put: 允许调用
PUT
HTTP方法来存储新的对象- allow_delete: 允许调用
DELETE
HTTP方法来移除对象- allow_mkcol: 允许调用
MKCOL
HTTP方法来创建新的池- allow_propfind: (要求版本uWSGI 2.1) 允许调用WebDAV
PROPFIND
方法- buffer_size:
GET
请求的最大缓冲大小,以字节为单位 (最小8192,最大的16777216,默认是131072)- put_buffer_size:
PUT
请求的最大缓冲大小 (默认为buffer_size)
在这个例子中,你的内容地址将会是http://localhost:9090/rad/list.html, http://localhost:9090/rad/imgs/first.jpeg和http://localhost:9090/rad/imgs/second.jpeg。
高可用性¶
RADOS存储系统是全分布的,只要使用相同的’ceph.conf’,在多个机器上启动几个uWSGI worker,那么所有的worker都能看到同一个池。如果它们都在相同的挂载点上提供服务,那么你会得到一个抗故障的RADOS-HTTP网关。
多挂载点¶
你可以声明多个’rados-mount’项,每一个会定义一个新的挂载点。通过这种方式,你可以在不同的URL上公开不同的RADOS池。
HTTP方法¶
支持以下方法:
- GET -> 检索资源
- HEAD -> 和GET一样,但是没有请求体
- OPTIONS -> (要求版本uWSGI 2.1) 返回允许的HTTP方法和WebDAV支持的列表
- PUT -> 要求mountpoint选项中有allow_put,存储资源到ceph:curl -T /etc/services http://localhost:8080/services
- MKCOL -> 要求mountpoint选项中有allow_mkcol,创建一个新的池:curl -X MKCOL http://localhost:8080/anewpool (将会创建池’anewpool’)
- DELETE -> 要求mountpoint选项中有allow_delete,移除一个对象
- PROPFIND -> 要求mountpoint选项中有allow_propfind (uWSGI 2.1+),实现WebDAV PROPFIND方法
特性¶
- 支持多进程
- 异步支持功能齐全,ugreen挂起引擎是唯一支持的引擎:
[uwsgi]
; bind on port 9090
http-socket = :9090
; set the default modifier1 to the rados one
http-socket-modifier1 = 28
; mount our rados pool
rados-mount = mountpoint=/rad/,pool=data,config=/etc/ceph/ceph.conf
; spawn 1000 async cores
async = 1000
; required !!!
ugreen = true
缓存样例¶
强烈建议使用缓存来改进性能和减少Ceph集群上的负载。这是一个好例子:
[uwsgi]
; create a bitmap cache with max 1000 items storable in 10000 4k blocks
cache2 = name=radoscache,items=1000,blocks=10000,blocksize=4096,bitmap=1
; check every object ending with .html in the 'radoscache' cache
route = \.html$ cache:key=${PATH_INFO},name=radoscache,content_type=text/html
; if not found, store it at the end of the request for 3600 seconds (this will automatically enable Expires header)
route = \.html$ cachestore:key=${PATH_INFO},name=radoscache,expires=3600
; general options
; master is always a good idea
master = true
; bind on http port 9090 (better to use a uwsgi socket behind a proxy like nginx)
http-socket = :9090
; set the default modifier1 to the rados one
http-socket-modifier1 = 28
; mount our rados 'htmlpages' pool
rados-mount = mountpoint=/,pool=htmlpages
; spawn multiple processes and threads
processes = 4
threads = 8
要测试缓存行为,诸如uwsgicachetop (https://pypi.python.org/pypi/uwsgicachetop) 这样的工具将非常有用。
更多关于缓存的信息在这里: CachingCookbook
安全注意事项¶
启用MKCOL, PUT和DELETE可能会有很高的安全风险。
将它们与内部路由框架结合,以添加鉴权/认证策略:
[uwsgi]
master = true
; bind on http port 9090 (better to use a uwsgi socket behind a proxy like nginx)
http-socket = :9090
; set the default modifier1 to the rados one
http-socket-modifier1 = 28
; mount our rados 'htmlpages' pool
rados-mount = mountpoint=/,pool=htmlpages,allow_put=1,allow_mkcol=1
; spawn multiple processes and threads
processes = 4
threads = 8
; permit PUT only to authenticated 'foo' user
route-if = equal:${REQUEST_METHOD};PUT basicauth:my secret area,foo:bar
; allow MKCOL only from 127.0.0.1
route-if = equal:${REQUEST_METHOD};MKCOL goto:check_localhost
; end of the chain
route-run = last:
route-label = check_localhost
; if REMOTE_ADDR = 127.0.0.1 -> continue to rados plugin
route-remote-addr = ^127\.0\.0\.1$ continue:
; otherwise break with 403
route-run = break:403 Forbidden
注意事项¶
- 这个插件自动启用MIME type引擎。
- 无目录索引支持。在rados/ceph上下文中,它并无意义。
- 你应该在你的uWSGI实例中移除特权,因此,确保你把正确的权限给予了ceph keyring。
- 如果你用它来获取/存储大对象,那么考虑提高
buffer_size
。4194304是个非常高性能的值,如果你想节约内存,那么1048576也不错。 - 支持放入Erasure编码的池。会自动调整
put_buffer_size
来满足池对齐要求。