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 🙏

© 2025 – Pkg Stats / Ryan Hefner

@obosbbl/validation

v0.3.1

Published

A collection of validation methods for OBOS

Readme

@obosbbl/validation

NPM Version

A collection of validation methods for both 🇳🇴 and 🇸🇪 with zero dependencies.

Install

# npm
npm install @obosbbl/validation

# pnpm
pnpm add @obosbbl/validation

Usage

The package has two entrypoints, one for no and one for se. That allows you to import for only the locale you need.

// 🇳🇴 example
import { validateOrganizationNumber } from '@obosbbl/validation/no';
validateOrganizationNumber('937052766') // => true

validateOrganizationNumber('000') // => false

// 🇸🇪 example
import { validateOrganizationNumber } from '@obosbbl/validation/se';
validateOrganizationNumber('5592221054') // => true

validateOrganizationNumber('000') // => false

Strictness and formatting characters

The methods are "strict" by default, meaning no formatting characters in the input is allowed. This even applies to separators such as in Swedish national identity numbers.

When doing server-side validation, for instance, before insertion into a database, strictness is often preferrable. The value is often expected to be a "clean" value in standardized format.

On the client side, formatting characters could be allowed, as they are more user-friendly, for instance, allowing the user to input their phone number in their preferred format.

If you want to allow formatting characters in the value, you can pass allowFormatting: true in the options object to the method.

import { validateOrganizationNumber } from '@obosbbl/validation/no';

validateOrganizationNumber('937052766') // true

// formatting characters disallowed by default
validateOrganizationNumber('937 052 766') // false;

// allow formatting characters
validateOrganizationNumber('937 052 766', { allowFormatting: true }) // true;

Methods

validateNationalIdentityNumber()

Validates that the value is a valid national identity number.

Validation is done for the both checksum and if the date is a valid date. It accepts both fødselsnummer and d-nummer for Norway, and personnummer and samordningsnummer for Sweden.

By default, both the short (10 digit) and long (12 digit) format is allowed for Sweden. You can use the format option to specify the format to validate.

// 🇳🇴 example
import { validateNationalIdenityNumber } from '@obosbbl/validation/no';
validateNationalIdenityNumber('DDMMYYXXXX') // => true

// 🇸🇪 example
import { validateNationalIdentityNumber } from "@obosbbl/validation/se";
// short
validatePersonalIdentityNumber('YYMMDDXXXX') // => true
// long
validateOrganizationNumber('YYYYMMDDXXXX'') // => true

// separator (formatting) is important for Swedish national identity numbers
validatePersonalIdentityNumber('YYMMDD-XXXX', { allowFormatting: true }) // => true
validateOrganizationNumber('YYYY-MMDDXXXX', { allowFormatting: true })) // => true

// specific format
validatePersonalIdentityNumber('YYMMDDXXXX', { format: 'short' }) // => true
validatePersonalIdentityNumber('YYMMDDXXXX', { format: 'long' }) // => false

validatePersonalIdentityNumber('YYYYMMDDXXXX', { format: 'long' }) // => true

[!TIP] Did you know that you cannot assume that the date in the number is person's date of birth? See Skatteetaten fødselsnummer.

validatePhoneNumber()

Validates that the value is a valid phone number. Specify mobileOnly to only allow mobile numbers.

// 🇳🇴 example
import { validatePhoneNumber } from '@obosbbl/validation/no';
validatePhoneNumber('00000000') // => true
validatePhoneNumber('90000000', { mobileOnly: true }) // => true

// 🇸🇪 example
import { validatePhoneNumber } from '@obosbbl/validation/se';
validatePhoneNumber('00000000') // => true
validatePhoneNumber('000000000') // => true
validatePhoneNumber('0000000000') // => true
validatePhoneNumber('0700000000', { mobileOnly: true }) // => true

validatePostalCode()

Validates that the value is a valid postal code.

// 🇳🇴 example
import { validatePostalCode } from '@obosbbl/validation/no';
validatePostalCode('0000') // => true

// 🇸🇪 example
import { validatePostalCode } from '@obosbbl/validation/se';
validatePostalCode('00000') // => true

validateOrganizationNumber()

Validates that the value is a valid organization number. Validates the checksum of the number.

// 🇳🇴 example
import { validateOrganizationNumber } from '@obosbbl/validation/no';
validateOrganizationNumber('937052766') // => true

// 🇸🇪 example
import { validateOrganizationNumber } from '@obosbbl/validation/se';
validateOrganizationNumber('5592221054') // => true

validateObosMembershipNumber()

Validates that the value is a valid OBOS membership number.

[!NOTE] There is no difference between a Norwegian and Swedish OBOS membership number. The method in use is in fact the same one, re-exported for the different locales.

// 🇳🇴 example
import { validateObosMembershipNumber } from '@obosbbl/validation/no';
validateObosMembershipNumber('0000000') // => true

// 🇸🇪 example
import { validateObosMembershipNumber } from '@obosbbl/validation/se';
validateObosMembershipNumber('0000000') // => true

validateAccountNumber()

Validates that the value is a valid organization number. Validates the checksum of the number.

// 🇳🇴 example
import { validateAccountNumber } from '@obosbbl/validation/no';
validateAccountNumber('12345678903'); // => true

// 🇸🇪 example
// TODO: implement

Example usage with Zod

import { z } from 'zod';
import { validatePhoneNumber } from '@obosbbl/validation/no';

const mobileOnlySchema = z.object({
  name: z.string(),
  phoneNumber: z
    .string()
    .refine(
      (val) => validatePhoneNumber(val, { mobileOnly: true }),
      'Telefonnummeret er ikke et gyldig mobilnummer',
    ),
});

const validData = {
  name: 'Kari Nordmann',
  phoneNumber: '92345678',
};

mobileOnlySchema.parse(validData); // => { name: 'Kari Nordmann', phoneNumber: '92345678' }

const invalidData = {
  name: 'Ola Nordmann',
  phoneNumber: '22865500',
}

mobileOnlySchema.parse(invalidData); // => throws ZodError