Skip to content

NOAA-GSL/idsse-muppet

Repository files navigation

Publish to GitHub Packages

IDSSe MUPPET Library

Modern UI Peer-to-Peer Event (MUPPETs)

This is a React Javascript library for two or more React apps to connect to MUPPET data channels (WebRTC/websockets under the hood), then use simple, React-like interfaces to forward each other serialized UI events from their app (like user clicks, selections, or input) via the MUPPETs protocol.

Table of Contents

Usage

Log into GitHub's Package repo

Login to GitHub's NPM repository on the command line by following this GitHub guide.

If you already have a GitHub Personal Token with registry read access saved somewhere on your local machine (maybe an environment variable), skip straight to the command:

npm login --scope=@noaa-gsl --auth-type=legacy --registry=https://npm.pkg.github.com

entering your GitHub username as the username, and your generated GitHub personal token as the password (should be a 40-character string starting with "ghp_").

This command is pointing NPM to GitHub's Package repository (rather than the default NPM address registry.npmjs.org) and logging in your CLI session as your GitHub user.

To check that this worked, run this command:

npm whoami --registry=https://npm.pkg.github.com

If it prints your GitHub account name, you're good to go. If it throws a 401 or ENEEDAUTH, your CLI session is still not logged in GitHub's Package repository.

Install the library

npm install @noaa-gsl/idsse-muppet

Now you can use the MUPPET library to create new connections to a MUPPET channel and send/receive events over it in your React application.

Developer Guide

To use MUPPET channels in your React app, first need to wrap your top-level React component in a MuppetProvider:

// main.jsx
import ReactDOM from "react-dom/client";
import { MuppetProvider } from "@noaa-gsl/idsse-muppet";
import App from "./App";

ReactDOM.createRoot(document.getElementById("root")).render(
  <MuppetProvider
    clientName="MY_APP"
    serverUrl="http://example.com" // URL of WebRTC signaling server
    serverPath="/"
    channelNames={["my-channel"]}
  >
    <App>
  </MuppetProvider>
);
  • channelNames: 1 or more WebRTC rooms on the WebRTC server that you wish to connect to. This will need to line up with the room(s) used by the app with which you want to send/receive messages.
  • clientName: how your app identifies itself to other apps using MUPPET. This will be prepended to the eventClass of every event you send. For example, other apps may subscribe to events from you with eventClass MY_APP.SOME_BUTTON_CLICKED, or if they want to send an RPC type message to your app specifically, they would use this clientName string to address the message.

With that Provider in place, now any components in your React component tree have access to shared, persistent MuppetChannel instances. You can fetch this channel and use it directly in your React component:

// MyComponent.jsx
import { useState } from 'react';
import { useMuppetChannel, useMuppetCallback } from '@noaa-gsl/idsse-muppet';

function MyComponent() {
  // track user's favorite color from other app
  const [currentColor, setCurrentColor] = useState('');

  const channel = useMuppetChannel('my-channel');

  useMuppetCallback(
    'my-channel',
    (channel, evt) => {
      console.log('Received new color selection from OTHER_APP:', evt);
      setCurrentColor(event.color);
    },
    ['OTHER_APP.COLOR_SELECTED'],
  );

  const onButtonClick = () => {
    channel?.sendEvent({
      eventClass: 'BUTTON_CLICKED',
      event: { value: 123 },
    });
  };

  return (
    <div>
      <button onClick={onButtonClick}>Hello world</button>
      <p>Favorite color:</p>
      <p>{currentColor}</p>
    </div>
  );
}

export default MyComponent;

For more details, see the Developer Guide - React.

Although it's not recommended because it can be much harder to manage app state, if you want to use the underlying JS without the niceties of React Context or custom Hooks, see Developer Guide - Vanilla JS

Contributing

  1. Ensure you have NPM installed locally
  2. Clone this repository with git clone <repo_url>
  3. Install any 3rd-party JS libraries needed by cding into your newly-cloned repo and running npm install

If you have changes you wish to be incorporated into the main branch, feel free to submit your feature branch for code review! Code should run quickly, quietly (without noisy console messages), and without crashing the page of a project that imports it.

Publishing

To publish a new version of this package:

  1. In the package.json file, increase the version number (either the patch or minor number are usually fine).
    1. This step is needed so NPM recognizes it as a new version for any repos that install it with npm install. If you don't do this, NPM will reject the publish due to a conflict with the last version, and the publish GitHub Action will fail.
  2. Go to the Releases page on the GitHub repository and click "Draft a new release"
    1. Releases should be shown in a sidebar on the right of the Code page on GitHub.
  3. Click the "Choose a tag" dropdown, then start typing a new version number in the text box
    1. This should start with "v", then the same version that you set in the package.json file in step 1.
    2. Click "Create new tag"
    3. Type a bullet point or two about what was changed, or click "Generate release notes" which just links to a diff between this version and the last.
  4. Make sure "Set as pre-release" is not checked
    1. This will ensure that projects using this library will download your new version the next time they run npm install.
    2. If "pre-release" is checked, it would still publish to NPM but not upgrade by default. Users of the library would have to "opt in" to this latest version by installing it explicitly, e.g. npm install @noaa-gsl/[email protected]
  5. Click "Publish release"

That's it! A GitHub Action will be kicked off to auto-publish the new version to NPM. You can watch the status on the Actions tab of GitHub.

Once that finishes, projects that use this library can run npm install, and NPM will upgrade them to the new version of this library in their project (in their package.json, or by running npm ls | grep idsse-muppet).