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 🙏

© 2025 – Pkg Stats / Ryan Hefner

smart-widget-handler

v1.0.34

Published

An sdk to communicate with embeded apps on nostr smart widgets

Readme

smart-widget-handler

A lightweight JavaScript/TypeScript library for facilitating communication between a host application and a client widget, with support for Nostr account metadata and event handling via window.postMessage. Ideal for building smart widgets that interact with Nostr-based ecosystems.

Installation

Install the package via npm:

npm install smart-widget-handler

Usage

The library provides two main interfaces: host for the parent application and client for the embedded widget. Import the default export SWHandler to send and receive messages between contexts.

Example: Host Sending and Listening Send a connected Nostr account to a widget and listen for messages from the widget:

import SWHandler from "smart-widget-handler";

// Listen for messages from the widget
let listener = SWHandler.host.listen((data) => {
  console.log("Received from widget:", data.kind, data.data);
  if (data.kind === "custom-data") {
    console.log("Custom data:", data.data);
  }
});

// To close the listener
listener.close()

// Send user context to the widget
const context = {
    pubkey: "npub1example...",
    display_name: "string",
    name: "string",
    picture: "string",
    nip05: "string",
    lud16: "string",
    lud06: "string",
    website: "string",
};
let host_origin: "https://myapp.com";

SWHandler.host.sendContext(context, host_origin, "https://widget.example.com", <YOUR_IFRAME_ELEMENT>);

Example: Client Sending and Listening


Notify the host that the widget is ready, listen for messages, and send custom data:

import SWHandler from "smart-widget-handler";

// Notify host that widget is loaded
SWHandler.client.ready();

// Listen for messages from the host
let listener = SWHandler.client.listen((data) => {
  console.log("Received from host:", data.kind, data.data);
  if (data.kind === "user-metadata") {
    const { display_name } = data.data;
    console.log(`Hello, ${display_name}!`);
  }
});

// To close the listener
listener.close();

// Send custom data to the host
SWHandler.client.sendContext("User clicked a button", "https://myapp.com");

Example: Client Requesting Event Signing

Request the host to sign a Nostr event:

import SWHandler from "smart-widget-handler";

const event = {
  content: "Hello, Nostr!",
  tags: [["t", "greeting"]],
  kind: 1,
};

SWHandler.client.requestEventSign(event, "https://myapp.com");

Example: Client Requesting Payment

Request the host to initiate a Lightning payment:

import SWHandler from "smart-widget-handler";

const paymentRequest = {
  address: "lnbc1...", // or LNURL, or Lightning address
  amount: 1000, // sats (ignored if address is a BOLT11 invoice)
  nostrPubkey: "npub1example...", // optional
  nostrEventIDEncode: "note1example...", // optional
};

SWHandler.client.requestPayment(paymentRequest, "https://myapp.com");

Example: Host Sending Payment Response

Send a payment response from the host to the client:

import SWHandler from "smart-widget-handler";

const paymentResponse = {
  status: true, // true for success, false for error
  preImage: "abcdef123456...", // optional, only for successful payments
};

SWHandler.host.sendPaymentResponse(paymentResponse, "https://widget.example.com", <YOUR_IFRAME_ELEMENT>);

Message Types

The library uses different message types identified by the data.kind property to handle various communication scenarios between host and client. Here's a comprehensive list of all available message types:

| Message Type | Direction | Description | |-------------|-----------|-------------| | user-metadata | Host → Client | Contains Nostr account information of the connected user | | nostr-event | Host → Client | Contains a signed and/or published Nostr event | | err-msg | Host → Client | Contains an error message from the host | | payment-response | Host → Client | Contains the result of a payment request (success/failure) | | app-loaded | Client → Host | Notifies the host that the client widget is loaded and ready | | sign-event | Client → Host | Requests the host to sign a Nostr event | | sign-publish | Client → Host | Requests the host to sign and publish a Nostr event | | payment-request | Client → Host | Requests the host to make a Lightning payment | | custom-data | Client → Host | Contains custom data sent from the client to the host |

When implementing listeners with SWHandler.host.listen() or SWHandler.client.listen(), you can filter and handle these message types based on your application's needs.