Git Product home page Git Product logo

rimless's Introduction

rimless

npm Commitizen friendly

Rimless makes event based communication easy with a promise-based API wrapping postMessage. Works with both iframes and webworkers.

You can use rimless to call remote procedures, exchange data or expose local functions with iframes/webworkers.

You can see it in action here https://au-re.github.io/rimless.

Installation

Rimless can be installed via npm.

$ npm i -S rimless

or from a CDN

<script src="https://unpkg.com/rimless/lib/rimless.min.js"></script>

Example Usage

in the host website

import { host }  from "rimless";

const connection = await host.connect(iframe, {
  myVariable: 12,
  myFunction: (value) => `hello ${value}`,
});

// access variables on the iframe
console.log(connection.remote.myIframeVariable);  // 42

// call remote procedures on the iframe
const result = await connection.remote.myIframeFunction("here");
console.log(result);  // hello here

// close the connection
connection.close();

in the iframe

import { guest }  from "rimless";

const connection = await guest.connect({
  myIframeVariable: 42,
  myIframeFunction: (value) => `hello ${value}`,
});

// access variables on the host
console.log(connection.remote.myVariable); // 12

// call remote procedures on host
const res = await connection.remote.myFunction("there");
console.log(res);   // hello there

// close the connection
connection.close();

Getting Started

This is how you can connect your website to an iframe or webworker:

import { host }  from "rimless";

const iframe = document.getElementById("myIframe");
const worker = new Worker("myWorker");

// connect to the iframe
host.connect(iframe);

// connect to the worker
host.connect(worker);

You also need to connect your iframe/webworker to the host website.

Usage from an iframe:

import { guest }  from "rimless";

// connect to the parent website
guest.connect();

Usage from a webworker:

importScripts("https://unpkg.com/rimless/lib/rimless.min.js");

const { guest } = rimless;

// connect to the parent website
guest.connect();

Exposing an API

To do anything meaningful with this connection you need to provide a schema that defines the API of the host/iframe/webworker. Any serializeable values as well as functions are ok to use. In the example below the host website provides a function that will update its background color when invoked.

import { host }  from "rimless";

const api = {
  setColor: (color) => {
    document.body.style.background = color;
  },
};

const iframe = document.getElementById("myIframe");

host.connect(iframe, api);

The api schema must be passed on connection, the same applies to the iframe/webworker.

Calling an RPC

With the host API exposed we can now invoke the remote procedure from the iframe.

import { guest }  from "rimless";

// connect returns a promise that resolves in a connection object
// `connection.remote` contains the api you can invoke
guest.connect().then((connection) => {
  connection.remote.setColor("#011627");
});

Closing a connection

Closing a connection will remove all event listeners that were registered.

import { guest }  from "rimless";

guest.connect().then((connection) => {
  connection.close();
});

How it Works

  1. The guest (iframe/webworker) sends a handshake request to the host with a schema describing its API
  2. The host confirms the handshake and returns a schema with its own API

Now both can make use of the APIs they have shared with each other, e.g.

  1. The guest requests someAction on the parent.
  2. After verifying the origin, the parent will execute the function mapped to someAction and the result is returned to the guest.

Limitations

All parameters passed through postMessage need to be serializeable. This applies also for all return values of the functions you expose.

// someFunction would return undefined when called in the remote.
const api = {
  someFunction: () => () => {},
};

Alternatives

This library is inspired by Postmate and Penpal.

So why does this library exist?

  • works with webworkers!
  • does not create the iframe (easier to work with libraries like react)
  • works with iframes using srcdoc
  • works with multiple iframes from the same origin

API

Rimless exports two objects: host and guest.

host.connect

Connect your website to a "guest" (iframe/webworker).

host.connect(iframe, {
  log: (value) => console.log(value)
});
Name Type Description Required
guest HTMLIFrameElement or Worker Target of the connection required
schema object schema of the api you want to expose -
options object - -

guest.connect

Connect a "guest" to your website. The guest connection automatically happens based on the environment it is run.

guest.connect({
  log: (value) => console.log(value)
});
Name Type Description Default
schema object schema of the api you want to expose -
options object - -

Contributing

We use the airbnb style guide when writing javascript, with some minor modifications. Make sure eslint is installed and running before making changes, as it will ensure your coding style matches that of the project.

We use commitizen and angular's conventional changelog to enforce a consistent commit format. When writing commits, make sure you run npm run commit instead of git commit.

License

MIT

rimless's People

Contributors

apifever avatar au-re avatar dependabot-preview[bot] avatar ivan-saorin avatar

Stargazers

 avatar  avatar  avatar

Watchers

 avatar  avatar

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.