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

nuxt-phone-number

v0.1.3

Published

Nuxt-first phone input module with UPhoneInput, usePhone and global phoneInput config

Readme

nuxt-phone-number

npm version npm downloads

nuxt-phone-number is a Nuxt-first phone input module built around a simple DX:

  • auto-registered <UPhoneInput />
  • usePhone() composable
  • global defaults through nuxt.config.ts
  • live formatting and validation with libphonenumber-js
  • UI props inspired by Nuxt UI conventions

Features

  • Auto-imported UPhoneInput component
  • Country selector with flags and search
  • Live formatting while typing
  • E.164, national or international output
  • Global module config with phoneInput
  • usePhone() helpers for parsing, formatting and validation
  • UI props for color, variant, size and rounded
  • Better edit-form UX: prefilled values no longer show Invalid phone number immediately on open

Installation

npm install nuxt-phone-number libphonenumber-js

Quick Start

Add the module to your Nuxt config:

// nuxt.config.ts
export default defineNuxtConfig({
  modules: ["nuxt-phone-number"],
});

Then use the component anywhere without importing it manually:

<script setup lang="ts">
const phone = ref("");
</script>

<template>
  <UPhoneInput v-model="phone" />
</template>

Nuxt Config

You can configure app-wide defaults with the phoneInput key:

// nuxt.config.ts
export default defineNuxtConfig({
  modules: ["nuxt-phone-number"],

  phoneInput: {
    defaultCountry: "SN",
    preferredCountries: ["SN", "FR"],
    onlyCountries: [],
    ignoredCountries: [],
    useBrowserLocale: true,
    format: "international",
    ui: {
      color: "primary",
      variant: "outline",
      size: "md",
      rounded: "lg",
    },
  },
});

Basic Usage

<script setup lang="ts">
const phone = ref("");
</script>

<template>
  <UPhoneInput
    v-model="phone"
    color="primary"
    variant="outline"
    size="md"
    rounded="lg"
  />
</template>

Edit Form Example

When you use the component in an update form with an existing phone number, the component now avoids showing an error immediately on load before the user interacts with the field:

<script setup lang="ts">
const form = reactive({
  phone: "+221772233284",
});
</script>

<template>
  <UPhoneInput
    v-model="form.phone"
    default-country="SN"
    variant="outline"
  />
</template>

Output Format

The format prop controls what v-model receives:

  • international
  • national
  • e164

Example:

<UPhoneInput
  v-model="phone"
  format="e164"
/>

UI Props

color

Accepted values:

  • primary
  • secondary
  • success
  • info
  • warning
  • error
  • neutral

Example:

<UPhoneInput
  v-model="phone"
  color="success"
/>

variant

Accepted values:

  • outline
  • soft
  • subtle
  • ghost
  • none

Example:

<UPhoneInput
  v-model="phone"
  variant="subtle"
/>

size

Accepted values:

  • xs
  • sm
  • md
  • lg
  • xl

Example:

<UPhoneInput
  v-model="phone"
  size="xl"
/>

rounded

Accepted values:

  • none
  • sm
  • md
  • lg
  • xl
  • full

Example:

<UPhoneInput
  v-model="phone"
  rounded="full"
/>

Component Props

Value and country

  • modelValue?: string
  • countryCode?: CountryCode | string
  • defaultCountry?: string

Country list behavior

  • preferredCountries?: string[]
  • onlyCountries?: string[]
  • ignoredCountries?: string[]
  • useBrowserLocale?: boolean

Display and validation

  • placeholder?: string
  • disabled?: boolean
  • error?: string | boolean
  • locale?: string
  • searchPlaceholder?: string
  • noResultsText?: string
  • invalidMessage?: string
  • format?: "national" | "international" | "e164"

UI

  • color?: "primary" | "secondary" | "success" | "info" | "warning" | "error" | "neutral"
  • variant?: "outline" | "soft" | "subtle" | "ghost" | "none"
  • size?: "xs" | "sm" | "md" | "lg" | "xl"
  • rounded?: "none" | "sm" | "md" | "lg" | "xl" | "full"

Events

update:modelValue

Emits the current formatted value according to the selected format.

update:countryCode

Emits the currently selected country code.

data

Emits a normalized payload:

interface PhoneInputData {
  e164: string | null;
  countryCode: CountryCode | null;
  formatted: string;
  isValid: boolean;
}

Example:

<script setup lang="ts">
function onPhoneData(data: {
  e164: string | null;
  countryCode: string | null;
  formatted: string;
  isValid: boolean;
}) {
  console.log(data);
}
</script>

<template>
  <UPhoneInput
    v-model="phone"
    @data="onPhoneData"
  />
</template>

usePhone()

The module injects a usePhone() composable:

<script setup lang="ts">
const { formatPhone, validatePhone, parsePhone, defaults } = usePhone();

const formatted = formatPhone("+221772233284");
const valid = validatePhone("+221772233284");
const parsed = parsePhone("+221772233284");
</script>

Returned helpers

formatPhone(phone, countryCode?, format?)

Formats a phone number into:

  • national
  • international
  • e164

validatePhone(phone, countryCode?)

Returns a boolean indicating whether the number is valid.

parsePhone(phone, countryCode?)

Returns:

{
  e164: string | null
  countryCode: CountryCode | null
  formatted: string
  isValid: boolean
}

defaults

Exposes the resolved module defaults from phoneInput.

Common Examples

Restrict countries

<UPhoneInput
  v-model="phone"
  :only-countries="['SN', 'FR', 'CI']"
/>

Preferred countries first

<UPhoneInput
  v-model="phone"
  :preferred-countries="['SN', 'FR']"
/>

Custom validation message

<UPhoneInput
  v-model="phone"
  invalid-message="Numéro invalide"
/>

Force an error from parent form state

<UPhoneInput
  v-model="phone"
  error="Ce numéro est déjà utilisé"
/>

Notes

  • The component is Nuxt-first and meant to be used inside Nuxt 3 or Nuxt 4 projects.
  • @nuxt/ui is optional. The API style is inspired by it, but the package does not require it.
  • The component formats and validates numbers with libphonenumber-js.
  • Validation errors are interaction-aware, so prefilled values in edit forms do not immediately show an error before the user changes the field.

Scripts

npm run dev
npm run build
npm run typecheck

Links