# Installation

> 

unjwt is published to npm as [`unjwt`](https://npmx.dev/package/unjwt).

## Install

<code-group>

```sh [npm]
npm install unjwt
```

```sh [pnpm]
pnpm add unjwt
```

```sh [yarn]
yarn add unjwt
```

```sh [bun]
bun add unjwt
```

```sh [deno]
deno add unjwt
```

</code-group>

Or use [`nypm`](https://github.com/unjs/nypm) to auto-detect the package manager:

```sh
npx nypm install unjwt
```

## Requirements

- **Node.js 22+**, or any runtime with the [Web Crypto API](https://developer.mozilla.org/en-US/docs/Web/API/Web_Crypto_API) globally available (Deno, Bun, Cloudflare Workers, browsers).
- **ESM only.** unjwt is shipped as pure ECMAScript modules.

The core package has **zero runtime dependencies**. The H3 session adapters ([`unjwt/adapters/h3v1`](/adapters), [`unjwt/adapters/h3v2`](/adapters)) use optional peer dependencies (`h3`, `cookie-es`) which you install alongside your framework.

## Import paths

unjwt is split across several named entry points so bundlers can tree-shake aggressively:

<table>
<thead>
  <tr>
    <th>
      Import from
    </th>
    
    <th>
      What it gives you
    </th>
  </tr>
</thead>

<tbody>
  <tr>
    <td>
      <code>
        unjwt
      </code>
    </td>
    
    <td>
      Everything — a flat barrel suitable for bundlers.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        unjwt/jws
      </code>
    </td>
    
    <td>
      <code>
        sign
      </code>
      
      , <code>
        verify
      </code>
      
      , <code>
        signMulti
      </code>
      
      , <code>
        verifyMulti
      </code>
      
      , <code>
        verifyMultiAll
      </code>
      
      .
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        unjwt/jwe
      </code>
    </td>
    
    <td>
      <code>
        encrypt
      </code>
      
      , <code>
        decrypt
      </code>
      
      , <code>
        encryptMulti
      </code>
      
      , <code>
        decryptMulti
      </code>
      
      .
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        unjwt/jwk
      </code>
    </td>
    
    <td>
      Key generation, import/export, wrapping, PEM conversion, PBES2 derivation, cache control.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        unjwt/utils
      </code>
    </td>
    
    <td>
      Base64URL, type guards, claim validation, random bytes.
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        unjwt/adapters/h3v1
      </code>
    </td>
    
    <td>
      H3 v1 session adapter (Nuxt v4, Nitro v2).
    </td>
  </tr>
  
  <tr>
    <td>
      <code>
        unjwt/adapters/h3v2
      </code>
    </td>
    
    <td>
      H3 v2 session adapter (Nuxt v5, Nitro v3).
    </td>
  </tr>
</tbody>
</table>

Both patterns work:

```ts
// Namespaced — smallest bundle if you only use one module
import { sign, verify } from "unjwt/jws";

// Flat — convenient for bundlers
import { sign, encrypt, generateJWK } from "unjwt";
```

## AI-assistant skill

A pre-built [Agent Skill](https://claude.com/blog/skills) is available for [Claude Code](https://claude.com/claude-code) (and compatible harnesses) covering unjwt's public API:

```sh
npx skills add sandros94/unjwt
```

Once installed, asking your agent about unjwt, JWS, JWE, or JWK will trigger the skill and load the reference files from [`/unjwt`](https://github.com/sandros94/unjwt/tree/main/skills/unjwt).

## Next

[Create your first signed token →](/getting-started/quickstart)
