https://github.com/dr5hn/countrystatecity
Official Country State City - NPM Packages
https://github.com/dr5hn/countrystatecity
cities city countries country nodejs npm package state states
Last synced: 8 months ago
JSON representation
Official Country State City - NPM Packages
- Host: GitHub
- URL: https://github.com/dr5hn/countrystatecity
- Owner: dr5hn
- License: other
- Created: 2025-10-07T07:31:40.000Z (8 months ago)
- Default Branch: main
- Last Pushed: 2025-10-22T15:21:02.000Z (8 months ago)
- Last Synced: 2025-10-22T17:24:51.060Z (8 months ago)
- Topics: cities, city, countries, country, nodejs, npm, package, state, states
- Language: TypeScript
- Homepage: https://www.npmjs.com/package/@countrystatecity/countries
- Size: 8.98 MB
- Stars: 1
- Watchers: 1
- Forks: 0
- Open Issues: 2
-
Metadata Files:
- Readme: README.md
- Contributing: CONTRIBUTING.md
- License: LICENSE
Awesome Lists containing this project
README
# @countrystatecity/* Package Ecosystem
[](https://github.com/dr5hn/countrystatecity/actions/workflows/ci.yml)
[](https://github.com/dr5hn/countrystatecity/actions/workflows/update-data.yml)
Official package ecosystem for countries, states, cities, and geographic data with iOS/Safari support and minimal bundle sizes.
## ๐ฆ Packages
### @countrystatecity/countries [](https://www.npmjs.com/package/@countrystatecity/countries)
Complete countries, states, and cities database with lazy loading and iOS compatibility.
- **Location:** [`packages/countries`](./packages/countries)
- **Documentation:** [README](./packages/countries/README.md)
- **Bundle Size:** <10KB initial load
- **Data:** 250+ countries, 5,000+ states, 150,000+ cities
- **Environment:** ๐ฅ๏ธ **Server-side only** (Node.js, Next.js API routes, Express, etc.)
- **Status:** โ
Implemented
```bash
npm install @countrystatecity/countries
```
> **โ ๏ธ Server-Side Only**: This package requires Node.js file system access. For browser/frontend use, see [@countrystatecity/countries-browser](#countrystatecitycountries-browser) (coming soon).
### @countrystatecity/timezones [](https://www.npmjs.com/package/@countrystatecity/timezones)
Comprehensive timezone data with conversion utilities and iOS compatibility.
- **Location:** [`packages/timezones`](./packages/timezones)
- **Documentation:** [README](./packages/timezones/README.md)
- **Bundle Size:** <20KB initial load
- **Data:** 392 IANA timezones, 223 countries, 131 abbreviations
- **Environment:** ๐ฅ๏ธ **Server-side only** (Node.js, Next.js API routes, Express, etc.)
- **Status:** โ
Implemented
```bash
npm install @countrystatecity/timezones
```
### @countrystatecity/countries-browser
Browser-compatible version of the countries package for frontend/client-side usage.
- **Location:** TBD
- **Documentation:** [Specification](./specs/4-countries-browser-package-spec.md)
- **Bundle Size:** ~75KB gzipped for typical use
- **Data:** Same as server package (250+ countries, 5,000+ states, 150,000+ cities)
- **Environment:** ๐ **Browser/Frontend** (React, Vue, Svelte, Vite, etc.)
- **Status:** ๐ Planned (see [Issue #17](https://github.com/dr5hn/countrystatecity/issues/17))
This package will provide fetch-based data loading for browser environments with the same API as the server package.
## ๐ Quick Start
> **๐ก Choose the right package for your environment:**
> - **Server-side** (Node.js, Next.js API routes, Express): Use `@countrystatecity/countries`
> - **Browser/Frontend** (React, Vue, Svelte, Vite): Use `@countrystatecity/countries-browser` (coming soon) or create API endpoints
### Countries, States, and Cities (Server-Side)
```typescript
import { getCountries, getStatesOfCountry, getCitiesOfState } from '@countrystatecity/countries';
// Get all countries (lightweight - ~5KB)
const countries = await getCountries();
// Get states for a country
const states = await getStatesOfCountry('US');
// Get cities in a state
const cities = await getCitiesOfState('US', 'CA');
```
### Timezones
```typescript
import { getTimezones, getTimezonesByCountry, convertTime } from '@countrystatecity/timezones';
// Get all timezones
const timezones = await getTimezones();
// Get timezones for a country
const usTimezones = await getTimezonesByCountry('US');
// Convert time between timezones
const converted = await convertTime(
'2025-10-18 14:00',
'America/New_York',
'Asia/Tokyo'
);
```
## โจ Key Features
- ๐ฑ **iOS Compatible**: No stack overflow errors on Safari/iOS browsers
- ๐ **Minimal Bundle**: <10KB initial load with lazy loading
- ๐ **Dynamic Loading**: Uses dynamic imports for code-splitting
- ๐ **Full Data**: Countries, states, cities with translations
- โฐ **Timezone Support**: Comprehensive timezone information
- ๐ **TypeScript**: Full type definitions included
- ๐ง **Tree-Shakeable**: Only bundle what you use
## ๐ฏ Why This Ecosystem?
### The Problem
The popular `country-state-city` package (162K weekly downloads) has critical issues:
- ๐ด 8MB bundle size (includes ALL data upfront)
- ๐ด iOS Safari crashes with stack overflow errors
- ๐ด Unmaintained for 2+ years
- ๐ด Static imports force entire bundle inclusion
### Our Solution
- โ
Minimal bundle (<10KB initial)
- โ
Dynamic imports & lazy loading
- โ
iOS/Safari compatible
- โ
Always updated from authoritative database
- โ
Tree-shakeable & code-splittable
### Bundle Size Comparison
| Action | @countrystatecity/countries | country-state-city |
|--------|----------------------------|-------------------|
| Install & import | 5KB | 8MB |
| Load countries | +2KB | - |
| Load US states | +30KB | - |
| Load CA cities | +15KB | - |
| **Total for typical use** | **~50KB** | **8MB** |
**160x smaller bundle size!**
## ๐ Package Comparison
### Server vs Browser Packages
| Feature | @countrystatecity/countries | @countrystatecity/countries-browser |
|---------|----------------------------|-------------------------------------|
| **Environment** | Node.js, Bun, Deno | Browser, Frontend |
| **Data Loading** | File system (`fs`) | Fetch API |
| **Dependencies** | Node.js built-ins | Zero |
| **Initial Bundle** | ~15KB | ~15KB + 130KB countries data |
| **Lazy Loading** | โ
Via file system | โ
Via HTTP requests |
| **TypeScript** | โ
| โ
|
| **Same API** | โ
| โ
|
| **Use Cases** | Next.js API routes, Express, serverless functions | React, Vue, Svelte, vanilla JS |
| **iOS Compatible** | โ
| โ
|
| **Caching** | OS file cache | HTTP cache + memory |
| **Status** | โ
Available now | ๐ Planned |
### When to Use Each Package
**Use `@countrystatecity/countries` (Server) when:**
- โ
Building API endpoints or backends
- โ
Using Next.js App Router server components
- โ
Running in Node.js, serverless functions (Vercel, AWS Lambda)
- โ
You have file system access
- โ
Building command-line tools
**Use `@countrystatecity/countries-browser` (Browser) when:**
- โ
Building client-side React/Vue/Svelte apps
- โ
Using Vite for frontend development
- โ
Need to load data in the browser directly
- โ
Building single-page applications (SPAs)
- โ
Running in browser environments only
**Current Workaround (until browser package is ready):**
Create API endpoints using the server package, then fetch from your frontend:
```typescript
// pages/api/countries.ts (Next.js API route)
import { getCountries } from '@countrystatecity/countries';
export default async function handler(req, res) {
const countries = await getCountries();
res.json(countries);
}
// components/CountrySelector.tsx (Frontend)
const countries = await fetch('/api/countries').then(r => r.json());
```
See [Vite Deployment Guide](./docs/VITE_DEPLOYMENT.md) for detailed patterns.
## ๐๏ธ Monorepo Structure
```
countrystatecity/
โโโ .github/
โ โโโ workflows/ # CI/CD workflows
โ โโโ ci.yml # Continuous Integration
โ โโโ update-data.yml # Automated data updates
โ โโโ publish.yml # NPM publishing
โโโ packages/
โ โโโ countries/ # @countrystatecity/countries package
โโโ specs/ # Technical specifications
โโโ package.json # Root package configuration
โโโ pnpm-workspace.yaml # Workspace configuration
```
## ๐ CI/CD & Automation
### Continuous Integration
Every push and PR automatically:
- โ
Runs type checking
- โ
Executes 42 comprehensive tests
- โ
Builds all packages
- โ
Validates bundle sizes
- โ
Tests iOS/Safari compatibility
### Automated Data Updates
Weekly automated updates (Sundays at 00:00 UTC):
- ๐ฅ Downloads latest data from [source repository](https://github.com/dr5hn/countries-states-cities-database)
- ๐ Transforms into optimized split structure
- ๐งช Runs full test suite
- ๐ Creates PR for review if changes detected
**Manual trigger:** Go to [Actions](https://github.com/dr5hn/countrystatecity/actions/workflows/update-data.yml) โ Run workflow
### Publishing
Automated publishing to NPM on version changes:
- ๐ Detects version bumps in package.json
- ๐ฆ Builds and tests before publishing
- ๐ Publishes to NPM registry
- ๐ท๏ธ Creates GitHub release with changelog
See [Workflow Documentation](./.github/workflows/README.md) for details.
## ๐ ๏ธ Development
### Prerequisites
- Node.js >= 18.0.0
- pnpm >= 8.0.0
### Setup
```bash
# Install dependencies
pnpm install
# Build all packages
pnpm build
# Run tests
pnpm test
# Run tests in watch mode
cd packages/countries && pnpm test:watch
```
### Commands
```bash
# Build all packages
pnpm build
# Test all packages
pnpm test
# Clean build artifacts
pnpm clean
```
## ๐ Testing
All packages include comprehensive tests:
- โ
Unit tests
- โ
Integration tests
- โ
iOS/Safari compatibility tests
Current coverage: 42 tests passing
## ๐ Documentation
- [Monorepo Plan](./specs/1-monorepo-plan.md)
- [@countrystatecity/countries Spec](./specs/2-world-countries-npm-package-spec.md)
- [Package Ecosystem Spec](./specs/3-world-package-ecosystem-spec.md)
## ๐ค Contributing
Contributions are welcome! Please:
1. Fork the repository
2. Create a feature branch
3. Make your changes
4. Add tests
5. Submit a pull request
**For data-related issues** (incorrect country names, missing cities, wrong coordinates, etc.), please report them to the [Countries States Cities Database](https://github.com/dr5hn/countries-states-cities-database/issues) repository, which is the source of data for this package.
## ๐ License
[ODbL-1.0](./LICENSE) ยฉ [dr5hn](https://github.com/dr5hn)
This package and its data are licensed under the Open Database License (ODbL) v1.0. The data is sourced from the [Countries States Cities Database](https://github.com/dr5hn/countries-states-cities-database) which is also licensed under ODbL-1.0.
You are free to share, create, and adapt this database as long as you:
- **Attribute**: Credit the original sources
- **Share-Alike**: Distribute adaptations under the same license
- **Keep Open**: Don't use technical restrictions
## ๐ Links
- [GitHub Repository](https://github.com/dr5hn/countrystatecity)
- [Issues](https://github.com/dr5hn/countrystatecity/issues)
- [NPM Organization](https://www.npmjs.com/org/countrystatecity)