图床项目后台框架
- 0、后台数据处理框架
- 一、注册功能
- 二、登陆功能
- 三、用户文件列表
-
- 四、上传文件之秒传机制
- 五、上传文件
- 六、获取共享文件或下载榜
-
- 6.1、获取共享文件数量
- 6.2、获取共享文件列表
- 6.3 获取下载榜
- 七、分享/删除文件以及更新下载计数
-
- 7.1、分享文件
- 7.2、删除文件
- 7.3、更新文件下载计数
- 八、取消分享/转存/更新下载计数
-
- 8.1、取消分享
- 8.2、转存文件
- 8.3、更新共享文件下载计数
- 九、分享图片
-
- 9.1、请求图片分享
- 9.2、请求浏览图片
- 9.3、我的图片分享
0、后台数据处理框架
一、注册功能
Server
Client
post 请求
json格式回复
分析数据,提取数据(decodeRegisterJson)
处理API (apiRegisterUser)
如果不存在则保存到数据库,registerUser
封装返回信息(encodeRegisterJson)
成功:{“code”:0},失败:{“code”:1},
用户已存在:{“code”:2}
HTTP
post:{
“Email”: “......”
“firstPwd”: “......”
“nickName”: “......”
“phone”: “......”
“userName”: “......”
}
根据状态码进行相关处理
MD5 即 Message-Digest Algorithm 5(信息-摘要算法 5),用于确保信息传输完整一致。是计算机广泛使用的杂凑算法之一(又译摘要算法、哈希算法),主流编程语言普遍已有 MD5 实现。
理论上 MD5 是不可逆的,而且 MD5 本来也不是作加密使用,而是用来校验数据的完整性,只是因为其不可逆且稳定、快速的特点,被广泛用于对明文密码的加密。
二、登陆功能
Server
Client
post 请求
json格式回复
分析数据,提取数据(decodeLoginJson)
处理API (ApiRegisterUser)
musql验证用户名密码,verifyUserPassword
生成和设置token,并保存到redis。
setToken
封装返回信息(encodeRegisterJson)
成功:{“code”:0,“token”:......},
失败:{“code”:1}
HTTP
post:{
“pwd”:“......”
“user”: “......”
}
根据状态码进行相关处理
Token 的中文有人翻译成 “令牌”,意思就是,你拿着这个令牌,才能过一些关卡。
Token 是一个用户自定义的任意字符串。在成功提交了开发者自定义的这个字符串之后,Token 的值会保存到服务器后台。只有服务器和客户端前端知道这个字符串,于是 Token 就成了这两者之间的密钥,它可以让服务器确认请求是来自客户端还是恶意的第三方。
使用基于 Token 的身份验证方法,在服务端不需要存储用户的登录记录。大概的流程是这样的:
- 客户端使用用户名跟密码请求登录。
- 服务端收到请求,去验证用户名与密码。
- 验证成功后,服务端生成一个 Token,这个 Token 可以存储在内存、磁盘、或者数据库里,再把这个 Token 发送给客户端。
- 客户端收到 Token 以后可以把它存储起来,比如放在 Cookie 里或者 Local Storage 。
- 客户端每次向服务端请求资源的时候需要带着服务端签发的 Token。
- 服务端收到请求,然后去验证客户端请求里面带着的 Token,如果验证成功,就向客户端返回请求的数据。
三、用户文件列表
3.1、文件数量
Server
Client
post 请求
json格式回复
解析command参数(QueryParseKeyValue)
处理API (ApiMyFiles)
提取用户和token数据,decodeCountJson
校验用户名和token,VerifyToken
获取文件总数量,handleUserFilesCount
encodeCountJson
{ “total”:......,“code”:0 }
异常code:1,正常code:0
HTTP
post:{
“token”:“......”,
“user”:“......”
}
根据状态码进行相关处理
3.2、文件列表
Server
Client
post 请求
json格式回复
解析command参数,
QueryParseKeyValue
处理API ,
ApiMyFiles
解析Json数据,
decodeFilesListJson
校验用户名和token,
VerifyToken
从mysql读取文件信息,
getUserFileList
根据参数按普通、升序、降序排序
获取文件数量,
getUserFilesCount
请求参数从mysql读取文件列表信息
异常{code:1},
正常 {code:0,文件列表}
HTTP (normal/pvasc升序/pvdesc降序)
post:{
“count”: 2,
“start”: 0,
“token”:“...”,
“user”: “...”
}
根据状态码进行相关处理
升序(order by pv asc)和 cmd=normal 逻辑一致,只是稍微改了 sql 语句的查询方式。
降序(order by pv desc)和 cmd=normal 逻辑一致,只是稍微改了 sql 语句的查询方式。
四、上传文件之秒传机制
请求对比数据库文件信息的md5。
每个文件都有一个唯一的 MD5 值(比如 2bf8170b42cc7124b04a8886c83a9c6f),就好比每个人的指纹都是唯一的一样,效验 MD5 就是用来确保文件在传输过程中未被修改过。
- 客户端在上传文件之前将文件的 MD5 码上传到服务器
- 服务器端判断是否已存在此 MD5 码,如果存在,说明该文件已存在,则此文件无需再上传,在此文件的计数器加 1,说明此文件多了一个用户共用。
- 如果服务器没有此 MD5 码,说明上传的文件是新文件,则真正上传此文件。
Server
Client
post请求
json格式回复
json格式回复
失败
成功
秒传失败
文件已存在
文件不存在
秒传成功
分析数据,提取数据
decodeMd5Json
处理API,ApiMd5
校验token,
VerifyToken
token验证失败,
{“code”:4}
秒传后台数据处理,
handledealMd5
检测file_info是否存在该md5记录,
如果有并获取count引用计数
秒传失败:{“code”:1}
秒传失败:{“code”:0}
文件已存在:{“code”:2}
没有md5
检测个人文件
user_file_list
是否有文件名和md5记录
有md5
多一个记录引用file_info
文件引用计数+1
user_file_list
更新用户文件信息
user_file_count
更新用户文件数量
{
“fileName”: “...”,
“md5”: “......”,
“token”: “.......”,
“user”: “...”
}
根据状态码进行相应处理
五、上传文件
Server
nginx
Client
post 请求
中转
json格式回复
解析文件类型,file_content_type
解析文件名,file_name
解析文件md5,file_md5
解析文件路径,file_path
解析文件大小,file_size
解析用户名,user
根据文件后缀名对临时文件做重命名,rename
将文件上传到fastdfs并获取fileid,
upload FileToFastDfs
根据fileid获取王者下载的url,
getFullurlByFileid
保存文件信息到数据库,storeFileinfo
删除临时文件,unlink
成功:{“code”:0}
失败:{“code”:1}
nginx-upload-module文件上传模块
HTTP
post: 用户信息和文件内容
根据状态码进行相关处理
六、获取共享文件或下载榜
获取共享文件个数,获取共享文件列表,获取共享文件下载排行榜。
6.1、获取共享文件数量
处理逻辑:
Server
Client
post 请求
json格式回复
解析command参数(QueryParseKeyValue)
处理API (apiShareFiles)
获取共享文件数量(handleGetShareFilesCount)
封装返回信息(encodeShareCountJson)
HTTP
根据状态码进行相关处理
6.2、获取共享文件列表
处理逻辑:
Server
Client
post 请求
json格式回复
normal
pvdesc 下载量降序
解析command参数,
QueryParseKeyValue
处理API (apiShareFiles)
读取要解析的内容,fread()
解析json内容,
get_filelist_json_info
获取共享文件列表,
handleGetShareFileList
获取下载榜,
handleGetRankingFileList
封装返回信息
HTTP
根据状态码进行相关处理
6.3 获取下载榜
score
member
value
fileid
key
下载量pv
下载量pv
下载量pv
......
文件md5+文件名
文件md5+文件名
文件md5+文件名
......
文件名
文件名
文件名
......
文件md5+文件名
文件md5+文件名
文件md5+文件名
......
FILE_NAME_HASH
hash结构key
FILE_NAME_HASH
zset结构key
七、分享/删除文件以及更新下载计数
7.1、分享文件
处理逻辑:
Server
Client
post 请求
json格式回复
json格式回复
校验失败
存在
不存在
有记录
没有记录
解析command参数,
QueryParseKeyValue
处理API,
apiDealFiles
分析数据,提取数据,
decodeDealFileJson
{“code”:4}
校验token,
VerifyToken
处理分享文件,
handleShareFile
检查是否已经分享,
FILE_PUBLIC_ZSET
encodeDealFileJson,
成功:{“code”:0}
失败:{“code”:1}
已经分享:{“code”:3}
已经分享,
share_state=ShareHad
继续检测MySQL,
share_file_list
增加到排行榜,
FILE_PUBLIC_ZSET
位置文件分享状态,
user_file_list shared_st
添加分享文件记录,
share_file_count
更新共享文件计数,
user_file_count
添加到redis,
FILE_PUBLIC_ZSET,
FILE_NAME_HASH
HTTP
post:{
“filename”:“......”
“md5”:“......”
“token”:“......”
“user”:“......”
}
根据状态码进行相关处理
7.2、删除文件
处理逻辑:
Server
Client
post 请求
json格式回复
json格式回复
校验失败
校验成功
不存在
1
0
存在
解析command参数,
QueryParseKeyValue
处理API ,
apiShareFiles
分析数据,提取数据,
decodeDealFileJson
校验用户名和token,
VerifyToken
encodeDealFileJson,
token错误{“code”:4}
删除文件,
handleDeleteFile
先检查文件是否被分享,
FILE_PUBLIC_ZSET
继续检测user_file_list里
该文件的分享状态,
shared_status
从共享文件列表删除,
share_file_list
is_shared=1
更新用户文件计数,
user_file_count
is_shared=0
is_shared=1
redis_has_record=1
更新共享文件计数,
user_file_count
如果redis有记录,
删除zset、hash对应记录
删除用户文件信息,
user_file_list
文件引用计数减一,
file_info_count
如果文件引入计数为0,
从fastdfs删除文件
encodeDealFileJson,
成功:{“code”:0}
失败:{“code”:1}
HTTP
post:{
“filename”:“......”
“md5”:“......”
“token”:“......”
“user”:“......”
}
根据状态码进行相关处理
- 先判断此文件是否已经分享;
- 判断集合有没有这个文件,如果有,说明别人已经分享此文件(redis 操作) ;
- 如果集合没有此元素,可能因为 redis 中没有记录,再从 mysql 中查询,如果 mysql 也没有,说明真没有(mysql 操作);
- 如果 mysql 有记录,而 redis 没有记录,那么分享文件处理只需要处理 mysql (mysql 操作) ;
- 如果 redis 有记录,mysql 和 redis 都需要处理,删除相关记录。
注意:
- 如果删除文件,则也将其从共享列表删除,其他人如果想要保存共享文件则可以转存到个人文件列表。
- 共享文件和我的文件 指向的是同一个文件。
- 一个人共享了一个文件,删除文件的时候也会删除共享文件;两个人同时删除文件则才会删除共享文件。
- 本质上而言,删除自己的文件时是否该删除共享文件,是业务的问题,确定了业务根据业务做代码实现即可。
7.3、更新文件下载计数
处理逻辑:
Server
Client
get方式下载
post请求
json格式回复
校验成功
校验失败
FastDFS+nginx自动处理
解析command参数,
QueryParseKeyValue
处理API,
apiDealFile
分析数据,提取数据,
decodeDealFileJson
校验用户名和token,
VerifyToken
更新文件下载次数,
handlePvFile
encodeDealFileJson,
token错误{“code”:4}
encodeDealFileJson,
成功:{“code”:0}
失败:{“code”:1}
文件url地址
HTTP
post:{
“filename”:“......”
“md5”:“......”
“token”:“......”
“user”:“......”
}
下载完成
根据状态码进行相关处理
八、取消分享/转存/更新下载计数
8.1、取消分享
Server
Client
post请求
json格式返回
中间有些步骤错误则返回
解析command参数,
QueryParseKeyValue
处理API ,
apiDealShareFile
提取数据,
decodeDealShareFileJson
暂时不做token认证
把share_status置为0,
user_file_list
获取共享文件数量,
user_file_count
共享文件计数减一,
user_file_count
删除共享文件记录,
share_file_list
从redis中删除
FILE_PUBLIC_ZSET和FILE_NAME_HASH
对应数据
取消共享文件
handleCancelShareFile
成功:{“code”:0}
失败:{“code”:1}
HTTP
post:{
“filename”:“......”
“md5”:“......”
“user”:“......”
}
根据状态码进行相关处理
8.2、转存文件
Server
Client
post请求
json格式返回
json格式返回
已存在
不存在
中间有些步骤错误则返回
解析command参数,
QueryParseKeyValue
处理API ,
apiDealShareFile
提取数据,
decodeDealShareFileJson
暂时不做token认证
转存文件,
handleSaveFile
检测用户是否已经存在该文件,
user_file_list
{“code”:5}
用户文件数量+1,
user_file_count
获取文件引用计数,
file_info
添加文件引用计数,
file_info
用户文件列表添加记录,
user_file_list
获取用户文件数量,
user_file_count
成功:{“code”:0}
失败:{“code”:1}
HTTP
post:{
“filename”:“......”
“md5”:“......”
“user”:“......”
}
根据状态码进行相关处理
8.3、更新共享文件下载计数
Server
Client
post请求
json格式返回
解析command参数,
QueryParseKeyValue
处理API ,
apiDealShareFile
提取数据,
decodeDealShareFileJson
暂时不做token认证
共享文件pv值加一,
share_file_list
查询该共享文件pv值,
share_file_list
更新文件下载次数,
handlePvFile
成功:{“code”:0}
失败:{“code”:1}
如果在FILE_PUBLIC_ZSET则+1,
如果不在则添加到FILE_PUBLIC_ZSET和
FILE_NAME_HASH
HTTP
post:{
“filename”:“......”
“md5”:“......”
“user”:“......”
}
根据状态码进行相关处理
九、分享图片
9.1、请求图片分享
Server
Client
post请求
json格式返回
添加图片分享记录,
share_picture_list (filemd5、urlmd5等)
生成图片记录唯一的值,
urlmd5
请求分享图片,
handleSharePicture
解析json数据,
decodeSharePictureJson
解析command参数,
QueryParseKeyValue
处理API ,
apiSharePicture
成功:{“code”:0,“urlmd5”:“......”}
失败:{“code”:1}
共享图片数量加1,
user_file_count
获取共享图片数量,
user_file_count
HTTP
post:{
“filename”:“......”
“md5”:“......”
“user”:“......”
}
根据状态码进行相关处理
9.2、请求浏览图片
Server
Client
get方式
返回网页
post请求
json格式返回
nginx web
封装返回结果,
encodeBrowseIPictureJson
更新浏览次数,
share_picture_list
根据文件md5从
file_info获取完整url
根据urlmd5查询分享信息,
share_picture_list
根据urlmd5查找完整url,
handleBrowsePicture
解析json数据,
decodeBrowseIPictureJson
解析command参数,
QueryParseKeyValue
处理API ,
apiSharePicture
访问网址
HTTP
post:{
“filename”:“......”
“md5”:“......”
“user”:“......”
}
加载网页
根据状态码进行相关处理
9.3、我的图片分享
Server
Client
post请求
json格式返回
查询share_picture_list和file_info
获取文件列表
获取图片列表,
handleGetSharePicturesList
解析json数据,
decodePictureListJson
解析command参数,
QueryParseKeyValue
HTTP
post:{
“token”:“......”
“user”:“......”
“count”:...
“start”:...
}
处理API ,
apiSharePicture
a2
成功:{“code”:0,文件列表}
失败:{“code”:1}