From fcc348e38fdd927d8e1bd8ef36185f8d201d580d Mon Sep 17 00:00:00 2001 From: jgoteam Date: Thu, 18 Apr 2024 15:03:01 -0700 Subject: [PATCH 01/13] feat: basic landing page skeleton - Incorporate fade-in scroll effect on landing page with `useIsVisible` hook and `FadeInSection` component - Insert initial CLI gif Co-authored-by: Alex Sklar Co-authored-by: Erik Margetis --- blog/2019-05-28-first-blog-post.md | 12 -- blog/2019-05-29-long-blog-post.md | 44 ----- blog/2021-08-01-mdx-blog-post.mdx | 20 -- .../docusaurus-plushie-banner.jpeg | Bin 96122 -> 0 bytes blog/2021-08-26-welcome/index.md | 25 --- blog/authors.yml | 17 -- docs/index.md | 1 + docusaurus.config.js | 6 +- .../HomepageFeatures/FadeInSection.jsx | 20 ++ src/components/HomepageFeatures/index.js | 172 ++++++++++++------ src/hooks/useIsVisible.js | 18 ++ src/pages/case-study.mdx | 4 + src/pages/index.js | 6 +- static/img/syncosaurus-deploy.gif | Bin 0 -> 27096 bytes 14 files changed, 163 insertions(+), 182 deletions(-) delete mode 100644 blog/2019-05-28-first-blog-post.md delete mode 100644 blog/2019-05-29-long-blog-post.md delete mode 100644 blog/2021-08-01-mdx-blog-post.mdx delete mode 100644 blog/2021-08-26-welcome/docusaurus-plushie-banner.jpeg delete mode 100644 blog/2021-08-26-welcome/index.md delete mode 100644 blog/authors.yml create mode 100644 src/components/HomepageFeatures/FadeInSection.jsx create mode 100644 src/hooks/useIsVisible.js create mode 100644 static/img/syncosaurus-deploy.gif diff --git a/blog/2019-05-28-first-blog-post.md b/blog/2019-05-28-first-blog-post.md deleted file mode 100644 index 02f3f81..0000000 --- a/blog/2019-05-28-first-blog-post.md +++ /dev/null @@ -1,12 +0,0 @@ ---- -slug: first-blog-post -title: First Blog Post -authors: - name: Gao Wei - title: Docusaurus Core Team - url: https://github.com/wgao19 - image_url: https://github.com/wgao19.png -tags: [hola, docusaurus] ---- - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet diff --git a/blog/2019-05-29-long-blog-post.md b/blog/2019-05-29-long-blog-post.md deleted file mode 100644 index 26ffb1b..0000000 --- a/blog/2019-05-29-long-blog-post.md +++ /dev/null @@ -1,44 +0,0 @@ ---- -slug: long-blog-post -title: Long Blog Post -authors: endi -tags: [hello, docusaurus] ---- - -This is the summary of a very long blog post, - -Use a `` comment to limit blog post size in the list view. - - - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet - -Lorem ipsum dolor sit amet, consectetur adipiscing elit. Pellentesque elementum dignissim ultricies. Fusce rhoncus ipsum tempor eros aliquam consequat. Lorem ipsum dolor sit amet diff --git a/blog/2021-08-01-mdx-blog-post.mdx b/blog/2021-08-01-mdx-blog-post.mdx deleted file mode 100644 index c04ebe3..0000000 --- a/blog/2021-08-01-mdx-blog-post.mdx +++ /dev/null @@ -1,20 +0,0 @@ ---- -slug: mdx-blog-post -title: MDX Blog Post -authors: [slorber] -tags: [docusaurus] ---- - -Blog posts support [Docusaurus Markdown features](https://docusaurus.io/docs/markdown-features), such as [MDX](https://mdxjs.com/). - -:::tip - -Use the power of React to create interactive blog posts. - -```js - -``` - - - -::: diff --git a/blog/2021-08-26-welcome/docusaurus-plushie-banner.jpeg b/blog/2021-08-26-welcome/docusaurus-plushie-banner.jpeg deleted file mode 100644 index 11bda0928456b12f8e53d0ba5709212a4058d449..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 96122 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 diff --git a/blog/2021-08-26-welcome/index.md b/blog/2021-08-26-welcome/index.md deleted file mode 100644 index 9455168..0000000 --- a/blog/2021-08-26-welcome/index.md +++ /dev/null @@ -1,25 +0,0 @@ ---- -slug: welcome -title: Welcome -authors: [slorber, yangshun] -tags: [facebook, hello, docusaurus] ---- - -[Docusaurus blogging features](https://docusaurus.io/docs/blog) are powered by the [blog plugin](https://docusaurus.io/docs/api/plugins/@docusaurus/plugin-content-blog). - -Simply add Markdown files (or folders) to the `blog` directory. - -Regular blog authors can be added to `authors.yml`. - -The blog post date can be extracted from filenames, such as: - -- `2019-05-30-welcome.md` -- `2019-05-30-welcome/index.md` - -A blog post folder can be convenient to co-locate blog post images: - -![Docusaurus Plushie](./docusaurus-plushie-banner.jpeg) - -The blog supports tags as well! - -**And if you don't want a blog**: just delete this directory, and use `blog: false` in your Docusaurus config. diff --git a/blog/authors.yml b/blog/authors.yml deleted file mode 100644 index bcb2991..0000000 --- a/blog/authors.yml +++ /dev/null @@ -1,17 +0,0 @@ -endi: - name: Endilie Yacop Sucipto - title: Maintainer of Docusaurus - url: https://github.com/endiliey - image_url: https://github.com/endiliey.png - -yangshun: - name: Yangshun Tay - title: Front End Engineer @ Facebook - url: https://github.com/yangshun - image_url: https://github.com/yangshun.png - -slorber: - name: Sébastien Lorber - title: Docusaurus maintainer - url: https://sebastienlorber.com - image_url: https://github.com/slorber.png diff --git a/docs/index.md b/docs/index.md index f06e3b3..bd76b7f 100644 --- a/docs/index.md +++ b/docs/index.md @@ -1,5 +1,6 @@ --- slug: / +title: Introduction sidebar_position: 1 --- diff --git a/docusaurus.config.js b/docusaurus.config.js index 6a3ac24..f21b97f 100644 --- a/docusaurus.config.js +++ b/docusaurus.config.js @@ -7,8 +7,6 @@ import 'dotenv/config' import { themes as prismThemes } from 'prism-react-renderer' import tailwindPlugin from './plugins/tailwind-config.cjs' -import remarkMath from 'remark-math' -import rehypeKatex from 'rehype-katex' /** @type {import('@docusaurus/types').Config} */ const config = { @@ -53,9 +51,7 @@ const config = { sidebarPath: './sidebars.js', sidebarCollapsed: false, }, - blog: { - showReadingTime: true, - }, + blog: false, theme: { customCss: './src/css/custom.css', }, diff --git a/src/components/HomepageFeatures/FadeInSection.jsx b/src/components/HomepageFeatures/FadeInSection.jsx new file mode 100644 index 0000000..f8e5034 --- /dev/null +++ b/src/components/HomepageFeatures/FadeInSection.jsx @@ -0,0 +1,20 @@ +import { useRef } from 'react'; +import useIsVisible from '@site/src/hooks/useIsVisible' + +const FadeInSection = ({ children }) => { + const sectionRef = useRef(); + const isVisible = useIsVisible(sectionRef); + + return ( +
+ {children} +
+ ); +} + +export default FadeInSection; diff --git a/src/components/HomepageFeatures/index.js b/src/components/HomepageFeatures/index.js index 67625be..998861f 100644 --- a/src/components/HomepageFeatures/index.js +++ b/src/components/HomepageFeatures/index.js @@ -2,63 +2,127 @@ import clsx from 'clsx' import Heading from '@theme/Heading' import styles from './styles.module.css' -const FeatureList = [ - { - title: 'Easy to Use', - Svg: require('@site/static/img/undraw_docusaurus_mountain.svg').default, - description: ( - <> - Docusaurus was designed from the ground up to be easily installed and - used to get your website up and running quickly. - - ), - }, - { - title: 'Focus on What Matters', - Svg: require('@site/static/img/undraw_docusaurus_tree.svg').default, - description: ( - <> - Docusaurus lets you focus on your docs, and we'll do the chores. Go - ahead and move your docs into the docs directory. - - ), - }, - { - title: 'Powered by React', - Svg: require('@site/static/img/undraw_docusaurus_react.svg').default, - description: ( - <> - Extend or customize your website layout by reusing React. Docusaurus can - be extended while reusing the same header and footer. - - ), - }, -] - -function Feature({ Svg, title, description }) { - return ( -
-
- -
-
- {title} -

{description}

-
-
- ) -} +import FadeInSection from './FadeInSection' export default function HomepageFeatures() { return ( -
-
-
- {FeatureList.map((props, idx) => ( - - ))} + <> + +
+
+
+
+
+ image +
+
+
+
+
+

+ Awesome CLI tool +

+

+ A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application +

+
+
+
+
+
+
+
+ +
+
+
+
+
+ image +
+
+
+
+
+

+ Awesome CLI tool +

+

+ A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application +

+
+
+
+
+
+
+
+ +
+
+
+
+
+ image +
+
+
+
+
+

+ Awesome CLI tool +

+

+ A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application +

+
+
+
+
+
+
+
+ +
+
+
+
+
+ image +
+
+
+
+
+

+ Awesome CLI tool +

+

+ A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application +

+
+
+
+
+
-
-
+ + ) } diff --git a/src/hooks/useIsVisible.js b/src/hooks/useIsVisible.js new file mode 100644 index 0000000..7fa1fb7 --- /dev/null +++ b/src/hooks/useIsVisible.js @@ -0,0 +1,18 @@ +import { useEffect, useState } from 'react'; + +export default function useIsVisible(ref) { + const [isIntersecting, setIntersecting] = useState(false); + + useEffect(() => { + const observer = new IntersectionObserver(([entry]) => { + setIntersecting(entry.isIntersecting); + }) + + observer.observe(ref.current); + return () => { + observer.disconnect(); + } + }, [ref]) + + return isIntersecting; +} diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index faeafbf..88c8ed1 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -1,3 +1,7 @@ +--- +title: Case Study +--- + import Dia2ClientChangesSync from './diagrams/Dia2ClientChangesSync.jsx' import LatencySlider from '@site/src/components/LatencySlider/LatencySlider' diff --git a/src/pages/index.js b/src/pages/index.js index 8a01dc4..487f78a 100644 --- a/src/pages/index.js +++ b/src/pages/index.js @@ -30,12 +30,8 @@ function HomepageHeader() { } export default function Home() { - const { siteConfig } = useDocusaurusContext() return ( - +
diff --git a/static/img/syncosaurus-deploy.gif b/static/img/syncosaurus-deploy.gif new file mode 100644 index 0000000000000000000000000000000000000000..d14e3b5b68f4684a6b04a0a77118c0ded1c9ba80 GIT binary patch literal 27096 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 literal 0 HcmV?d00001 From c863860b8f4c0d4c7e8a27f776084499c40eab11 Mon Sep 17 00:00:00 2001 From: jgoteam Date: Thu, 18 Apr 2024 15:41:27 -0700 Subject: [PATCH 02/13] style: make initial landing header take full viewport height Co-authored-by: Alex Sklar Co-authored-by: Erik Margetis --- src/components/HomepageFeatures/index.js | 71 ++++++----------------- src/pages/index.js | 2 +- static/img/dashboard_screenshot.png | Bin 0 -> 127233 bytes 3 files changed, 18 insertions(+), 55 deletions(-) create mode 100644 static/img/dashboard_screenshot.png diff --git a/src/components/HomepageFeatures/index.js b/src/components/HomepageFeatures/index.js index 998861f..0fcf762 100644 --- a/src/components/HomepageFeatures/index.js +++ b/src/components/HomepageFeatures/index.js @@ -8,13 +8,13 @@ export default function HomepageFeatures() { return ( <> -
-
+
+
image @@ -24,11 +24,8 @@ export default function HomepageFeatures() {

- Awesome CLI tool + A synchronization engine based on server reconciliation

-

- A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application -

@@ -37,39 +34,20 @@ export default function HomepageFeatures() {
-
-
+
+
-
- image -
-
-
-
+

- Awesome CLI tool + A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application

-

- A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application -

-
-
-
- - -
-
-
-
+
+
-
-
-
-

- Awesome CLI tool -

-

- A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application -

-
-
-
-
-
+
+
-
+
image
-
+

- Awesome CLI tool + An analytics dashboard to monitor your collaborative application's usage and error metrics

-

- A convenient CLI tool to seamlessly create, configure, manage, and deploy your collaborative application -

diff --git a/src/pages/index.js b/src/pages/index.js index 487f78a..4ecbf70 100644 --- a/src/pages/index.js +++ b/src/pages/index.js @@ -11,7 +11,7 @@ import styles from './index.module.css' function HomepageHeader() { const { siteConfig } = useDocusaurusContext() return ( -
+

{siteConfig.title}

diff --git a/static/img/dashboard_screenshot.png b/static/img/dashboard_screenshot.png new file mode 100644 index 0000000000000000000000000000000000000000..6db1cc7eb4f5ea001d70fd4efa2901274d83f9b0 GIT binary patch literal 127233 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

5LR0#_ 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

lo~Avp))t+ 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 literal 0 HcmV?d00001 From 2409bc4f17badcaa7991b9d611a20fbf838e086d Mon Sep 17 00:00:00 2001 From: jgoteam Date: Sat, 20 Apr 2024 13:00:36 -0700 Subject: [PATCH 03/13] style: rounded navbar + hero section with minimal transparency effect Co-authored-by: Alex Sklar Co-authored-by: Erik Margetis --- docusaurus.config.js | 12 +++++---- package-lock.json | 1 + package.json | 1 + src/css/custom.css | 21 +++++++++++++++ src/pages/index.js | 41 +++++++++++++++++++++++++----- static/img/logo_transparent.png | Bin 0 -> 45553 bytes static/img/outlink.svg | 1 + static/img/scroll-down-arrow.png | Bin 0 -> 225 bytes static/img/syncosaurus-deploy.gif | Bin 27096 -> 26593 bytes 9 files changed, 66 insertions(+), 11 deletions(-) create mode 100644 static/img/logo_transparent.png create mode 100644 static/img/outlink.svg create mode 100644 static/img/scroll-down-arrow.png diff --git a/docusaurus.config.js b/docusaurus.config.js index f21b97f..4036d36 100644 --- a/docusaurus.config.js +++ b/docusaurus.config.js @@ -12,7 +12,7 @@ import tailwindPlugin from './plugins/tailwind-config.cjs' const config = { title: 'Syncosaurus', tagline: - 'Syncosaurus is a React-and-Javascript-based framework for building real-time, collaborative React applications backed by the Cloudflare edge network of Workers and Durable Objects.', + "A performant, collaborative, real-time Javascript framework that enables developers to focus on their application's features and business logic, instead of the complexities of state synchronization and conflict resolution.", favicon: 'img/favicon.ico', // Set the production url of your site here @@ -62,8 +62,6 @@ const config = { themeConfig: /** @type {import('@docusaurus/preset-classic').ThemeConfig} */ ({ - // Replace with your project's social card - image: 'img/docusaurus-social-card.jpg', navbar: { title: 'Syncosaurus', logo: { @@ -76,7 +74,7 @@ const config = { { type: 'doc', label: 'Docs', docId: 'index', position: 'right' }, { to: 'https://github.com/syncosaurus', - label: 'GitHub', + label: 'Github', position: 'right', }, ], @@ -97,9 +95,13 @@ const config = { to: '/case-study', }, { - label: 'Team', + label: 'The Team', to: '/team', }, + { + label: 'Docs', + to: '/docs', + }, { label: 'GitHub', to: 'https://github.com/syncosaurus', diff --git a/package-lock.json b/package-lock.json index b81d395..31fbad9 100644 --- a/package-lock.json +++ b/package-lock.json @@ -8,6 +8,7 @@ "name": "syncosaurus-github-io", "version": "0.0.0", "dependencies": { + "@babel/plugin-syntax-jsx": "^7.24.1", "@docusaurus/core": "3.2.1", "@docusaurus/preset-classic": "3.2.1", "@emotion/styled": "^11.11.5", diff --git a/package.json b/package.json index 0f17bc3..51257d0 100644 --- a/package.json +++ b/package.json @@ -14,6 +14,7 @@ "write-heading-ids": "docusaurus write-heading-ids" }, "dependencies": { + "@babel/plugin-syntax-jsx": "^7.24.1", "@docusaurus/core": "3.2.1", "@docusaurus/preset-classic": "3.2.1", "@emotion/styled": "^11.11.5", diff --git a/src/css/custom.css b/src/css/custom.css index f8c5762..c996558 100644 --- a/src/css/custom.css +++ b/src/css/custom.css @@ -33,6 +33,27 @@ --docusaurus-highlighted-code-line-bg: rgba(0, 0, 0, 0.3); } +#hero-landing { + width: 99.5%; + align-self: center; +} + +.navbar { + width: 99.5%; + align-self: center; + background-color: white; + opacity: 90%; + outline: none; + border-bottom-right-radius: 1.5rem; /* 24px */ + border-bottom-left-radius: 1.5rem; /* 24px */ + box-shadow: 0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1); + font-weight: bold; +} + +.navbar__items { + font-weight: bold; +} + .col--2 { --ifm-col-width: calc(20%); } diff --git a/src/pages/index.js b/src/pages/index.js index 4ecbf70..c424e83 100644 --- a/src/pages/index.js +++ b/src/pages/index.js @@ -4,28 +4,57 @@ import useDocusaurusContext from '@docusaurus/useDocusaurusContext' import Layout from '@theme/Layout' import HomepageFeatures from '@site/src/components/HomepageFeatures' import Puzzle from '@site/src/components/Puzzle' +import { useState, useEffect } from 'react' import Heading from '@theme/Heading' import styles from './index.module.css' function HomepageHeader() { + const [scrollDownArrowDisplay, setScrollDownArrowDisplay] = useState('block') + + const setScroll = () => { + const displayValue = + window.scrollY / document.body.scrollHeight < 0.05 ? 'block' : 'none' + setScrollDownArrowDisplay(displayValue) + } + + useEffect(() => { + window.addEventListener('scroll', setScroll) + return () => { + window.removeEventListener('scroll', setScroll) + } + }, []) + const { siteConfig } = useDocusaurusContext() + return ( -
+ // rounded-2xl bg-indigo-50 py-10 overflow-hidden m-5 lg:m-0 2xl:py-16 xl:py-8 lg:rounded-tl-2xl lg:rounded-bl-2xl +

{siteConfig.title}

-

+

{siteConfig.tagline}

-
+
- Read the case study + Read Case Study
-
+
+ +
+
) } diff --git a/static/img/logo_transparent.png b/static/img/logo_transparent.png new file mode 100644 index 0000000000000000000000000000000000000000..e13cf1289c7ae8f940705f52e8413b0a096b3975 GIT binary patch literal 45553 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 %I~-Nkclv4 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 diff --git a/static/img/scroll-down-arrow.png b/static/img/scroll-down-arrow.png new file mode 100644 index 0000000000000000000000000000000000000000..1361200dc1c03bd6690d143cdd62be3b000e9de3 GIT binary patch literal 225 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 delta 5554 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 From 482810bffcbf680528c559fb9d4a6fb201d8060a Mon Sep 17 00:00:00 2001 From: emargetis Date: Sat, 20 Apr 2024 17:49:59 -0500 Subject: [PATCH 04/13] feat (case-study): initial conversion of case study to markdown Co-authored-by: Alex Sklar Co-authored-by: Franco Waisfeld Co-authored-by: Joseph Liang --- src/pages/case-study.mdx | 548 +++++++++++++++++++++++++++++++++++++++ 1 file changed, 548 insertions(+) diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index 6d692d9..f0f37a9 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -52,3 +52,551 @@ On the surface, building real-time collaborative applications may not seem any d + +# Overview + +- Syncosaurus is a React-Javascript developer framework for rapidly building browser-based real-time, collaborative web applications +- In this case study, we will: + - define real-time collaborative applications + - explain why real-time collaborative applications are not trivial to build + - compare existing solutions used to facilitate building collaborative applications, including Syncosaurus + - discuss how to use Syncosaurus + - explain how Syncosaurus was built + - discuss future improvements for Syncosaurus + +# Introduction + +## Defining Real-Time Collaboration Applications + +Broadly, real-time collaboration is a term used to describe software or technologies that allow multiple users to [work together on a project simultaneously](https://www.techopedia.com/definition/15608/real-time-collaboration). For our purposes, collaborative applications are browser-based web applications [that enable multiple users to simultaneously edit and maintain a synchronized view of an artifact](https://ably.com/blog/the-rise-of-realtime-collaboration) (e.g. a word document or an online whiteboard). + +With the rise of [remote work and distributed teams](https://medium.com/@anupamr/distributed-teams-are-the-new-cloud-for-startups-14240a9822d7), apps like these [are becoming critical in the modern work environment](https://northzone.com/2023/06/20/perspectives-the-rise-of-multiplayer-software/). Well-known examples include Google Docs, Figma, and Notion among others: + +[graphic here] + +While [a broader definition](https://www.microsoft.com/en-us/microsoft-365/business-insights-ideas/resources/real-time-collaboration-what-it-is-and-how-it-helps-your-business) of real-time collaboration applications can include video conferencing and messaging software, those types of applications have different technical requirements and will be excluded from the scope of this case study. + +## Preface on Architecture + +At a fundamental level when multiple users are “collaborating” on the same artifact, they are exchanging data to manipulate the synchronized view of the artifact. Practically, this means that all users who are collaborating on the artifact will need to exchange information back and forth in real-time via the open internet. Although there are numerous architectures for web applications, [they can broadly be categorized ](https://www.geeksforgeeks.org/difference-between-client-server-and-peer-to-peer-network/)into two categories: + +- Centralized +- Decentralized + +### Centralized + +Centralized includes the client-server architecture where client machines send resource requests to a backend server. In the client-server architecture, the server is generally [authoritative](https://medium.com/mighty-bear-games/what-are-server-authoritative-realtime-games-e2463db534d1), meaning it is the source of truth. + +[graphic here] + +### Decentralized + +Decentralized includes the peer-to-peer architecture where every machine (known as a node) is treated equally and is responsible for sending for and responding to requests for resources. In the peer-to-peer architecture, every machine has equal authority and a consensus must usually be reached to determine the truth + +[graphic here] + +Though [it is possible](https://www.tag1consulting.com/blog/yjs-webrtc-part-1) to build decentralized real-time collaboration web apps, decentralized architectures are notoriously complex. Instead [many existing real-time collaborative apps use a form of the client-server architecture](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) due to their comparative [efficiency and ease of maintenance](https://fwx.finance/learn/article/centralized-app-vs-dapp). Therefore, we will assume that any application considering Syncosaurus will be using a form of centralized architecture + +# Building Real-Time Collaborative Applications Is Not Trivial + +Initially, building real-time collaborative web apps may not seem different than building other web apps, however, if we break down each word of “real-time collaboration” into more concrete requirements, we quickly realize that is not the case + +## What Does Real-time Entail? + +### Defining Real-time + +Due to the laws of physics (e.g. the speed of light) and other causes of [network latency](https://aws.amazon.com/what-is/latency/), [true real-time](https://www.merriam-webster.com/dictionary/real%20time) on the internet can never be achieved. Therefore, real-time communication benchmarks for the Internet are often described in milliseconds - response times of up to [100 milliseconds](https://www.pubnub.com/blog/how-fast-is-realtime-human-perception-and-technology/) are usually categorized as real-time. The basis for this benchmark is a study that determined the average human requires [250 milliseconds](https://www.pubnub.com/blog/how-fast-is-realtime-human-perception-and-technology/) to register and process a visual event. + +### Importance of Real-time + +The need for real-time depends on the web application and generally apps that mirror in-person interaction or need rapid information sharing are strong candidates, including: + +- [Gaming](https://www.pubnub.com/blog/how-fast-is-realtime-human-perception-and-technology/) +- [Collaborative productivity and e-learning](https://www.mdpi.com/2079-9292/11/24/4152) +- [Video conferencing](https://21stcenturyav.com/good-latency-for-video-conferencing/) + +To illustrate this need and the impact latency can have on a user’s experience, use the demo below and notice how increased latency causes a noticeable delay in changing the red circle’s position to match the blue one: + +[graphic here] + +### Achieving Real-time Communication + +At the application layer of the internet, HTTP underpins much of the communication, however, it is designed around a request-response cycle pattern which is not necessarily conducive to real-time latency standards given that a roundtrip from client to server is required for all communication. Therefore, since the type of real-time collaboration applications we are considering uses a client-server architecture, need [bi-directional communication](https://en.wikibooks.org/wiki/Communication_Networks/Network_Basics) due to sub 100 ms latency requirements, and need [high data integrity](https://ably.com/topic/webrtc-vs-websocket#:~:text=While%20WebSocket%20works%20only%20over,the%20underlying%20reliability%20of%20TCP) to ensure all users see the same view, only a few communication options ([among several](https://rxdb.info/articles/websockets-sse-polling-webrtc-webtransport.html)) merit our consideration: + +- Long polling +- WebSockets +- WebTransport + +Note that using [streams over HTTP/2](https://getstream.io/blog/communication-protocols/) was also considered due to its bi-directional nature and built-in multiplexing, however, the need to broadcast data to multiple clients in real-time collaborative apps (which we will discuss later) made them unsuitable for our purposes + +#### Long Polling + +Long polling is a technique to emulate server push communications via normal HTTP requests. Long polling works like this: + +[graphic here] + +Although every browser supports long polling, it has high latency compared to other options such as WebSockets, and a risk of missing messages without extensive code on the client and server. Therefore, long polling [is generally better suited as a fallback option as opposed to a primary means of bi-directional communication](https://ably.com/topic/long-polling#:~:text=HTTP%20long%20polling%20solves%20the,make%20requests%20and%20servers%20respond.) + +#### WebSockets + +[WebSockets](https://developer.mozilla.org/en-US/docs/Web/API/WebSocket?retiredLocale=de) is an application layer protocol that provides a [full-duplex](https://www.comms-express.com/infozone/article/half-full-duplex/) communication channel over a single, long-lived connection between the client and server. This means that similar to a phone call, the connection from the client to the server will stay open as long the network is not interrupted and neither the client nor the server actively terminates it. This open connection enables clients and servers to freely exchange data without the overhead of the HTTP request-response cycle, but because it is built on top of [TCP](https://www.ibm.com/docs/ro/aix/7.1?topic=protocols-transmission-control-protocol), it still has guaranteed in-order message delivery. WebSockets work like this: + +[graphic here] + +Once the handshake is complete, the WebSocket connection is established and both parties are now free to transmit data at any time + +Overall, Websockets are [low latency compared to HTTP](https://ably.com/topic/websockets-pros-cons) and [are widely supported in modern browsers](https://caniuse.com/websockets), though they can be somewhat tricky to scale and maintain in production because the connections [have to remain open and there is a risk of message loss when connections are interrupted](https://ably.com/topic/websockets-pros-cons) + +#### WebTransport + +WebTransport is an application layer protocol built on the [QUIC protocol, a more performant alternative to TCP](https://ably.com/blog/can-webtransport-replace-websockets) that still provides the benefits of guaranteed message delivery, with the performance of UDP. The WebTransport process works very similarly to WebSockets, however, the [handshake process](https://www.fastly.com/blog/quic-handshake-tls-compression-certificates-extension-study) is quicker. Unlike WebSockets though, WebTransport provides [multiplexing](https://en.wikipedia.org/wiki/Multiplexing), [which can decrease latency](https://www.videosdk.live/blog/websocket-vs-webtransport#what-is-websocket) and reduce [head-of-line blocking](https://en.wikipedia.org/wiki/Head-of-line_blocking) concerns. + +While the characteristics of WebTransport make it seem like a strong [fit for real-time collaborative ](https://www.videosdk.live/blog/websocket-vs-webtransport#what-is-websocket)web apps, the technology has [yet to reach the same level of browser support as previously mentioned options](https://caniuse.com/webtransport). + +### Choosing A Technique + +With real-time collaborative apps requiring a communication option with low latency, bi-directional messaging, wide browser support, and minimal data loss, many developers, including us, opt to use WebSockets. Though, as noted Websockets are not without their concerns, which will be discussed later in the case study. + +Now that we have a more concrete definition of real-time communication latency requirements (< 100 milliseconds) and the communication options to enable that, we will seek to define collaboration. + +## What Does Collaboration Entail? + +As mentioned previously, when multiple clients are “collaborating” on the same artifact, they are exchanging data to manipulate the synchronized view of the artifact. This synchronized view is known as the application state - the data or variables that determine the application’s appearance or behavior and which is often referred to as the [“document”](https://diginomica.com/brief-history-collaborative-documents) in collaborative applications. + +To better illustrate the concepts of the current and subsequent sections in our case study, we will use a hypothetical example - a collaborative whiteboard application built using WebSockets. + +### Demonstrating Collaboration + +In our example whiteboard application, all users expect to simultaneously see the same shapes (i.e. a consistent application state) so that they can react and respond accordingly: + +[graphic here] + +If we assume the app is using a client-server architecture where the clients do not hold any state of their own (i.e. [thin clients](https://www.fortinet.com/resources/cyberglossary/thin-client)), the change-initiating client would need to wait until the change is received and confirmed by the server and then propagated to all clients before seeing the change reflected in its state. + +### Consistency vs Latency + +One may assume that because our application is using WebSockets, the information would travel fast enough to meet real-time latency requirements. However, depending on where the backend server(s) is located (among other factors), [the distance between the client and the server can increase latency](https://www.inkandswitch.com/local-first/#1-no-spinners-your-work-at-your-fingertips). Unfortunately, this latency can create a laggy user experience for the change-initiating client while it waits to communicate with the server (note that this discussion alludes to the inverse relationship between state consistency and latency which is described by the [PACELC theorem](https://www.scylladb.com/glossary/pacelc-theorem/)). Using our whiteboard example, you can see that the users have a different experience when latency is introduced: + +[graphic here] + +To increase consistency in our application, we will now explore [tools and techniques](https://developer.mozilla.org/en-US/docs/Web/Performance) to help us reduce latency. + +### Latency Reduction to Local Client-state + +When striving to reduce latency in real-time applications for the change-initiating client, some potential approaches include: + +- Using the edge network +- Tuning WebSocket messaging +- Updating the UI optimistically + +The edge network is a distributed computing paradigm that brings computation and data storage as close as possible to the client. While using the [edge network](https://www.heavy.ai/technical-glossary/edge-network) could be advantageous in reducing latency, it may involve overhauling the backend and could introduce [complexity and consistency concerns of its own](https://originstamp.com/blog/what-are-the-challenges-of-edge-computing/) due to its distributed nature. Therefore, it may not be our initial choice. + +Next, while [tuning our WebSocket messaging](https://pusher.com/blog/websockets-realtime-gaming-low-latency/#websockets-to-reduce-latency-and-ensure-smooth-gameplay) to be more performant could also help in reducing latency, this strategy reaches diminishing returns because there will always be at least some latency in the network. Therefore, it will only get us so far. + +Finally, [optimistically updating the client’s UI](https://javascript.plainenglish.io/what-is-optimistic-ui-656b9d6e187c#:~:text=An%20Optimistic%20User%20Interface%20is%20a%20design,a%20user%20performs%20an%20action%20(such%20as%E2%80%A6) (known as [client-side prediction](https://en.wikipedia.org/wiki/Client-side_prediction) in the gaming world) takes a different approach - instead of seeking to reduce actual latency, it seeks to reduce [perceived latency](https://developer.mozilla.org/en-US/docs/Learn/Performance/Perceived_performance) (i.e. how fast a website seems to the user), which as [demonstrated in product design](https://medium.com/@danielpidcock/actual-usability-vs-perception-of-usability-db236cd77bde) is often just as powerful. For our whiteboard application, this means the latency will still exist, but it will not be as apparent to the user. Optimistic UI works like this: + +[graphic here] + +An important implication of implementing optimistic UI is that each client has a local replica of the state that must be kept in sync with the server. Thus using it in our whiteboard app means that it now has distributed state. [Figma uses this same technique](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) - when a client opens a Figma design file, a copy of the document is sent from the server to the client and it must be kept in sync: + +[graphic here] + +However, as we’ll see in the next section, maintaining multiple copies of client state and a server state in the context of shared editing means conflicts can and will arise. + +### Inevitability of conflicts + +Since the advent of Google Docs, the ability for multiple clients to simultaneously edit a document has [become commonplace](https://diginomica.com/brief-history-collaborative-documents). However, simultaneous editing [invariably leads to shared state conflicts](https://rocicorp.dev/blog/ready-player-two) because multiple clients can make changes to the same part of the state at the same time. Using our whiteboard app as a demonstration let’s say client A decides that they want to change the color of an existing blue shape to green, while client B decides they want to change the color of the same shape to red at the same time: + +[graphic here] + +If these changes occur simultaneously, a conflict clearly occurs and to maintain a consistent, synchronized view across clients (i.e. state convergence), there must be some kind of conflict-resolution strategy in place + +### Conflict Resolution Strategies + +There are [several well-known strategies](https://exaspark.medium.com/top-5-ways-to-implement-real-time-rich-text-editor-ranked-by-complexity-3bc26e3c777f) for resolving conflicts in a distributed state, including: + +- Transactional Conflict Resolution +- Conflict-free Replicated Data Types (CRDTs) +- Operational Transformation (OT) + +However, before comparing strategies, it is worth reiterating that the initial decision to focus on apps using the client-server architecture affords the option to designate the server as the source of truth and the machine with the sole authority to resolve conflicts to ensure state convergence. Whereas with a peer-to-peer architecture, the only option to ensure state convergence is to use some kind of [consensus algorithm](https://www.baeldung.com/cs/consensus-algorithms-distributed-systems), which can be complex and difficult to implement. + +#### Transactional Conflict Resolution + +[Transactional conflict resolution](https://rocicorp.dev/blog/ready-player-two), also known as Client-side Prediction and Server Reconciliation [in video games](https://www.gabrielgambetta.com/client-side-prediction-server-reconciliation.html), is a technique to resolve conflicts using the intent of each state change rather than the outcome of each change to ensure that state converges. + +This means that if a change is intended to be applied relative to the current state (e.g. adding 1 to a count shared across multiple clients), multiple changes that could be considered conflicting would be stacked on top of each other instead. For example: + +[graphic here] + +However, if a change is meant to be [deterministic](https://en.wikipedia.org/wiki/Deterministic_algorithm), meaning the same outcome is produced based on the same input (e.g. changing the color of shape), multiple changes to that property would result in the last one to arrive as the outcome: + +[graphic here] + +The process of transactional conflict resolution is somewhat simple to reason about and [works as follows](https://rocicorp.dev/blog/ready-player-two): + +- If two clients make a concurrent change to the same object but modify a different property, no conflicts occur. Because clients only send the **intent **of a change, these can both be processed in the order of arrival by the server + +[graphic here] + +- When concurrent changes occur to the same property, a conflict occurs. By default, the server resolves this conflict using a simple [Last Write Wins](https://dzone.com/articles/conflict-resolution-using-last-write-wins-vs-crdts) (LWW) approach. The server then broadcasts the resolved state to all clients. + +[graphic here] + +- However, depending on the application, it is possible to build in any custom conflict resolution that would override the default Last Write Wins Behavior + +While this strategy may not be best suited for use cases where LLW is not the desired default resolution strategy or for decentralized architectures, it is highly flexible and easy to reason about + +#### Conflict-Free Replicated Data Types (CRDTs) + +A CRDT is a technique to solve conflicts using [a complex data structure that relies on the mathematical properties of commutativeness](https://en.wikipedia.org/wiki/Conflict-free_replicated_data_type) (i.e. states can be merged in any order and the same result will be produced) to ensure that conflicts are resolved and states converge. There are CRDTs designed for different use cases, but broadly, [there are two categories](https://jakelazaroff.com/words/an-interactive-intro-to-crdts/): + +- State-based CRDTs which transmit their full state between peers, and a new state is obtained by merging all the states together +- Operation-based CRDTs which transmit only the actions that users take, which can be used to calculate a new state + +We will use a simple operation-based CRDT example to demonstrate how they work in a broad sense: + +[graphic here] + +Generally, although CRDTs [can be used in server authority models](https://exaspark.medium.com/top-5-ways-to-implement-real-time-rich-text-editor-ranked-by-complexity-3bc26e3c777f), they are best suited [for decentralized systems](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) because they do not require an authoritative server. CRDTs are also a strong fit for [applications with offline support](https://exaspark.medium.com/top-5-ways-to-implement-real-time-rich-text-editor-ranked-by-complexity-3bc26e3c777f) because the data structure can preserve edits by an offline client and automatically merge them when the client regains connectivity. + +However, CRDTs require a lot of [computational and bandwidth overhead](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) and are [overkill for some use cases where they are applied](https://rocicorp.dev/blog/ready-player-two). + +#### Operation Transformation (OT) + +OT is a technique to solve conflicts using [a set of algorithms that compare concurrent operations]() and detect if the operations will allow the state to converge. If not, the operations are modified (or transformed) to resolve conflicts before being applied to the state: + +[graphic here] + +Much like CRDTs, OT is known to be complex to reason about and can [theoretically be implemented in a distributed fashion](https://digitalfreepen.com/2018/01/04/operational-transform-hard.html), however, it is overly complex so most OT implementations rely on a central server, which is still complex to implement itself. Unlike CRDTs, however, OT [is known to be less overhead](https://news.ycombinator.com/item?id=23806285#:~:text=You%20can%20approximately%20view%20it,store%20a%20lot%20of%20metadata.). + +### Choosing a Strategy + +As illustrated, no one-size-fits-all solution for conflict resolution exists because it depends on developer preference, application requirements, and the application’s architecture. However, because transactional conflict resolution meshes well with the client-server model, is the most flexible (it can even be used in tandem with CRDTs), and gives control back to the developer to resolve any conflict how they see fit, it is a natural fit for many real-time collaborative applications + +## Real-time Collaboration in an Application + +As demonstrated WebSockets and transactional conflict resolution are a strong fit for many real-time, collaborative applications. However, there are additional considerations if we were to build a production-ready collaborative application. + +### Rooms + +Returning to our whiteboard example, once clients have sent a request to connect to the whiteboard, we’d need a way to maintain their WebSocket connection, handle incoming updates, and then broadcast those updates to each client's WebSocket connections. Multiple collaborative application framework providers ([Reflect](https://hello.reflect.net/concepts/rooms) and [Liveblocks](https://liveblocks.io/docs/concepts/how-liveblocks-works#Rooms)) refer to this concept of a group of active WebSocket connections and a document as a “Room.” It is also the term Syncosaurus adopted in its terminology and we will be using it throughout the rest of this case study. + +### Client Routing + +Let’s also assume we want to extend our application to allow a user to create multiple whiteboards and collaborate on each one with a unique set of other users. To achieve this, we’d need a routing mechanism to ensure clients are connected to the correct room and can initially load the correct document. + +### Document Storage + +Finally, let’s assume we want to extend our whiteboard application to allow clients to collaborate on the same document across multiple sessions. To achieve this, we’d need a storage mechanism to enable the persistent storage and retrieval of documents upon room connection. + +# Solutions + +Now that we understand some of the considerations of building real-time collaborative applications, let’s imagine we were to follow through with the implementation of our whiteboard application. Broadly, we’d have two options: + +- **DIY** - provision infrastructure and build everything from scratch and/or integrate existing tools +- **Commercial** - use a comprehensive framework that addresses infrastructure, state syncing, and conflict resolution for real-time collaborative applications + +## DIY + +From a simplified perspective, implementing a DIY solution will consist of the following steps: + +- Deploy Infrastructure: + 1. Choose a cloud provider (e.g. AWS) + 2. Set up servers to maintain WebSocket connections + 3. Set up persistent storage for documents + 4. Set up routing for clients +- Write application code: 5. Research and implement a conflict-resolution and state-syncing strategy (e.g. [YJS](https://yjs.dev/) could be used for CRDTs) 6. Write backend logic to handle updates from clients, manage shared state via the chosen conflict-resolution strategy, persist state to storage, and broadcast updates to clients via WebSockets 7. Write client logic to capture user events, make changes to the state, implement optimistic UI, and communicate with the server + +As you can see, building from scratch is quite an undertaking, even if you take advantage of existing tools. However, this approach does offer greater control and customization over the entire system. + +## Commercial + +Some of the most notable commercial solutions are [Liveblocks](https://liveblocks.io/) and [Reflect](https://reflect.net/), which are primarily differentiated by the conflict resolution model each one employs. These commercial solutions offer convenience by abstracting much of the discussed complexity of a DIY solution by automatically deploying the infrastructure and handling the backend logic while exposing a client-side SDK to developers. However, this convenience comes with a price - these solutions each use a monthly [freemium](https://www.investopedia.com/terms/f/freemium.asp#:~:text=our%20editorial%20policies-,What%20Is%20Freemium%3F,for%20supplemental%20or%20advanced%20features.) pricing model. Liveblocks paid tiers start at $99 / month and Reflect paid tiers start at $30 / month as of the time of writing this. Additionally, using a commercial solution limits the amount of control and customization the developer has over the backend of their application. + +## Where does Syncosaurus fit in? + +Syncosaurus is a React Javascript client-side SDK with full ready-to-be-deployed backend functionality. It is best suited for developers of small-to-medium-sized applications who want to rapidly develop and ship real-time, collaborative features in their applications. + +Similar to commercial solutions like Liveblocks and Reflect, Syncosaurus exposes a client-side SDK while abstracting the backend logic and handling much of the deployment - the only thing a developer has to do to get the backend deployed is sign up for a Cloudflare account and use our CLI to deploy. However, unlike the commercial solutions, the Syncosaurus framework is free to use and open source so a developer can alter the default backend code if they choose. + +[insert comparison table] + +# Using Syncosaurus + +To better understand Syncosaurus we will explore the syncing model and then walk through how a developer might use the tool. + +## Syncing Model + +As mentioned, Syncosaurus uses a real-time syncing model with transactional conflict resolution to keep state consistent across multiple clients: + +- When a client makes a change to state, it is immediately applied to the client’s locally and the client places a copy of the intent of the change (i.e. a state mutation) in a pending queue. +- Next, the mutation is sent across the WebSocket connection to the Syncosaurus server. + +[graphic here] + +- Once the change is made to the authoritative state, the server sends a confirmation update to the client, which the client then uses to update its state to match the server and remove the pending state mutation from the queue. + +[graphic here] + +- When more than one client is connected to a given room, any mutations from one client are broadcast to all other clients by the server. Because an update from the server is authoritative, all client states are guaranteed to converge. + +[graphic here]) + +## Development + +Now that we understand the fundamental syncing model of Syncosaurus, we will discuss how to use the framework. + +### CLI Setup + +The first step to use Syncosaurus is to install the CLI tool by running `npm install -g syncosaurus-cli` + +Next one can choose to add Syncosaurus to an existing React project using `npx syncosaurus setup` or create a project from scratch using `npx syncosaurus init` + +[insert nice CLI graphic / gif] + +### Create and launch + +To use Syncosaurus in a React application’s code, one should import and initialize Syncosaurus: + +```JavaScript +const synco = new Syncosaurus({ + mutators, + userID: user.id, +}); +``` + +Next define the logic to create and/or join a room by passing in a RoomID to the `launch` method: + +```JavaScript +synco.launch(roomID); +``` + +### Model Data Shape + +Next, one should model the data shape that backs their application. Though the data shape of the key-value data store (i.e. document) is not strictly enforced, modeling it upfront allows a developer to better reason about their application logic + +The shape for our to-do list could look like this in JavaScript: + +```JavaScript +{ + 'todo/1234': { + id: 1234, + text: 'walk the dog', + complete: true + }, + 'todo/1235': { + id: 1235, + text: 'take out the trash', + complete: false + } +} +``` + +### Define Mutators + +Next, we need to define the “write” logic for the application using mutators. Mutators are javascript developer-defined functions that contain the logic to update and manipulate the shared state based on user events in your application. + +A mutator to add a new to-do to a list could look like this: + +```Javascript +function addTodo(tx, { id, text }) { + const todo = { id, text, complete: false }; + await tx.set(`todo/${id}`, todo); + return todo; +} +``` + +### Define Subscriptions + +Finally, to render the shared state on the client, we need to read the data from our local key-value store and determine how to display it using subscriptions. A subscription is implemented in the client code using a custom React hook called `useSubscribe` that reads data from the local store and re-renders components when updates to the value(s) for a specific key or set of keys (known as a watchlist) in the local storage occur. + +A subscription to get all todos could look like this: + +```Javascript + const todos = useSubscribe( + syncosaurus, + (tx) => { + let todoObject = tx.scan(key => { + return key.includes('todo'); + }); + return Object.values(todoObject); + }, + [] + ); +``` + +### Putting it together + +We have prepared a sample todo list application to demonstrate the mutator and client code and the behavior we expect. + +[insert code example] + +Go ahead and enter some todos into Client 1: + +[insert todo list demo] + +## Deployment + +After you’re satisfied with the local version of the application, it can be deployed to Cloudflare by running `npx syncosaurus deploy`. Your deployed Cloudflare architecture will consist of Cloudflare Workers and Durable Objects. For each room your clients create, a new Durable Object will be created and any client will be able to connect to it through a worker: + +## Monitoring + +After your application is deployed, you can monitor its usage and get help debugging via the analytics dashboard and a live tail log. + +The dashboard includes hourly time-series metrics related to errors and usage for each room so you can verify users are able to access and use the application in a bug-free manner + +[insert screenshot of dashboard] + +For even more detail, a tail logging session for your deployed backend can be started by running `npx syncosaurus tail` + +# Building Syncosaurus + +Now that we understand Syncosaurus at a high level, we will discuss how we built it, starting with a brief recap on requirements, then a discussion on architecture, followed by a discussion on decisions and tradeoffs made while building Syncosaurus. + +## Requirements + +Before we can discuss the architecture of Syncosaurus, it’s important to summarize the requirements we’ve mentioned so far. Since we are building Syncosaurus to support production-ready applications, at a minimum it should support: + +- The syncing model with transactional conflict resolution +- Multiple concurrent rooms (maintaining WebSocket connections and broadcasting messages) +- Persistent storage of documents + +[insert graphic of multiple rooms with clients connected and a new client trying to connect to a particular room] + +## Architecture + +### Server vs Serverless + +There are many different models of cloud computing [ranging from infrastructure-as-a-service to serverless](https://azure.microsoft.com/en-us/resources/cloud-computing-dictionary/what-is-cloud-computing) and each one offers varying degrees of infrastructure upkeep and flexibility. While server-based models (e.g. virtual private servers) offer greater control over the infrastructure, when choosing a model for Syncosaurus we quickly narrowed in on a [serverless model](https://martinfowler.com/articles/serverless.html#WhatIsServerless) (i.e. [functions-as-a-service](https://www.redhat.com/en/topics/cloud-native-apps/what-is-faas)) due to its alignment with our use case of supporting the rapid development and release of real-time features in small-to-medium sized applications, including: + +- Less overhead because there is no need to manage and maintain servers +- Granular scalability which creates potential cost savings as there are fewer wasted resources compared to a server-based model where you have to pay for the server even if it is not being used +- High availability which can reduce response times and aid in meeting real-time latency requirements + +Although, serverless is not without its tradeoffs including [cold start issues and challenges around testing and debugging](https://www.cloudflare.com/learning/serverless/why-use-serverless/) + +### Traditional Cloud vs Edge + +Several serverless model cloud providers offer both traditional and edge-based options (e.g. AWS Lambda vs AWS Lambda@Edge). Traditional cloud computing connotes remote servers in managed data centers that are not necessarily close to their clients which can increase latency. Whereas edge computing means servers and data storage are positioned “as close as possible” to the source of data with the intent of reducing latency. + +For Syncosarus, we ultimately elected to deploy on the edge and accept tradeoffs around [added complexity and reduced robustness](https://www.kio.tech/en-us/blog/data-center/advantages-and-disadvantages-of-edge-computing) since reducing latency in real-time applications is paramount. + +### Cloudflare Workers and Durable Objects + +When choosing a provider to build on, we narrowed in on a couple of options + +First, we could have built our serverless edge infrastructure using a combination of AWS Lambda@Edge, Amazon API Gateway, and a persistent storage mechanism like AWS Dynamo DB: + +[insert graphic] + +While this is a perfectly valid approach, it does involve provisioning and connecting several components which can increase the complexity of deployment and maintenance. + +As previously mentioned, we instead ended up choosing a Cloudflare-based architecture consisting of Workers and Durable Objects due to its simplicity and extremely strong fit for our use case. + +[insert graphic] + +A Worker is an edge-based serverless function on the Cloudflare network. A Durable Object (DO) is a special type of Worker - a globally unique [JavaScript isolate ](https://v8docs.nodesource.com/node-0.8/d5/dda/classv8_1_1_isolate.html)(a unique JS engine) with access to its own private strongly consistent [storage](https://developers.cloudflare.com/durable-objects/api/transactional-storage-api/) and built-in [caching](https://developers.cloudflare.com/durable-objects/reference/in-memory-state/#:~:text=The%20Durable%20Object's%20storage%20has,be%20instantly%20returned%20from%20cache.). + +DOs provide a single point of coordination for WebSockets and have built-in document persistence allowing us to make the workers stateful without the use of a remote persistent storage mechanism like Dynamo DB in the above AWS solution, which can lead to increased latency. It is important to note that a DO (including its persistent storage) can be [geographically migrated based on client location, which limits the latency negation of requests accessing storage](https://developers.cloudflare.com/durable-objects/reference/data-location/#provide-a-location-hint), an important factor when deciding between cloud vs edge + +However, it should also be noted that DOs have limitations, most notably that the persistent storage only supports key-value pairs and that a DO has a soft limit of 1,000 requests per second. This means that depending on the volume of requests a single client sends and the number of concurrent WebSocket connections, a DO could run into scaling issues. + +As we’ve defined, real-time collaborative applications should emulate at most a board meeting (~15 WebSocket connections), not a town hall (~100 WebSocket connections), therefore scaling concerns around the number of concurrent WebSocket connections and the number of requests per second were minor with optimizations put in place as we’ll discuss shortly + +## Engineering Challenges + +When engineering Syncosuaurus, we had to be thoughtful about the efficiency of the syncing system and ensure that a developer using the framework would have a pleasant experience. In this section, we will discuss some of the considerations that went into those engineering decisions. + +### Challenge: Authoritative Update Size + +A naive implementation of authoritative updates sent from the server to clients would be to broadcast the entire state from the server to all clients when each change occurs. However, an issue with this approach is that as the document grows in size, the message size containing the authoritative state sent from the server to the client will grow equivalently. This has two consequences: + +- Larger update sizes mean that the WebSocket messages will take longer to transmit +- Once a message arrives at the client, it will take longer to process and update its entire local state + +An alternative approach to prevent this is to send an update that only contains the changes that the server, also known as a [delta update](https://en.wikipedia.org/wiki/Delta_update) approach: + +[insert example delta update message example here] + +We ultimately decided on the delta update approach for the efficiency gains, however, this decision introduced the risk that a missed update by a client could lead to a divergent state. + +### Challenge: Missed Authoritative Updates + +As mentioned, a risk of using delta updates is the heightened potential for missed messages and divergent state. This is because [when a WebSocket connection temporarily drops and reconnects, missed updates can occur in the interim](https://socket.io/docs/v4/connection-state-recovery). Therefore, we needed to implement a connection state recovery mechanism that would bring the client back up to date in this scenario. + +To do so, we implemented an incrementing `batchID` which is sent by the DO as a property on every update message broadcasted to the clients. Each client tracks the `batchID` of the last message it received from the DO and when it receives a new message, it compares the previous `batchID` against the new one to determine if it missed an update. If a client misses an update, it sends a special request to the DO for a copy of the entire latest state. + +[insert diagram of process] + +Note that sending only the delta updates missed could reduce the state recovery message size and latency, however, the DO currently does not keep a log of the updates it broadcasts. This is an area for future investigation since it would likely create greater memory and storage demands on the DO. + +### Challenge: Authoritative Update Frequency + +Another area of consideration was the trigger mechanism of authoritative updates sent by the DO. Generally, we considered two approaches: + +- Event-driven model +- Time-driven model + +#### Event-driven model + +Using an event-driven model means that for every message sent by a single client to the DO, M update messages are broadcasted by the DO, where M represents the number of connected clients. While this approach requires simple logic, in production, it can quickly present a scaling concern. + +If we assume all clients are sending messages simultaneously and we are targeting a certain message per second rate (i.e. [frame rate per second (FPS)](https://www.100ms.live/blog/frame-rate#)) broadcasting would scale at a rate of O(M^2\*N) where N represents the number of messages sent per second by a single client + +[insert graphic] + +In [testing](https://news.ycombinator.com/item?id=37942258) done by Reflect, the target budget of a DO should be approximately 2,000 calls per second to `WebSocket.send `(a call to transmit a message over a WebSocket connection). This means, that if an app wants to target 60 FPS (a standard [in gaming](https://www.100ms.live/blog/frame-rate#)) it can only have 6 concurrent users (60 messages/second = 2000 calls / (6 users^2)). While a 6-user limit is suitable for some applications, it does shrink the pool of applications Syncosaurus could support. + +#### Time-driven model + +A time-driven model means that the DO would group state changes into a single update and send out a periodic message based on a configurable time frequency + +[insert graphic] + +This frequency directly correlates with the frame rate and makes the messaging system scale at a rate of O(M\*N). Therefore, if an app wanted to target 60 FPS (approximately every 16ms), it can support up to 33 concurrent connections. + +The tradeoff with this approach is that a message will be sent whether an update has occurred or not, meaning there may be unnecessary empty messages sent. However, we decided this tradeoff was worth it to make our messaging more efficient (message scales at a rate of O(M*N) instead of O(M^2 * N)) and to expand the pool of Syncosaurus-compatible applications. + +[insert graphic] + +### Challenge: Re-rendering and Subscriptions + +An additional consideration was reducing unnecessary client-side rendering in React and making our subscription system robust. A naive implementation of subscriptions would re-rendered the entire UI every time an update from the server was received. However, this could lead to [performance bottlenecks](https://medium.com/@nadeem.ahmad.na/react-bottlenecks-uncovered-a-comprehensive-guide-to-solving-common-performance-issues-in-your-app-90a3f98b3669) and does not take advantage of React’s model to re-render modular components individually when an update to the state they are concerned with occurs. + +To make subscriptions fit React’s granular rendering model, we decided to allow developers to write query functions on per component basis that indicate which keys in the local store they want to watch for updates (known as a key “watchlist”). Furthermore, by allowing subscriptions to accept a query callback, the developer can transform data in this callback before returning the value to React to be rendered. Finally, an additional mechanism we put in place to reduce unnecessary re-renders was a check to ensure the result of the query had changed since its last rerender (i.e. memoization), otherwise a new render would not be initiated. + +[insert diagram of process] + +Though, there may be additional memory overhead with memoizing query results and maintaining a key watchlist, eliminating unnecessary UI re-renders and making subscriptions more robust leads to a snappier UI and gives developers more control over the rendering of their application, respectively + +### Challenge: Ease of use + +The last area of consideration was how to make Syncosaurus easier to use by other developers. After researching several solutions in the space and putting ourselves in a developer’s shoes, we decided to implement a couple of additional features: + +- Optional authentication support for room access using JWTs +- An Analytics Dashboard to monitor and debug rooms + +#### Authentication + +The Syncosaurus framework supports token-based authentication that allows a developer to enforce proper room access if they choose. JWTs are commonly utilized for this, but other types of token-based authentication like OAuth can be used as well. To implement authentication, a developer must provide two components to work with our authentication handler: + +- A token(s) or preferably a library or service that can generate new tokens +- An authentication service that verifies the validity of tokens + +#### Analytics Dashboard + +As demonstrated, Syncosaurus includes an analytics tool to easily view and analyze aggregate and single-room metrics for an application. The dashboard allows a developer to gain insights into usage and debug their application if necessary. The architecture for the analytics dashboard displays data from Cloudflare’s endpoints and visualizes it in a locally running front-end application that pulls from a custom-built GraphQL backend : + +[insert graphic] + +# Future of Syncosaurus + +And that's Sycosaurus! While it fully supports real-time collaborative applications like the puzzle shown on our landing page and beyond, there is still much room for improvement and feature parity with existing solutions. A few areas we plan to investigate next are: + +- Offline mode support +- Undo/redo support +- More robust web socket connection handling +- More syncing model efficiency improvements + +For more information regarding how to use Syncosaurus please see our documentation From cd3b1af89960a92481cf0c3290624a5c643bf6bf Mon Sep 17 00:00:00 2001 From: emargetis Date: Sat, 20 Apr 2024 20:51:29 -0500 Subject: [PATCH 05/13] feat (case study): cleaned up case study and added code snippets Co-authored-by: Alex Sklar Co-authored-by: Franco Waisfeld Co-authored-by: Joseph Liang --- src/pages/case-study.mdx | 306 ++++++++++++++++++++++---------- src/pages/todo-list-client.jsx | 62 +++++++ src/pages/todo-list-mutators.js | 14 ++ 3 files changed, 284 insertions(+), 98 deletions(-) create mode 100644 src/pages/todo-list-client.jsx create mode 100644 src/pages/todo-list-mutators.js diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index f0f37a9..adc772b 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -8,61 +8,18 @@ import TodoList from '@site/src/components/TodoList/TodoList' import Tabs from '@theme/Tabs' import TabItem from '@theme/TabItem' -## Overview +# Overview - +Syncosaurus is a React-Javascript developer framework for rapidly building browser-based real-time, collaborative web applications backed by Cloudflare Workers and Durable Objects. -Syncosaurus is a React Javascript developer framework for rapidly building real-time, collaborative applications backed by the Cloudflare edge network of Workers and Durable Objects In this case study, we will: -- define real-time collaborative applications -- explain why they are not trivial to build -- explore existing solutions -- discuss core concepts to understand and use Syncosaurus -- explain how Syncosaurus was built -- discuss potential future improvements - -### Preface on architecture - -At a fundamental level when multiple users are “collaborating” on the same artifact, they are exchanging data to manipulate the synchronized view of the artifact. Practically, this means that all users who are observing and making changes to the artifact on the web application will need to exchange information back and forth in real-time via the open internet. - -Although there are numerous architectures for web applications, they can broadly be categorized as: - -- **Centralized** such as the client-server architecture where client machines send resource requests to a backend server. In the client-server architecture, the server is generally authoritative, meaning it is the source of truth. - - - -- **Decentralized** such as the peer-to-peer architecture where every machine (known as a node) is treated equally and responsible for sending and responding to requests for resources. In the peer-to-peer architecture, every machine has equal authority and a consensus must usually be reached to determine the truth. - -Though it is possible to build decentralized real-time collaboration web apps, it is notoriously complex and many existing real-time collaborative apps use a form of the client-server architecture. This is because the client-server architecture is often more efficient and easier to maintain, although, it does introduce a single point of failure risk. -Given this and the predominance of the client-server architecture in web apps, we will assume that any application considering Syncosaurus will be using some form of a centralized backend. Note that the centralized backend of a client-server architecture can be made up of many servers in the case of a distributed client-server architecture, however, we will still refer to the backend collectively as the “server”. - -# Building Real-Time Collaborative Applications Is Not Trivial - -On the surface, building real-time collaborative applications may not seem any different than building other web applications, however, if we break down each word of “real-time collaboration” into more concrete and technical definitions, we quickly realize that is not the case. - - - - ``` Javascript console.log('hello') console.log('hello') ``` - - - ``` Javascript console.log('subscriptions'); console.log('subscriptions'); - ``` - - - - - -# Overview - -- Syncosaurus is a React-Javascript developer framework for rapidly building browser-based real-time, collaborative web applications -- In this case study, we will: - - define real-time collaborative applications - - explain why real-time collaborative applications are not trivial to build - - compare existing solutions used to facilitate building collaborative applications, including Syncosaurus - - discuss how to use Syncosaurus - - explain how Syncosaurus was built - - discuss future improvements for Syncosaurus +- Define real-time collaborative applications +- Explain why real-time collaborative applications are not trivial to build +- Compare existing solutions used to facilitate building collaborative applications, including Syncosaurus +- Discuss how to use Syncosaurus +- Explain how Syncosaurus was built +- Discuss future improvements for Syncosaurus # Introduction @@ -83,23 +40,19 @@ At a fundamental level when multiple users are “collaborating” on the same a - Centralized - Decentralized -### Centralized - Centralized includes the client-server architecture where client machines send resource requests to a backend server. In the client-server architecture, the server is generally [authoritative](https://medium.com/mighty-bear-games/what-are-server-authoritative-realtime-games-e2463db534d1), meaning it is the source of truth. [graphic here] -### Decentralized - -Decentralized includes the peer-to-peer architecture where every machine (known as a node) is treated equally and is responsible for sending for and responding to requests for resources. In the peer-to-peer architecture, every machine has equal authority and a consensus must usually be reached to determine the truth +Decentralized includes the peer-to-peer architecture where every machine (known as a node) is treated equally and is responsible for sending for and responding to requests for resources. In the peer-to-peer architecture, every machine has equal authority and a consensus must usually be reached to determine the truth. [graphic here] -Though [it is possible](https://www.tag1consulting.com/blog/yjs-webrtc-part-1) to build decentralized real-time collaboration web apps, decentralized architectures are notoriously complex. Instead [many existing real-time collaborative apps use a form of the client-server architecture](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) due to their comparative [efficiency and ease of maintenance](https://fwx.finance/learn/article/centralized-app-vs-dapp). Therefore, we will assume that any application considering Syncosaurus will be using a form of centralized architecture +Though [it is possible](https://www.tag1consulting.com/blog/yjs-webrtc-part-1) to build decentralized real-time collaboration web apps, decentralized architectures are notoriously complex. Instead [many existing real-time collaborative apps use a form of the client-server architecture](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) due to their comparative [efficiency and ease of maintenance](https://fwx.finance/learn/article/centralized-app-vs-dapp). Therefore, we will assume that any application considering Syncosaurus will be using a form of centralized architecture. # Building Real-Time Collaborative Applications Is Not Trivial -Initially, building real-time collaborative web apps may not seem different than building other web apps, however, if we break down each word of “real-time collaboration” into more concrete requirements, we quickly realize that is not the case +Initially, building real-time collaborative web apps may not seem different than building other web apps, however, if we break down each word of “real-time collaboration” into more concrete requirements, we quickly realize that is not the case. ## What Does Real-time Entail? @@ -115,9 +68,9 @@ The need for real-time depends on the web application and generally apps that mi - [Collaborative productivity and e-learning](https://www.mdpi.com/2079-9292/11/24/4152) - [Video conferencing](https://21stcenturyav.com/good-latency-for-video-conferencing/) -To illustrate this need and the impact latency can have on a user’s experience, use the demo below and notice how increased latency causes a noticeable delay in changing the red circle’s position to match the blue one: +To illustrate this need and the impact latency can have on a user’s experience, drag the blue slider below and notice how higher latencies cause a noticeable delay in updating the red slider’s position to match: -[graphic here] + ### Achieving Real-time Communication @@ -127,7 +80,7 @@ At the application layer of the internet, HTTP underpins much of the communicati - WebSockets - WebTransport -Note that using [streams over HTTP/2](https://getstream.io/blog/communication-protocols/) was also considered due to its bi-directional nature and built-in multiplexing, however, the need to broadcast data to multiple clients in real-time collaborative apps (which we will discuss later) made them unsuitable for our purposes +Note that using [streams over HTTP/2](https://getstream.io/blog/communication-protocols/) was also considered due to its bi-directional nature and built-in multiplexing, however, the need to broadcast data to multiple clients in real-time collaborative apps (which we will discuss later) made them unsuitable for our purposes. #### Long Polling @@ -135,7 +88,7 @@ Long polling is a technique to emulate server push communications via normal HTT [graphic here] -Although every browser supports long polling, it has high latency compared to other options such as WebSockets, and a risk of missing messages without extensive code on the client and server. Therefore, long polling [is generally better suited as a fallback option as opposed to a primary means of bi-directional communication](https://ably.com/topic/long-polling#:~:text=HTTP%20long%20polling%20solves%20the,make%20requests%20and%20servers%20respond.) +Although every browser supports long polling, it has high latency compared to other options such as WebSockets, and a risk of missing messages without extensive code on the client and server. Therefore, long polling [is generally better suited as a fallback option as opposed to a primary means of bi-directional communication](https://ably.com/topic/long-polling#:~:text=HTTP%20long%20polling%20solves%20the,make%20requests%20and%20servers%20respond.). #### WebSockets @@ -143,9 +96,9 @@ Although every browser supports long polling, it has high latency compared to ot [graphic here] -Once the handshake is complete, the WebSocket connection is established and both parties are now free to transmit data at any time +Once the handshake is complete, the WebSocket connection is established and both parties are now free to transmit data at any time. -Overall, Websockets are [low latency compared to HTTP](https://ably.com/topic/websockets-pros-cons) and [are widely supported in modern browsers](https://caniuse.com/websockets), though they can be somewhat tricky to scale and maintain in production because the connections [have to remain open and there is a risk of message loss when connections are interrupted](https://ably.com/topic/websockets-pros-cons) +Websockets are [low latency compared to HTTP](https://ably.com/topic/websockets-pros-cons) and [are widely supported in modern browsers](https://caniuse.com/websockets), though they can be somewhat tricky to scale and maintain in production because the connections [have to remain open and there is a risk of message loss when connections are interrupted](https://ably.com/topic/websockets-pros-cons). #### WebTransport @@ -153,7 +106,7 @@ WebTransport is an application layer protocol built on the [QUIC protocol, a mor While the characteristics of WebTransport make it seem like a strong [fit for real-time collaborative ](https://www.videosdk.live/blog/websocket-vs-webtransport#what-is-websocket)web apps, the technology has [yet to reach the same level of browser support as previously mentioned options](https://caniuse.com/webtransport). -### Choosing A Technique +### Choosing a Technique With real-time collaborative apps requiring a communication option with low latency, bi-directional messaging, wide browser support, and minimal data loss, many developers, including us, opt to use WebSockets. Though, as noted Websockets are not without their concerns, which will be discussed later in the case study. @@ -175,7 +128,9 @@ If we assume the app is using a client-server architecture where the clients do ### Consistency vs Latency -One may assume that because our application is using WebSockets, the information would travel fast enough to meet real-time latency requirements. However, depending on where the backend server(s) is located (among other factors), [the distance between the client and the server can increase latency](https://www.inkandswitch.com/local-first/#1-no-spinners-your-work-at-your-fingertips). Unfortunately, this latency can create a laggy user experience for the change-initiating client while it waits to communicate with the server (note that this discussion alludes to the inverse relationship between state consistency and latency which is described by the [PACELC theorem](https://www.scylladb.com/glossary/pacelc-theorem/)). Using our whiteboard example, you can see that the users have a different experience when latency is introduced: +One may assume that because our application is using WebSockets, the information would travel fast enough to meet real-time latency requirements. However, depending on where the backend server(s) is located (among other factors), [the distance between the client and the server can increase latency](https://www.inkandswitch.com/local-first/#1-no-spinners-your-work-at-your-fingertips). Unfortunately, this latency can create a laggy user experience for the change-initiating client while it waits to communicate with the server (note that this discussion alludes to the inverse relationship between state consistency and latency which is described by the [PACELC theorem](https://www.scylladb.com/glossary/pacelc-theorem/)). + +Using our whiteboard example, you can see that the users have a different experience when latency is introduced: [graphic here] @@ -193,7 +148,9 @@ The edge network is a distributed computing paradigm that brings computation and Next, while [tuning our WebSocket messaging](https://pusher.com/blog/websockets-realtime-gaming-low-latency/#websockets-to-reduce-latency-and-ensure-smooth-gameplay) to be more performant could also help in reducing latency, this strategy reaches diminishing returns because there will always be at least some latency in the network. Therefore, it will only get us so far. -Finally, [optimistically updating the client’s UI](https://javascript.plainenglish.io/what-is-optimistic-ui-656b9d6e187c#:~:text=An%20Optimistic%20User%20Interface%20is%20a%20design,a%20user%20performs%20an%20action%20(such%20as%E2%80%A6) (known as [client-side prediction](https://en.wikipedia.org/wiki/Client-side_prediction) in the gaming world) takes a different approach - instead of seeking to reduce actual latency, it seeks to reduce [perceived latency](https://developer.mozilla.org/en-US/docs/Learn/Performance/Perceived_performance) (i.e. how fast a website seems to the user), which as [demonstrated in product design](https://medium.com/@danielpidcock/actual-usability-vs-perception-of-usability-db236cd77bde) is often just as powerful. For our whiteboard application, this means the latency will still exist, but it will not be as apparent to the user. Optimistic UI works like this: +Finally, [optimistically updating the client’s UI](https://javascript.plainenglish.io/what-is-optimistic-ui-656b9d6e187c#) (known as [client-side prediction](https://en.wikipedia.org/wiki/Client-side_prediction) in the gaming world) takes a different approach - instead of seeking to reduce actual latency, it seeks to reduce [perceived latency](https://developer.mozilla.org/en-US/docs/Learn/Performance/Perceived_performance) (i.e. how fast a website seems to the user), which as [demonstrated in product design](https://medium.com/@danielpidcock/actual-usability-vs-perception-of-usability-db236cd77bde) is often just as powerful. For our whiteboard application, this means the latency will still exist, but it will not be as apparent to the user. + +Optimistic UI works like this: [graphic here] @@ -233,17 +190,17 @@ However, if a change is meant to be [deterministic](https://en.wikipedia.org/wik [graphic here] -The process of transactional conflict resolution is somewhat simple to reason about and [works as follows](https://rocicorp.dev/blog/ready-player-two): +The process of transactional conflict resolution is somewhat simple to reason about. -- If two clients make a concurrent change to the same object but modify a different property, no conflicts occur. Because clients only send the **intent **of a change, these can both be processed in the order of arrival by the server +If two clients make a concurrent change to the same object but modify a different property, no conflicts occur. Because clients only send the intent of a change, these can both be processed in the order of arrival by the server [graphic here] -- When concurrent changes occur to the same property, a conflict occurs. By default, the server resolves this conflict using a simple [Last Write Wins](https://dzone.com/articles/conflict-resolution-using-last-write-wins-vs-crdts) (LWW) approach. The server then broadcasts the resolved state to all clients. +When concurrent changes occur to the same property, a conflict occurs. By default, the server resolves this conflict using a simple [Last Write Wins](https://dzone.com/articles/conflict-resolution-using-last-write-wins-vs-crdts) (LWW) approach. The server then broadcasts the resolved state to all clients. [graphic here] -- However, depending on the application, it is possible to build in any custom conflict resolution that would override the default Last Write Wins Behavior +However, depending on the application, it is possible to build in any custom conflict resolution that would override the default Last Write Wins Behavior While this strategy may not be best suited for use cases where LLW is not the desired default resolution strategy or for decentralized architectures, it is highly flexible and easy to reason about @@ -268,11 +225,13 @@ OT is a technique to solve conflicts using [a set of algorithms that compare con [graphic here] -Much like CRDTs, OT is known to be complex to reason about and can [theoretically be implemented in a distributed fashion](https://digitalfreepen.com/2018/01/04/operational-transform-hard.html), however, it is overly complex so most OT implementations rely on a central server, which is still complex to implement itself. Unlike CRDTs, however, OT [is known to be less overhead](https://news.ycombinator.com/item?id=23806285#:~:text=You%20can%20approximately%20view%20it,store%20a%20lot%20of%20metadata.). +Much like CRDTs, OT is known to be complex to reason about and can [theoretically be implemented in a distributed fashion](https://digitalfreepen.com/2018/01/04/operational-transform-hard.html), however, it is overly complex so most OT implementations rely on a central server, which is still complex to implement itself. + +Unlike CRDTs, however, OT [is known to be less overhead](https://news.ycombinator.com/item?id=23806285#:~:text=You%20can%20approximately%20view%20it,store%20a%20lot%20of%20metadata.). ### Choosing a Strategy -As illustrated, no one-size-fits-all solution for conflict resolution exists because it depends on developer preference, application requirements, and the application’s architecture. However, because transactional conflict resolution meshes well with the client-server model, is the most flexible (it can even be used in tandem with CRDTs), and gives control back to the developer to resolve any conflict how they see fit, it is a natural fit for many real-time collaborative applications +As illustrated, no one-size-fits-all solution for conflict resolution exists because it depends on developer preference, application requirements, and the application’s architecture. However, because transactional conflict resolution meshes well with the client-server model, is the most flexible (it can even be used in tandem with CRDTs), and gives control back to the developer to resolve any conflict how they see fit, it is a natural fit for many real-time collaborative applications. ## Real-time Collaboration in an Application @@ -294,25 +253,30 @@ Finally, let’s assume we want to extend our whiteboard application to allow cl Now that we understand some of the considerations of building real-time collaborative applications, let’s imagine we were to follow through with the implementation of our whiteboard application. Broadly, we’d have two options: -- **DIY** - provision infrastructure and build everything from scratch and/or integrate existing tools -- **Commercial** - use a comprehensive framework that addresses infrastructure, state syncing, and conflict resolution for real-time collaborative applications +- DIY which means provisionining infrastructure and building everything from scratch and/or integrating existing tools +- Commercial which means using a comprehensive framework that addresses infrastructure, state syncing, and conflict resolution for real-time collaborative applications ## DIY From a simplified perspective, implementing a DIY solution will consist of the following steps: -- Deploy Infrastructure: - 1. Choose a cloud provider (e.g. AWS) - 2. Set up servers to maintain WebSocket connections - 3. Set up persistent storage for documents - 4. Set up routing for clients -- Write application code: 5. Research and implement a conflict-resolution and state-syncing strategy (e.g. [YJS](https://yjs.dev/) could be used for CRDTs) 6. Write backend logic to handle updates from clients, manage shared state via the chosen conflict-resolution strategy, persist state to storage, and broadcast updates to clients via WebSockets 7. Write client logic to capture user events, make changes to the state, implement optimistic UI, and communicate with the server +1. Deploy Infrastructure: + 1. Choose a cloud provider (e.g. AWS) + 2. Set up servers to maintain WebSocket connections + 3. Set up persistent storage for documents + 4. Set up routing for clients +2. Write application code: + 1. Research and implement a conflict-resolution and state-syncing strategy (e.g. [YJS](https://yjs.dev/) could be used for CRDTs) + 2. Write backend logic to handle updates from clients, manage shared state via the chosen conflict-resolution strategy, persist state to storage, and broadcast updates to clients via WebSockets + 3. Write client logic to capture user events, make changes to the state, implement optimistic UI, and communicate with the server As you can see, building from scratch is quite an undertaking, even if you take advantage of existing tools. However, this approach does offer greater control and customization over the entire system. ## Commercial -Some of the most notable commercial solutions are [Liveblocks](https://liveblocks.io/) and [Reflect](https://reflect.net/), which are primarily differentiated by the conflict resolution model each one employs. These commercial solutions offer convenience by abstracting much of the discussed complexity of a DIY solution by automatically deploying the infrastructure and handling the backend logic while exposing a client-side SDK to developers. However, this convenience comes with a price - these solutions each use a monthly [freemium](https://www.investopedia.com/terms/f/freemium.asp#:~:text=our%20editorial%20policies-,What%20Is%20Freemium%3F,for%20supplemental%20or%20advanced%20features.) pricing model. Liveblocks paid tiers start at $99 / month and Reflect paid tiers start at $30 / month as of the time of writing this. Additionally, using a commercial solution limits the amount of control and customization the developer has over the backend of their application. +Some of the most notable commercial solutions are [Liveblocks](https://liveblocks.io/) and [Reflect](https://reflect.net/), which are primarily differentiated by the conflict resolution model each one employs. These commercial solutions offer convenience by abstracting much of the discussed complexity of a DIY solution by automatically deploying the infrastructure and handling the backend logic while exposing a client-side SDK to developers. + +However, this convenience comes with a price - these solutions each use a monthly [freemium](https://www.investopedia.com/terms/f/freemium.asp#:~:text=our%20editorial%20policies-,What%20Is%20Freemium%3F,for%20supplemental%20or%20advanced%20features.) pricing model. Liveblocks paid tiers start at $99 / month and Reflect paid tiers start at $30 / month as of the time of writing this. Additionally, using a commercial solution limits the amount of control and customization the developer has over the backend of their application. ## Where does Syncosaurus fit in? @@ -320,7 +284,64 @@ Syncosaurus is a React Javascript client-side SDK with full ready-to-be-deployed Similar to commercial solutions like Liveblocks and Reflect, Syncosaurus exposes a client-side SDK while abstracting the backend logic and handling much of the deployment - the only thing a developer has to do to get the backend deployed is sign up for a Cloudflare account and use our CLI to deploy. However, unlike the commercial solutions, the Syncosaurus framework is free to use and open source so a developer can alter the default backend code if they choose. -[insert comparison table] + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
DIYLiveblocksReflectSyncosaurus
Open-source
Managed Service
Easy to Deploy
Conflict Resolution MechanismAnyCRDTsTransactional Conflict ResolutionTransactional Conflict Resolution
Authentication Support
Offline Client Support
Analytics
# Using Syncosaurus @@ -341,7 +362,7 @@ As mentioned, Syncosaurus uses a real-time syncing model with transactional conf - When more than one client is connected to a given room, any mutations from one client are broadcast to all other clients by the server. Because an update from the server is authoritative, all client states are guaranteed to converge. -[graphic here]) +[graphic here] ## Development @@ -426,20 +447,109 @@ A subscription to get all todos could look like this: ); ``` -### Putting it together +### Putting it all together -We have prepared a sample todo list application to demonstrate the mutator and client code and the behavior we expect. +We have prepared a simple todo list application to illustrate the mutator and client code and the behavior we expect. -[insert code example] + + + ```Javascript + export default { + addTodo, + removeTodo, + } + + function addTodo(tx, { id, text }) { + const todo = { id, text, complete: false } + tx.set(`todo/${id}`, todo) + return todo + } + + function removeTodo(tx, { id }) { + tx.delete(`todo/${id}`) + } + ``` -Go ahead and enter some todos into Client 1: + + + ```Javascript + import { useState } from 'react' + import Syncosaurus from 'syncosaurus' + import { useSubscribe } from 'syncosaurus' + import mutators from '../mutators.js' + + const synco = new Syncosaurus({ + mutators, + userID: '1234', + server: import.meta.env.VITE_DO_URL, + }) + + synco.launch('yourRoomID') + + export default function App() { + const [inputValue, setInputValue] = useState('') + + function handleChange(e) { + setInputValue(e.target.value) + } + + function handleSubmit(e) { + e.preventDefault() + synco.mutate.addTodo({ + id: uuidv4(), + text: inputValue, + }) + + setInputValue('') + } + + function handleDelete(id) { + synco.mutate.removeTodo({ id }) + } + + const todos = useSubscribe( + synco, + tx => { + let todoObject = tx.scan(key => { + return key.includes('todo') + }) + return Object.values(todoObject) + }, + [] + ) + + return ( +
+
+ + +
+
    + {todos.map(todo => ( +
  • + {todo.text} + +
  • + ))} +
+
+ ) + } + ``` -[insert todo list demo] +
+
+ +Go ahead and enter some todos into Client 1 and watch them appear on Client 2 after a simulated latency of 1 second: + + ## Deployment After you’re satisfied with the local version of the application, it can be deployed to Cloudflare by running `npx syncosaurus deploy`. Your deployed Cloudflare architecture will consist of Cloudflare Workers and Durable Objects. For each room your clients create, a new Durable Object will be created and any client will be able to connect to it through a worker: +[insert screenshot of architecture] + ## Monitoring After your application is deployed, you can monitor its usage and get help debugging via the analytics dashboard and a live tail log. @@ -474,7 +584,7 @@ There are many different models of cloud computing [ranging from infrastructure- - Granular scalability which creates potential cost savings as there are fewer wasted resources compared to a server-based model where you have to pay for the server even if it is not being used - High availability which can reduce response times and aid in meeting real-time latency requirements -Although, serverless is not without its tradeoffs including [cold start issues and challenges around testing and debugging](https://www.cloudflare.com/learning/serverless/why-use-serverless/) +Although, serverless is not without its tradeoffs including [cold start issues and challenges around testing and debugging](https://www.cloudflare.com/learning/serverless/why-use-serverless/). ### Traditional Cloud vs Edge @@ -484,13 +594,13 @@ For Syncosarus, we ultimately elected to deploy on the edge and accept tradeoffs ### Cloudflare Workers and Durable Objects -When choosing a provider to build on, we narrowed in on a couple of options +When choosing a provider to build on, we narrowed in on a couple of options. First, we could have built our serverless edge infrastructure using a combination of AWS Lambda@Edge, Amazon API Gateway, and a persistent storage mechanism like AWS Dynamo DB: [insert graphic] -While this is a perfectly valid approach, it does involve provisioning and connecting several components which can increase the complexity of deployment and maintenance. +While this is a totally valid approach, it does involve provisioning and connecting several components which can increase the complexity of deployment and maintenance. As previously mentioned, we instead ended up choosing a Cloudflare-based architecture consisting of Workers and Durable Objects due to its simplicity and extremely strong fit for our use case. @@ -502,7 +612,7 @@ DOs provide a single point of coordination for WebSockets and have built-in docu However, it should also be noted that DOs have limitations, most notably that the persistent storage only supports key-value pairs and that a DO has a soft limit of 1,000 requests per second. This means that depending on the volume of requests a single client sends and the number of concurrent WebSocket connections, a DO could run into scaling issues. -As we’ve defined, real-time collaborative applications should emulate at most a board meeting (~15 WebSocket connections), not a town hall (~100 WebSocket connections), therefore scaling concerns around the number of concurrent WebSocket connections and the number of requests per second were minor with optimizations put in place as we’ll discuss shortly +As we’ve defined, real-time collaborative applications should emulate at most a board meeting (~15 WebSocket connections), not a town hall (~100 WebSocket connections), therefore scaling concerns around the number of concurrent WebSocket connections and the number of requests per second were minor with optimizations put in place as we’ll discuss shortly. ## Engineering Challenges @@ -542,7 +652,7 @@ Another area of consideration was the trigger mechanism of authoritative updates Using an event-driven model means that for every message sent by a single client to the DO, M update messages are broadcasted by the DO, where M represents the number of connected clients. While this approach requires simple logic, in production, it can quickly present a scaling concern. -If we assume all clients are sending messages simultaneously and we are targeting a certain message per second rate (i.e. [frame rate per second (FPS)](https://www.100ms.live/blog/frame-rate#)) broadcasting would scale at a rate of O(M^2\*N) where N represents the number of messages sent per second by a single client +If we assume all clients are sending messages simultaneously and we are targeting a certain message per second rate (i.e. [frame rate per second (FPS)](https://www.100ms.live/blog/frame-rate#)) broadcasting would scale at a rate of O(M^2\*N) where N represents the number of messages sent per second by a single client. [insert graphic] @@ -550,7 +660,7 @@ In [testing](https://news.ycombinator.com/item?id=37942258) done by Reflect, the #### Time-driven model -A time-driven model means that the DO would group state changes into a single update and send out a periodic message based on a configurable time frequency +A time-driven model means that the DO would group state changes into a single update and send out a periodic message based on a configurable time frequency. [insert graphic] @@ -568,7 +678,7 @@ To make subscriptions fit React’s granular rendering model, we decided to allo [insert diagram of process] -Though, there may be additional memory overhead with memoizing query results and maintaining a key watchlist, eliminating unnecessary UI re-renders and making subscriptions more robust leads to a snappier UI and gives developers more control over the rendering of their application, respectively +Though, there may be additional memory overhead with memoizing query results and maintaining a key watchlist, eliminating unnecessary UI re-renders and making subscriptions more robust leads to a snappier UI and gives developers more control over the rendering of their application, respectively. ### Challenge: Ease of use @@ -577,7 +687,7 @@ The last area of consideration was how to make Syncosaurus easier to use by othe - Optional authentication support for room access using JWTs - An Analytics Dashboard to monitor and debug rooms -#### Authentication +### Authentication The Syncosaurus framework supports token-based authentication that allows a developer to enforce proper room access if they choose. JWTs are commonly utilized for this, but other types of token-based authentication like OAuth can be used as well. To implement authentication, a developer must provide two components to work with our authentication handler: @@ -586,7 +696,7 @@ The Syncosaurus framework supports token-based authentication that allows a deve #### Analytics Dashboard -As demonstrated, Syncosaurus includes an analytics tool to easily view and analyze aggregate and single-room metrics for an application. The dashboard allows a developer to gain insights into usage and debug their application if necessary. The architecture for the analytics dashboard displays data from Cloudflare’s endpoints and visualizes it in a locally running front-end application that pulls from a custom-built GraphQL backend : +As demonstrated, Syncosaurus includes an analytics tool to easily view and analyze aggregate and single-room metrics for an application. The dashboard allows a developer to gain insights into usage and debug their application if necessary. The architecture for the analytics dashboard displays data from Cloudflare’s endpoints and visualizes it in a locally running front-end application that pulls from a custom-built GraphQL backend: [insert graphic] diff --git a/src/pages/todo-list-client.jsx b/src/pages/todo-list-client.jsx new file mode 100644 index 0000000..c92a33f --- /dev/null +++ b/src/pages/todo-list-client.jsx @@ -0,0 +1,62 @@ +// import { useState } from 'react' +// import Syncosaurus from 'syncosaurus' +// import { useSubscribe } from 'syncosaurus' +// import mutators from '../mutators.js' + +// const synco = new Syncosaurus({ +// mutators, +// userID: '1234', +// server: import.meta.env.VITE_DO_URL, +// }) + +// synco.launch('yourRoomID') + +// export default function App() { +// const [inputValue, setInputValue] = useState('') + +// function handleChange(e) { +// setInputValue(e.target.value) +// } + +// function handleSubmit(e) { +// e.preventDefault() +// synco.mutate.addTodo({ +// id: uuidv4(), +// text: inputValue, +// }) + +// setInputValue('') +// } + +// function handleDelete(id) { +// synco.mutate.removeTodo({ id }) +// } + +// const todos = useSubscribe( +// synco, +// tx => { +// let todoObject = tx.scan(key => { +// return key.includes('todo') +// }) +// return Object.values(todoObject) +// }, +// [] +// ) + +// return ( +//
+//
+// +// +//
+//
    +// {todos.map(todo => ( +//
  • +// {todo.text} +// +//
  • +// ))} +//
+//
+// ) +// } diff --git a/src/pages/todo-list-mutators.js b/src/pages/todo-list-mutators.js new file mode 100644 index 0000000..d168b9e --- /dev/null +++ b/src/pages/todo-list-mutators.js @@ -0,0 +1,14 @@ +// export default { +// addTodo, +// removeTodo, +// } + +// function addTodo(tx, { id, text }) { +// const todo = { id, text, complete: false } +// tx.set(`todo/${id}`, todo) +// return todo +// } + +// function removeTodo(tx, { id }) { +// tx.delete(`todo/${id}`) +// } From 2becb992a86caa4b7ef006e5e552a6bea651d7d5 Mon Sep 17 00:00:00 2001 From: emargetis Date: Sat, 20 Apr 2024 22:54:49 -0500 Subject: [PATCH 06/13] chore: added aws diagram image to static directory Co-authored-by: Alex Sklar Co-authored-by: Franco Waisfeld Co-authored-by: Joseph Liang --- src/pages/case-study.mdx | 2 +- static/img/diagrams/AWS-Lambda-Diagram.png | Bin 0 -> 86181 bytes 2 files changed, 1 insertion(+), 1 deletion(-) create mode 100644 static/img/diagrams/AWS-Lambda-Diagram.png diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index adc772b..b76ec27 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -600,7 +600,7 @@ First, we could have built our serverless edge infrastructure using a combinatio [insert graphic] -While this is a totally valid approach, it does involve provisioning and connecting several components which can increase the complexity of deployment and maintenance. +While this is a valid approach, it does involve provisioning and connecting several components which can increase the complexity of deployment and maintenance. As previously mentioned, we instead ended up choosing a Cloudflare-based architecture consisting of Workers and Durable Objects due to its simplicity and extremely strong fit for our use case. diff --git a/static/img/diagrams/AWS-Lambda-Diagram.png b/static/img/diagrams/AWS-Lambda-Diagram.png new file mode 100644 index 0000000000000000000000000000000000000000..f823c96c38e13cc1b128d5e2ae6becc351d0bcc2 GIT binary patch literal 86181 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 AegFUf literal 0 HcmV?d00001 From 4b551506c8ec50c738577c3e99bea3be4d57ba52 Mon Sep 17 00:00:00 2001 From: Alex Sklar Date: Mon, 22 Apr 2024 14:54:15 -0700 Subject: [PATCH 07/13] feat(diag): remove old files Co-authored-by: Erik Margetis Co-authored-by: Joseph Liang --- src/pages/1-ClientMakesChange.svg | 6 ------ src/pages/diagrams/Dia2ClientChangesSync.jsx | 16 ---------------- src/pages/diagrams/Dia2ClientChangesSync.svg | 4 ---- 3 files changed, 26 deletions(-) delete mode 100644 src/pages/1-ClientMakesChange.svg delete mode 100644 src/pages/diagrams/Dia2ClientChangesSync.jsx delete mode 100644 src/pages/diagrams/Dia2ClientChangesSync.svg diff --git a/src/pages/1-ClientMakesChange.svg b/src/pages/1-ClientMakesChange.svg deleted file mode 100644 index c390adf..0000000 --- a/src/pages/1-ClientMakesChange.svg +++ /dev/null @@ -1,6 +0,0 @@ - - - diff --git a/src/pages/diagrams/Dia2ClientChangesSync.jsx b/src/pages/diagrams/Dia2ClientChangesSync.jsx deleted file mode 100644 index 41c717c..0000000 --- a/src/pages/diagrams/Dia2ClientChangesSync.jsx +++ /dev/null @@ -1,16 +0,0 @@ -import { useEffect } from 'react' -import DiagramSvg from './Dia2ClientChangesSync.svg' - -const Dia2ClientChangesSync = () => { - useEffect(() => { - !function(t,e){"object"==typeof exports&&"undefined"!=typeof module?module.exports=e():"function"==typeof __SVGATOR_DEFINE__&&__SVGATOR_DEFINE__.amd?__SVGATOR_DEFINE__(e):((t="undefined"!=typeof globalThis?globalThis:t||self).__SVGATOR_PLAYER__=t.__SVGATOR_PLAYER__||{},t.__SVGATOR_PLAYER__["91c80d77"]=e())}(this,(function(){"use strict";function t(t,e){var n=Object.keys(t);if(Object.getOwnPropertySymbols){var r=Object.getOwnPropertySymbols(t);e&&(r=r.filter((function(e){return Object.getOwnPropertyDescriptor(t,e).enumerable}))),n.push.apply(n,r)}return n}function e(e){for(var n=1;nt.length)&&(e=t.length);for(var n=0,r=new Array(e);n1&&void 0!==arguments[1]?arguments[1]:6;return y(t,e,"round")}function m(t,e){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:g;return Math.abs(t-e)0&&void 0!==arguments[0]?arguments[0]:0,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:1,r=arguments.length>3&&void 0!==arguments[3]?arguments[3]:1;return t<0||t>1||n<0||n>1?null:m(t,e)&&m(n,r)?_:function(i){if(i<=0)return t>0?i*e/t:0===e&&n>0?i*r/n:0;if(i>=1)return n<1?1+(i-1)*(r-1)/(n-1):1===n&&t<1?1+(i-1)*(e-1)/(t-1):1;for(var o,u=0,a=1;u0&&void 0!==arguments[0]?arguments[0]:1,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0;if(1===t){if(0===e)return O;if(1===e)return S}var n=1/t;return function(t){return t>=1?1:(t+=e*n)-t%n}}var j=Math.sin,M=Math.cos,P=Math.acos,B=Math.asin,I=Math.tan,T=Math.atan2,N=Math.sqrt,R=function(){function t(){var e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:1,n=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,i=arguments.length>2&&void 0!==arguments[2]?arguments[2]:0,o=arguments.length>3&&void 0!==arguments[3]?arguments[3]:1,u=arguments.length>4&&void 0!==arguments[4]?arguments[4]:0,a=arguments.length>5&&void 0!==arguments[5]?arguments[5]:0;r(this,t),this.m=[e,n,i,o,u,a],this.i=null,this.w=null,this.s=null}return o(t,[{key:"determinant",get:function(){var t=this.m;return t[0]*t[3]-t[1]*t[2]}},{key:"isIdentity",get:function(){if(null===this.i){var t=this.m;this.i=1===t[0]&&0===t[1]&&0===t[2]&&1===t[3]&&0===t[4]&&0===t[5]}return this.i}},{key:"point",value:function(t,e){var n=this.m;return{x:n[0]*t+n[2]*e+n[4],y:n[1]*t+n[3]*e+n[5]}}},{key:"translateSelf",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:0,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0;if(!t&&!e)return this;var n=this.m;return n[4]+=n[0]*t+n[2]*e,n[5]+=n[1]*t+n[3]*e,this.w=this.s=this.i=null,this}},{key:"rotateSelf",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:0;if(t%=360){t=w(t);var e=j(t),n=M(t),r=this.m,i=r[0],o=r[1];r[0]=i*n+r[2]*e,r[1]=o*n+r[3]*e,r[2]=r[2]*n-i*e,r[3]=r[3]*n-o*e,this.w=this.s=this.i=null}return this}},{key:"scaleSelf",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:1,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1;if(1!==t||1!==e){var n=this.m;n[0]*=t,n[1]*=t,n[2]*=e,n[3]*=e,this.w=this.s=this.i=null}return this}},{key:"skewSelf",value:function(t,e){if(e%=360,(t%=360)||e){var n=this.m,r=n[0],i=n[1],o=n[2],u=n[3];t&&(t=I(w(t)),n[2]+=r*t,n[3]+=i*t),e&&(e=I(w(e)),n[0]+=o*e,n[1]+=u*e),this.w=this.s=this.i=null}return this}},{key:"resetSelf",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:1,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:0,r=arguments.length>3&&void 0!==arguments[3]?arguments[3]:1,i=arguments.length>4&&void 0!==arguments[4]?arguments[4]:0,o=arguments.length>5&&void 0!==arguments[5]?arguments[5]:0,u=this.m;return u[0]=t,u[1]=e,u[2]=n,u[3]=r,u[4]=i,u[5]=o,this.w=this.s=this.i=null,this}},{key:"recomposeSelf",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:null,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:null,n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null,r=arguments.length>3&&void 0!==arguments[3]?arguments[3]:null,i=arguments.length>4&&void 0!==arguments[4]?arguments[4]:null;return this.isIdentity||this.resetSelf(),t&&(t.x||t.y)&&this.translateSelf(t.x,t.y),e&&this.rotateSelf(e),n&&(n.x&&this.skewSelf(n.x,0),n.y&&this.skewSelf(0,n.y)),!r||1===r.x&&1===r.y||this.scaleSelf(r.x,r.y),i&&(i.x||i.y)&&this.translateSelf(i.x,i.y),this}},{key:"decompose",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:0,e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:0,n=this.m,r=n[0]*n[0]+n[1]*n[1],i=[[n[0],n[1]],[n[2],n[3]]],o=N(r);if(0===o)return{origin:{x:p(n[4]),y:p(n[5])},translate:{x:p(t),y:p(e)},scale:{x:0,y:0},skew:{x:0,y:0},rotate:0};i[0][0]/=o,i[0][1]/=o;var u=n[0]*n[3]-n[1]*n[2]<0;u&&(o=-o);var a=i[0][0]*i[1][0]+i[0][1]*i[1][1];i[1][0]-=i[0][0]*a,i[1][1]-=i[0][1]*a;var l,s=N(i[1][0]*i[1][0]+i[1][1]*i[1][1]);return 0===s?{origin:{x:p(n[4]),y:p(n[5])},translate:{x:p(t),y:p(e)},scale:{x:p(o),y:0},skew:{x:0,y:0},rotate:0}:(i[1][0]/=s,i[1][1]/=s,a/=s,i[1][1]<0?(l=k(P(i[1][1])),i[0][1]<0&&(l=360-l)):l=k(B(i[0][1])),u&&(l=-l),a=k(T(a,N(i[0][0]*i[0][0]+i[0][1]*i[0][1]))),u&&(a=-a),{origin:{x:p(n[4]),y:p(n[5])},translate:{x:p(t),y:p(e)},scale:{x:p(o),y:p(s)},skew:{x:p(a),y:0},rotate:p(l)})}},{key:"multiply",value:function(t){return this.clone().multiplySelf(t)}},{key:"preMultiply",value:function(t){return t.multiply(this)}},{key:"multiplySelf",value:function(t){var e=F(this.m,t.m),n=e.a,r=e.b,i=e.c,o=e.d,u=e.tx,a=e.ty;return this.resetSelf(n,r,i,o,u,a),this}},{key:"preMultiplySelf",value:function(t){var e=F(t.m,this.m),n=e.a,r=e.b,i=e.c,o=e.d,u=e.tx,a=e.ty;return this.resetSelf(n,r,i,o,u,a),this}},{key:"clone",value:function(){var t=this.m;return new this.constructor(t[0],t[1],t[2],t[3],t[4],t[5])}},{key:"toString",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:" ";if(null===this.s){var e=this.m.map((function(t){return p(t)}));1===e[0]&&0===e[1]&&0===e[2]&&1===e[3]?this.s="translate("+e[4]+t+e[5]+")":this.s="matrix("+e.join(t)+")"}return this.s}}],[{key:"create",value:function(t){return t?Array.isArray(t)?f(this,v(t)):t instanceof this?t.clone():(new this).recomposeSelf(t.origin,t.rotate,t.skew,t.scale,t.translate):new this}}]),t}();function F(t,e){return{a:t[0]*e[0]+t[2]*e[1],b:t[1]*e[0]+t[3]*e[1],c:t[0]*e[2]+t[2]*e[3],d:t[1]*e[2]+t[3]*e[3],tx:t[0]*e[4]+t[2]*e[5]+t[4],ty:t[1]*e[4]+t[3]*e[5]+t[5]}}function D(t,e,n){return t>=.5?n:e}function C(t,e,n){return 0===t||e===n?e:t*(n-e)+e}function q(t,e,n){var r=C(t,e,n);return r<=0?0:r}function L(t,e,n){var r=C(t,e,n);return r<=0?0:r>=1?1:r}function V(t,e,n){return 0===t?e:1===t?n:{x:C(t,e.x,n.x),y:C(t,e.y,n.y)}}function G(t,e,n){return 0===t?e:1===t?n:{x:q(t,e.x,n.x),y:q(t,e.y,n.y)}}function z(t,e,n){var r=function(t,e,n){return Math.round(C(t,e,n))}(t,e,n);return r<=0?0:r>=255?255:r}function Y(t,e,n){return 0===t?e:1===t?n:{r:z(t,e.r,n.r),g:z(t,e.g,n.g),b:z(t,e.b,n.b),a:C(t,null==e.a?1:e.a,null==n.a?1:n.a)}}function U(t,e,n){var r=e.length;if(r!==n.length)return D(t,e,n);for(var i=new Array(r),o=0;o0);return t}var H,Q=function(){function t(e){r(this,t),this.list=e,this.length=e.length}return o(t,[{key:"setAttribute",value:function(t,e){for(var n=this.list,r=0;r1&&void 0!==arguments[1]?arguments[1]:_;if(!Array.isArray(t))return e;switch(t.length){case 1:return E(t[0])||e;case 2:return E(t[0],t[1])||e;case 4:return x(t[0],t[1],t[2],t[3])||e}return e}(t,null):function(t,e){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:_;switch(t){case"linear":return _;case"steps":return E(e.steps||1,e.jump||0)||n;case"bezier":case"cubic-bezier":return x(e.x1||0,e.y1||0,e.x2||0,e.y2||0)||n}return n}(t.type,t.value,null):null}function tt(t,e,n){var r=arguments.length>3&&void 0!==arguments[3]&&arguments[3],i=e.length-1;if(t<=e[0].t)return r?[0,0,e[0].v]:e[0].v;if(t>=e[i].t)return r?[i,1,e[i].v]:e[i].v;var o,u=e[0],a=null;for(o=1;o<=i;o++){if(!(t>e[o].t)){a=e[o];break}u=e[o]}return null==a?r?[i,1,e[i].v]:e[i].v:u.t===a.t?r?[o,1,a.v]:a.v:(t=(t-u.t)/(a.t-u.t),u.e&&(t=u.e(t)),r?[o,t,n(t,u.v,a.v)]:n(t,u.v,a.v))}function et(t,e){var n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:null;return t&&t.length?"function"!=typeof e?null:("function"!=typeof n&&(n=null),function(r){var i=tt(r,t,e);return null!=i&&n&&(i=n(i)),i}):null}function nt(t,e){return t.t-e.t}function rt(t,e,r,i,o){var u,a="@"===r[0],l="#"===r[0],s=H[r],f=D;switch(a?(u=r.substr(1),r=u.replace(X,J)):l&&(r=r.substr(1)),n(s)){case"function":if(f=s(i,o,tt,Z,r,a,e,t),l)return f;break;case"string":f=et(i,K(s));break;case"object":if((f=et(i,K(s.i),s.f))&&"function"==typeof s.u)return s.u(e,f,r,a,t)}return f?function(t,e,n){if(arguments.length>3&&void 0!==arguments[3]&&arguments[3])return t instanceof Q?function(r){return t.style(e,n(r))}:function(r){return t.style[e]=n(r)};if(Array.isArray(e)){var r=e.length;return function(i){var o=n(i);if(null==o)for(var u=0;u0?i:0,s=t%i,f=1+(t-s)/i;e*=r.direction,r.alternate&&f%2==0&&(e=-e);var c=!1;if(f>a)s=l,c=!0,-1===r.fill&&(s=r.direction>0?0:i);else if(e<0&&(s=i-s),s===u)return!1;u=s;for(var h=0;h1&&void 0!==arguments[1]?arguments[1]:document,n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:0,r=at(t,e);if(r)return r;if(n>=20)return null;for(var i=lt(e),o=0;o1&&void 0!==arguments[1]?arguments[1]:null,n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:Number,r=arguments.length>3&&void 0!==arguments[3]?arguments[3]:"undefined"!=typeof BigInt&&BigInt,i="0x"+(t.replace(/[^0-9a-fA-F]+/g,"")||27);return e&&r&&n.isSafeInteger&&!n.isSafeInteger(+i)?n(r(i))%e+e:+i}function ht(t,e,n){return!t||!n||e>t.length?t:t.substring(0,e)+ht(t.substring(e+1),n,n)}function vt(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:27;return!t||t%e?t%e:[0,1].includes(e)?e:vt(t/e,e)}function dt(t,e,n){if(t&&t.length){var r=ct(n),i=vt(r)+5,o=ht(t,vt(r,5),i);return o=o.replace(/\x7c$/g,"==").replace(/\x2f$/g,"="),o=function(t,e,n){var r=+("0x"+t.substring(0,4));t=t.substring(4);for(var i=ct(e,r)%r+n%27,o=[],u=0;u2&&void 0!==arguments[2]?arguments[2]:null;r(this,t),this._id=0,this._running=!1,this._rollingBack=!1,this._animations=e,this._settings=n,(!o||o<"2022-05-02")&&delete this._settings.speed,yt.forEach((function(t){i._settings[t.key]=i._settings[t.key]||t.def})),this.duration=n.duration,this.offset=n.offset||0,this.rollbackStartOffset=0}return o(t,[{key:"alternate",get:function(){return this._settings.alternate}},{key:"fill",get:function(){return this._settings.fill}},{key:"iterations",get:function(){return this._settings.iterations}},{key:"direction",get:function(){return this._settings.direction}},{key:"speed",get:function(){return this._settings.speed}},{key:"fps",get:function(){return this._settings.fps}},{key:"maxFiniteDuration",get:function(){return this.iterations>0?this.iterations*this.duration:this.duration}},{key:"_apply",value:function(t){for(var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:{},n=this._animations,r=n.length,i=0,o=0;oe.duration&&n!==1/0){var a=!!e.alternate&&u/e.duration%2>1,l=u%e.duration;u=(l+=a?e.duration:0)||e.duration}var s=(e.fps?1e3/e.fps:0)*e.speed,f=Math.max(0,u);f<=n-s&&(e.offset=f,n=f,e._apply(f));var c=e.iterations>0&&-1===e.fill&&u>=e.maxFiniteDuration;(u<=0||e.offset0&&void 0!==arguments[0]?arguments[0]:0,n=-1/0,r=null,i={};this._running=!0;var o=function o(u){null==r&&(r=u);var a=Math.round((u-r)*t.speed+e),l=(t.fps?1e3/t.fps:0)*t.speed;if(a>=n+l&&!t._rollingBack&&(t.offset=a,n=a,t._apply(a,i)===t._animations.length))return void t.pause(!0);t._id=window.requestAnimationFrame(o)};this._id=window.requestAnimationFrame(o)}},{key:"_pause",value:function(){this._id&&window.cancelAnimationFrame(this._id),this._running=!1}},{key:"play",value:function(){if(!this._running)return this._rollingBack?this._rollback(this.offset):this._start(this.offset)}},{key:"stop",value:function(){this._pause(),this.offset=0,this.rollbackStartOffset=0,this._rollingBack=!1,this._apply(0)}},{key:"reachedToEnd",value:function(){return this.iterations>0&&this.offset>=this.iterations*this.duration}},{key:"restart",value:function(){var t=arguments.length>0&&void 0!==arguments[0]&&arguments[0];this.stop(t),this.play(t)}},{key:"pause",value:function(){this._pause()}},{key:"reverse",value:function(){this.direction=-this.direction}}],[{key:"build",value:function(t,e){delete t.animationSettings,t.options=dt(t.options,t.root,"91c80d77"),t.animations.map((function(e){e.settings=dt(e.s,t.root,"91c80d77"),delete e.s,t.animationSettings||(t.animationSettings=e.settings)}));var n=t.version;if(!(t=ft(t,e)))return null;var r=t.options||{},i=new this(t.animations,t.animationSettings,n);return{el:t.svg,options:r,player:i}}},{key:"push",value:function(t){return this.build(t)}},{key:"init",value:function(){var t=this,e=window.__SVGATOR_PLAYER__&&window.__SVGATOR_PLAYER__["91c80d77"];Array.isArray(e)&&e.splice(0).forEach((function(e){return t.build(e)}))}}]),t}();!function(){for(var t=0,e=["ms","moz","webkit","o"],n=0;n2&&void 0!==arguments[2]?arguments[2]:n,r=!1,i=null,o=function(){for(var o=0,u=n.innerHeight,a=0,l=n.innerWidth,s=t.parentNode;s instanceof Element;){var f=n.getComputedStyle(s);if("visible"!==f.overflowY||"visible"!==f.overflowX){var c=s.getBoundingClientRect();"visible"!==f.overflowY&&(o=Math.max(o,c.top),u=Math.min(u,c.bottom)),"visible"!==f.overflowX&&(a=Math.max(a,c.left),l=Math.min(l,c.right))}if(s===s.parentNode)break;s=s.parentNode}r=!1;var h=t.getBoundingClientRect(),v=Math.min(h.height,Math.max(0,o-h.top)),d=Math.min(h.height,Math.max(0,h.bottom-u)),y=Math.min(h.width,Math.max(0,a-h.left)),g=Math.min(h.width,Math.max(0,h.right-l)),p=(h.height-v-d)/h.height,m=(h.width-y-g)/h.width,b=Math.round(p*m*100);null!==i&&i===b||(i=b,e(b))};return function(t){r&&clearTimeout(r),r=setTimeout((function(){return o()}),100)}}(this.el,this.onVisibilityUpdate.bind(this),o.window),this.bindScrollWatchers(),this.visibilityCalculator()}return o(t,[{key:"bindScrollWatchers",value:function(){for(var t=this.el.parentNode;t&&(this._handlers.push({element:t,event:"scroll",handler:this.visibilityCalculator}),t.addEventListener("scroll",this.visibilityCalculator),t!==t.parentNode&&t!==document);)t=t.parentNode}},{key:"onVisibilityUpdate",value:function(t){var e=this.currentVisibility>=this.thresholdPercent,n=t>=this.thresholdPercent;if(null===this.currentVisibility||e!==n)return this.currentVisibility=t,void this.onThresholdChange(n);this.currentVisibility=t}},{key:"destruct",value:function(){this._handlers.forEach((function(t){t.element.removeEventListener(t.event,t.handler)}))}}]),t}();function mt(t){return p(t)+""}function bt(t){var e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:" ";return t&&t.length?t.map(mt).join(e):""}function wt(t){return mt(t.x)+","+mt(t.y)}function kt(t){return t?null==t.a||t.a>=1?function(t){if(!t)return"transparent";var e=function(t){return parseInt(t).toString(16).padStart(2,"0")};return function(t){for(var e=[],n="#"===t[0]?e.push("#"):0;n=1?"":e(255*t.a)))}(t):"rgba("+t.r+","+t.g+","+t.b+","+t.a+")":"transparent"}function _t(t){return t?"url(#"+t+")":"none"}var At={f:null,i:G,u:function(t,e){return function(n){var r=e(n);t.setAttribute("rx",mt(r.x)),t.setAttribute("ry",mt(r.y))}}},xt={f:null,i:function(t,e,n){return 0===t?e:1===t?n:{width:q(t,e.width,n.width),height:q(t,e.height,n.height)}},u:function(t,e){return function(n){var r=e(n);t.setAttribute("width",mt(r.width)),t.setAttribute("height",mt(r.height))}}};Object.freeze({M:2,L:2,Z:0,H:1,V:1,C:6,Q:4,T:2,S:4,A:7});var St={},Ot=null;function Et(t){var e=function(){if(Ot)return Ot;if("object"!==("undefined"==typeof document?"undefined":n(document))||!document.createElementNS)return{};var t=document.createElementNS("http://www.w3.org/2000/svg","svg");return t&&t.style?(t.style.position="absolute",t.style.opacity="0.01",t.style.zIndex="-9999",t.style.left="-9999px",t.style.width="1px",t.style.height="1px",Ot={svg:t}):{}}().svg;if(!e)return function(t){return null};var r=document.createElementNS(e.namespaceURI,"path");r.setAttributeNS(null,"d",t),r.setAttributeNS(null,"fill","none"),r.setAttributeNS(null,"stroke","none"),e.appendChild(r);var i=r.getTotalLength();return function(t){var e=r.getPointAtLength(i*t);return{x:e.x,y:e.y}}}function jt(t){return St[t]?St[t]:St[t]=Et(t)}function Mt(t,e,n,r){if(!t||!r)return!1;var i=["M",t.x,t.y];if(e&&n&&(i.push("C"),i.push(e.x),i.push(e.y),i.push(n.x),i.push(n.y)),e?!n:n){var o=e||n;i.push("Q"),i.push(o.x),i.push(o.y)}return e||n||i.push("L"),i.push(r.x),i.push(r.y),i.join(" ")}function Pt(t,e,n,r){var i=arguments.length>4&&void 0!==arguments[4]?arguments[4]:1,o=Mt(t,e,n,r),u=jt(o);try{return u(i)}catch(t){return null}}function Bt(t,e,n){return t+(e-t)*n}function It(t,e,n){var r=arguments.length>3&&void 0!==arguments[3]&&arguments[3],i={x:Bt(t.x,e.x,n),y:Bt(t.y,e.y,n)};return r&&(i.a=Tt(t,e)),i}function Tt(t,e){return Math.atan2(e.y-t.y,e.x-t.x)}function Nt(t,e,n,r){var i=1-r;return i*i*t+2*i*r*e+r*r*n}function Rt(t,e,n,r){return 2*(1-r)*(e-t)+2*r*(n-e)}function Ft(t,e,n,r){var i=arguments.length>4&&void 0!==arguments[4]&&arguments[4],o=Pt(t,e,null,n,r);return o||(o={x:Nt(t.x,e.x,n.x,r),y:Nt(t.y,e.y,n.y,r)}),i&&(o.a=Dt(t,e,n,r)),o}function Dt(t,e,n,r){return Math.atan2(Rt(t.y,e.y,n.y,r),Rt(t.x,e.x,n.x,r))}function Ct(t,e,n,r,i){var o=i*i;return i*o*(r-t+3*(e-n))+3*o*(t+n-2*e)+3*i*(e-t)+t}function qt(t,e,n,r,i){var o=1-i;return 3*(o*o*(e-t)+2*o*i*(n-e)+i*i*(r-n))}function Lt(t,e,n,r,i){var o=arguments.length>5&&void 0!==arguments[5]&&arguments[5],u=Pt(t,e,n,r,i);return u||(u={x:Ct(t.x,e.x,n.x,r.x,i),y:Ct(t.y,e.y,n.y,r.y,i)}),o&&(u.a=Vt(t,e,n,r,i)),u}function Vt(t,e,n,r,i){return Math.atan2(qt(t.y,e.y,n.y,r.y,i),qt(t.x,e.x,n.x,r.x,i))}function Gt(t,e,n){var r=arguments.length>3&&void 0!==arguments[3]&&arguments[3];if(Yt(e)){if(Ut(n))return Ft(e,n.start,n,t,r)}else if(Yt(n)){if(Wt(e))return Ft(e,e.end,n,t,r)}else{if(Wt(e))return Ut(n)?Lt(e,e.end,n.start,n,t,r):Ft(e,e.end,n,t,r);if(Ut(n))return Ft(e,n.start,n,t,r)}return It(e,n,t,r)}function zt(t,e,n){var r=Gt(t,e,n,!0);return r.a=k(function(t){return arguments.length>1&&void 0!==arguments[1]&&arguments[1]?t+Math.PI:t}(r.a)),r}function Yt(t){return!t.type||"corner"===t.type}function Ut(t){return null!=t.start&&!Yt(t)}function Wt(t){return null!=t.end&&!Yt(t)}var $t=new R;var Ht={f:function(t){return t?t.join(" "):""},i:function(t,e,r){if(0===t)return e;if(1===t)return r;var i=e.length;if(i!==r.length)return D(t,e,r);for(var o,u=new Array(i),a=0;a1&&void 0!==arguments[1]?arguments[1]:" ";return t&&t.length>0&&(t=t.map((function(t){return p(t,4)}))),bt(t,e)},i:function(t,e,n){var r,i,o,u=e.length,a=n.length;if(u!==a)if(0===u)e=W(u=a,0);else if(0===a)a=u,n=W(u,0);else{var l=(o=(r=u)*(i=a)/function(t,e){for(var n;e;)n=e,e=t%e,t=n;return t||1}(r,i))<0?-o:o;e=$(e,Math.floor(l/u)),n=$(n,Math.floor(l/a)),u=a=l}for(var s=[],f=0;f3&&void 0!==arguments[3]?arguments[3]:null;return t[n]?r(i,t[n],o):e&&e[n]?e[n]:u};return e&&e.a&&t.o?function(e){var n=r(e,t.o,zt);return $t.recomposeSelf(n,o("r",e,C,0)+n.a,o("k",e,V),o("s",e,V),o("t",e,V)).toString()}:function(t){return $t.recomposeSelf(o("o",t,Gt,null),o("r",t,C,0),o("k",t,V),o("s",t,V),o("t",t,V)).toString()}},"#filter":function(t,e,n,r,i,o,u,a){if(!e.items||!t||!t.length)return null;var l=function(t,e){var n=(t=t.map((function(t){return t&&se[t[0]]?(e.getElementById(t[1]),se[t[0]](e.getElementById(t[1]),t[1],e)):null}))).length;return function(e){for(var r=0;r3&&void 0!==arguments[3]?arguments[3]:[];return function(){var i,o=Array.prototype.slice.call(arguments);return o.unshift.apply(o,v(r)),(i=t[e]).call.apply(i,[t].concat(v(o))),n}}var ge=function t(e){r(this,t);var n={},i=["on","off"],o={get:function(t,e,r){return ve[e]?"function"==typeof ve[e]?ve[e].call(t,t,r):t[ve[e]]:de[e]?"function"==typeof de[e]?de[e].call(t,t,r):ye(t,de[e],r):-1!==i.indexOf(e)?n[e]:"ready"===e?function(t){return t&&t.call(r,r),r}:void 0},set:function(t,e,r){return-1!==i.indexOf(e)&&(n[e]=r)},ownKeys:function(t){return Object.keys(ve)},has:function(t,e){return void 0!==ve[e]}};if("function"==typeof Proxy)return new Proxy(e,o);var u=Object.keys(ve).concat(Object.keys(de)).concat(i),a={};return u.forEach((function(t){var n={enumerable:!1,configurable:!1,get:function(){return o.get(e,t,a)}};-1!==i.indexOf(t)&&(n.set=function(n){return o.set(e,t,n)}),Object.defineProperty(a,t,n)})),a};function pe(t){t||(t=this);var e={};this.on=function(t,n){var r=arguments.length>2&&void 0!==arguments[2]&&arguments[2];return"function"==typeof n&&(t.split(/[, ]+/g).forEach((function(t){return e[t]=e[t]||[],r?e[t].unshift(n):e[t].push(n)})),!0)},this.off=function(t,n){for(var r in e)if(e.hasOwnProperty(r)&&r.substr(0,t.length)===t)if(n)for(var i=0;i2&&void 0!==arguments[2]?arguments[2]:null;return r(this,u),(n=i.call(this,t,e,o))._handlers=[],n}return o(u,[{key:"_adjustOffset",value:function(){var t=arguments.length>0&&void 0!==arguments[0]&&arguments[0],e=this.alternate?2*this.duration:this.duration;if(t){if(!this._rollingBack&&0===this.offset)return void(this.offset=e);this._rollingBack&&(this.offset,this.maxFiniteDuration)}!this._rollingBack||this.rollbackStartOffset<=this.duration?0!==this.iterations&&(this.offset=Math.min(this.offset,this.maxFiniteDuration)):(this.offset=this.rollbackStartOffset-(this.rollbackStartOffset-this.offset)%e,this.rollbackStartOffset=0)}},{key:"reverse",value:function(){var t=arguments.length>0&&void 0!==arguments[0]&&arguments[0];if(!this._running)return this._adjustOffset(t),this._rollingBack=!this._rollingBack,t&&this.play(!1),void this.trigger("reverse",this.offset);this.pause(!1,!1),this._adjustOffset(),this._rollingBack=!this._rollingBack,this.play(!1),this.trigger("reverse",this.offset)}},{key:"play",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:me,e=h(a(u.prototype),"play",this).call(this);return t===me&&this.trigger("play",this.offset),e}},{key:"pause",value:function(){var t=arguments.length>0&&void 0!==arguments[0]&&arguments[0],e=arguments.length>1&&void 0!==arguments[1]?arguments[1]:me,n=h(a(u.prototype),"pause",this).call(this);return e===me&&this.trigger(t?"end":"pause",this.offset),n}},{key:"restart",value:function(){var t=h(a(u.prototype),"restart",this).call(this,!1);return this.trigger("restart",this.offset),t}},{key:"stop",value:function(){var t=arguments.length>0&&void 0!==arguments[0]?arguments[0]:me,e=h(a(u.prototype),"stop",this).call(this);return t===me&&this.trigger("stop",this.offset),e}},{key:"_apply",value:function(t){var e=this,n=arguments.length>2&&void 0!==arguments[2]?arguments[2]:me,r=h(a(u.prototype),"_apply",this).call(this,t);if(n===me){var i=function(){return e.trigger("keyframe",t)};window.requestAnimationFrame(i)}return r}},{key:"seekTo",value:function(t){var e,n,r,i=this._running;i&&this.pause(!1,!1),this.offset=this.iterations>0?(e=t,n=0,r=this.maxFiniteDuration,er?r:e):Math.max(t,0),this._apply(this.offset),i&&this.play(!1)}},{key:"seek",value:function(t){return this.seekTo(Math.round(t/100*this.maxFiniteDuration))}},{key:"seekBy",value:function(t){return this.seekTo(this.offset+t)}},{key:"toggle",value:function(){return this._running?this.pause():this.reachedToEnd()?this.restart():this.play()}},{key:"set",value:function(t,e){if(be.includes(t)){var n=this._running;n&&this.pause(!1,!1),this._settings[t]=e,n?this.play(!1):this._apply(this.offset,{},!1)}}},{key:"destruct",value:function(){var t=this;this.stop(),this._handlers.forEach((function(t){t.element?t.element.removeEventListener(t.event,t.handler):t.callback&&t.callback.call&&t.callback.call()}));var e=function(){},n=Object.getOwnPropertyNames(Object.getPrototypeOf(this));n.push.apply(n,v(Object.getOwnPropertyNames(this))),n.forEach((function(n){"function"==typeof t[n]?t[n]=e:delete t[n]}))}}],[{key:"build",value:function(t){var e=h(a(u),"build",this).call(this,t,he);if(!e)return null;var n=e.el,r=e.options,i=e.player,o=new ge(i),l=new pe(o);o.on=l.on,o.off=l.off,i.trigger=l.trigger;var s=n.svgatorPlayer&&n.svgatorPlayer.ready&&n.svgatorPlayer.ready.call&&n.svgatorPlayer.ready.call();n.svgatorPlayer=o,function(t){var e,n,r=t&&1===(null===(e=t.ownerDocument)||void 0===e||null===(n=e.childNodes)||void 0===n?void 0:n.length)&&window.parent!==window,i=null==t?void 0:t.firstElementChild;if(!r||!i||"a"!==i.tagName||i.getAttribute("target"))return;i.setAttributeNS(null,"target","_parent")}(n),function(t,e,n){if("click"===n.start){var r=function(){switch(n.click){case"freeze":return!t._running&&t.reachedToEnd()?t.restart():t.toggle();case"restart":return t.offset>0?t.restart():t.play();case"reverse":return t._running?t.reverse():t.reachedToEnd()?1===t.fill?t.reverse(!0):t.restart():t.play();case"none":default:if(t._running)return;return t.reachedToEnd()?t.restart():t.play()}};return t._handlers.push({element:e,event:"click",handler:r}),void e.addEventListener("click",r)}if("hover"===n.start){var i=function(){return t.reachedToEnd()?t.restart():t._rollingBack?t.reverse():t.play()};t._handlers.push({element:e,event:"mouseenter",handler:i}),e.addEventListener("mouseenter",i);var o=function(){switch(n.hover){case"freeze":return t.pause();case"reset":return t.stop();case"reverse":if(t.reverse(),t._running)return;return t.play();case"none":default:return}};return t._handlers.push({element:e,event:"mouseleave",handler:o}),void e.addEventListener("mouseleave",o)}if("scroll"===n.start){var u=new pt(e,n.scroll||25,(function(e){e?t.reachedToEnd()?t.restart():t.play():t.pause()}));return void t._handlers.push({callback:function(){return u.destruct()}})}if("programmatic"===n.start)return;t.play()}(i,n,r),function(t,e,n){var r;"function"==typeof Event?r=new Event("ready"):(r=document.createEvent("Event")).initEvent("ready",!0,!0);if(t.dispatchEvent(r),!n||!n.length)return;n.forEach((function(t){return e.ready(t)}))}(n,n.svgatorPlayer,s)}}]),u}(gt);return we.init(),we})); - (function(s,i,o,w,d,a,b){(a=Array.from(d.querySelectorAll('svg#' + i.root)).filter(n=> !n.svgatorPlayer)[0]||{}).svgatorPlayer={ready:(function(a){b=[];return function(c){return c?(b.push(c),a.svgatorPlayer):b}})(a)};w[o]=w[o]||{};w[o][s]=w[o][s]||[];w[o][s].push(i);})('91c80d77',{"root":"eHQdCTlEWVF1","version":"2022-05-04","animations":[{"elements":{"eHQdCTlEWVF5":{"transform":{"keys":{"o":[{"t":1290,"v":{"x":247.7493,"y":256.340688,"type":"corner"},"e":[0.42,0,0.58,1]},{"t":2200,"v":{"x":397.7493,"y":256.340688,"type":"corner"}},{"t":2400,"v":{"x":373.7493,"y":256.340688,"type":"corner"},"e":[0.42,0,0.58,1]},{"t":3490,"v":{"x":237.7493,"y":256.340688,"type":"corner"}}]}}},"eHQdCTlEWVF6":{"transform":{"keys":{"o":[{"t":2520,"v":{"x":428.7493,"y":256.340688,"type":"corner"},"e":[0.42,0,0.58,1]},{"t":3290,"v":{"x":554.7493,"y":256.340688,"type":"corner"}}]}}},"eHQdCTlEWVF14":{"opacity":[{"t":790,"v":1},{"t":950,"v":0.5},{"t":3310,"v":0.5},{"t":3850,"v":1}],"fill":[{"t":3310,"v":{"t":"g","s":[{"c":{"r":202,"g":104,"b":111,"a":1},"o":0},{"c":{"r":193,"g":18,"b":31,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF14-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":3850,"v":{"t":"g","s":[{"c":{"r":129,"g":190,"b":246,"a":1},"o":0},{"c":{"r":64,"g":122,"b":199,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF14-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":5600,"v":{"t":"g","s":[{"c":{"r":129,"g":190,"b":246,"a":1},"o":0},{"c":{"r":64,"g":122,"b":199,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF14-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":6000,"v":{"t":"g","s":[{"c":{"r":202,"g":104,"b":111,"a":1},"o":0},{"c":{"r":193,"g":18,"b":31,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF14-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}}]},"eHQdCTlEWVF15":{"transform":{"keys":{"o":[{"t":3310,"v":{"x":51.32821,"y":52.643268,"type":"corner"},"e":[0.42,0,1,1]},{"t":3850,"v":{"x":-26.56879,"y":52.643268,"type":"corner"}}]}},"opacity":[{"t":790,"v":0,"e":[0,0,0.58,1]},{"t":950,"v":1},{"t":3310,"v":1},{"t":3850,"v":0}]},"eHQdCTlEWVF23":{"fill":[{"t":3310,"v":{"t":"g","s":[{"c":{"r":202,"g":104,"b":111,"a":1},"o":0},{"c":{"r":193,"g":18,"b":31,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF23-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":3850,"v":{"t":"g","s":[{"c":{"r":129,"g":190,"b":246,"a":1},"o":0},{"c":{"r":64,"g":122,"b":199,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF23-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":5600,"v":{"t":"g","s":[{"c":{"r":129,"g":190,"b":246,"a":1},"o":0},{"c":{"r":64,"g":122,"b":199,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF23-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":6000,"v":{"t":"g","s":[{"c":{"r":202,"g":104,"b":111,"a":1},"o":0},{"c":{"r":193,"g":18,"b":31,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF23-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}}]},"eHQdCTlEWVF55":{"fill":[{"t":1930,"v":{"t":"g","s":[{"c":{"r":202,"g":104,"b":111,"a":1},"o":0},{"c":{"r":193,"g":18,"b":31,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF55-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":2210,"v":{"t":"g","s":[{"c":{"r":114,"g":188,"b":251,"a":1},"o":0},{"c":{"r":64,"g":122,"b":199,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF55-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":5600,"v":{"t":"g","s":[{"c":{"r":114,"g":188,"b":251,"a":1},"o":0},{"c":{"r":64,"g":122,"b":199,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF55-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}},{"t":6000,"v":{"t":"g","s":[{"c":{"r":202,"g":104,"b":111,"a":1},"o":0},{"c":{"r":193,"g":18,"b":31,"a":1},"o":0.821706}],"r":"eHQdCTlEWVF55-fill","gt":[1,0,0,1,0.2353,0.103735],"c":{"x":0,"y":0},"rd":1.086611}}]},"eHQdCTlEWVF57":{"transform":{"data":{"o":{"x":12.500806,"y":12.813618,"type":"corner"},"t":{"x":-12.500806,"y":-12.813618}},"keys":{"s":[{"t":0,"v":{"x":0,"y":0},"e":[0.68,-0.1,0.265,1.55]},{"t":260,"v":{"x":1,"y":1}},{"t":620,"v":{"x":1,"y":1},"e":[0.42,0,1,1]},{"t":700,"v":{"x":0.8,"y":0.8},"e":[0.315456,0,0.658684,0.394044]},{"t":790,"v":{"x":0.8,"y":0.8},"e":[0.42,0,1,1]},{"t":850,"v":{"x":1,"y":1}},{"t":1130,"v":{"x":1,"y":1},"e":[0.42,0,0.58,1]},{"t":1350,"v":{"x":0,"y":0}}]}},"#filter":{"keys":[{"t":620,"v":[{"type":"drop-shadow","value":{"blur":{"x":6,"y":6},"offset":{"x":3,"y":3},"color":{"r":0,"g":0,"b":0,"a":0.5}}}],"e":[0.42,0,1,1]},{"t":700,"v":[{"type":"drop-shadow","value":{"blur":{"x":0,"y":0},"offset":{"x":1,"y":1},"color":{"r":0,"g":0,"b":0,"a":0.5}}}]},{"t":790,"v":[{"type":"drop-shadow","value":{"blur":{"x":0,"y":0},"offset":{"x":0,"y":0},"color":{"r":0,"g":0,"b":0,"a":0.5}}}],"e":[0.42,0,1,1]},{"t":850,"v":[{"type":"drop-shadow","value":{"blur":{"x":6,"y":6},"offset":{"x":3,"y":3},"color":{"r":0,"g":0,"b":0,"a":0.5}}}]}],"data":{"items":[["drop-shadow","eHQdCTlEWVF57-filter-drop-shadow-0"]]}}}},"s":"MDTA1ZGM2NmRhZLmMwYmRhY2JmJYjRiYWI5NmQB4NU04MTdiN2AI3Yjc3NmRhZGkdiNGJkYjBhFZWJmYjRiYWIT5TjZkODU3YzSc3NmRiNFFiZCmIwYmRhY2JmDVmI0YmFiOWJMlNmQ4NTdiNzWc2ZGIxWGI0YDjdEYjdGNmQ4ANTdjNzdUNmRMhY2I3YmZMYjCBiZGI5YWNiZVmIwNmQ4NWIxMUGFjYjdLYmVRiMDc3NmRTYmEViYmIwYjBhZHjZkODU3Y1U3JNzZkYjFiYmJYlNmQ4NTdjN2RI3YmM4"}],"options":"MDBAxMDgyMjk3YFTdiNjg3OTdiLMjk0MTI5NzMB3NjY4NmIyOTBg0"},'__SVGATOR_PLAYER__',window,document) - }, []) - return ( -
- -
- ) -} - -export default Dia2ClientChangesSync diff --git a/src/pages/diagrams/Dia2ClientChangesSync.svg b/src/pages/diagrams/Dia2ClientChangesSync.svg deleted file mode 100644 index d177ff3..0000000 --- a/src/pages/diagrams/Dia2ClientChangesSync.svg +++ /dev/null @@ -1,4 +0,0 @@ - - - - From 09bd15457b6320d6d8320896f6c583f50d3adebb Mon Sep 17 00:00:00 2001 From: Alex Sklar Date: Mon, 22 Apr 2024 14:54:31 -0700 Subject: [PATCH 08/13] feat(diag): import Websockets Co-authored-by: Erik Margetis Co-authored-by: Joseph Liang --- src/components/Diagrams/index.js | 7 +++++++ src/pages/case-study.mdx | 6 ++++-- static/img/diagrams/diag-websocket-handshake.svg | 6 ++++++ 3 files changed, 17 insertions(+), 2 deletions(-) create mode 100644 src/components/Diagrams/index.js create mode 100644 static/img/diagrams/diag-websocket-handshake.svg diff --git a/src/components/Diagrams/index.js b/src/components/Diagrams/index.js new file mode 100644 index 0000000..0481612 --- /dev/null +++ b/src/components/Diagrams/index.js @@ -0,0 +1,7 @@ +export const Websockets = () => { + return +} \ No newline at end of file diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index b6c3e62..1e47d40 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -1,8 +1,10 @@ -import Dia2ClientChangesSync from './diagrams/Dia2ClientChangesSync.jsx' import LatencySlider from '@site/src/components/LatencySlider/LatencySlider' import TodoList from '@site/src/components/TodoList/TodoList' import Tabs from '@theme/Tabs' import TabItem from '@theme/TabItem' +import { Websockets } from '@site/src/components/Diagrams/index.js' + + ## Overview @@ -26,7 +28,7 @@ Although there are numerous architectures for web applications, they can broadly - **Centralized** such as the client-server architecture where client machines send resource requests to a backend server. In the client-server architecture, the server is generally authoritative, meaning it is the source of truth. - +[insert P2P] - **Decentralized** such as the peer-to-peer architecture where every machine (known as a node) is treated equally and responsible for sending and responding to requests for resources. In the peer-to-peer architecture, every machine has equal authority and a consensus must usually be reached to determine the truth. diff --git a/static/img/diagrams/diag-websocket-handshake.svg b/static/img/diagrams/diag-websocket-handshake.svg new file mode 100644 index 0000000..6563723 --- /dev/null +++ b/static/img/diagrams/diag-websocket-handshake.svg @@ -0,0 +1,6 @@ + + + From a5b4115f4c3c1af84aee9f30cc9d46b7017f17bf Mon Sep 17 00:00:00 2001 From: Alex Sklar Date: Mon, 22 Apr 2024 14:58:01 -0700 Subject: [PATCH 09/13] feat(diag): remove old files Co-authored-by: Erik Margetis Co-authored-by: Joseph Liang --- static/img/diagrams/3-Concurrent Change Diff Props.svg | 6 ------ static/img/diagrams/4-Concurrent Conflicting Edits.svg | 6 ------ 2 files changed, 12 deletions(-) delete mode 100644 static/img/diagrams/3-Concurrent Change Diff Props.svg delete mode 100644 static/img/diagrams/4-Concurrent Conflicting Edits.svg diff --git a/static/img/diagrams/3-Concurrent Change Diff Props.svg b/static/img/diagrams/3-Concurrent Change Diff Props.svg deleted file mode 100644 index af8525a..0000000 --- a/static/img/diagrams/3-Concurrent Change Diff Props.svg +++ /dev/null @@ -1,6 +0,0 @@ - - - diff --git a/static/img/diagrams/4-Concurrent Conflicting Edits.svg b/static/img/diagrams/4-Concurrent Conflicting Edits.svg deleted file mode 100644 index 8659da9..0000000 --- a/static/img/diagrams/4-Concurrent Conflicting Edits.svg +++ /dev/null @@ -1,6 +0,0 @@ - - - From 295285e206ba37cfe6fa706f88e31c2e5c2b79a5 Mon Sep 17 00:00:00 2001 From: Alex Sklar Date: Mon, 22 Apr 2024 18:26:56 -0700 Subject: [PATCH 10/13] feat(diag): add most diagrams, first drafts Co-authored-by: Erik Margetis Co-authored-by: Joseph Liang --- src/components/Diagrams/allDiagrams.js | 33 +++ src/components/Diagrams/index.js | 192 ++++++++++++++++ src/pages/case-study.mdx | 216 ++++++++++-------- static/img/diagrams/diag-CRDT.svg | 122 ++++++++++ static/img/diagrams/diag-DeltaUpdates.svg | 6 + static/img/diagrams/diag-ON-messaging.svg | 6 + static/img/diagrams/diag-ON2-messaging.svg | 6 + static/img/diagrams/diag-OT.svg | 94 ++++++++ static/img/diagrams/diag-StateUpdates.svg | 6 + static/img/diagrams/diag-absolute-update.svg | 6 + static/img/diagrams/diag-centralized.svg | 1 + static/img/diagrams/diag-conflict-edits.svg | 6 + static/img/diagrams/diag-long-polling.svg | 6 + .../diagrams/diag-new-client-connection.svg | 6 + .../img/diagrams/diag-no-conflict-edits.svg | 6 + static/img/diagrams/diag-optimistic-ui.svg | 29 +++ static/img/diagrams/diag-p2p.svg | 1 + static/img/diagrams/diag-relative-update.svg | 30 +++ static/img/diagrams/diag-syncingModel-1.svg | 6 + static/img/diagrams/diag-syncingModel-2.svg | 6 + static/img/diagrams/diag-syncingModel-3.svg | 6 + static/img/diagrams/diag-syncingModel-4.svg | 6 + .../img/diagrams/diag-timeDrivenMessages.svg | 6 + .../img/diagrams/diag-whiteboard-conflict.svg | 6 + .../diag-whiteboard-demo-dual-latency.svg | 18 ++ .../diagrams/diag-whiteboard-demo-dual.svg | 18 ++ 26 files changed, 752 insertions(+), 92 deletions(-) create mode 100644 src/components/Diagrams/allDiagrams.js create mode 100644 static/img/diagrams/diag-CRDT.svg create mode 100644 static/img/diagrams/diag-DeltaUpdates.svg create mode 100644 static/img/diagrams/diag-ON-messaging.svg create mode 100644 static/img/diagrams/diag-ON2-messaging.svg create mode 100644 static/img/diagrams/diag-OT.svg create mode 100644 static/img/diagrams/diag-StateUpdates.svg create mode 100644 static/img/diagrams/diag-absolute-update.svg create mode 100644 static/img/diagrams/diag-centralized.svg create mode 100644 static/img/diagrams/diag-conflict-edits.svg create mode 100644 static/img/diagrams/diag-long-polling.svg create mode 100644 static/img/diagrams/diag-new-client-connection.svg create mode 100644 static/img/diagrams/diag-no-conflict-edits.svg create mode 100644 static/img/diagrams/diag-optimistic-ui.svg create mode 100644 static/img/diagrams/diag-p2p.svg create mode 100644 static/img/diagrams/diag-relative-update.svg create mode 100644 static/img/diagrams/diag-syncingModel-1.svg create mode 100644 static/img/diagrams/diag-syncingModel-2.svg create mode 100644 static/img/diagrams/diag-syncingModel-3.svg create mode 100644 static/img/diagrams/diag-syncingModel-4.svg create mode 100644 static/img/diagrams/diag-timeDrivenMessages.svg create mode 100644 static/img/diagrams/diag-whiteboard-conflict.svg create mode 100644 static/img/diagrams/diag-whiteboard-demo-dual-latency.svg create mode 100644 static/img/diagrams/diag-whiteboard-demo-dual.svg diff --git a/src/components/Diagrams/allDiagrams.js b/src/components/Diagrams/allDiagrams.js new file mode 100644 index 0000000..f0d5ccc --- /dev/null +++ b/src/components/Diagrams/allDiagrams.js @@ -0,0 +1,33 @@ +import {Websockets, AbsoluteUpdates, Centralized, ConflictEdits, CRDT, DeltaUpdate, LongPolling, NewClientConnection, ONMessaging, ON2Messaging, OptimisticUI, OT, P2P, RelativeUpdate, StateUpdates, SyncingModel1, SyncingModel2, SyncingModel3, SyncingModel4, TimeDrivenMessages, WhiteboardDemo, WhiteboardDemoLatency } from '@site/src/components/Diagrams/index.js' + +const AllDiagrams = () => { + + return ( + <> + + + + + + + + + + + + + + + + + + + + + + + + ) +} + +export default AllDiagrams \ No newline at end of file diff --git a/src/components/Diagrams/index.js b/src/components/Diagrams/index.js index 0481612..5eeb1b6 100644 --- a/src/components/Diagrams/index.js +++ b/src/components/Diagrams/index.js @@ -4,4 +4,196 @@ export const Websockets = () => { data="/img/diagrams/diag-websocket-handshake.svg" className="w-96" > +} + +export const AbsoluteUpdates = () => { + return +} + +export const Centralized = () => { + return +} + +export const ConflictEdits = () => { + return +} + +export const CRDT = () => { + return +} + +export const DeltaUpdate = () => { + return +} + +export const LongPolling = () => { + return +} + +export const NewClientConnection = () => { + return +} + +export const ONMessaging = () => { + return +} + +export const ON2Messaging = () => { + return +} + +export const OptimisticUI = () => { + return +} + +export const OT = () => { + return +} + +export const P2P = () => { + return +} + +export const RelativeUpdate = () => { + return +} + +export const StateUpdates = () => { + return +} + +export const SyncingModel1 = () => { + return +} + +export const SyncingModel2 = () => { + return +} + +export const SyncingModel3 = () => { + return +} + +export const SyncingModel4 = () => { + return +} + +export const TimeDrivenMessages = () => { + return +} + +export const WhiteboardConflict = () => { + return +} + +export const WhiteboardDemo = () => { + return +} + +export const WhiteboardDemoLatency = () => { + return +} + +export const NoConflictEdits = () => { + return +} + +export const Template = () => { + return } \ No newline at end of file diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index 6f24776..2c046e4 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -2,9 +2,33 @@ import LatencySlider from '@site/src/components/LatencySlider/LatencySlider' import TodoList from '@site/src/components/TodoList/TodoList' import Tabs from '@theme/Tabs' import TabItem from '@theme/TabItem' -import { Websockets } from '@site/src/components/Diagrams/index.js' - - +import AllDiagrams from '@site/src/components/Diagrams/allDiagrams.js' +import { + Websockets, + AbsoluteUpdates, + Centralized, + ConflictEdits, + CRDT, + DeltaUpdate, + LongPolling, + NewClientConnection, + ONMessaging, + ON2Messaging, + OptimisticUI, + OT, + P2P, + RelativeUpdate, + StateUpdates, + SyncingModel1, + SyncingModel2, + SyncingModel3, + SyncingModel4, + TimeDrivenMessages, + WhiteboardConflict, + WhiteboardDemo, + WhiteboardDemoLatency, + NoConflictEdits, +} from '@site/src/components/Diagrams/index.js' # Overview @@ -27,7 +51,7 @@ Broadly, real-time collaboration is a term used to describe software or technolo With the rise of [remote work and distributed teams](https://medium.com/@anupamr/distributed-teams-are-the-new-cloud-for-startups-14240a9822d7), apps like these [are becoming critical in the modern work environment](https://northzone.com/2023/06/20/perspectives-the-rise-of-multiplayer-software/). Well-known examples include Google Docs, Figma, and Notion among others: -[graphic here] +[TODO graphic here] While [a broader definition](https://www.microsoft.com/en-us/microsoft-365/business-insights-ideas/resources/real-time-collaboration-what-it-is-and-how-it-helps-your-business) of real-time collaboration applications can include video conferencing and messaging software, those types of applications have different technical requirements and will be excluded from the scope of this case study. @@ -38,9 +62,11 @@ At a fundamental level when multiple users are “collaborating” on the same a - Centralized - Decentralized -Centralized includes the client-server architecture where client machines send resource requests to a backend server. In the client-server architecture, the server is generally [authoritative](https://medium.com/mighty-bear-games/what-are-server-authoritative-realtime-games-e2463db534d1), meaning it is the source of truth. + + +- **Centralized** includes the client-server architecture where client machines send resource requests to a backend server. In the client-server architecture, the server is generally [authoritative](https://medium.com/mighty-bear-games/what-are-server-authoritative-realtime-games-e2463db534d1), meaning it is the source of truth. -[insert P2P] + - **Decentralized** such as the peer-to-peer architecture where every machine (known as a node) is treated equally and responsible for sending and responding to requests for resources. In the peer-to-peer architecture, every machine has equal authority and a consensus must usually be reached to determine the truth. @@ -82,7 +108,7 @@ Note that using [streams over HTTP/2](https://getstream.io/blog/communication-pr Long polling is a technique to emulate server push communications via normal HTTP requests. Long polling works like this: -[graphic here] + Although every browser supports long polling, it has high latency compared to other options such as WebSockets, and a risk of missing messages without extensive code on the client and server. Therefore, long polling [is generally better suited as a fallback option as opposed to a primary means of bi-directional communication](https://ably.com/topic/long-polling#:~:text=HTTP%20long%20polling%20solves%20the,make%20requests%20and%20servers%20respond.). @@ -90,7 +116,7 @@ Although every browser supports long polling, it has high latency compared to ot [WebSockets](https://developer.mozilla.org/en-US/docs/Web/API/WebSocket?retiredLocale=de) is an application layer protocol that provides a [full-duplex](https://www.comms-express.com/infozone/article/half-full-duplex/) communication channel over a single, long-lived connection between the client and server. This means that similar to a phone call, the connection from the client to the server will stay open as long the network is not interrupted and neither the client nor the server actively terminates it. This open connection enables clients and servers to freely exchange data without the overhead of the HTTP request-response cycle, but because it is built on top of [TCP](https://www.ibm.com/docs/ro/aix/7.1?topic=protocols-transmission-control-protocol), it still has guaranteed in-order message delivery. WebSockets work like this: -[graphic here] + Once the handshake is complete, the WebSocket connection is established and both parties are now free to transmit data at any time. @@ -118,7 +144,7 @@ To better illustrate the concepts of the current and subsequent sections in our In our example whiteboard application, all users expect to simultaneously see the same shapes (i.e. a consistent application state) so that they can react and respond accordingly: -[graphic here] + If we assume the app is using a client-server architecture where the clients do not hold any state of their own (i.e. [thin clients](https://www.fortinet.com/resources/cyberglossary/thin-client)), the change-initiating client would need to wait until the change is received and confirmed by the server and then propagated to all clients before seeing the change reflected in its state. @@ -128,7 +154,7 @@ One may assume that because our application is using WebSockets, the information Using our whiteboard example, you can see that the users have a different experience when latency is introduced: -[graphic here] + To increase consistency in our application, we will now explore [tools and techniques](https://developer.mozilla.org/en-US/docs/Web/Performance) to help us reduce latency. @@ -148,11 +174,11 @@ Finally, [optimistically updating the client’s UI](https://javascript.plaineng Optimistic UI works like this: -[graphic here] + An important implication of implementing optimistic UI is that each client has a local replica of the state that must be kept in sync with the server. Thus using it in our whiteboard app means that it now has distributed state. [Figma uses this same technique](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) - when a client opens a Figma design file, a copy of the document is sent from the server to the client and it must be kept in sync: -[graphic here] + However, as we’ll see in the next section, maintaining multiple copies of client state and a server state in the context of shared editing means conflicts can and will arise. @@ -160,7 +186,7 @@ However, as we’ll see in the next section, maintaining multiple copies of clie Since the advent of Google Docs, the ability for multiple clients to simultaneously edit a document has [become commonplace](https://diginomica.com/brief-history-collaborative-documents). However, simultaneous editing [invariably leads to shared state conflicts](https://rocicorp.dev/blog/ready-player-two) because multiple clients can make changes to the same part of the state at the same time. Using our whiteboard app as a demonstration let’s say client A decides that they want to change the color of an existing blue shape to green, while client B decides they want to change the color of the same shape to red at the same time: -[graphic here] + If these changes occur simultaneously, a conflict clearly occurs and to maintain a consistent, synchronized view across clients (i.e. state convergence), there must be some kind of conflict-resolution strategy in place @@ -180,21 +206,21 @@ However, before comparing strategies, it is worth reiterating that the initial d This means that if a change is intended to be applied relative to the current state (e.g. adding 1 to a count shared across multiple clients), multiple changes that could be considered conflicting would be stacked on top of each other instead. For example: -[graphic here] + However, if a change is meant to be [deterministic](https://en.wikipedia.org/wiki/Deterministic_algorithm), meaning the same outcome is produced based on the same input (e.g. changing the color of shape), multiple changes to that property would result in the last one to arrive as the outcome: -[graphic here] + The process of transactional conflict resolution is somewhat simple to reason about. If two clients make a concurrent change to the same object but modify a different property, no conflicts occur. Because clients only send the intent of a change, these can both be processed in the order of arrival by the server -[graphic here] + When concurrent changes occur to the same property, a conflict occurs. By default, the server resolves this conflict using a simple [Last Write Wins](https://dzone.com/articles/conflict-resolution-using-last-write-wins-vs-crdts) (LWW) approach. The server then broadcasts the resolved state to all clients. -[graphic here] + However, depending on the application, it is possible to build in any custom conflict resolution that would override the default Last Write Wins Behavior @@ -209,7 +235,7 @@ A CRDT is a technique to solve conflicts using [a complex data structure that re We will use a simple operation-based CRDT example to demonstrate how they work in a broad sense: -[graphic here] + Generally, although CRDTs [can be used in server authority models](https://exaspark.medium.com/top-5-ways-to-implement-real-time-rich-text-editor-ranked-by-complexity-3bc26e3c777f), they are best suited [for decentralized systems](https://www.figma.com/blog/how-figmas-multiplayer-technology-works/) because they do not require an authoritative server. CRDTs are also a strong fit for [applications with offline support](https://exaspark.medium.com/top-5-ways-to-implement-real-time-rich-text-editor-ranked-by-complexity-3bc26e3c777f) because the data structure can preserve edits by an offline client and automatically merge them when the client regains connectivity. @@ -219,7 +245,7 @@ However, CRDTs require a lot of [computational and bandwidth overhead](https://w OT is a technique to solve conflicts using [a set of algorithms that compare concurrent operations]() and detect if the operations will allow the state to converge. If not, the operations are modified (or transformed) to resolve conflicts before being applied to the state: -[graphic here] + Much like CRDTs, OT is known to be complex to reason about and can [theoretically be implemented in a distributed fashion](https://digitalfreepen.com/2018/01/04/operational-transform-hard.html), however, it is overly complex so most OT implementations rely on a central server, which is still complex to implement itself. @@ -281,62 +307,64 @@ Syncosaurus is a React Javascript client-side SDK with full ready-to-be-deployed Similar to commercial solutions like Liveblocks and Reflect, Syncosaurus exposes a client-side SDK while abstracting the backend logic and handling much of the deployment - the only thing a developer has to do to get the backend deployed is sign up for a Cloudflare account and use our CLI to deploy. However, unlike the commercial solutions, the Syncosaurus framework is free to use and open source so a developer can alter the default backend code if they choose. - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
DIYLiveblocksReflectSyncosaurus
Open-source
Managed Service
Easy to Deploy
Conflict Resolution MechanismAnyCRDTsTransactional Conflict ResolutionTransactional Conflict Resolution
Authentication Support
Offline Client Support
Analytics
DIYLiveblocksReflectSyncosaurus
Open-source
Managed Service
Easy to Deploy
Conflict Resolution MechanismAnyCRDTsTransactional Conflict ResolutionTransactional Conflict Resolution
Authentication Support
Offline Client Support
Analytics
# Using Syncosaurus @@ -350,15 +378,15 @@ As mentioned, Syncosaurus uses a real-time syncing model with transactional conf - When a client makes a change to state, it is immediately applied to the client’s locally and the client places a copy of the intent of the change (i.e. a state mutation) in a pending queue. - Next, the mutation is sent across the WebSocket connection to the Syncosaurus server. -[graphic here] + - Once the change is made to the authoritative state, the server sends a confirmation update to the client, which the client then uses to update its state to match the server and remove the pending state mutation from the queue. -[graphic here] + - When more than one client is connected to a given room, any mutations from one client are broadcast to all other clients by the server. Because an update from the server is authoritative, all client states are guaranteed to converge. -[graphic here] + ## Development @@ -370,7 +398,7 @@ The first step to use Syncosaurus is to install the CLI tool by running `npm ins Next one can choose to add Syncosaurus to an existing React project using `npx syncosaurus setup` or create a project from scratch using `npx syncosaurus init` -[insert nice CLI graphic / gif] +[TODO insert nice CLI graphic / gif] ### Create and launch @@ -544,7 +572,7 @@ Go ahead and enter some todos into Client 1 and watch them appear on Client 2 af After you’re satisfied with the local version of the application, it can be deployed to Cloudflare by running `npx syncosaurus deploy`. Your deployed Cloudflare architecture will consist of Cloudflare Workers and Durable Objects. For each room your clients create, a new Durable Object will be created and any client will be able to connect to it through a worker: -[insert screenshot of architecture] +[TODO insert screenshot of architecture] ## Monitoring @@ -552,7 +580,7 @@ After your application is deployed, you can monitor its usage and get help debug The dashboard includes hourly time-series metrics related to errors and usage for each room so you can verify users are able to access and use the application in a bug-free manner -[insert screenshot of dashboard] +[TODO insert screenshot of dashboard] For even more detail, a tail logging session for your deployed backend can be started by running `npx syncosaurus tail` @@ -568,7 +596,7 @@ Before we can discuss the architecture of Syncosaurus, it’s important to summa - Multiple concurrent rooms (maintaining WebSocket connections and broadcasting messages) - Persistent storage of documents -[insert graphic of multiple rooms with clients connected and a new client trying to connect to a particular room] +[TODO insert graphic of multiple rooms with clients connected and a new client trying to connect to a particular room] ## Architecture @@ -594,13 +622,13 @@ When choosing a provider to build on, we narrowed in on a couple of options. First, we could have built our serverless edge infrastructure using a combination of AWS Lambda@Edge, Amazon API Gateway, and a persistent storage mechanism like AWS Dynamo DB: -[insert graphic] +[TODO insert graphic] While this is a valid approach, it does involve provisioning and connecting several components which can increase the complexity of deployment and maintenance. As previously mentioned, we instead ended up choosing a Cloudflare-based architecture consisting of Workers and Durable Objects due to its simplicity and extremely strong fit for our use case. -[insert graphic] +[TODO insert graphic] A Worker is an edge-based serverless function on the Cloudflare network. A Durable Object (DO) is a special type of Worker - a globally unique [JavaScript isolate ](https://v8docs.nodesource.com/node-0.8/d5/dda/classv8_1_1_isolate.html)(a unique JS engine) with access to its own private strongly consistent [storage](https://developers.cloudflare.com/durable-objects/api/transactional-storage-api/) and built-in [caching](https://developers.cloudflare.com/durable-objects/reference/in-memory-state/#:~:text=The%20Durable%20Object's%20storage%20has,be%20instantly%20returned%20from%20cache.). @@ -616,14 +644,18 @@ When engineering Syncosuaurus, we had to be thoughtful about the efficiency of t ### Challenge: Authoritative Update Size -A naive implementation of authoritative updates sent from the server to clients would be to broadcast the entire state from the server to all clients when each change occurs. However, an issue with this approach is that as the document grows in size, the message size containing the authoritative state sent from the server to the client will grow equivalently. This has two consequences: +A naive implementation of authoritative updates sent from the server to clients would be to broadcast the entire state from the server to all clients when each change occurs. + + + +However, an issue with this approach is that as the document grows in size, the message size containing the authoritative state sent from the server to the client will grow equivalently. This has two consequences: - Larger update sizes mean that the WebSocket messages will take longer to transmit - Once a message arrives at the client, it will take longer to process and update its entire local state An alternative approach to prevent this is to send an update that only contains the changes that the server, also known as a [delta update](https://en.wikipedia.org/wiki/Delta_update) approach: -[insert example delta update message example here] + We ultimately decided on the delta update approach for the efficiency gains, however, this decision introduced the risk that a missed update by a client could lead to a divergent state. @@ -633,7 +665,7 @@ As mentioned, a risk of using delta updates is the heightened potential for miss To do so, we implemented an incrementing `batchID` which is sent by the DO as a property on every update message broadcasted to the clients. Each client tracks the `batchID` of the last message it received from the DO and when it receives a new message, it compares the previous `batchID` against the new one to determine if it missed an update. If a client misses an update, it sends a special request to the DO for a copy of the entire latest state. -[insert diagram of process] +[TODO insert diagram of process] Note that sending only the delta updates missed could reduce the state recovery message size and latency, however, the DO currently does not keep a log of the updates it broadcasts. This is an area for future investigation since it would likely create greater memory and storage demands on the DO. @@ -650,7 +682,7 @@ Using an event-driven model means that for every message sent by a single client If we assume all clients are sending messages simultaneously and we are targeting a certain message per second rate (i.e. [frame rate per second (FPS)](https://www.100ms.live/blog/frame-rate#)) broadcasting would scale at a rate of O(M^2\*N) where N represents the number of messages sent per second by a single client. -[insert graphic] + In [testing](https://news.ycombinator.com/item?id=37942258) done by Reflect, the target budget of a DO should be approximately 2,000 calls per second to `WebSocket.send `(a call to transmit a message over a WebSocket connection). This means, that if an app wants to target 60 FPS (a standard [in gaming](https://www.100ms.live/blog/frame-rate#)) it can only have 6 concurrent users (60 messages/second = 2000 calls / (6 users^2)). While a 6-user limit is suitable for some applications, it does shrink the pool of applications Syncosaurus could support. @@ -658,13 +690,13 @@ In [testing](https://news.ycombinator.com/item?id=37942258) done by Reflect, the A time-driven model means that the DO would group state changes into a single update and send out a periodic message based on a configurable time frequency. -[insert graphic] + This frequency directly correlates with the frame rate and makes the messaging system scale at a rate of O(M\*N). Therefore, if an app wanted to target 60 FPS (approximately every 16ms), it can support up to 33 concurrent connections. The tradeoff with this approach is that a message will be sent whether an update has occurred or not, meaning there may be unnecessary empty messages sent. However, we decided this tradeoff was worth it to make our messaging more efficient (message scales at a rate of O(M*N) instead of O(M^2 * N)) and to expand the pool of Syncosaurus-compatible applications. -[insert graphic] + ### Challenge: Re-rendering and Subscriptions @@ -672,7 +704,7 @@ An additional consideration was reducing unnecessary client-side rendering in Re To make subscriptions fit React’s granular rendering model, we decided to allow developers to write query functions on per component basis that indicate which keys in the local store they want to watch for updates (known as a key “watchlist”). Furthermore, by allowing subscriptions to accept a query callback, the developer can transform data in this callback before returning the value to React to be rendered. Finally, an additional mechanism we put in place to reduce unnecessary re-renders was a check to ensure the result of the query had changed since its last rerender (i.e. memoization), otherwise a new render would not be initiated. -[insert diagram of process] +[TODO insert diagram of process] Though, there may be additional memory overhead with memoizing query results and maintaining a key watchlist, eliminating unnecessary UI re-renders and making subscriptions more robust leads to a snappier UI and gives developers more control over the rendering of their application, respectively. @@ -694,7 +726,7 @@ The Syncosaurus framework supports token-based authentication that allows a deve As demonstrated, Syncosaurus includes an analytics tool to easily view and analyze aggregate and single-room metrics for an application. The dashboard allows a developer to gain insights into usage and debug their application if necessary. The architecture for the analytics dashboard displays data from Cloudflare’s endpoints and visualizes it in a locally running front-end application that pulls from a custom-built GraphQL backend: -[insert graphic] +[TODO insert graphic] # Future of Syncosaurus diff --git a/static/img/diagrams/diag-CRDT.svg b/static/img/diagrams/diag-CRDT.svg new file mode 100644 index 0000000..f365c68 --- /dev/null +++ b/static/img/diagrams/diag-CRDT.svg @@ -0,0 +1,122 @@ + +Client 1 + +H + +0a + +e + +1a + +l + +2a + +o + +3a + +l + +4a + +! + +4b + +insert ' + +l + +' with ID + +4a + + after + +2a + +Client 2 + +H + +0a + +e + +1a + +l + +2a + +o + +3a + +! + +4b + +l + +4a + +insert ' + +! + +' with ID + +4b + + after + +3a + +Client 1 + +H + +0a + +e + +1a + +l + +2a + +o + +3a + +Client 2 + +H + +0a + +e + +1a + +l + +2a + +o + +3a + + + + + diff --git a/static/img/diagrams/diag-DeltaUpdates.svg b/static/img/diagrams/diag-DeltaUpdates.svg new file mode 100644 index 0000000..00131dd --- /dev/null +++ b/static/img/diagrams/diag-DeltaUpdates.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-ON-messaging.svg b/static/img/diagrams/diag-ON-messaging.svg new file mode 100644 index 0000000..fc50d39 --- /dev/null +++ b/static/img/diagrams/diag-ON-messaging.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-ON2-messaging.svg b/static/img/diagrams/diag-ON2-messaging.svg new file mode 100644 index 0000000..58c651c --- /dev/null +++ b/static/img/diagrams/diag-ON2-messaging.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-OT.svg b/static/img/diagrams/diag-OT.svg new file mode 100644 index 0000000..25b76b3 --- /dev/null +++ b/static/img/diagrams/diag-OT.svg @@ -0,0 +1,94 @@ + +Client 2 + +ab + +c + +x + +0    1   + +2 + +delete + +char + + at position + +2 + +Client 1 + +ab + +c + +x + +0    1    2 + +3 + +insert ' + +x + +' at position + +0 + +3 + +Client 2 + +ab + +c + +x + +0    1   + +2 + +delete + +char + + at position + +2 + +Client 1 + +ab + +c + +x + +0    1    2 + +3 + +insert ' + +x + +' at position + +0 + +3 + + + + + diff --git a/static/img/diagrams/diag-StateUpdates.svg b/static/img/diagrams/diag-StateUpdates.svg new file mode 100644 index 0000000..1635de4 --- /dev/null +++ b/static/img/diagrams/diag-StateUpdates.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-absolute-update.svg b/static/img/diagrams/diag-absolute-update.svg new file mode 100644 index 0000000..db584eb --- /dev/null +++ b/static/img/diagrams/diag-absolute-update.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-centralized.svg b/static/img/diagrams/diag-centralized.svg new file mode 100644 index 0000000..167886d --- /dev/null +++ b/static/img/diagrams/diag-centralized.svg @@ -0,0 +1 @@ + diff --git a/static/img/diagrams/diag-conflict-edits.svg b/static/img/diagrams/diag-conflict-edits.svg new file mode 100644 index 0000000..e4a2945 --- /dev/null +++ b/static/img/diagrams/diag-conflict-edits.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-long-polling.svg b/static/img/diagrams/diag-long-polling.svg new file mode 100644 index 0000000..f912707 --- /dev/null +++ b/static/img/diagrams/diag-long-polling.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-new-client-connection.svg b/static/img/diagrams/diag-new-client-connection.svg new file mode 100644 index 0000000..05fb580 --- /dev/null +++ b/static/img/diagrams/diag-new-client-connection.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-no-conflict-edits.svg b/static/img/diagrams/diag-no-conflict-edits.svg new file mode 100644 index 0000000..c2ea07b --- /dev/null +++ b/static/img/diagrams/diag-no-conflict-edits.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-optimistic-ui.svg b/static/img/diagrams/diag-optimistic-ui.svg new file mode 100644 index 0000000..8f41473 --- /dev/null +++ b/static/img/diagrams/diag-optimistic-ui.svg @@ -0,0 +1,29 @@ + +interaction + +User + +nothing + + Do + +Interface + +Update + +to server + + Send mutation + +update? + + Successful + +no + +yes + + + diff --git a/static/img/diagrams/diag-p2p.svg b/static/img/diagrams/diag-p2p.svg new file mode 100644 index 0000000..4c9b733 --- /dev/null +++ b/static/img/diagrams/diag-p2p.svg @@ -0,0 +1 @@ + diff --git a/static/img/diagrams/diag-relative-update.svg b/static/img/diagrams/diag-relative-update.svg new file mode 100644 index 0000000..d5d5a62 --- /dev/null +++ b/static/img/diagrams/diag-relative-update.svg @@ -0,0 +1,30 @@ + +1 + +0 + +2 + +4 + ++1 + ++2 + ++1 + +-1 + +-1 + ++2 + + + + + diff --git a/static/img/diagrams/diag-syncingModel-1.svg b/static/img/diagrams/diag-syncingModel-1.svg new file mode 100644 index 0000000..b5a64e6 --- /dev/null +++ b/static/img/diagrams/diag-syncingModel-1.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-syncingModel-2.svg b/static/img/diagrams/diag-syncingModel-2.svg new file mode 100644 index 0000000..eced9bf --- /dev/null +++ b/static/img/diagrams/diag-syncingModel-2.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-syncingModel-3.svg b/static/img/diagrams/diag-syncingModel-3.svg new file mode 100644 index 0000000..0ba075c --- /dev/null +++ b/static/img/diagrams/diag-syncingModel-3.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-syncingModel-4.svg b/static/img/diagrams/diag-syncingModel-4.svg new file mode 100644 index 0000000..f556055 --- /dev/null +++ b/static/img/diagrams/diag-syncingModel-4.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-timeDrivenMessages.svg b/static/img/diagrams/diag-timeDrivenMessages.svg new file mode 100644 index 0000000..97563c8 --- /dev/null +++ b/static/img/diagrams/diag-timeDrivenMessages.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-whiteboard-conflict.svg b/static/img/diagrams/diag-whiteboard-conflict.svg new file mode 100644 index 0000000..e554984 --- /dev/null +++ b/static/img/diagrams/diag-whiteboard-conflict.svg @@ -0,0 +1,6 @@ + + + diff --git a/static/img/diagrams/diag-whiteboard-demo-dual-latency.svg b/static/img/diagrams/diag-whiteboard-demo-dual-latency.svg new file mode 100644 index 0000000..644b29e --- /dev/null +++ b/static/img/diagrams/diag-whiteboard-demo-dual-latency.svg @@ -0,0 +1,18 @@ + + Bob + +Alice + + Bob + +Alice + + + + + diff --git a/static/img/diagrams/diag-whiteboard-demo-dual.svg b/static/img/diagrams/diag-whiteboard-demo-dual.svg new file mode 100644 index 0000000..4fc6c51 --- /dev/null +++ b/static/img/diagrams/diag-whiteboard-demo-dual.svg @@ -0,0 +1,18 @@ + + Bob + +Alice + + Bob + +Alice + + + + + From 348c8ad2bb09f2a4f10b4de173522e248d19a78e Mon Sep 17 00:00:00 2001 From: Alex Sklar Date: Mon, 22 Apr 2024 18:41:57 -0700 Subject: [PATCH 11/13] bug(snippets): remove todo-list code files that cause docusaurus build errors Co-authored-by: Erik Margetis Co-authored-by: Joseph Liang --- src/pages/todo-list-client.jsx | 62 --------------------------------- src/pages/todo-list-mutators.js | 14 -------- 2 files changed, 76 deletions(-) delete mode 100644 src/pages/todo-list-client.jsx delete mode 100644 src/pages/todo-list-mutators.js diff --git a/src/pages/todo-list-client.jsx b/src/pages/todo-list-client.jsx deleted file mode 100644 index c92a33f..0000000 --- a/src/pages/todo-list-client.jsx +++ /dev/null @@ -1,62 +0,0 @@ -// import { useState } from 'react' -// import Syncosaurus from 'syncosaurus' -// import { useSubscribe } from 'syncosaurus' -// import mutators from '../mutators.js' - -// const synco = new Syncosaurus({ -// mutators, -// userID: '1234', -// server: import.meta.env.VITE_DO_URL, -// }) - -// synco.launch('yourRoomID') - -// export default function App() { -// const [inputValue, setInputValue] = useState('') - -// function handleChange(e) { -// setInputValue(e.target.value) -// } - -// function handleSubmit(e) { -// e.preventDefault() -// synco.mutate.addTodo({ -// id: uuidv4(), -// text: inputValue, -// }) - -// setInputValue('') -// } - -// function handleDelete(id) { -// synco.mutate.removeTodo({ id }) -// } - -// const todos = useSubscribe( -// synco, -// tx => { -// let todoObject = tx.scan(key => { -// return key.includes('todo') -// }) -// return Object.values(todoObject) -// }, -// [] -// ) - -// return ( -//
-//
-// -// -//
-//
    -// {todos.map(todo => ( -//
  • -// {todo.text} -// -//
  • -// ))} -//
-//
-// ) -// } diff --git a/src/pages/todo-list-mutators.js b/src/pages/todo-list-mutators.js deleted file mode 100644 index d168b9e..0000000 --- a/src/pages/todo-list-mutators.js +++ /dev/null @@ -1,14 +0,0 @@ -// export default { -// addTodo, -// removeTodo, -// } - -// function addTodo(tx, { id, text }) { -// const todo = { id, text, complete: false } -// tx.set(`todo/${id}`, todo) -// return todo -// } - -// function removeTodo(tx, { id }) { -// tx.delete(`todo/${id}`) -// } From 2ee85526857ddb02e1f61dd73de4b8f346723973 Mon Sep 17 00:00:00 2001 From: Alex Sklar Date: Mon, 22 Apr 2024 19:48:33 -0700 Subject: [PATCH 12/13] feat(diag): syncing model diagrams Co-authored-by: Erik Margetis Co-authored-by: Joseph Liang --- src/components/Diagrams/index.js | 48 +++++++++++++++++++------------- src/pages/case-study.mdx | 11 +++++--- 2 files changed, 35 insertions(+), 24 deletions(-) diff --git a/src/components/Diagrams/index.js b/src/components/Diagrams/index.js index 5eeb1b6..b5a2728 100644 --- a/src/components/Diagrams/index.js +++ b/src/components/Diagrams/index.js @@ -119,35 +119,43 @@ export const StateUpdates = () => { } export const SyncingModel1 = () => { - return + return
+ +
} export const SyncingModel2 = () => { - return + return
+ +
} export const SyncingModel3 = () => { - return + return
+ +
} export const SyncingModel4 = () => { - return + return
+ +
} export const TimeDrivenMessages = () => { diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index 2c046e4..a4c1357 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -375,19 +375,22 @@ To better understand Syncosaurus we will explore the syncing model and then walk As mentioned, Syncosaurus uses a real-time syncing model with transactional conflict resolution to keep state consistent across multiple clients: + + - When a client makes a change to state, it is immediately applied to the client’s locally and the client places a copy of the intent of the change (i.e. a state mutation) in a pending queue. -- Next, the mutation is sent across the WebSocket connection to the Syncosaurus server. - + -- Once the change is made to the authoritative state, the server sends a confirmation update to the client, which the client then uses to update its state to match the server and remove the pending state mutation from the queue. +- Next, the mutation is sent across the WebSocket connection to the Syncosaurus server. -- When more than one client is connected to a given room, any mutations from one client are broadcast to all other clients by the server. Because an update from the server is authoritative, all client states are guaranteed to converge. +- Once the change is made to the authoritative state, the server sends a confirmation update to the client, which the client then uses to update its state to match the server and remove the pending state mutation from the queue. +- When more than one client is connected to a given room, any mutations from one client are broadcast to all other clients by the server. Because an update from the server is authoritative, all client states are guaranteed to converge. + ## Development Now that we understand the fundamental syncing model of Syncosaurus, we will discuss how to use the framework. From af112f52e39e6c3f26002213573ec50abf2e8e10 Mon Sep 17 00:00:00 2001 From: Alex Sklar Date: Tue, 23 Apr 2024 10:13:18 -0700 Subject: [PATCH 13/13] feat(diag): add AWS diagram Co-authored-by: Erik Margetis Co-authored-by: Joseph Liang --- src/pages/case-study.mdx | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/src/pages/case-study.mdx b/src/pages/case-study.mdx index a4c1357..5773242 100644 --- a/src/pages/case-study.mdx +++ b/src/pages/case-study.mdx @@ -583,7 +583,7 @@ After your application is deployed, you can monitor its usage and get help debug The dashboard includes hourly time-series metrics related to errors and usage for each room so you can verify users are able to access and use the application in a bug-free manner -[TODO insert screenshot of dashboard] +dashboard screenshot For even more detail, a tail logging session for your deployed backend can be started by running `npx syncosaurus tail` @@ -625,7 +625,10 @@ When choosing a provider to build on, we narrowed in on a couple of options. First, we could have built our serverless edge infrastructure using a combination of AWS Lambda@Edge, Amazon API Gateway, and a persistent storage mechanism like AWS Dynamo DB: -[TODO insert graphic] +AWS Architecture Diagram While this is a valid approach, it does involve provisioning and connecting several components which can increase the complexity of deployment and maintenance. @@ -649,7 +652,7 @@ When engineering Syncosuaurus, we had to be thoughtful about the efficiency of t A naive implementation of authoritative updates sent from the server to clients would be to broadcast the entire state from the server to all clients when each change occurs. - + However, an issue with this approach is that as the document grows in size, the message size containing the authoritative state sent from the server to the client will grow equivalently. This has two consequences: