GithubHelp home page GithubHelp logo

magic-bridge's Introduction

Magic Bridge

Magic Bridge lets you call functions on a Node.JS server from a client, abstracting away HTTP.

Register a function on the server:

const newBridge = require('@magic-bridge/bridge')
// import bridge from '@magic-bridge/bridge'
const bridge = newBridge()

// register functions (or classes)
bridge.register(function getServerThing() {
  return 'i am a string from server'
}

// use with express 
const app = express()
app.use('/jsonrpc/default', bridge.middleware())

Now you can call it from the client:

const bridge = require('@magic-bridge/client')
// import bridge from '@magic-bridge/client'
const bridge = newBridge()

// call a function on the server!
const thingFromServer = await bridge.getServerThing()
// thingFromServer === 'i am a string from server'

Install

At your server:

npm install @magic-bridge/bridge

At your client:

npm install @magic-bridge/client

Usage

Create a bridge instance

The Magic Bridge module exports a factory function for making new bridges both on the client and the server. The server optionally accepts some advanced options:

On the server

const newBridge = require('@magic-bridge/bridge')

const bridge = newBridge()
// or
const bridge = newBridge(opts)
Option Description Type Default
ignoreMethodNameRegex Functions registered that match this regex will be ignored. Such as methods on a class starting with an underscore to denote that they are private regex /^_/
throwOnDup Will throw an error if more than one function is added with the same name boolean true

On the client

The client accepts one optional arguemnt; the url/path of the Magic Bridge middleware

const newBridge = require('@magic-bridge/client')

const bridge = newBridge() // uses /jsonrpc/default
// or 
const bridge = newBridge('/my-magic-bridge-url')

the client bridge is now ready to call functions on the server:

// bridge calls must always be async
const thingFromServer = await bridge.doServerThing()

Registering functions

Magic Bridge provides a few ways of registering functions via register():

Just a function

bridge.register(function func() { ... })
// client: await bridge.func()

A function with context

const obj = {
  x: 99,
  func: function () { 
    return this.x
  }
}
bridge.register(obj.func, obj)
// client: await bridge.func() --> 99

A function with a given name

bridge.register('myFunc', () => { ... })
// client: await bridge.myFunc()

A function with a given name and context

const obj = {
  x: 99,
  func: function() { 
    return this.x
  }
}
bridge.register('myFunc', obj.func, obj)
// client: await bridge.myFunc() --> 99

An instance of a class

This is quite handy, espcially in combination with multiple bridges

class Clazz {
  myMethod() {
    return 99
  }
  anotherMethod() {
    return 88
  }
}
const clazz = new Clazz()
bridge.register(clazz)
// client: await bridge.myMethod() --> 99
// client: await bridge.anotherMethod() --> 88

Functions on a plain object

This is quite handy, espcially in combination with multiple bridges

const obj {
  myFunction() {
    return 99
  }
  anotherFunction() {
    return 88
  }
}

bridge.register(obj)
// client: await bridge.myFunction() --> 99
// client: await bridge.anotherFunction() --> 88

Using middleware with Express

Magic Bridge is designed to be used as Express middleware. The default path used by the client is /jsonrpc/default, so the default set up is to do this:

const app = express()
app.use('/jsonrpc/default', bridge.middleware())

If you do use a different path, you must also configure the bridge side on the client to use it:

// client side:
const bridge = newBridge('/my-magic-bridge-path')

Multple bridges

You can create multiple bridge instances in a single application, this useful for two main reasons:

  1. It acts as a namespace for classes or collections of related functions
  2. Registered functions/methods requiring different credentials can be used as separate middleware
const newBridge = require('@magic-bridge/bridge')

const auth = new Auth();
const account = new Account()

const authBridge = newBridge()
const accountBridge = newBridge()

app.use('/jsonrpc/auth', authBridge.middleware())
app.use('/jsonrpc/account', ensureLoggedIn(), accountBridge.middleware())

and on the client:

const newBridge = require('@magic-bridge/client')

const authBridge = newBridge('/jsonrpc/auth')
const accountBridge = newBridge('/jsonrpc/account')

await authBridge.login()
await accountBridge.changeUsername()

Local arg resolvers

Functions on the server can be injected with request, response, request.session and request.cookie arguments that are invisible to the client.

Use arguments with these method names in any postion to have them injected:

Argument Resolves to
_request_ The (express) request object
_response_ The (express) response object
_session_ The (express) request session object (if using express-session middleware
_cookies_ Parsed request cookies

Examples:

function changeUsername(_session_, newUsername) {
  const user = db.getUser(_session_.userId)
  user.setUsername(newUsername)
  ...
}
function changeUsername(newUsername, _cookies_) {
  const user = db.getUser(_cookies_.token)
  user.setUsername(newUsername)
  ...
}

Credits

Magic Bridge is inspired by JSON-RPC-Java (later renamed Jabsorb) a library I used circa 2006-8 to do Ajaxy stuff.

Magic bridge partially implements the JSON-RPC 2.0 specification (it doesn't do batches)

magic-bridge's People

Contributors

philmander 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.