当前位置: 首页 > news >正文

网盘系统设计:万亿 GB 网盘如何实现秒传与限速?

Java全能学习面试指南:https://javaxiaobear.cn

网盘,又称云盘,是提供文件托管和文件上传、下载服务的网站(File hostingservice)。人们通过网盘保管自己拍摄的照片、视频,通过网盘和他人共享文件,已经成为了一种习惯。我们准备开发一个自己的网盘应用系统,应用名称为“DBox”。

十几年前曾经有个段子,技术人员对老板说:您不能在公司电脑打开您家里电脑的文件,再贵的电脑也不能。事实上,随着网盘技术的成熟,段子中老板的需求已经成为现实:网盘可以自动将家里电脑的文件同步到公司电脑,老板可以在公司的电脑打开家里电脑的文件了。

网盘的主要技术挑战是**海量数据的高并发读写访问。**用户上传的海量数据如何存储?如何避免部分用户频繁读写文件,消耗太多资源,而导致其他的用户体验不佳?我们看下DBox 的技术架构以及如何解决这些问题。

1、需求分析

DBox 的核心功能是提供文件上传和下载服务。基于核心功能,DBox 需要在服务器端保存这些文件,并在下载和上传过程中实现断点续传。也就是说,如果上传或下载过程被中断了,恢复之后,还能从中断的地方重新上传或者下载,而不是从头再来。

DBox 还需要实现文件共享的需求。使用 DBox 的不同用户之间可以共享文件,一个用户上传的文件共享给其他用户后,其他用户也可以下载这个文件。

此外,网盘是一个存储和网络密集型的应用,用户文件占据大量硬盘资源,上传、下载需要占用大量网络带宽,并因此产生较高的运营成本。所以用户体验需要向付费用户倾斜,DBox 需要对上传和下载进行流速控制,保证付费用户得到更多的网络资源。DBox 用例图如下。

image-20231201105140483

1、负载指标估算

DBox 的设计目标是支持 10 亿用户注册使用,免费用户最大可拥有 1TB 存储空间。预计日活用户占总用户的 20%,即 2 亿用户。每个活跃用户平均每天上传、下载 4 个文件。

DBox 的存储量吞吐量带宽负载估算如下:

总存储量

理论上,总存储空间估算为 10 亿 TB,即 1 万亿 GB。10亿 × 1TB = 10亿TB

但考虑到大多数用户并不会完全用掉这个空间,还有很多用户存储的文件其实是和别人重复的(电影、电子书、软件安装包等),真正需要的存储空间大约是这个估算值的 10%,即 1 亿 TB。

QPS

系统需要满足的平均 QPS 约为 10000。2亿 × 4 ÷ (24 × 60 × 60) ≈ 1万

高峰期 QPS 约为平均 QPS 的两倍,即 2 万。

带宽负载

每次上传下载文件平均大小 1MB,所以需要网络带宽负载 10GB/s,即 80Gb/s。1万 × 1MB = 10GB/s = 80Gb/s,同样,高峰期带宽负载为 160Gb/s。

2、非功能需求

  1. 大数据量存储:10 亿注册用户,1000 亿个文件,约 1 亿 TB 的存储空间。
  2. 高并发访问:平均 1 万 QPS,高峰期 2 万 QPS。
  3. 大流量负载:平均网络带宽负载 80Gb/S,高峰期带宽负载 160Gb/s。
  4. 高可靠存储:文件不丢失,持久存储可靠性达到 99.9999% ,即 100 万个文件最多丢失(或损坏)1 个文件。
  5. 高可用服务:用户正常上传、下载服务可用性在 99.99% 以上,即一年最多 53 分钟不可用。
  6. 数据安全性:文件需要加密存储,用户本人及共享文件外,其他人不能查看文件内容。
  7. 不重复上传:相同文件内容不重复上传,也就是说,如果用户上传的文件内容已经被其他用户上传过了,该用户不需要再上传一次文件内容,进而实现“秒传”功能。从用户视角来看,不到一秒就可以完成一个大文件的上传。

