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

@mosaicag/swap-widget

v2.0.1

Published

Self-contained swap widget for DeFi token swapping

Readme

@mosaicag/swap-widget

Ready-to-embed swap widget for Movement ecosystem apps.

Overview

@mosaicag/swap-widget gives you a complete swap UI out of the box:

  • token input and output
  • quote refresh and route summary
  • slippage and liquidity source settings
  • wallet submit flow with callbacks
  • sensible Movement mainnet defaults

If you want a swap experience that works quickly with minimal setup, this package is the entry point.

Installation

Install the widget package:

npm install @mosaicag/swap-widget
pnpm add @mosaicag/swap-widget
yarn add @mosaicag/swap-widget

Requirements

Your app should already have:

  • react and react-dom 18+
  • a wallet object compatible with WalletStandard
  • access to the target network RPC and indexer if you want custom endpoints

The minimum wallet fields used by the swap flow are:

  • account
  • signTransaction
  • signAndSubmitTransaction

Quick Start

1. Import styles once

Import widget CSS in your app entry file.

SwapWidget already imports @mosaicag/common-ui/styles internally.

import '@mosaicag/swap-widget/dist/index.css';

2. Render the widget

wallet is the only required prop.

import { SwapWidget } from '@mosaicag/swap-widget';
import '@mosaicag/swap-widget/dist/index.css';

type Props = {
  wallet: any;
};

export function SwapSection({ wallet }: Props) {
  return <SwapWidget wallet={wallet} />;
}

3. Handle connect wallet action

When the wallet is not connected, the main button becomes Connect Wallet.

<SwapWidget wallet={wallet} onConnectWallet={() => wallet.connect?.()} />

Examples

Minimal Example

Use built-in defaults for Movement mainnet:

import { SwapWidget } from '@mosaicag/swap-widget';
import '@mosaicag/swap-widget/dist/index.css';

export function SwapCard({ wallet }: { wallet: any }) {
  return <SwapWidget wallet={wallet} />;
}

Example With Connect Action

import { SwapWidget } from '@mosaicag/swap-widget';
import '@mosaicag/swap-widget/dist/index.css';

export function SwapCard({
  wallet,
  connectWallet,
}: {
  wallet: any;
  connectWallet: () => void;
}) {
  return (
    <SwapWidget
      wallet={wallet}
      onConnectWallet={connectWallet}
      className='w-full max-w-[450px]'
    />
  );
}

Full Config Example

This is the recommended pattern when you want explicit control over endpoints, gas sponsorship, callbacks, and the initial token pair.

import { SwapWidget } from '@mosaicag/swap-widget';
import '@mosaicag/swap-widget/dist/index.css';

type SwapContainerProps = {
  wallet: any;
  connectWallet: () => void;
  rpcUrl: string;
  indexerUrl: string;
  bffUrl: string;
  gasStationUrl?: string;
  gasStationId?: string;
  rpcAuthorizationKey?: string;
  defaultTokenIn?: string;
  defaultTokenOut?: string;
};

export function SwapContainer({
  wallet,
  connectWallet,
  rpcUrl,
  indexerUrl,
  bffUrl,
  gasStationUrl,
  gasStationId,
  rpcAuthorizationKey,
  defaultTokenIn,
  defaultTokenOut,
}: SwapContainerProps) {
  return (
    <SwapWidget
      wallet={wallet}
      rpcUrl={rpcUrl}
      indexerUrl={indexerUrl}
      rpcAuthorizationKey={rpcAuthorizationKey}
      bffUrl={bffUrl}
      useBffSession
      defaultTokenIn={defaultTokenIn}
      defaultTokenOut={defaultTokenOut}
      useGasSponsor={Boolean(gasStationUrl && gasStationId)}
      gasStationUrl={gasStationUrl}
      gasStationId={gasStationId}
      onConnectWallet={connectWallet}
      onChangeTokenPair={(tokenIn, tokenOut) => {
        console.log('pair changed', { tokenIn, tokenOut });
      }}
      onTxSubmit={({ hash, metadata }) => {
        console.log('swap submitted', hash, metadata);
      }}
      onTxFail={({ error, metadata, hash }) => {
        console.error('swap failed', { error, metadata, hash });
      }}
      className='w-full max-w-[450px]'
    />
  );
}

Example With URL Synced Pair

<SwapWidget
  wallet={wallet}
  defaultTokenIn={tokenInFromUrl}
  defaultTokenOut={tokenOutFromUrl}
  onChangeTokenPair={(tokenIn, tokenOut) => {
    setTokenInInUrl(tokenIn);
    setTokenOutInUrl(tokenOut);
  }}
