数字货币交易所后台架构

基于区块链技术的数字资产交易系统,为全球用户提供7x24小时数字资产交易服务。类似国内的火币/Okex交易所,交易平台为用户提供充币、提币、下单、撤单、查询订单记录、行情信息等业务功能。

本系统的特色在于,底层戳和引擎是基于区块链技术,将用户资产和交易记录写入区块链,既可避免出现传统去中心化交易系统被黑客攻击导致的用户资产损失现象,保障用户资产安全,也可保证用户的每笔交易记录都是无法篡改的。

后台参考架构如下:

关键模块

  • gate:提供对用户资产、订单记录、行情、深度、k线、成交记录的查询接口,部分接口支持ws
  • parse:交易解析程序,拉取区块链最新交易信息(挂单、撤单、转账、成交记录)至数据库
  • redis:缓存区块链行情、深度、用户近3月订单历史、最新成交记录
  • mysql:解析数据库,存储用户信息、资产信息、交易记录、成交记录
  • mq: 消息队列
  • ops: 异步下单子模块,接收客户端的交易请求,生成订单信息写入用户订单表,发送到mq
  • rfs:异步下单子模块,从mq消费客户端交易请求,将请求转发到区块链戳和引擎

缓存

  • market(深度、行情):每隔0.5s从区块链合约读取,丢到缓存
  • 订单记录:缓存用户近3月至多1000条记录
  • 最新成交记录(提供给机器人):缓存最近5分钟内的成交细节
  • 活跃订单:
    • 若只显示已经上链的订单,可以从区块链合约读取
    • 若显示挂单中和已经上链的订单,则必须从 db 中读取(目前采用此方式)

分表

老版的解析数据库是按照交易对进行分表,一个交易对的历史订单存在一个表里面,此法的缺点是:

  • 历史订单数据只会越来越多,影响查询(实际查询只需返回近3月历史)
  • 交易历史分散在不同的交易对表,如果要追踪一个用户的交易行为,需要查询多个表

改动:订单和成交记录按月分表,“缺点”是查询需要同时查多个表数据后汇总(这个对开发人员来说小菜一碟),优点:

  • 历史数据不会影响查询效率
  • 所有用户的交易历史固定在一个表(单个月而言),方便追踪用户的交易行为
  • 方便迁移(最快只需拷贝近3/4个月数据)

异步下单

老版系统的用户下单接口是同步的,直接将用户交易请求发送给区块链并等待区块链打包、共识、出块响应交易处理结果,TPS明显不高。

异步模式:

  • ops 模块:接收客户端的交易请求,生成订单信息写入用户订单表,发送到 mq,这样交易请求就算是成功接收了,直接返回用户订单id给客户端。内部利用定时/定量的批量入库机制,每0.5秒或累计接收1000笔交易就往数据库写一次盘,提升写数据库的效率。
  • rfs 模块:从mq消费客户端交易请求,将请求转发到区块链戳和引擎处理,并更新对应用户订单的处理结果。

ops 写入 instructionId(即客户端拿到的用户订单id),rfs 查询到该交易戳和完成后更新 instructionId 对应的区块链订单id。

instructionId 区块链订单id
193034729012 2035

用户的 真实资产 记录在区块链合约中,由于采用了异步下单机制,用户的 实际可用资产 需要根据用户下单后立即更新(即使该订单还未进戳和引擎或未被戳和引擎处理完),防止用户的实际可用资产不足挂一些无效单,根据订单状态的变化,及时更新资产(冻结、可用)

  • 用户的可用资产 = 从区块链读到的可用资产 - 异步下单冻结的买单部分资产
  • 用户的冻结资产 = 从区块链读到的冻结资产 - 异步下单冻结的卖单部分资产

TODO

  • ops/rfs异步下单流程
  • 戳和流程
  • 风控模块设计思路
彦祖老师 wechat