2、概要设计

网盘设计的关键是元数据与文件内容的分离存储与管理。所谓文件元数据就是文件所有者、文件属性、访问控制这些文件的基础信息,事实上,传统文件系统也是元数据与文件内容分离管理的,比如 Linux 的文件元数据记录在文件控制块 FCB 中,Windows 的文件元数据记录在文件分配表 FAB 中,Hadoop 分布式文件系统 HDFS 的元数据记录在NameNode 中。

而 DBox 是将元信息存储在数据库中,文件内容则使用另外专门的存储体系。但是由于DBox 是一个互联网应用,出于安全和访问管理的目的,并不适合由客户端直接访问存储元数据的数据库和存储文件内容的存储集群,而是通过 API 服务器集群和数据块服务器集群分别进行访问管理。整体架构如下图。

image-20231201145340645

对于大文件,DBox 不会上传、存储一整个的文件,而是将这个文件进行切分,变成一个个单独的 Block,再将它们分别上传并存储起来。

这样做的核心原因是,DBox 采用对象存储作为最终的文件存储方案,而对象存储不适合存储大文件,需要进行切分。而大文件进行切分还带来其他的好处:可以以 Block 为单位进行上传和下载,提高文件传输速度;客户端或者网络故障导致文件传输失败,也只需要重新传输失败的 Block 就可以,进而实现断点续传功能。

Block 服务器就是负责 Block 上传和管理的。客户端应用程序根据 API 服务器的返回指令,将文件切分成一些 Block,然后将这些 Block 分别发送给 Block 服务器,Block 服务器再调用对象存储服务器集群,将 Block 存储在对象存储服务器中(DBox 选择 Ceph 作为对象存储)。

用户上传文件的时序图如下:

image-20231203173232695

用户上传文件时,客户端应用程序收集文件元数据,包括文件名、文件内容 MD5、文件大小等等,并根据文件大小计算 Block 的数量(DBox 设定每个 block 大小 4MB),以及每个 Block 的 MD5 值。

然后客户端应用程序将全部元数据(包括所有 Block 的 MD5 值列表)发送给 API 服务器。API 服务器收到文件元数据后,为每个 Block 分配全局唯一的 BlockID(BlockID 为严格递增的 64 位正整数,总可记录数据大小 ,足以满足 DBox的应用场景)。

下一步,API 服务器将文件元数据与 BlockID 记录在数据库中,并将 BlockID 列表和应用程序可以连接的 Block 服务器列表返回客户端。客户端连接 Block 服务器请求上传Block,Block 服务器连接 API 服务器进行权限和文件元数据验证。验证通过后,客户端上传 Block 数据,Block 服务器再次验证 Block 数据的 MD5 值,确认数据完整后,将BlockID 和 Block 数据保存到对象存储集群 Ceph 中。

类似的,用户下载文件的时序图如下:

image-20231203173348916

客户端程序访问 API 服务器,请求下载文件。然后 API 服务器会查找数据库,获得文件的元数据信息,再将元数据信息中的文件 BlockID 列表及可以访问的 Block 服务器列表返回给客户端。

下一步,客户端访问 Block 服务器,请求下载 Block。Block 服务器验证用户权限后,从Ceph 中读取 Block 数据,返回给客户端,客户端再将返回的 Block 组装为文件。

3、详细设计

为解决网盘的三个重要问题:元数据如何管理?网络资源如何向付费用户倾斜?如何做到不重复上传?DBox 详细设计将关注元数据库、上传下载限速、秒传的设计实现。

1、元数据设计

元数据库表结构设计如下:

image-20231203173453687

