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

@kryptos_connect/web-sdk

v1.0.22

Published

Kryptos simplifies Web3 finance for users globally with a comprehensive suite of solutions that include accounting, portfolio management, and tax reporting. Supporting over 2000+ DeFi protocols, 100+ exchanges and wallets, and 50+ blockchains, Kryptos is

Readme

Kryptos Connect

A modern React component library for seamless Kryptos integration with built-in authentication, theme support, and wallet connectivity. Connect your users to the complete Web3 finance ecosystem with support for 5000+ DeFi protocols, 200+ exchanges and wallets, and 100+ blockchains.

Installation

npm install @kryptos_connect/web-sdk

Prerequisites

Before using this package, you'll need:

  1. Client ID: Obtain from Kryptos Developer Portal
  2. WalletConnect Project ID: Get from WalletConnect Cloud

Quick Start

1. Import Styles

Import the package styles in your main app file:

import "@kryptos_connect/web-sdk/dist/styles/index.css";

2. Wrap Your App with Provider

Wrap your application with KryptosConnectProvider:

import { KryptosConnectProvider } from "@kryptos_connect/web-sdk";
import "@kryptos_connect/web-sdk/dist/styles/index.css";

function App() {
  return (
    <KryptosConnectProvider
      config={{
        appName: "My DeFi App",
        appLogo: "https://yourapp.com/logo.png",
        clientId: "your-kryptos-client-id",
        theme: "light", // or "dark"
        walletConnectProjectId: "your-walletconnect-project-id",
      }}
    >
      {/* Your app components */}
    </KryptosConnectProvider>
  );
}

Configuration Options

| Property | Type | Required | Description | | ------------------------ | --------------------------- | -------- | --------------------------------------------------- | | appName | string | Yes | Your application name | | appLogo | React.ReactNode \| string | No | Your app logo (URL string or React component) | | clientId | string | Yes | Your Kryptos client ID | | theme | "light" \| "dark" | No | Default theme mode (defaults to "light" if not set) | | walletConnectProjectId | string | Yes | Your WalletConnect project ID |

API Reference

KryptosConnectButton

The main button component that triggers the Kryptos connection flow. It handles the full authentication and wallet connection process.

Basic Usage

import { KryptosConnectButton } from "@kryptos_connect/web-sdk";

function MyComponent() {
  return (
    <KryptosConnectButton
      generateLinkToken={async () => {
        // Call your backend API to generate a link token
        const response = await fetch("/api/kryptos/create-link-token", {
          method: "POST",
          headers: {
            "Content-Type": "application/json",
          },
          body: JSON.stringify({
            // Optional: Include access_token for authenticated users
            // access_token: userAccessToken
          }),
        });
        const data = await response.json();
        // Return link_token and isAuthorized flag
        return {
          link_token: data.link_token,
          isAuthorized: data.isAuthorized, // Pass true if access_token was provided
        };
      }}
      onSuccess={(userConsent) => {
        console.log("Connection successful:", userConsent);
        // For new users, exchange the public token for an access token
        // For authorized users, userConsent might be null
        if (userConsent?.public_token) {
          exchangePublicToken(userConsent.public_token);
        }
      }}
      onError={(error) => {
        console.error("Connection failed:", error);
      }}
    >
      Connect to Kryptos
    </KryptosConnectButton>
  );
}

User Flow Variations

The SDK automatically handles two different user flows based on the isAuthorized flag returned from generateLinkToken:

Flow 1: New User (isAuthorized: false or undefined)

INIT → Connect → INTEGRATION → STATUS
  • User connects; an account is created for them on the backend
  • User selects integrations to connect
  • Returns public_token in onSuccess callback

Flow 2: Authenticated User (isAuthorized: true)

INIT → INTEGRATION → STATUS
  • Skips Connect (an account already exists for the user on the backend)
  • User directly selects integrations
  • Returns null in onSuccess callback (no new token needed)

Implementation Example:

generateLinkToken={async () => {
  const user = getCurrentUser(); // Your auth logic

  const response = await fetch("/api/kryptos/create-link-token", {
    method: "POST",
    body: JSON.stringify({
      // Include access_token if user is logged in
      access_token: user?.kryptosAccessToken || undefined,
    }),
  });

  const data = await response.json();

  return {
    link_token: data.link_token,
    // isAuthorized will be true if access_token was valid
    isAuthorized: !!user?.kryptosAccessToken,
  };
}}

