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 🙏

© 2026 – Pkg Stats / Ryan Hefner

@hedotdesign/beaverjs

v1.0.8

Published

For building custom nodejs web applications.

Readme

beaverjs

beaverjs is a lightweight JavaScript library for building page structure in Node.js and serving it as HTML, while also supporting frontend hydration through serialized page data.

At its core, the library centers around three classes:

  • Beaver: app and server orchestration
  • Page: document-level element management
  • Element: DOM node creation, placement, content, and events

Recent additions include bulk element lookup/deletion on Page and getter behavior for Element.content().

Quick Start

1. Install

npm install @hedotdesign/beaverjs

2. Create a basic app

// ./main.js file
import { Beaver } from "@hedotdesign/beaverjs";

const beaver = await new Beaver();
const { home } = beaver.pages;

home.make('section', {id: 'mainSection', style: "display: flex; justify-content: center; align-items: center; background-color: black; color: white; height: 100vh;"}).place("body")
.add(home.make("button", {id: "btn"}).content("Enter"))

home.make("h1", {id: 'text'}).content("Hello from Beaver!")

home.on("ready", () => {
  page.get("text").isOn = false
})

home.get("btn").on("click", () => {
  const [btn, text] = page.get(["btn", "text"])

  if (text.isOn) {
    text.remove()
    btn.place()
  } else {
    text.place("body")
    btn.remove()
  }

})

beaver.server(3000);

3. Run

node main

Then open http://localhost:3000.

Main Classes

1. Beaver

Main application class. Creates pages, manages endpoints, and starts the HTTP server.

Properties

  • pages: { [name: string]: Page }
    • Registry of created pages.
  • root: string
    • Set in browser context from window.location.
    • Used for internal hydration requests.

Methods

constructor()

: Promise`

  • In browser context:

    • Waits for DOMContentLoaded.
    • Determines endpoint from URL path.
    • Requests serialized page data from server and rebuilds DOM/events.
    • Exposes window.beaver = { page } once ready.
    • Returns promise that resolves once hydration is complete.
  • In Node context:

    • Creates a default home page.
    • RenewPage(name: string): Page`
  • Creates a Page instance and stores it in pages[name].

  • Automatically registers the page as an endpoint via endPoints({ [name]: page }).

  • Returns the page instance immediatelythe page as an endpoint via endPoints({ [name]: page }).

  • Returns the page promise.

forEachPage(func: (page: Page) => void): this

  • Runs a callback for each page in pages.
  • Returns the Beaver instance for chaining.

async server(port?: number): Promise<this>

  • Starts an HTTP server on port (default 3000).
  • Endpoint resolution behavior:
    • Serves files/directories via built-in handlers.
    • Falls back to registered endpoints.
    • Supports hydration requests when headers include type: beaver and page.
  • Returns the Beaver instance.

endPoints(data?: object | ((current: object) => object)): object

  • No argument: returns current endpoint map.
  • Function argument: receives current map and merges returned object.
  • Object argument: merges into endpoint map.

on(event: "file" | "directory", func: Function): object | void

  • Overrides internal event handlers used by the server for file/directory requests.
  • Returns current event handler map for invalid inputs.

2. Page

Represents a document context, manages element archive, and page-level events.

Properties

  • archive: Map<string, Element | Node>
    • Stores created elements and base nodes (head, body).
  • events: Record<string, Function[]>
    • Page-level event handlers (for custom lifecycle hooks like ready).
  • window: Window
    • Uses jsdom window in Node, browser window in frontend context.
  • name: string
    • Page name passed at creation.

Methods

constructor(name: string): Promise<Page>

  • Attempts to create a jsdom window.
  • Falls back to global window when available.
  • Initializes archive with head and body.

make(tag: string, attrs?: Record<string, string>): Element

  • Creates a new Element wrapper.
  • Auto-generates unique IDs in <base>_<index> format.
  • Adds element to archive and returns it.

get(id?: string | Array, index?: number | Function | true): any

  • No args: returns archive entries as array.
  • id + index: returns exact element by generated ID.
  • id + callback: iterates matching elements and returns one or many matches.
  • id + true: returns all matching elements without providing a callback.
  • Array input: resolves multiple lookups.

delete(id: string, index?: number | Function | true): this | void

  • Removes one or more matched elements from the DOM and from archive.
  • Accepts the same lookup forms as get() for targeting a specific element or all matching elements.

getHTML(): string

  • Returns full HTML document string including <!DOCTYPE html>.

on(event: string, func: Function): this

  • Registers page-level event handlers.
  • Stores handlers under events[event].

call(event: string): void

  • Executes all handlers registered for the event.

_serialize(): string

  • Serializes page elements and page events to JSON for client hydration.

3. Element

Wrapper around a DOM node with utilities for placement, composition, content, and event handling.

Properties

  • id: string
    • Generated unique ID.
  • tag: string
    • Original tag name.
  • node: Node
    • Actual DOM node.
  • doc: Document
    • Document reference used for creation and lookup.
  • page: Page
    • Owning page instance.
  • parent: Element | Node | undefined
    • Parent assigned during placement/addition.
  • innerContent: string | undefined
    • Last value passed to content().
  • events: Record<string, Function[]>
    • Element event registry.

Methods

constructor(tag: string, attrs: object, page: Page)

  • Reuses an existing node by ID when possible.
  • Otherwise creates a new HTML or SVG element.
  • Applies all attributes to the node.

place(id?: string | Function | Element): this | void

  • Places current element under matching archive key (head, body, or custom base ID).
  • Accepts an Element, callback, or string ID/base ID.

remove(): void

  • Removes node from the DOM.

add(id: string | Function | Element | Array): this | void

  • Appends child element(s) to current element.
  • Accepts element instances, IDs, callback, or array.

content(data?: string): this | string

  • With data: sets innerHTML and tracks content in innerContent.
  • With no argument: returns the current innerHTML.

on(event: string, func: Function): this

  • Adds DOM event listener to the node.
  • Stores handler for serialization/hydration.

removeEvent(event: string, func: Function): this

  • Removes DOM event listener and updates internal event map.

_serialize(): string

  • Serializes tag, attributes, content, parent reference, and handlers.

Notes

  • The package exports Beaver from the top-level module:
    • import { Beaver } from "beaverjs"
  • Frontend hydration depends on including a browser build that instantiates Beaver (for example beaver.min.js).