从图中可以看出,元数据库表结构中主要包括三个表,分别是 User 用户表、File 文件表和Block 数据块表,表的用途和包含的主要字段如下:

  1. User 用户表记录用户基本信息:用户名、创建时间、用户类型(免费、VIP)、用户已用空间、电话号码、头像等等。
  2. File 文件表记录文件元信息:文件名、是否为文件夹、上级文件夹、文件 MD5、创建时间、文件大小、文件所属用户、是否为共享文件等。
  3. Block 数据块表记录 Block 数据,包括 BlockID、Block MD5、对应文件等。

其中,User 表和 File 表为一对多的关系,File 表和 Block 表也是一对多的关系。

这 3 种表的记录数都是百亿级以上,所以元数据表采用分片的关系数据库存储。

因为查询的主要场景是根据用户 ID 查找用户信息和文件信息,以及根据文件 ID 查询block 信息,所以 User 和 File 表都采用 user_id 作为分片键,Block 表采用 file_id 作为分片键。

2、限速

DBox 根据用户付费类型决定用户的上传、下载速度。而要控制上传、下载速度,可以通过限制并发 Block 服务器数目,以及限制 Block 服务器内的线程数来实现。

具体过程是,客户端程序访问 API 服务器,请求上传、下载文件的时候,API 服务器可以根据用户类型,决定分配的 Block 服务器数目和 Block 服务器内的服务线程数,以及每个线程的上传、下载速率。

Block 服务器会根据 API 服务器的返回值,来控制客户端能够同时上传、下载的 Block 数量以及传输速率,以此对不同用户进行限速。

3、秒传

秒传是用户快速上传文件的一种功能。

事实上,网盘保存的很多文件,内容其实是重复的,比如电影、电子书等等。一方面,重复上传这些文件会加大网盘的存储负载压力;另一方面,每次都要重新上传重复的内容,会导致用户网络带宽的浪费和用户等待时间过长的问题。

所以,在设计中,物理上相同的文件,DBox 只会保存一份。用户每次上传文件时,DBox都会先在客户端计算文件的 MD5 值,再根据 MD5 值判断该文件是否已经存在。对于已经存在的文件,只需要建立用户文件和该物理文件的关联即可,并不需要用户真正上传该

文件,这样就可以实现秒传的功能。

但是,计算 MD5 可能会发生 Hash 冲突,也就是不同文件算出来的 MD5 值是相同的,这样会导致 DBox 误判,将本不相同的文件关联到一个物理文件上。不但会使上传者丢失自己的文件,还会被黑客利用:上传一个和目标文件 MD5 相同的文件,然后就可以下载

目标文件了。

所以,DBox 需要通过更多信息判断文件是否相同:只有文件长度、文件开头 256KB 的MD5 值、文件的 MD5 值,三个值都相同,才会认为文件相同。当文件长度小于256KB,则直接上传文件,不启用秒传功能。

为此,我们需要将上面的元数据库表结构进行一些改动,将原来的 File 表拆分成物理文件表 Physics_File 和逻辑文件表 Logic_File。其中,Logic_File 记录用户文件的元数据,并和物理文件表 Physics_File 建立多对 1 关联关系,而 Block 表关联的则是 Physics_File

表,如下:

image-20231203173716367

Logic_File 中字段 double_md5 记录了文件头 256KB 的 MD5、文件 MD5 两个数据拼接后的数据,而 size 记录了文件长度,只有这两个字段都相同才会启用秒传。

4、总结

我们在需求分析中讨论过,DBox 需要支持大数据量存储、高并发访问、高可用服务、高可靠存储等非功能需求。事实上,对于网盘应用而言,元数据 API 服务其实和一般的高并发互联网系统网关没有太大差别。真正有挑战的是海量文件的高可用存储,而这一挑战,

在 DBox 中,被委托给了分布式对象存储 Ceph 来完成。而 Ceph 本身设计就是支持大数据量存储、高并发访问、高可用服务、高可靠存储的。

架构师按照职责,可以分成两种,一种是应用系统架构师,负责设计、开发类似网盘、爬虫这样的应用系统;另一种是基础设施架构师,负责设计、开发类似 Ceph、HDFS 这样的基础设施系统。

