Loro项目JSON Schema详解:操作日志的可视化与解析

Loro项目JSON Schema详解:操作日志的可视化与解析

loro Reimagine state management with CRDTs. Easily enable collaboration and time-travel on your app. loro 项目地址: https://gitcode.com/gh_mirrors/lo/loro

前言

在现代协同编辑系统中,操作日志(OpLog)是记录所有编辑操作的核心数据结构。Loro项目通过引入JSON Schema,为开发者提供了一种直观理解操作日志的方式。本文将深入解析Loro的JSON Schema设计,帮助开发者更好地理解和使用这一功能。

为什么需要JSON Schema

Loro支持多种数据结构并引入了许多新概念。如果仅提供二进制导出格式,开发者将难以理解底层过程。JSON Schema的设计初衷包括:

  1. 提升可读性:人类可读的JSON表示使开发者更容易理解和操作文档
  2. 开发便利性:便于开发相关工具和进行调试
  3. 透明性:让开发者清楚地看到数据结构和操作流程

核心数据结构概览

Loro的JSON Schema主要包含以下几个核心部分:

  1. 根对象(Root Object):包含所有变更、操作和关键元数据
  2. 变更(Change):记录编辑操作的基本单元
  3. 操作(Operation):具体的数据操作内容
  4. 值类型(Value):支持的数据类型定义

根对象详解

根对象是整个JSON Schema的顶层结构,其定义如下:

{
    "schema_version": 1,
    "start_version": {"peer1": 0, "peer2": 1},
    "peers": ["123456789", "987654321"],
    "changes": [...]
}
  • schema_version:当前规范版本,目前为1
  • start_version:文档的起始版本边界,表示为PeerID到Counter的映射
  • peers:文档中所有参与者的列表,PeerID以十进制字符串表示
  • changes:文档中的所有变更列表

这种设计优化了文档大小和可读性,特别是对PeerID的处理方式。

变更(Change)结构

变更是Loro操作日志中的基本单元,构成了Replayable Event Graph(REG)的节点。每个变更包含以下信息:

{
    "id": "1@0",
    "timestamp": 1625097600,
    "deps": ["0@1", "1@2"],
    "lamport": 3,
    "msg": "initial commit",
    "ops": [...]
}
  • id:变更的唯一标识符,格式为{Counter}@{PeerID}
  • timestamp:Unix时间戳(可选)
  • deps:该变更的因果依赖项列表
  • lamport:Lamport时间戳
  • msg:提交消息(类似Git commit)
  • ops:该变更包含的所有操作

操作(Operation)类型详解

操作是JSON Schema中最复杂的部分,Loro支持多种容器类型,每种容器有特定的操作类型。

通用操作结构

所有操作都遵循以下基本格式:

{
    "container": "cid:root-list:List",
    "counter": 1,
    "content": {...}
}
  • container:容器ID,格式为cid:{ID}:{ContainerType}
  • counter:操作计数器
  • content:具体操作内容,因容器类型而异

列表(List)操作

列表支持两种基本操作:

  1. 插入(insert)

    {
        "type": "insert",
        "pos": 0,
        "value": "hello"
    }
    
  2. 删除(delete)

    {
        "type": "delete",
        "pos": 0,
        "len": 1,
        "start_id": "1@0"
    }
    

可移动列表(MovableList)操作

可移动列表在基础列表操作上增加了移动和设置操作:

  1. 移动(move)

    {
        "type": "move",
        "from": 0,
        "to": 1,
        "elem_id": "L1@0"
    }
    
  2. 设置(set)

    {
        "type": "set",
        "elem_id": "L1@0",
        "value": "new value"
    }
    

映射(Map)操作

映射支持键值对的插入和删除:

  1. 插入(insert)

    {
        "type": "insert",
        "key": "name",
        "value": "Alice"
    }
    
  2. 删除(delete)

    {
        "type": "delete",
        "key": "name"
    }
    

富文本(Text)操作

富文本支持更复杂的文本操作:

  1. 标记(mark)

    {
        "type": "mark",
        "start": 0,
        "end": 5,
        "style_key": "bold",
        "style_value": true,
        "info": 1
    }
    
  2. 标记结束(mark_end)

    {
        "type": "mark_end"
    }
    

树(Tree)操作

树结构支持节点的创建、移动和删除:

  1. 创建(create)

    {
        "type": "create",
        "target": "1@0",
        "parent": null,
        "fractional_index": "a1b2"
    }
    
  2. 移动(move)

    {
        "type": "move",
        "target": "1@0",
        "parent": "2@0",
        "fractional_index": "c3d4"
    }
    

值类型系统

Loro支持丰富的数据类型,在JSON Schema中统称为LoroValue:

  • 基本类型:null、布尔值、数字
  • 复合类型:二进制数据、字符串、列表、映射
  • 特殊类型:容器引用(以🦜:前缀标识)
{
    "string": "hello",
    "number": 42,
    "list": [1, 2, 3],
    "map": {"key": "value"},
    "container": "🦜:cid:1@0:List"
}

兼容性处理

为了处理版本兼容性问题,Loro引入了Unknown类型:

{
    "type": "unknown",
    "prop": 1,
    "value_type": "binary",
    "value": "base64encoded..."
}

当新版本遇到不支持的容器类型时,会将其作为Unknown类型处理,确保系统不会崩溃。

最佳实践建议

  1. 版本控制:始终检查schema_version字段
  2. 变更分析:利用depslamport字段分析操作依赖关系
  3. 数据类型:正确处理LoroValue的各种类型,特别是容器引用
  4. 错误处理:妥善处理Unknown类型操作

总结

Loro的JSON Schema设计为开发者提供了深入了解协同编辑过程的窗口。通过这种结构化的表示方式,开发者可以更容易地:

  • 调试协同编辑问题
  • 开发可视化工具
  • 理解数据变更历史
  • 构建自定义同步逻辑

理解这些数据结构将帮助开发者更好地利用Loro构建强大的协同应用。

loro Reimagine state management with CRDTs. Easily enable collaboration and time-travel on your app. loro 项目地址: https://gitcode.com/gh_mirrors/lo/loro

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

叶准鑫Natalie

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值