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

@latellu/atlas-sdk

v0.3.0

Published

Typed delivery + management client for Atlas CMS

Downloads

1,554

Readme

@latellu/atlas-sdk

Typed delivery + management client for Atlas CMS.

Full documentation: https://docs.atlas.latellu.com

  • Delivery client — read entries, pages, and media from the Public API (/api/v1/public/*).
  • Management client — create, update, publish, and delete content via the Management API (/api/v1/manage/*).

Server-side only. The management client (and any atlas_mgmt_* key) grants full write access to a workspace. Never import createManagementClient / makeManagementClient, or ship an atlas_mgmt_* key, in browser-bundled code (client components, SPA bundles). Keep it in server components, API routes, or backend services. The delivery client with an atlas_live_* key is read-only and safe for server-side rendering, but still avoid embedding it in client-shipped JS unless the key is meant to be public.

Known limitation: draft preview isn't wrapped yet (the preview-token mint endpoint is pending) — see Notes.

Install

npm install @latellu/atlas-sdk
# Generate typed interfaces for your workspace (recommended):
npx @latellu/atlas-cli generate --api-key=atlas_live_xxx --output=./src

Requires Node 18+ (uses global fetch). For older runtimes, pass fetchImpl.

Quick start — Delivery client

import { createClient } from '@latellu/atlas-sdk';
import type { AtlasContentTypes } from './atlas.types'; // from @latellu/atlas-cli

const atlas = createClient<AtlasContentTypes>({
  url: 'https://api.atlas.latellu.com',
  apiKey: 'atlas_live_xxx',
});

// List entries
const { items } = await atlas.entries('article').list({ locale: 'en', page: 1, limit: 20 });

// Get one entry by slug
const post = await atlas.entries('article').get('hello-world', { locale: 'ja' });
// post.data is typed as Article; locale translation merged over base

// Pages (lightweight list, or full with SEO + blocks)
const pages = await atlas.pages.list();
const home = await atlas.pages.get('home', { locale: 'en' });

// Media
const asset = await atlas.media.get(mediaId);

Delivery API reference

atlas.entries(slug)

| Method | Options | Returns | | --- | --- | --- | | .list(options?) | locale?, page?, limit?, sort? | { items, total, page, pageSize } | | .get(slug, options?) | locale? | AtlasEntry<T> \| null |

  • sort — expression like "created_at:desc" or "title:asc".
  • page defaults to 1; pagination metadata in total / page / pageSize.
  • get() returns null for 404; other failures throw AtlasError.

atlas.pages

| Method | Options | Returns | | --- | --- | --- | | .list(options?) | locale?, page?, limit? | { items, total, page, pageSize } of page summaries (no blocks) | | .get(slug, options?) | locale? | AtlasPage \| null (SEO + blocks resolved for locale) |

atlas.media

| Method | Options | Returns | | --- | --- | --- | | .get(id) | — | MediaAsset \| null |

atlas.raw

Low-level requester for delivery endpoints not yet wrapped by a resource:

const { data, meta } = await atlas.raw.get<MyShape>('/some/public/path', { locale: 'en' });

Path is relative to /api/v1/public.

Locale merging

For entries and pages, passing locale merges localized fields over the base (default-locale) values. Untranslated fields fall back to the base.

Error handling

get() methods return null for 404. All other failures throw AtlasError with .status, .code, and .message.

import { AtlasError } from '@latellu/atlas-sdk';

try {
  await atlas.entries('article').list();
} catch (err) {
  if (err instanceof AtlasError) {
    console.error(err.status, err.code, err.message);
  }
}

Quick start — Management client

⚠️ Server-side only — see the warning above. Do not call this from browser-shipped code.

Authenticates with a management key (atlas_mgmt_...). Create one at cms.atlas.latellu.com/dashboard/api-keys (sidebar: Developer → API Keys); see Management API authentication for scopes.

Promise surface (default)

import { createManagementClient, AtlasError } from '@latellu/atlas-sdk/management';

const client = createManagementClient({
  url: 'https://api.atlas.latellu.com',
  token: process.env.ATLAS_MGMT_KEY!,
});

// Create → publish → update → delete
const entry = await client.entries('article').create({
  slug: 'hello-world',
  data: { title: 'Hello, world' },
}, { idempotencyKey: crypto.randomUUID() });

await client.entries('article').publish('hello-world');
await client.entries('article').update('hello-world', { data: { title: 'Updated' } });
await client.entries('article').delete('hello-world');

Effect-native surface

For codebases built on Effect:

import { makeManagementClient, AtlasError } from '@latellu/atlas-sdk/management/effect';
import { Effect } from 'effect';

const client = makeManagementClient({
  url: 'https://api.atlas.latellu.com',
  token: process.env.ATLAS_MGMT_KEY!,
});

const program = client.entries('article').publish('hello-world');
await Effect.runPromise(program);

Importing @latellu/atlas-sdk (delivery) or @latellu/atlas-sdk/management (Promise) never pulls Effect into your bundle. Effect is only a dependency of .../management/effect.

Management API reference

client.entries(type)

| Method | Description | | --- | --- | | .create(input, opts?) | Create a draft entry | | .update(idOrSlug, input, opts?) | Update an entry | | .publish(idOrSlug, opts?) | Publish (make visible to delivery API) | | .unpublish(idOrSlug, opts?) | Unpublish (hide from delivery API) | | .archive(idOrSlug, opts?) | Archive an entry | | .schedule(idOrSlug, publishAt, opts?) | Schedule publish at a future timestamp | | .duplicate(idOrSlug, opts?) | Clone an entry as a new draft | | .delete(idOrSlug, opts?) | Delete an entry | | .bulk(operations, opts?) | Batch multiple operations |

Input shapes:

interface CreateEntryInput {
  slug: string;
  data: Record<string, unknown>;
}

interface UpdateEntryInput {
  slug?: string;
  data?: Record<string, unknown>;
}

client.pages

| Method | Description | | --- | --- | | .create(input, opts?) | Create a page | | .update(slug, input, opts?) | Update a page | | .delete(slug, opts?) | Delete a page | | .publish(slug, opts?) | Publish a page | | .unpublish(slug, opts?) | Unpublish a page | | .archive(slug, opts?) | Archive a page | | .schedule(slug, publishAt, opts?) | Schedule publish | | .blocksReorder(slug, blockIds, opts?) | Reorder page blocks |

client.media

| Method | Description | | --- | --- | | .upload(file, meta?, opts?) | Upload a media asset (Blob) | | .delete(id, opts?) | Delete a media asset |

Idempotency

All write methods accept { idempotencyKey?: string } to prevent duplicates on retry. The client also auto-retries 429 responses with exponential backoff.

Management error handling

Same AtlasError as delivery, with additional .errors array for validation failures:

try {
  await client.entries('article').create({ slug: '', data: {} });
} catch (err) {
  if (err instanceof AtlasError) {
    console.error(err.status, err.code, err.message, err.errors);
    // err.errors: [{ field: "slug", message: "slug is required" }]
  }
}

Passing an atlas_live_ key (instead of atlas_mgmt_) throws ManagementConfigError immediately.


Notes

  • Draft preview is not wrapped yet (the preview-token mint endpoint is pending).
  • entry.data arrives from the delivery API as a JSON string; the SDK parses it into your typed object.
  • For entries().get(slug, { locale }), the matching translation is merged over the base data (untranslated fields fall back to the base value).
  • createClient is generic: without a schema type, slugs are unconstrained and data is unknown. Pass AtlasContentTypes for full typing.