应用架构师需要掌握的技术栈更加广泛,要能够掌握各种基础设施技术的特性,并能根据业务特点选择最合适的方案;而基础设施架构师需要的技术栈更加深入,需要掌握计算机软硬件更深入的知识,才能开发出一个稳定的基础技术产品。

当然,最好的架构师应该是技术栈既广泛又深入,既能灵活应用各种基础设施来开发应用系统,也能在需要的时候自己动手开发新的基础设施系统。
在这里插入图片描述

相关文章:

网盘系统设计:万亿 GB 网盘如何实现秒传与限速?

Java全能学习面试指南:https://javaxiaobear.cn 网盘,又称云盘,是提供文件托管和文件上传、下载服务的网站(File hostingservice)。人们通过网盘保管自己拍摄的照片、视频,通过网盘和他人共享文件&#xff…...

整数和浮点数在内存中的存储

文章目录 每日一言整数在内存中的存储方式浮点数在内存中的存储结语 每日一言 You just can’t beat the person who never gives up. 你无法打败那位永不放弃的人。 整数在内存中的存储方式 整数在内存中的存储方式通常采用二进制形式,即将整数的数值转化为二进制…...

rabbitMQ镜像队列的使用

在rabbitMQ集群中,默认发送消息时,队列默认时在一个节点上存在的。 我们以node01 node02 node03三节点集群为例,在node01声明队列发送消息后,发现: 测试队列只在节点node01上出现。 我们手动停止node01后&#xff0c…...

ros来保存图像和保存记录视频的方法---gmsl相机保存视频和图片

1,保存图片 rosrun image_view image_view image:=/myimg_topic这个命令只是用来查看图像的,它并不会保存图像。如果你想要保存图像,你需要使用image_saver节点,并指定保存路径。例如: 下面指令就可以了,可以用 rosrun image_view image_saver image:=/myimg_topic _fi…...

Oracle19c使用adrci清理日志文件

Oracle中通常有好多日志文件,遇到异常情况会产生大量日志,造成磁盘空间紧张。 故需要清理对应文件。包括trace文件,incident文件,listener log文件等。 19c中oracle提供了一个ADRCI的命令行工具来查看ADR中的alert日志和trace信息…...

Ubuntu之Sim2Real环境配置(坑居多)

不要一上来就复制哦,因为很多下面的步骤让我走了很多弯路,如果可能的话,我会重新整理再发出来 前提: 参考教程 Docs 创建工作空间(不用跟着操作,无用) 1.创建sim2real server container 1.尝试创建sim2r…...

java中BigDecimal里面的subtract函数的意思?

在Java中,BigDecimal类提供了一个名为subtract()的函数,用于执行两个BigDecimal对象的减法操作。该函数返回一个新的BigDecimal对象,表示两个操作数相减的结果。 下面是BigDecimal.subtract()函数的用法示例: java Copy code im…...

线程变量引发的session混乱问题

最近不是在救火,就是在救火的路上。 也没什么特别可写的,今天记录下最近遇到的一个问题,个人觉得挺有意思, 待有缘人阅读 言归正传,售后反馈: 营业查询中付款方式为第三方支付的几条银行缴费,创…...

dockerfile与docker-compose解释及对比

Dockerfile 是一个文本文件,用于定义单个Docker镜像的构建过程和配置。它包含了一系列的指令,如FROM、RUN、COPY、CMD等,按照顺序执行这些指令来构建镜像。Dockerfile可以定义容器的基础镜像、安装依赖软件、拷贝文件、运行命令等操作。通过…...

数据库更换版本

目录 0.前言 1.官网下载MySQL 2.配置初始化文件my.ini 3.初始化MySQL 4.安装mysql服务并启动修改密码 5.配置环境变量​编辑 0.前言 心累,为了完成实验,必须使用8.0版本导致我更新版本的时候,把sqlyog干崩溃了,什么版本不兼…...

