Automerge vs Yjs

조승빈·2024년 8월 30일

WYSIWYG??

WYSIWYG [ What You See Is What You Get ] : 사용자가 편집기에 입력하거나 조작한 내용이 출력 결과와 동일하게 표시되는 편집기.
단순히 텍스트 입력뿐만 아니라 이미지나 동영상 등 복잡한 포맷팅 작업을 쉽게 처리할 수 있다.
사용자의 텍스트나 이미지를 입력할 때, 그 결과물이 최종 출력물(==웹페이지)과 동일한 형태로 즉시 화면에 표시된다.

WYSIWYG 에디터를 사용하는 이유

crdt는 텍스트 입력과 같은 데이터 동기화와 충돌 해결을 위한 기술이다. 따라서 텍스트의 굵기나 기울기같은 텍스트 포맷팅을 동기화하고 일관되게 유지하기 위해서는 텍스트 에디터가 필요하다.

CRDT (Conflict-Free Replicated Data Types)

CRDT는 중앙 서버 없이도 여러 복제본이 독립적으로 동작하고, 병합 가능한 데이터 구조를 통해 충돌 없이 병합이 가능합니다. 각 복제본은 독립적으로 업데이트될 수 있으며, 나중에 병합되어 일관된 상태를 유지한다. 이는 Git과 유사한 구조를 따른다.

주요 라이브러리로는 Automerge와 Yjs가 있음

Automerge

Automerge는 JSON과 유사한 형태의 데이터 구조를 사용하여 문서를 관리한다. 문서를 수정할 때마다 새로운 버전을 생성하여 충돌 없이 동기화할 수 있다. 주요 특징은 다음과 같다:

스냅샷 (Snapshot): 문서의 현재 상태를 나타내며, 전체 문서의 특정 시점의 데이터를 저장한다.
동기화 상태 (Sync-state): 네트워크를 통해 다른 클라이언트와 동기화될 때의 상태를 저장한다.

예제 서버 코드 (Automerge)

Automerge의 기본 서버는 WebSocket을 사용하여 클라이언트와 실시간으로 데이터를 주고받는다. 이 서버는 automerge-repo 라이브러리를 활용하여 여러 클라이언트 간의 데이터 동기화를 처리한다.

Repo: Automerge의 데이터 저장소로, NodeFSStorageAdapter를 통해 파일 시스템에 데이터를 저장한다.
WebSocket Server: NodeWSServerAdapter를 사용하여 WebSocket을 통해 클라이언트와 연결을 관리한다.

import { Repo } from "@automerge/automerge-repo";
import { NodeWSServerAdapter } from "@automerge/automerge-repo-network-websocket";
import { NodeFSStorageAdapter } from "@automerge/automerge-repo-storage-nodefs";

// Repo 초기화
const serverRepo = new Repo({
  network: [new NodeWSServerAdapter(wsServer)],
  storage: new NodeFSStorageAdapter(),
});

// WebSocket 서버 생성 및 연결 처리
wsServer.on("connection", (socket, request) => {
  console.log(`New connection from ${request.socket.remoteAddress}`);
  
  // 메시지 및 연결 관리 로직
  // ...
});

이런 식으로 파일로 저장된다.

Yjs

Yjs는 효율적인 바이트 단위의 데이터를 처리하며, 다양한 네트워크 전송 방식에 최적화되어 있다. 이진 포맷을 사용해 네트워크 대역폭을 절약하고 성능을 극대화한다. 주요 특징은 다음과 같다:

  • 크로스 탭 통신 (Cross-Tab Communication): Yjs는 BroadcastChannel API나 localStorage를 사용해 동일 브라우저 내 여러 탭 간 상태를 동기화한다.
  • 내장 동기화 메커니즘: Yjs는 다양한 네트워크 공급자(WebSocket, WebRTC 등)를 지원해 동기화를 처리합니다. 웹소켓을 사용하지 않아도 동기화가 가능하다.

예제 서버 코드 (Yjs)

Yjs의 기본 서버는 WebSocket을 사용하여 클라이언트와 실시간으로 데이터를 주고받으며, MySQL 데이터베이스를 사용하여 문서 데이터를 저장하고 관리한다.

WebSocket Server: Yjs는 WebSocket을 사용해 클라이언트와의 연결을 관리하며, setupWSConnection을 통해 문서 업데이트 시 데이터를 MySQL에 저장한다.
MySQL Database: 문서의 업데이트된 데이터를 MySQL에 저장하고, 필요 시 불러올 수 있다.

const ywsUtils = require('y-websocket/bin/utils');
const setupWSConnection = ywsUtils.setupWSConnection;

// WebSocket 서버 생성 및 문서 업데이트 처리
wss.on('connection', (conn, req) => {
  setupWSConnection(conn, req, {
    onUpdate: (update, doc) => {
      saveOrUpdateDocument(doc.name, update); // MySQL에 업데이트된 문서 데이터 저장
    }
  });
});

// 문서 데이터 MySQL 저장 함수
function saveOrUpdateDocument(docName, updateData) {
  // MySQL 저장 로직
}

다른 Yjs 공식 문서의 예시와의 비교

  • Quill: WYSIWYG 편집기 (리치 텍스트 편집기)
  • ProseMirror: WYSIWYG 편집기
  • CodeMirror: 코드 편집기 (WYSIWYG가 아님)
  • Monaco: 코드 편집기 (WYSIWYG가 아님)

Automerge vs Yjs

데이터 구조: Automerge는 JSON 기반, Yjs는 바이트 단위의 이진 포맷.
성능: Yjs가 더 최적화되어 있으며, 대규모 문서 및 다수 사용자 환경에서 더 뛰어난 성능을 제공한다.
개발자 경험: Yjs는 더 많은 레퍼런스와 개발자 친화적인 API를 제공하는 경향이 있다.

profile
평범

0개의 댓글