Direct Integration Flow

You can use the integrationName prop to direct users to a specific integration, bypassing the general integration selection page. This is useful when you want to provide dedicated buttons for specific exchanges or wallets.

Getting Supported Integration IDs:

Fetch available integration IDs from the public Kryptos API endpoint:

GET {BASE_URL}/integrations/public/list

Usage Example:

// Direct connection to a specific integration (e.g., Binance)
<KryptosConnectButton
  generateLinkToken={generateLinkToken}
  integrationName="binance"
  onSuccess={(userConsent) => {
    console.log("Binance connected:", userConsent);
  }}
>
  Connect Binance Account
</KryptosConnectButton>

// Or without children (uses default button with custom text)
<KryptosConnectButton
  generateLinkToken={generateLinkToken}
  integrationName="metamask"
  onSuccess={(userConsent) => {
    console.log("MetaMask connected:", userConsent);
  }}
  // Button will display: "Connect Metamask Account"
/>

Use Cases:

  1. Dedicated Integration Buttons: Create separate buttons for popular integrations

    <KryptosConnectButton integrationName="binance">
      Connect Binance
    </KryptosConnectButton>
    <KryptosConnectButton integrationName="coinbase">
      Connect Coinbase
    </KryptosConnectButton>
    <KryptosConnectButton integrationName="metamask">
      Connect MetaMask
    </KryptosConnectButton>
  2. Contextual Integration: Direct users to relevant integrations based on their context

    // In an exchange-focused feature
    <KryptosConnectButton integrationName="kraken">
      Add Kraken Account
    </KryptosConnectButton>
  3. Onboarding Flows: Guide users to connect specific integrations during onboarding

    // Step 1: Connect wallet
    <KryptosConnectButton integrationName="metamask">
      Connect Your Wallet
    </KryptosConnectButton>
    
    // Step 2: Connect exchange
    <KryptosConnectButton integrationName="binance">
      Connect Your Exchange
    </KryptosConnectButton>

Note: The integrationName value must match an integration ID from the supported providers list. An invalid ID will result in an error.

Custom Styling Example

<KryptosConnectButton
  generateLinkToken={createLinkToken}
  onSuccess={(userConsent) => {
    console.log("Success:", userConsent);
    exchangePublicToken(userConsent?.public_token);
  }}
  onError={(error) => console.error("Error:", error)}
  className="my-custom-class"
  style={{
    width: "100%",
    padding: "12px 24px",
    fontSize: "16px",
  }}
>
  🔐 Connect Your Wallet
</KryptosConnectButton>

Props

| Property | Type | Required | Description | | ------------------- | --------------------------------------------------------------- | -------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | generateLinkToken | () => Promise<{ link_token: string; isAuthorized?: boolean }> | Yes | Function that returns link token and authorization status. isAuthorized: true skips Connect for authenticated users (account already exists for them on the backend) | | onSuccess | (data: UserConsent \| null) => void | No | Callback invoked when connection succeeds. Receives public_token for new users, null for authorized users | | onError | (error: Error) => void | No | Callback invoked when connection fails | | integrationName | string | No | Integration ID from the supported providers list. When provided, skips the integration list and goes directly to the specific integration | | children | React.ReactNode | No | Button text or content. Defaults to "Connect with Kryptos", or "Connect using {integrationName}" when integrationName is set | | className | string | No | Custom CSS class name | | style | React.CSSProperties | No | Inline styles |

TypeScript Types

interface KryptosConnectButtonProps {
  generateLinkToken: () => Promise<{
    link_token: string;
    isAuthorized?: boolean;
  }>;
  onSuccess?: (data: UserConsent | null) => void;
  onError?: (error: Error) => void;
  integrationName?: string; // Integration ID from the supported providers list
  children?: React.ReactNode;
  className?: string;
  style?: React.CSSProperties;
}

interface UserConsent {
  public_token: string;
  // Additional consent data
}

// Note: onSuccess receives:
// - UserConsent with public_token for new users (isAuthorized: false)
// - null for authenticated users (isAuthorized: true)