Unity Meta Quest 一体机开发(九):【手势追踪】通过录制抓取手势实现自定义抓取姿势

文章目录 📕教程说明📕录制前的准备📕第一种录制方法(Hand Grab Pose Tool 场景)⭐在运行模式中确认录制⭐保存录制的手势,将物体做成 Prefab⭐在编辑阶段调整抓取手势🔍Fingers Freedom&#x…...

Git 简介及异常场景处理

一、简介 介绍Git之前,还得先介绍下 版本控制系统(VCS), 和它的发展历史 纵观版本控制系统的发展历史,广义上讲,版本控制工具的历史可以分为三代: 第一代 第一代版本控制系统被称为本地版本控…...

龙迅LT2611UX 四端口LVDS转HDMI(2.0)

1.描述: LT2611UX 四端口LVDS TO HDMI2.0。 LT2611UX是一款高性能得LVDS到HDMI2.0转换器得STB,DVD应用程序,LVDS输入可以配置单端口,双端口或者四端口,带有一个高速时钟通道,最多可运行三到四个高速数据…...

MySQL基础『数据类型』

✨个人主页: 北 海 🎉所属专栏: MySQL 学习 🎃操作环境: CentOS 7.6 阿里云远程服务器 🎁软件版本: MySQL 5.7.44 文章目录 1.数据类型一览2.整型2.1.INT2.2.BIT 3.浮点数3.1.FLOAT3.2.DECIMAL3…...

SQL手工注入漏洞测试(PostgreSQL数据库)-墨者

———靶场专栏——— 声明:文章由作者weoptions学习或练习过程中的步骤及思路,非正式答案,仅供学习和参考。 靶场背景: 来源: 墨者学院 简介: 安全工程师"墨者"最近在练习SQL手工注入漏洞&#…...

STM32单片机项目实例:基于TouchGFX的智能手表设计(1)项目介绍及GUI界面基础

STM32单片机项目实例:基于TouchGFX的智能手表设计(1)项目介绍及GUI界面基础 一、项目介绍 1.1方案提供 1.2主控选择 1.3硬件平台 1.4 开发环境 1.5 关于华清 二、GUI界面基础 2.1.1 嵌入式绘图系统 2.1.1 色彩格式 2.1.1帧缓冲区 …...

【超详细教程】基于html+js实现轮播图

轮播图是现代网页设计中常见的元素之一,它能够展示多张图片或内容,在有限的空间内循环播放,提升网页的视觉效果和用户体验。下面将以一个简单的网页轮播图为例,说明如何基于HTML和JavaScript实现。 ​ 1、R5Ai智能助手 chatgpt国…...

C++11(上)

统一的列表初始化 首先要说明: 这个列表初始化和类和对象那里的初始化列表不是一个概念. {} 初始化 在C98中, 标准允许使用花括号{}对数组或者结构体元素进行统一的列表初始值设定. 比如: C语言里面其实就是这样支持的, 所以可以认为C支持这样就是因为要兼容C. 在…...

web前端开发规范、HTML规范、JavaScript规范、style规范

MENU 前言目的 HTML规范用法规范注释规范 CSS规范用法规范书写顺序样式覆盖注释规范 JavaScript规范用法规范组件选项注释规范 命名规范目录命名图片命名文件命名方法命名样式命名常用词 工程结构目录构建代码风格 Git规范分支说明使用说明 相关连接 前言 目的 规范的目的是为…...

骨传导耳机会影响听力么?盘点骨传导耳机的好处与坏处都有哪些?

先说结论,使用骨传导耳机是不会影响听力的!并且由于骨传导耳机的特殊传声原理,相比于传统的入耳式耳机,骨传导耳机拥有更多的优点,下面带大家了解一下骨传导耳机的优点和缺点都有哪些。 一、骨传导耳机的优点是什么&a…...

