深入云存储系统Swift存储节点存储实现分析.docx_第1页
深入云存储系统Swift存储节点存储实现分析.docx_第2页
深入云存储系统Swift存储节点存储实现分析.docx_第3页
深入云存储系统Swift存储节点存储实现分析.docx_第4页
深入云存储系统Swift存储节点存储实现分析.docx_第5页
已阅读5页,还剩8页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

在深入云存储系统Swift核心组件:Ring实现原理剖析和深入云存储系统Swift核心组件:Ring数据结构及构建、重平衡操作两篇博文中,我们详细地分析了Swift中数据的映射机制和具体操作。那么在集群中的每一台存储节点上,Swift是如何实现Account、Container、Object的具体存储呢?本篇旨在分析Storage node与partition,partition与data间的映射关系在实际存储目录中的以何种格式存储,即怎么存,存什么。 在Storage node上运行着Linux系统并使用了XFS文件系统,逻辑上使用一致性哈希算法将固定总数的partition映射到每个Storage node上,每个Data也使用同样的哈希算法映射到Partition上,其层次结构如下图所示:Figure1:Stoage node hierachy以我们的一台storage node sws51为例,该device的文件路径挂载到/srv/node/sdc,目录结构如下所示:rootsws51:/srv/node/sdc# lsaccounts async_pending containers objects quarantined tmp其中accounts、containers、objects分别是账号、容器、对象的存储目录,async_pending是异步待更新目录,quarantined是隔离目录,tmp是临时目录。1.objects目录在objects目录下存放的是各个partition目录,其中每个partition目录是由若干个suffix_path名的目录和一个hashes.pkl文件组成,suffix_path目录下是由object的hash_path名构成的目录,在hash_path目录下存放了关于object的数据和元数据,object存储目录的层次结构如图2所示。Figure2: Object directory hierachyhashes.pkl是存放在每个partition中的一个2进制pickle化文件。例如:rootsws50:/srv/node/sdc/objects/100000# ls8bd hashes.pklIn 1: with open(hashes.pkl, rb) as fp: .: import pickle .: hashes = pickle.load(fp) .: .:In 2: hashesOut2: 8bd: 9e99c8eedaa3197a63f685dd92a5b4b88bd是suffix_dir,而9e99c8eedaa3197a63f685dd92a5b4b8则是该partition下数据的md5哈希值。Object path生成过程object的存储路径由object server进程内部称为DiskFile类初始化时产生,过程如下:1.由文件所属的account、container和object名称产生/account/container/object格式的字符串,和HASH_PATH_SUFFIX组成新的字符串,调用hash_path函数,生成md5 hash值name_hash。其中HASH_PATH_SUFFIX作为salt来增加安全性,HASH_PATH_SUFFIX值存放在/etc/swift/swift.conf中。2.调用storage_directory函数,传入DATADIR, partition, hash_path参数生成DATADIR/partition/name_path-3:/name_path格式字符串3.连结path/devcie/storage_directory(DATADIR, partition,name_ hash)生成数据存储路径datadir4.调用normalize_timestamp函数生成“16位.5位”的时间戳+扩展名的格式生成对象名称例如,某object的存储路径为:/srv/node/sdc/objects/19892/ab1/136d0ab88371e25e16663fbd2ef42ab1/1320050752.09979.data其中每个目录分别表示:Figure3: Object directory representionObject数据Object的数据存放在后缀为.data的文件中,它的metadata存放在以后缀为.meta的文件中,将被删除的Object以一个0字节后缀为.ts的文件存放。2.accounts目录在accounts目录下存放的是各个partition,而每个partition目录是由若干个suffix_path目录组成,suffix_path目录下是由account的hsh名构成的目录,在hsh目录下存放了关于account的sqlite db,account存储目录的层次结构如图4所示。Figure4: Account directory hierachyAccount path生成过程account使用AccountController类来生成path,其过程与object类似,唯一的不同之处在于,account的db命名调用hash_path(account)来生成,而不是使用时间戳的形式。例如,某account的db存储路径为:/srv/node/sdc/accounts/20443/ac8/c7a5e0f94b23b79345b6036209f9cac8/c7a5e0f94b23b79345b6036209f9cac8.dbFigure5: Object directory representionAccount db数据在account的db文件中,包含了account_stat、container、incoming_sync、outgoing_sync4张表。表account_stat是记录关于account的信息,如名称、创建时间、container数统计等等,其schema如下:CREATETABLEaccount_stat ( account TEXT, created_at TEXT, put_timestamp TEXTDEFAULT0, delete_timestamp TEXTDEFAULT0, container_count INTEGER, object_count INTEGERDEFAULT0, bytes_used INTEGERDEFAULT0, hash TEXTdefault00000000000000000000000000000000, id TEXT, status TEXTDEFAULT, status_changed_at TEXTDEFAULT0, metadata TEXTDEFAULT );account表示account名称,created_at表示创建时间,put_timestamp表示put request的时间戳,delete_timestamp表示delete request的时间戳,container_count为countainer的计数,object_count为object的计数,bytes_used表示已使用的字节数,hash表示db文件的hash值,id表示统一标识符,status表示account是否被标记为删除,status_changed_at表示状态修改时间,metadata表示account的元数据。以test账号为例,该db的表account_stat中存放了以下数据项:表container记录关于container的信息,其schema如下:CREATETABLEcontainer ( ROWID INTEGERPRIMARYKEYAUTOINCREMENT, name TEXT, put_timestamp TEXT, delete_timestamp TEXT, object_count INTEGER, bytes_used INTEGER, deleted INTEGERDEFAULT0 );CREATEINDEXix_container_deleted_nameON container (deleted, name);CREATETRIGGERcontainer_deleteAFTERDELETEONcontainerBEGINUPDATEaccount_statSETcontainer_count = container_count - (1-old.deleted), object_count = object_count -old.object_count, bytes_used = bytes_used -old.bytes_used, hash = chexor(hash,,old.put_timestamp |-|old.delete_timestamp |-|old.object_count |-|old.bytes_used);END;CREATETRIGGERcontainer_insertAFTERINSERTONcontainerBEGINUPDATEaccount_statSETcontainer_count = container_count + (1-new.deleted), object_count = object_count +new.object_count, bytes_used = bytes_used +new.bytes_used, hash = chexor(hash,,new.put_timestamp |-|new.delete_timestamp |-|new.object_count |-|new.bytes_used);END;CREATETRIGGERcontainer_updateBEFOREUPDATEONcontainerBEGINSELECTRAISE(FAIL,UPDATE not allowed; DELETE and INSERT);END;其中ROWID字段表示自增的主键,name字段表示container的名称,put_timestamp和delete_timestamp分别表示container的put和delete的时间戳,object_count表示container内的object数,bytes_used表示已使用的空间,deleted表示container是否标记为删除。账号test的account表中的数据项如下所示:表incoming_sync记录到来的同步数据项,其schema如下:CREATETABLEincoming_sync ( remote_id TEXTUNIQUE, sync_point INTEGER, updated_at TEXTDEFAULT0 );CREATETRIGGERincoming_sync_insertAFTERINSERTONincoming_syncBEGINUPDATEincoming_syncSETupdated_at = STRFTIME(%s,NOW)WHEREROWID =new.ROWID;END;CREATETRIGGERincoming_sync_updateAFTERUPDATEONincoming_syncBEGINUPDATEincoming_syncSETupdated_at = STRFTIME(%s,NOW)WHEREROWID =new.ROWID;END;remote_id字段表示远程节点的id,sync_point字段表示上一次更新所在的行位置,updated_at字段表示更新时间。账号test的表incoming_sync中的数据项如下所示:表outgoing_sync表示推送出的同步数据项,其schema如下:CREATETABLEoutgoing_sync ( remote_id TEXTUNIQUE, sync_point INTEGER, updated_at TEXTDEFAULT0 );CREATETRIGGERoutgoing_sync_insertAFTERINSERTONoutgoing_syncBEGINUPDATEoutgoing_syncSETupdated_at = STRFTIME(%s,NOW)WHEREROWID =new.ROWID;END;CREATETRIGGERoutgoing_sync_updateAFTERUPDATEONoutgoing_syncBEGINUPDATEoutgoing_syncSETupdated_at = STRFTIME(%s,NOW)WHEREROWID =new.ROWID;END;remote_id字段表示远程节点的id,sync_point字段表示上一次更新所在的行位置,updated_at字段表示更新时间。账号test的表remote_id中的数据项如下所示:3.Container目录Container目录结构和生成过程与Account类似,Containerdb中共有5张表,其中incoming_sync和outgoing_sync的schema与Account中的相同。其他3张表分别为container_stat、object、sqlite_sequence。表container_stat与表account_stat相似,其区别是container_stat存放的是关于container信息:CREATETABLEcontainer_stat ( account TEXT, container TEXT, created_at TEXT, put_timestamp TEXTDEFAULT0, delete_timestamp TEXTDEFAULT0, object_count INTEGER, bytes_used INTEGER, reported_put_timestamp TEXTDEFAULT0, reported_delete_timestamp TEXTDEFAULT0, reported_object_count INTEGERDEFAULT0, reported_bytes_used INTEGERDEFAULT0, hash TEXTdefault00000000000000000000000000000000, id TEXT, status TEXTDEFAULT, status_changed_at TEXTDEFAULT0, metadata TEXTDEFAULT, x_container_sync_point1 INTEGERDEFAULT-1, x_container_sync_point2 INTEGERDEFAULT-1 );其中account字段表示container所示的account,container字段表示container名称,created_at表示创建时间,put_timestamp表示put request的时间戳,delete_timestamp表示delete request的时间戳,object_count表示object计数,bytes_used表示使用空间,hash表示db文件的哈希值,reported_put_timestamp,reported_delete_timestamp,reported_object_count,reported_bytes_used表示reported的状态信息,id表示统一标识符,status表示container状态,status_changed_at表示更改时间,metadata表示container的元数据,x_container_sync_point1表示同步点1,x_container_sync_point2表示同步点2.以名称为test的container db为例,其中的表container_stat数据项如下:表object的schema如下:CREATETABLEobject( ROWID INTEGERPRIMARYKEYAUTOINCREMENT, name TEXT, created_at TEXT,sizeINTEGER, content_type TEXT, etag TEXT, deleted INTEGERDEFAULT0 );CREATEINDEXix_object_deleted_nameONobject(deleted, name);CREATETRIGGERobject_deleteAFTERDELETEONobjectBEGINUPDATEcontainer_statSETobject_count = object_count - (1-old.deleted), bytes_used = bytes_used -old.size, hash = chexor(hash,,old.created_at);END;CREATETRIGGERobject_insertAFTERINSERTONobjectBEGINUPDATEcontainer_statSETobject_count = object_count + (1-new.deleted), bytes_used = bytes_used +new.size, hash = chexor(hash,,new.created_at);END;CREATETRIGGERobject_updateBEFOREUPDATEONobjectBEGINSELECTRAISE(FAIL,UPDATE not allowed; DELETE and INSERT);END;test container db的表object数据项如下所示:4.tmp目录tmp目录作为account/container/object server向partition目录内写入数据前的临时目录。例如,在client向服务端上传某一文件,object server调用DiskFile类的mkstemp方法在创建路径为path/device/tmp的目录。在数据上传完成之后,调用put()方法,将数据移动到相应路径。5.async_pending目录本地server在与remote server建立http连接或者发送数据时超时导致更新失败时,将把文件放入async_pending目录。这种情况经常发生在系统故障或者是高负荷的情况下。如果更新失败,本次更新被加入队列,然后由Updater继续处理这些失败的更新工作。例如,假设一个containerserver处于负荷下,此时一个新的对象被加入到系统。当Proxy成功地响应Client的请求时,这个对象将变为直接可访问的。但是container服务器并没有更新对象列表,本次更新将进入队列等待延后的更新。所以,container列表不可能马上就包含这个新对象。随后Updater使用object_sweep扫描device上的async pendings目录,遍历每一个prefix目录并执行升级。一旦完成升级,则移除pending目录下的文件(实际上,是通过调用renamer函数将文件移动到object相应的目录下)。为了验证以上过程,通过执行一个并发上传1000个文件的脚本,观察sws50的async_pending目录下的所发生的变化。async_pending的路径为/srv/node/sdc/async_pending/,在执行脚本前,该目录下为空。脚本执行完毕后,async_pending目录下产生了一些prefix目录,cd到一个prefix为cb9的目录中,观察其中的数据:rootsws50:/srv/node/sdc/async_pending/cb9# lltotal 24-rw- 1 swift swift 324 2011-11-08 10:15 69a5ee25ea7a4a4b08ea47102930fcb9-1320718532.01864-rw- 1 swift swift 324 2011-11-08 10:15 69a5ee25ea7a4a4b08ea47102930fcb9-1320718537.04863-rw- 1 swift swift 324 2011-11-08 10:15 69a5ee25ea7a4a4b08ea47102930fcb9-1320718543.08122-rw- 1 swift swift 324 2011-11-08 10:15 69a5ee25ea7a4a4b08ea47102930fcb9-1320718550.13288-rw- 1 swift swift 324 2011-11-08 10:15 69a5ee25ea7a4a4b08ea47102930fcb9-1320718558.18801-rw- 1 swift swift 324 2011-11-08 10:16 69a5ee25ea7a4a4b08ea47102930fcb9-1320718567.25494文件路径的组成如下图所示,其中数据名称是由hash_path后面紧跟-,后面是以发送container request的header中包含的时间戳所产生:Figure6: async_pendingdirectory represention2分钟之后,查看该目录下的文件,仅剩下一个文件:rootsws50:/srv/node/sdc/async_pending/cb9# lltotal 4-rw- 1 swift swift 356 2011-11-08 10:18 69a5ee25ea7a4a4b08ea47102930fcb9-1320718567.25494最后,async_pending目录变为空。account和container的db pending文件并不会独立地存在于async_pending目录下,它们的pending文件会与其db文件在一个目录下存放。例如:某container的db文件为b8e7f40f8c2012d17aca4e0483d391d0.db,其pending文件为b8e7f40f8c2012d17aca4e0483d391d0.db.pending,一起存放在suffix目录1d0下。再次执行测试脚本观察1d0目录下的变化,执行前pending文件的大小为0kb,执行过程中,pending的大小慢慢增加到12kb左右,接着又缓慢下降直到0kb。读取此过程某一时刻的pending文件。其中内容如下所示::gAIoVQM3MzVxAVUQMTMyMTE4NjczMy4yNTQ0N3ECSgBwAQBVGGFwcGxpY2F0aW9uL29jdGV0LXN0ncmVhbXEDVSBkYmQzZjhmYjQ1ZmQyZjBkZGZmNTA1ODZkNWU0ZGY3ZnEESwB0Lg=n:gAIoVQM3MzhxAVUQMTMyMTE4NjczMy41MjM4MXECTQDcVRhhcHBsaWNhdGlvbi9vY3RldC1zdHJlnYW1xA1UgOGI3YzRiZGVlYzNkZGU4ZDI5OWU1Yzk1ZmE1N2ExZWVxBEsAdC4=n:gAIoVQM3MzlxAVUQMTMyMTE4NjczMy42Mzg0NnECTQCgVRhhcHBsaWNhdGlvbi9vY3RldC1zdHJlnYW1xA1UgMmQ1ZDlhYjk0MzlkMTNiMmZhODhiZmFmNTk3NTRkMjZxBEsAdC4=n:g.AIoVQM3NDdxAVUQMTMyMTE4NjczNC40MzIxNnECSgBoAQBVGGFwcGxpY2F0aW9uL29jdGV0LXN0ncmVhbXEDVSBjYTgzNmZhY2FhMzY0MGQwNDc4YTU5OGQzZmUzYmRiNHEESwB0Lg=n:gAIoVQM3NDlxAVUQMTMyMTE4NjczNC42MzA1NXECTQCUVRhhcHBsaWNhdGlvbi9vY3RldC1zdHJlnYW1xA1UgY2Y5NWU3MDIxNWEzOTFlNzcwZDBkODBjZjlhN2Q5OTlxBEsAdC4=n:gAIoVQM3NTBxAVUQMTMyMTE4NjczNC43NTA2MXECSgAoAQBVGGFwcGxpY2F0aW9uL29jdGV0LXN0ncmVhbXEDVSAyYzU4Zjc3ZGIwMGUxMTgxNjZmNjg2Zjc0YzlmZmNjZHEESwB0Lg=n使用:对以上字符串进行分割成list,我们得到第一个非空元素y1:gAIoVQM3MzVxAVUQMTMyMTE4NjczMy4yNTQ0N3ECSgBwAQBVGGFwcGxpY2F0aW9uL29jdGV0LXN0ncmVhbXEDVSBkYmQzZjhmYjQ1ZmQyZjBkZGZmNTA1ODZkNWU0ZGY3ZnEESwB0Lg=n使用pickle模块对其进行解码pickle.loads(y1.decode(base64),获得一个dict类型的数据:name, timestamp, size, content_type, etag,deleted=(735,1321186733.25447,94208,application/octet-stream,dbd3f8fb45fd2f0ddff50586d5e4df7f,0)表示一个名称为735,大小为94208B,md5哈希值为dbd3f8fb45fd2f0ddff50586d5e4df7f,可访问的字节流文件。此过程由ContainerBroker类的_commit_puts方法完成,随后使用put_object方法把这些数据项放入container db的object表中,.pending文件中的数据类型与object表中的字段定义一致。从account与container的db和object两者的pending文件处理方式中发现其不同之处在于,db的pending文件在更新完其中的一项数据之后,删除pending文件中的相应的数据项,而object的数据在更新完成之后,移动pending文件到目标目录。6.quarantined目录Auditor进程会在本地服务器上每隔一段时间就扫面一次磁盘来检测account、container、object的完整性。一旦发现不完整的数据,该文件就会被隔

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论