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

@thorprovider/types

v3.2.0

Published

Shared TypeScript types for Thor Commerce ecosystem - Framework-agnostic type definitions

Readme

@thorprovider/types

Shared TypeScript types for Thor Commerce ecosystem

Pure type definitions with zero runtime dependencies. This package provides the foundation for type-safe commerce operations across all Thor Commerce packages.


🎯 Why This Package Exists

Problem: Without shared types:

  • ❌ Each package defines own types (Product in 4 places = 4x maintenance)
  • ❌ Type mismatches between layers (Adapters Product ≠ Elements Product)
  • ❌ Circular dependencies (adapters imports elements imports adapters)
  • ❌ Violates Dependency Inversion Principle (high-level depends on low-level)

Solution: @thorprovider/types provides:

  • Single Source of Truth: Product defined once, used everywhere
  • Dependency Inversion: All layers depend on abstractions (SOLID DIP)
  • Zero Runtime: Type-only package (0 bytes in production bundle)
  • Framework Agnostic: No React/Next.js/Medusa dependencies

SOLID Compliance:

L5 (Starters)       ─┐
L4 (Feature Modules) ├─→ ALL depend on ──→ @thorprovider/types (L1: Foundation)
L3 (Design System)  ─┤                      ↑
L2 (Infrastructure) ─┘                      │
                                        Abstractions
                                    (Dependency Inversion)

Inspired by: TypeScript's @types/* packages, tRPC (end-to-end type safety), GraphQL schemas


💰 ROI / Value Proposition

Type Safety Across Layers

// Without @thorprovider/types (each layer defines own types)
packages/adapters/src/types.ts:
  interface Product { id: string; name: string; }  // Missing 'handle'

packages/components/src/types.ts:
  interface Product { id: string; title: string; }  // Different field name!

packages/core/types.ts:
  interface Product { id: number; title: string; }  // Wrong type for id!

// Result: Runtime errors, bugs, inconsistencies

// With @thorprovider/types (single definition)
packages/types/src/product.ts:
  export interface Product {
    id: string;
    handle: string;
    title: string;
    // ... complete, consistent definition
  }

// All layers use same type → zero mismatches

Maintenance Cost Reduction

// Scenario: Add 'tags' field to Product

// Without @thorprovider/types:
1. Update adapters/types.ts: 30 min
2. Update elements/types.ts: 30 min
3. Update starters/types.ts: 30 min
4. Fix type mismatches: 2 hours
5. Update 50+ files using Product: 3 hours
= 6.5 hours per change

// With @thorprovider/types:
1. Update types/src/product.ts: 5 min
2. TypeScript errors guide changes: auto
= 5 minutes per change

// ROI: 6.5 hours → 5 min = 78x faster changes

Bundle Size Impact

// Type-only package: ZERO runtime cost
import type { Product } from '@thorprovider/types';  // Erased at build time

// vs. importing from package with logic:
import { Product } from '@thorprovider/adapters';  // Brings entire adapters code

// Bundle size difference: 0 KB vs 50 KB
// For 10 packages × 50 KB = 500 KB saved

AI Type Inference

// AI Agent generates code with auto-complete
const product: Product = {  // ← AI knows ALL fields from @thorprovider/types
  id: '123',
  handle: 'shirt',  // ← Auto-suggested
  title: 'T-Shirt',  // ← Auto-suggested
  // ... AI can't miss required fields
};

// Without shared types: AI guesses fields → runtime errors

🤖 AI Agent Decision Framework

When to Use @thorprovider/types

✅ ALWAYS when working with commerce entities (Product, Cart, Order)
✅ Creating new packages that handle commerce data
✅ Building transformations (Medusa → unified types)
✅ Type-checking at build time (no runtime needed)
✅ Sharing types between frontend and backend

When NOT to Use

❌ Never (this is foundational layer) — always use @thorprovider/types for commerce types
⚠️ Only exception: Component-specific props (use local .props.ts files)

Decision Tree

Defining commerce data structure?
├─ YES → Is it used across packages?
│  ├─ YES → Define in @thorprovider/types ✅
│  └─ NO → Is it component-specific?
│     ├─ YES → Local .props.ts file
│     └─ NO → Still use @thorprovider/types (future reuse)
└─ NO → Is it UI-specific props?
   └─ YES → Local .props.ts file

Key Rules for AI Agents

  1. NEVER add runtime code to @thorprovider/types (only types/interfaces)
  2. ALWAYS use import type when importing from @thorprovider/types
  3. DOCUMENT every field with JSDoc comments (AI needs context)
  4. EXTEND, don't modify existing types (add new fields, don't remove)
  5. FOLLOW Shopify schema for consistency (Money, Image, Connection)

Type Definition Pattern

// ALWAYS follow this pattern

/**
 * Product entity representing a sellable item
 * @example { id: '123', handle: 'shirt', title: 'T-Shirt' }
 */
export interface Product {
  /** Unique identifier */
  id: string;
  
  /** URL-friendly slug */
  handle: string;
  
  /** Display name */
  title: string;
  
  // ... more fields with JSDoc
}

When to Add New Types

// Adding new commerce entity?
// 1. Create file: packages/types/src/my-entity.ts
export interface MyEntity {
  id: string;
  // ... fields
}

// 2. Export from index:
export * from './my-entity';

// 3. Document in README:
// - **MyEntity**: Description here

// 4. Use across packages:
import type { MyEntity } from '@thorprovider/types';

Purpose

Centralized type definitions following SOLID principles:

  • Single Responsibility: Only type definitions, no logic
  • Dependency Inversion: All packages depend on abstractions, not implementations
  • Interface Segregation: Clean, focused interfaces

Usage

import type { Product, Cart, CartItem, Collection } from '@thorprovider/types';

Included Types

  • Common: Money, Image, SEO, Connection, Edge
  • Product: Product, ProductVariant, ProductOption
  • Cart: Cart, CartItem, CartCost
  • Collection: Collection
  • Customer: Customer, Address
  • Order: Order, OrderItem, OrderStatus
  • Auth: AuthProvider, LoginCredentials, RegisterData

Architecture

@thorprovider/types (L1: Foundation - Type Abstractions)
    ↓ used by
@thorprovider/adapters (Backend transformations)
    ↓ used by
@thorprovider/components (UI components)
    ↓ used by
@thorprovider/starters (Applications)

All packages depend on this shared type layer, ensuring consistency across the ecosystem.