npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

@speedapi/driver

v1.5.1

Published

SpeedAPI wire protocol implementation for TypeScript

Downloads

6

Readme

License Version Coverage Downloads Size PRs and issues

SpeedAPI wire protocol implementation

This library provides a SpeedAPI implementation for JS and TS in all major environments (browser, node, etc.). Install it with:

npm i @speedapi/driver

Also install a transport level library according to your environment:

  • npm i @speedapi/node for Node.JS
  • don't see an appropriate transport here? implement your own

You don't need additional libraries if you just use the Serializer class.

If you're using a BigInt polyfill, add this as close to entry as possible:

import * as speedapi from "@speedapi/driver";

// if using a polyfill that provides a BigInt(string, radix) constructor
// (e.g. 'big-integer', 'bigint-polyfill'):
speedapi.repr.BigInteger.polyfillMode = "radix";

// if using a polyfill that supports BigInt("0x<data>"):
speedapi.repr.BigInteger.polyfillMode = "0x";

// if not using a polyfill or using a polyfill that implements
// operators like native BigInts do (haven't seen one of those
// in the wild):
speedapi.repr.BigInteger.polyfillMode = "none";
// OR don't do anything, this is the default value

What is SpeedAPI?

It's a platform-agnostic API and serialization tool specifically geared towards high-throughput realtime applications. You can read more about its features here

How do I use it?

There's a complete tutorial over here.

Implementing a transport layer

You just have to write glue code between an implementation of your desired transport protocol and SpeedAPI. The requirements for the underlying protocol are as follows:

  • for datagram/packet/frame-based protocols like UDP: reliable and unordered - packets must not get lost, but their order may be mixed up (note that UDP doesn't fit this description as it's unreliable)
  • for stream-based protocols like TCP: reliable and ordered - bytes must not get lost and their order must not get mixed up

You will need to write 3 or 4 classes depending on the protocol nature:

  • A Link, Client and Server if the protocol is two-partied in nature, meaning there are only two active devices on the bus/network (e.g. UART)
  • A Link, Client, Server and Listener if one server can serve multiple clients (the overwhelming majority of Internet protocols)

Note that for every client-to-server link there's a Client object on the client and a Server object on the server. There's only one Listener on the server.

Link

This class acts as the reader/writer for SpeedAPI and should extend Duplex. Its only job is to read and write Uint8Arrays. This class will be instantiated by you, therefore you can make the constructor of an arbitrary signature. Here's the skeleton for such a class:

import { Duplex } from "@speedapi/driver";
class MyLink extends Duplex {
    constructor(/* pass what you need (e.g. a socket) */) { }
    async write(data: Uint8Array): Promise<void> { }
    async read(cnt: number): Promise<Uint8Array> { }
    async close(): Promise<void> { }
}

Alternatively, you can extend from BufferedLink if the underlying protocol implementation is event-driven, meaning it provides a "data has arrived" callback, but not a "read me N bytes" function.

import { BufferedLink } from "@speedapi/driver/transport/universal";
class MyLink extends BufferedLink {
    constructor(/* again, pass what you need */) {
        someProtocol.on("bytesArrived", (data: Uint8Array) => {
            // feed BufferedLink data as it arrives
            this.dataArrived(data);
        });
    }

    protected async dataWrite(data: Uint8Array): Promise<void> { }
    override async close(): Promise<void> { }
}

Server and Client

Very thin wrappers that tell SpeedAPI about your Link while preserving type information.

Important: if you omit type information (e.g. if you're using plain JS to implement these two classes), your IDE will not be able to provide suggestions.

import { SpecSpaceGen, Session } from "@speedapi/driver";
class MyClient<Gen extends SpecSpaceGen> extends Session<Gen> {
    constructor(specSpace: Gen /* any other arguments */) {
        super(specSpace, new MyLink(/* your arguments */), "client");
    }
}
class MyServer<Gen extends SpecSpaceGen> extends Session<Gen> {
    constructor(specSpace: Gen /* any other arguments */) {
        super(specSpace, new MyLink(/* your arguments */), "server");
    }
}

Listener (optional)

The notice from before applies here as well.

class MyListener<Gen extends SpecSpaceGen> {
    constructor(specSpace: Gen, /* any other arguments */, callback: (server: MyServer<Gen>) => void /* optional too */) {
        someProtocol.on("clientConnected", (socket) => {
            const session = new MyServer(specSpace, socket /* or any other arguments per your definition */);
            callback(session);
        });
    }

    async close() { }
}

Testing

Warning: this repository uses a pnpm lock file, hence you can't substitute it for npm below.

git clone https://github.com/speedapi/driver-ts
cd driver-ts
pnpm i
pip3 install susc
pnpm test

TypeScript notice

This project relies heavily on typing. As such, the language server gets misled into thinking that an expression type is any even though it's not just because the type is deeply nested. If you see a type error in your IDE that you think shouldn't be there or you're missing some autocomplete entries, try restarting your IDE and/or language server.