Backend Integration

You need to implement two backend endpoints.

Base URLs

| Environment | URL | | -------------- | -------------------------------- | | Production | https://connect-api.kryptos.io |

1. Create Link Token

A link token can be created in two ways: to authenticate an existing user or to create a new session.

| Approach | When to use | Jump to | | ------------------------- | -------------------------------- | ---------------------------------------- | | Option A | New user, no access token | Create link token without access_token | | Option B | Returning user, has access token | Create link token with access_token |

Option A: Without Access Token (New User)

Use this approach for new users or when you want an account to be created for the user on the backend:

// Example: Node.js/Express
app.post("/api/kryptos/create-link-token", async (req, res) => {
  try {
    const response = await fetch(`${KRYPTOS_BASE_URL}/link-token`, {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
        "X-Client-Id": YOUR_CLIENT_ID,
        "X-Client-Secret": YOUR_CLIENT_SECRET,
      },
      body: JSON.stringify({
        scopes:
          "openid profile offline_access email portfolios:read transactions:read integrations:read tax:read accounting:read reports:read workspace:read users:read",
      }),
    });

    const data = await response.json();
    res.json({
      link_token: data.link_token,
      isAuthorized: false, // No access token provided
    });
  } catch (error) {
    res.status(500).json({ error: "Failed to create link token" });
  }
});

User Experience Flow:

  1. User clicks "Connect to Kryptos"
  2. User connects; an account is created for them on the backend
  3. User selects integrations
  4. onSuccess receives public_token to exchange

Option B: With Access Token (Authenticated User)

Use this approach for existing authenticated users (an account already exists for them on the backend):

// Example: Node.js/Express
app.post("/api/kryptos/create-link-token", async (req, res) => {
  try {
    // Get the user's stored access token from your database
    const userAccessToken = await getUserAccessToken(req.user.id);

    const response = await fetch(`${KRYPTOS_BASE_URL}/link-token`, {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
        "X-Client-Id": YOUR_CLIENT_ID,
        "X-Client-Secret": YOUR_CLIENT_SECRET,
      },
      body: JSON.stringify({
        scopes:
          "openid profile offline_access integrations:read integrations:write",
        access_token: userAccessToken, // Pass the user's access token
      }),
    });

    const data = await response.json();
    res.json({
      link_token: data.link_token,
      isAuthorized: true, // Access token provided, user is authenticated
    });
  } catch (error) {
    res.status(500).json({ error: "Failed to create link token" });
  }
});

User Experience Flow:

  1. User clicks "Connect to Kryptos"
  2. Integration selection is shown directly (account already exists for the user on the backend)
  3. User selects integrations
  4. onSuccess receives null (no new token needed)
Choosing the Right Approach

Implementation: Option A (new user, no token) · Option B (authenticated user, with token)

| Scenario | Use Option | isAuthorized | User Flow (UI) | Returns public_token | | ------------------------------------------ | ---------------------------------- | ------------ | ----------------------------------------------------------- | -------------------- | | First-time user connecting to Kryptos | A (Without Token) | false | Connect → INTEGRATION (account created for user on backend) | ✅ Yes | | User doesn't have an access token yet | A (Without Token) | false | Connect → INTEGRATION (account created for user on backend) | ✅ Yes | | Returning user with stored access token | B (With Token) | true | INTEGRATION only (account already exists for user) | ❌ No | | Adding more integrations for existing user | B (With Token) | true | INTEGRATION only (account already exists for user) | ❌ No |

Important Notes:

  • After the first successful connection (Option A), store the access_token you receive from the token exchange
  • Use the stored access_token for subsequent connections (Option B) to provide a seamless experience
  • For authorized users (isAuthorized: true), the onSuccess callback receives null instead of a public_token
  • Authorized users go directly to integration selection (an account already exists for them on the backend)

2. Exchange Public Token

After a successful connection, exchange the public_token for an access_token. Important: Store this access_token securely in your database. You will use it to create link tokens for authenticated users (Option B above).