/>

Theme

SwapWidget supports a theme prop for color customization.

import { SwapWidget, type CustomThemeType } from '@mosaicag/swap-widget';

const widgetTheme: CustomThemeType = {
  primaryColor: '#53CBF3',
  secondaryColor: '#A8E6FA',
  textColor: '#000000',
  primaryBackgroundColor: '#FFFFFF',
  secondaryBackgroundColor: '#F5F5F5',
  borderColor: '#53CBF3',
  showBorder: true,
};

<SwapWidget wallet={wallet} theme={widgetTheme} />;

Theme Fields

  • primaryColor: primary accent color used by actions/highlights.
  • secondaryColor: secondary accent color used by supporting states.
  • textColor: base text color.
  • primaryBackgroundColor: main surface background.
  • secondaryBackgroundColor: secondary surface background.
  • borderColor: border color for themed surfaces.
  • showBorder: toggles themed borders on/off.
  • mode: optional (light | dark) for future compatibility.

Theme Notes

  • Accepts hex (#RRGGBB / #RGB) and rgb/rgba-like values.
  • If secondaryColor is not set, it may fall back to textColor, then primaryColor.
  • For best results, set both primaryColor and secondaryColor explicitly.

Default Behavior

If you do not pass custom values, the widget uses these defaults:

  • rpcUrl: https://mainnet.movementnetwork.xyz/v1
  • indexerUrl: https://indexer.mainnet.movementnetwork.xyz/v1/graphql
  • bffUrl: https://bff.mosaic.ag/api/v1
  • useBffSession: false
  • networkType: mainnet
  • minGasPreserve: 0.2

Props

| Prop | Type | Required | Default | Description | | --------------------- | ------------------------------------- | -------- | ------------------------------ | ------------------------------------------------------------- | | wallet | WalletStandard | Yes | - | Wallet used for signing and submitting transactions. | | className | string | No | undefined | Extra classes for the widget root. | | useGasSponsor | boolean | No | false | Enables gas sponsorship flow. | | gasStationId | string | No | undefined | Gas station ID when sponsorship is enabled. | | gasStationUrl | string | No | undefined | Gas station URL when sponsorship is enabled. | | rpcUrl | string | No | Movement mainnet RPC | Custom RPC endpoint. | | indexerUrl | string | No | Movement mainnet indexer | Custom indexer endpoint. | | rpcAuthorizationKey | string | No | undefined | Optional auth key for RPC requests. | | queryClient | QueryClient | No | Internal instance | Pass your own client if you want shared cache behavior. | | bffUrl | string | No | https://bff.mosaic.ag/api/v1 | Backend URL for token and price data. | | useBffSession | boolean | No | false | Enables cookie session for BFF requests. | | networkType | NetworkType | No | NetworkType.MAINNET | Target network. | | defaultTokenIn | string | No | Widget default | Initial sell token. | | defaultTokenOut | string | No | Widget default | Initial buy token. | | onChangeTokenPair | (tokenIn, tokenOut) => void | No | undefined | Called when the selected pair changes. | | onConnectWallet | () => void | No | undefined | Called when the user clicks connect. | | onTxSubmit | ({ hash, metadata }) => void | No | undefined | Called when a transaction hash is received. | | onTxFail | ({ error, metadata, hash }) => void | No | undefined | Called when transaction submit fails. | | onTxSuccess | ({ hash, metadata }) => void | No | undefined | Called when the widget reports a successful transaction flow. | | minGasPreserve | number | No | 0.2 | Native token amount reserved for gas. | | theme | CustomThemeType | No | undefined | Overrides widget color tokens and themed surfaces. |

Transaction Metadata

onTxSubmit, onTxSuccess, and onTxFail work with swap metadata that typically includes:

  • source token
  • destination token
  • source amount
  • destination amount
  • transaction hash when available

Common use cases:

  • activity history
  • analytics
  • toast notifications
  • updating URL or local state after submit

Next.js

The package is client-side ("use client"). Render SwapWidget inside a client component.

Troubleshooting

  • Widget is unstyled: Import @mosaicag/swap-widget/dist/index.css once in your app entry.
  • The button always shows Connect Wallet: Make sure wallet.account is available after connecting.
  • Quote requests fail: Check rpcUrl, indexerUrl, and bffUrl.
  • Sponsored transactions do not work: Set useGasSponsor, gasStationId, and gasStationUrl together.
  • Some themed states look darker/lighter than expected: Set both primaryColor and secondaryColor in theme to avoid fallback surprises.