从智慧灯杆到无人驾驶:如何用Raspberry Pi 4和Arduino搭建微型智慧城市实验平台

从智慧灯杆到无人驾驶:如何用Raspberry Pi 4和Arduino搭建微型智慧城市实验平台 在创客文化和高校工程教育中,低成本硬件的创新应用正掀起一场微型智慧城市实验的革命。只需一块树莓派主板、几个传感器和开源软件,就能在桌面上复现价值数百万…...

Verilog实战精要:从语法基础到高效状态机设计

1. Verilog语法基础:从硬件思维出发 第一次接触Verilog时,很多人会把它当成普通编程语言来学,结果发现处处碰壁。我当年在FPGA项目上栽的第一个跟头,就是把阻塞赋值用在了时钟触发的always块里,导致仿真结果和实际硬件…...

BepInEx游戏插件加载器完全指南:从入门到精通Unity游戏扩展工具

BepInEx游戏插件加载器完全指南:从入门到精通Unity游戏扩展工具 【免费下载链接】BepInEx Unity / XNA game patcher and plugin framework 项目地址: https://gitcode.com/GitHub_Trending/be/BepInEx 如何用BepInEx解锁游戏自定义功能?解决玩家…...

单片机通用按键处理模块设计与实现

单片机通用按键处理模块设计与实现1. 项目概述1.1 模块功能特性本按键处理模块为单片机系统提供了一套完整的按键事件处理解决方案,具有以下核心功能:基础按键检测:支持按下(PRESS)和释放(RELEASE)事件检测高级触发模式:长按触发(…...

OpenClaw技能扩展:用QwQ-32B实现公众号自动发布

OpenClaw技能扩展:用QwQ-32B实现公众号自动发布 1. 为什么需要公众号自动化发布 作为一个技术博主,我每周都要在公众号发布2-3篇技术文章。最让我头疼的不是写作本身,而是发布前的繁琐流程:手动调整Markdown格式、生成封面图、上…...

自动化周报生成:OpenClaw+GLM-4.7-Flash整合多平台数据

自动化周报生成:OpenClawGLM-4.7-Flash整合多平台数据 1. 为什么需要自动化周报 每周五下午,我的心情总是特别复杂。一方面期待着周末的到来,另一方面又要面对那个令人头疼的任务——写周报。相信很多技术从业者都有类似的经历:…...

交易数据一致性保障:大数据环境下的挑战

交易数据一致性保障:大数据环境下的挑战 1. 引入与连接:数字世界的"货币守卫" 想象一下:当你在电商平台下单支付后,银行显示扣款成功,但商家却显示支付失败;或者在股票交易中,你看到的股价与实际成交价格存在差异。这些看似微小的数据不一致,可能导致企业声…...

游戏玩家如何选?网易UU/ToDesk远程控制延迟实测(含手机投屏技巧)

游戏玩家专属远程控制工具深度评测:延迟、画质与投屏技巧全解析 作为一名资深游戏玩家,你是否遇到过这样的场景:出差在外想用手机继续刷副本,却苦于找不到合适的远程控制方案;或是想在平板上玩PC独占的3A大作&#xff…...

手把手教你用J-Link Commander设置仿真器序列号(2023最新版)

2023年J-Link仿真器序列号配置全指南:从入门到精通 第一次拿到J-Link仿真器时,很多开发者都会遇到一个看似简单却容易踩坑的问题——如何正确设置设备序列号。作为嵌入式开发中不可或缺的调试工具,J-Link仿真器的序列号不仅是设备身份标识&am…...

开源工具Cowabunga Lite:iOS设备零门槛个性化方案全解析

开源工具Cowabunga Lite:iOS设备零门槛个性化方案全解析 【免费下载链接】CowabungaLite iOS 15 Customization Toolbox 项目地址: https://gitcode.com/gh_mirrors/co/CowabungaLite 在iOS生态系统中,用户对设备个性化的需求与系统封闭性之间始终…...