// Example: Node.js/Express
app.post("/api/kryptos/exchange-token", async (req, res) => {
  try {
    const { public_token } = req.body;

    const response = await fetch(`${KRYPTOS_BASE_URL}/token/exchange`, {
      method: "POST",
      headers: {
        "Content-Type": "application/json",
        "X-Client-Id": YOUR_CLIENT_ID,
        "X-Client-Secret": YOUR_CLIENT_SECRET,
      },
      body: JSON.stringify({
        public_token,
      }),
    });

    const data = await response.json();

    // IMPORTANT: Store the access_token securely in your database
    // You'll need this token to:
    // 1. Create authenticated link tokens (account already exists for user on backend)
    // 2. Make API calls on behalf of the user
    await saveUserAccessToken(req.user.id, data.access_token);

    res.json({ success: true });
  } catch (error) {
    res.status(500).json({ error: "Failed to exchange token" });
  }
});

Complete Integration Flow:

  1. First Connection (New User - isAuthorized: false):

    Frontend → generateLinkToken() [returns { link_token, isAuthorized: false }]
    → SDK Flow: INIT → Connect → INTEGRATION → STATUS
    → User connects; an account is created for them on the backend
    → User connects integrations
    → onSuccess receives { public_token: "..." }
    → Backend exchanges public_token for access_token
    → Store access_token in database ← IMPORTANT
  2. Subsequent Connections (Returning User - isAuthorized: true):

    Frontend → generateLinkToken() [returns { link_token, isAuthorized: true }]
    → SDK Flow: INIT → INTEGRATION → STATUS (skip Connect)
    → User directly sees integrations (account already exists for them on the backend)
    → User connects more integrations
    → onSuccess receives null (no new token needed)
    → Integrations are added to user's existing account

Customization

The library uses CSS variables and unique kc- prefixed classes for easy customization without conflicts.

See CUSTOMIZATION_GUIDE.md for detailed CSS customization options.

Quick Theme Customization

Override CSS variables to customize the look and feel:

/* custom-theme.css */
:root {
  --kc-primary: #8b5cf6;
  --kc-primary-hover: #7c3aed;
  --kc-bg-primary: #ffffff;
  --kc-text-primary: #000000;
  --kc-border: #e5e7eb;
  --kc-border-radius: 8px;
}

[data-kc-theme="dark"] {
  --kc-bg-primary: #1a1a1a;
  --kc-text-primary: #ffffff;
  --kc-border: #404040;
}

Import your custom styles after the package styles:

import "@kryptos_connect/web-sdk/dist/styles/index.css";
import "./custom-theme.css";

Custom Component Styling

<KryptosConnectButton
  className="my-custom-button"
  style={{
    background: "linear-gradient(to right, #667eea, #764ba2)",
    borderRadius: "12px",
  }}
>
  Connect Wallet
</KryptosConnectButton>

Framework Support

Next.js

Works with both Pages Router and App Router:

// app/layout.tsx (App Router)
import { KryptosConnectProvider } from "@kryptos_connect/web-sdk";
import "@kryptos_connect/web-sdk/dist/styles/index.css";

export default function RootLayout({ children }) {
  return (
    <html lang="en">
      <body>
        <KryptosConnectProvider config={config}>
          {children}
        </KryptosConnectProvider>
      </body>
    </html>
  );
}

React

// main.tsx or index.tsx
import React from "react";
import ReactDOM from "react-dom/client";
import { KryptosConnectProvider } from "@kryptos_connect/web-sdk";
import "@kryptos_connect/web-sdk/dist/styles/index.css";
import App from "./App";

ReactDOM.createRoot(document.getElementById("root")!).render(
  <React.StrictMode>
    <KryptosConnectProvider config={config}>
      <App />
    </KryptosConnectProvider>
  </React.StrictMode>,
);

TypeScript Support

This package provides full TypeScript support with type definitions.

import type {
  KryptosConnectButtonProps,
  KryptosConnectProviderProps,
  UserConsent,
} from "@kryptos_connect/web-sdk";

Browser Support

  • Chrome/Edge (latest)
  • Firefox (latest)
  • Safari (latest)
  • Mobile browsers (iOS Safari, Chrome Mobile)

Support

Contributing

Contributions are welcome! Please read our Contributing Guide for details on our code of conduct and the process for submitting pull requests.

License

MIT © Kryptos


Made with ❤️ by the Kryptos team