Skip to content

Commit

Permalink
major: ts rewrite
Browse files Browse the repository at this point in the history
  • Loading branch information
tjmehta committed Dec 24, 2024
1 parent 5a7adf8 commit 3a65584
Show file tree
Hide file tree
Showing 21 changed files with 7,517 additions and 162 deletions.
13 changes: 13 additions & 0 deletions .babelrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
{
"presets": [
[
"@babel/preset-env",
{
"targets": {
"node": "current"
}
}
],
"@babel/preset-typescript"
]
}
20 changes: 20 additions & 0 deletions .github/workflows/npm-publish.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
name: Publish package to npm
on:
push:
tags:
- 'v*'
branches:
- master
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v1
- uses: actions/setup-node@v1
with:
node-version: 18
- run: npm install
- run: npm test
- uses: JS-DevTools/npm-publish@v1
with:
token: ${{ secrets.NPM_TOKEN }}
4 changes: 4 additions & 0 deletions @types/101/is-number.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
declare module '101/is-number' {
function isNumber(value: unknown): value is number;
export = isNumber;
}
4 changes: 4 additions & 0 deletions @types/101/is-string.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
declare module '101/is-string' {
function isString(value: unknown): value is string;
export = isString;
}
4 changes: 4 additions & 0 deletions @types/is-positive-integer.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
declare module 'is-positive-integer' {
function isPositiveInteger(value: unknown): value is number;
export = isPositiveInteger;
}
3 changes: 3 additions & 0 deletions CHANGELOG.MD
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
v2.0.0
major: ts rewrite, all tests still pass
minor: add debug info to errors
85 changes: 85 additions & 0 deletions dist/cjs/index.cjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,85 @@
"use strict";
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.Lex62GetPrefixError = exports.Lex62Error = void 0;
exports.encode = encode;
exports.decode = decode;
const is_number_1 = __importDefault(require("101/is-number"));
const is_string_1 = __importDefault(require("101/is-string"));
const is_positive_integer_1 = __importDefault(require("is-positive-integer"));
const baseerr_1 = __importDefault(require("baseerr"));
class Lex62Error extends baseerr_1.default {
}
exports.Lex62Error = Lex62Error;
class Lex62GetPrefixError extends baseerr_1.default {
}
exports.Lex62GetPrefixError = Lex62GetPrefixError;
const characters = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
const charMap = {
'0': 0, '1': 1, '2': 2, '3': 3, '4': 4, '5': 5, '6': 6, '7': 7, '8': 8, '9': 9,
'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15, 'G': 16, 'H': 17, 'I': 18,
'J': 19, 'K': 20, 'L': 21, 'M': 22, 'N': 23, 'O': 24, 'P': 25, 'Q': 26, 'R': 27,
'S': 28, 'T': 29, 'U': 30, 'V': 31, 'W': 32, 'X': 33, 'Y': 34, 'Z': 35, 'a': 36,
'b': 37, 'c': 38, 'd': 39, 'e': 40, 'f': 41, 'g': 42, 'h': 43, 'i': 44, 'j': 45,
'k': 46, 'l': 47, 'm': 48, 'n': 49, 'o': 50, 'p': 51, 'q': 52, 'r': 53, 's': 54,
't': 55, 'u': 56, 'v': 57, 'w': 58, 'x': 59, 'y': 60, 'z': 61
};
const CHAR_INDEX_OFFSET = 9; // 'A' is 10, 'B' is 11, etc.
// Prefix with length (starting at 'A' for length 1) to ensure the id's sort lexicographically.
function getPrefix(len, method, debug) {
const index = len + CHAR_INDEX_OFFSET;
if (index >= 62) {
throw new Lex62GetPrefixError(`${method}: number not supported (too large)`, {
method,
...debug
});
}
return characters[index];
}
function encode(base10) {
if (!(0, is_number_1.default)(base10)) {
throw new Lex62Error('encode: invalid base10 (not a number)', { base10 });
}
if (base10 !== 0 && !(0, is_positive_integer_1.default)(base10)) {
throw new Lex62Error('encode: number not supported (must be a positive integer or zero)', { base10 });
}
let str = base10 === 0 ? '0' : '';
let num = base10;
while (num > 0) {
const digit = num % characters.length;
str = characters[digit] + str;
num -= digit;
num /= characters.length;
}
const prefix = getPrefix(str.length, 'encode', { base10, partialBase62: str });
return prefix + str;
}
function decode(base62) {
if (!(0, is_string_1.default)(base62)) {
throw new Lex62Error('decode: invalid base62 (not a string)', { base62 });
}
const base62Char = base62[0];
if (!(base62Char in charMap)) {
throw new Lex62Error(`decode: invalid base62 ("${base62}" not base62)`, { base62 });
}
const expectedPrefix = getPrefix(base62.length - 1, 'decode', { base62 });
if (base62Char !== expectedPrefix) {
throw new Lex62GetPrefixError('decode: number not supported (unexpected prefix)', { method: 'decode', base62, expectedPrefix });
}
if (base62[1] === '0' && expectedPrefix !== 'A') {
throw new Lex62GetPrefixError('decode: number not supported (unexpected zero)', { method: 'decode', base62, expectedPrefix });
}
let base10 = 0;
for (let i = 1; i < base62.length; i++) {
base10 *= characters.length;
const base62Char = base62[i];
if (!(base62Char in charMap)) {
throw new Lex62Error(`decode: invalid base62 ("${base62}" not base62)`, { base62, partialBase10: base10 });
}
base10 += charMap[base62Char];
}
return base10;
}
//# sourceMappingURL=index.js.map
1 change: 1 addition & 0 deletions dist/cjs/index.cjs.map

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

17 changes: 17 additions & 0 deletions dist/cjs/index.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import BaseError from 'baseerr';
export interface Lex62ErrorProps {
base10?: number;
partialBase62?: string;
base62?: string;
partialBase10?: number;
}
export declare class Lex62Error extends BaseError<Lex62ErrorProps> {
}
export interface Lex62GetPrefixErrorProps extends Lex62ErrorProps {
method: string;
expectedPrefix?: string;
}
export declare class Lex62GetPrefixError extends BaseError<Lex62GetPrefixErrorProps> {
}
export declare function encode(base10: number): string;
export declare function decode(base62: string): number;
17 changes: 17 additions & 0 deletions dist/esm/index.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import BaseError from 'baseerr';
export interface Lex62ErrorProps {
base10?: number;
partialBase62?: string;
base62?: string;
partialBase10?: number;
}
export declare class Lex62Error extends BaseError<Lex62ErrorProps> {
}
export interface Lex62GetPrefixErrorProps extends Lex62ErrorProps {
method: string;
expectedPrefix?: string;
}
export declare class Lex62GetPrefixError extends BaseError<Lex62GetPrefixErrorProps> {
}
export declare function encode(base10: number): string;
export declare function decode(base62: string): number;
75 changes: 75 additions & 0 deletions dist/esm/index.mjs
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import isNumber from '101/is-number';
import isString from '101/is-string';
import isPositiveInteger from 'is-positive-integer';
import BaseError from 'baseerr';
export class Lex62Error extends BaseError {
}
export class Lex62GetPrefixError extends BaseError {
}
const characters = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz';
const charMap = {
'0': 0, '1': 1, '2': 2, '3': 3, '4': 4, '5': 5, '6': 6, '7': 7, '8': 8, '9': 9,
'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15, 'G': 16, 'H': 17, 'I': 18,
'J': 19, 'K': 20, 'L': 21, 'M': 22, 'N': 23, 'O': 24, 'P': 25, 'Q': 26, 'R': 27,
'S': 28, 'T': 29, 'U': 30, 'V': 31, 'W': 32, 'X': 33, 'Y': 34, 'Z': 35, 'a': 36,
'b': 37, 'c': 38, 'd': 39, 'e': 40, 'f': 41, 'g': 42, 'h': 43, 'i': 44, 'j': 45,
'k': 46, 'l': 47, 'm': 48, 'n': 49, 'o': 50, 'p': 51, 'q': 52, 'r': 53, 's': 54,
't': 55, 'u': 56, 'v': 57, 'w': 58, 'x': 59, 'y': 60, 'z': 61
};
const CHAR_INDEX_OFFSET = 9; // 'A' is 10, 'B' is 11, etc.
// Prefix with length (starting at 'A' for length 1) to ensure the id's sort lexicographically.
function getPrefix(len, method, debug) {
const index = len + CHAR_INDEX_OFFSET;
if (index >= 62) {
throw new Lex62GetPrefixError(`${method}: number not supported (too large)`, {
method,
...debug
});
}
return characters[index];
}
export function encode(base10) {
if (!isNumber(base10)) {
throw new Lex62Error('encode: invalid base10 (not a number)', { base10 });
}
if (base10 !== 0 && !isPositiveInteger(base10)) {
throw new Lex62Error('encode: number not supported (must be a positive integer or zero)', { base10 });
}
let str = base10 === 0 ? '0' : '';
let num = base10;
while (num > 0) {
const digit = num % characters.length;
str = characters[digit] + str;
num -= digit;
num /= characters.length;
}
const prefix = getPrefix(str.length, 'encode', { base10, partialBase62: str });
return prefix + str;
}
export function decode(base62) {
if (!isString(base62)) {
throw new Lex62Error('decode: invalid base62 (not a string)', { base62 });
}
const base62Char = base62[0];
if (!(base62Char in charMap)) {
throw new Lex62Error(`decode: invalid base62 ("${base62}" not base62)`, { base62 });
}
const expectedPrefix = getPrefix(base62.length - 1, 'decode', { base62 });
if (base62Char !== expectedPrefix) {
throw new Lex62GetPrefixError('decode: number not supported (unexpected prefix)', { method: 'decode', base62, expectedPrefix });
}
if (base62[1] === '0' && expectedPrefix !== 'A') {
throw new Lex62GetPrefixError('decode: number not supported (unexpected zero)', { method: 'decode', base62, expectedPrefix });
}
let base10 = 0;
for (let i = 1; i < base62.length; i++) {
base10 *= characters.length;
const base62Char = base62[i];
if (!(base62Char in charMap)) {
throw new Lex62Error(`decode: invalid base62 ("${base62}" not base62)`, { base62, partialBase10: base10 });
}
base10 += charMap[base62Char];
}
return base10;
}
//# sourceMappingURL=index.js.map
1 change: 1 addition & 0 deletions dist/esm/index.mjs.map

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

63 changes: 0 additions & 63 deletions index.js

This file was deleted.

Loading

0 comments on commit 3a65584

Please sign in to comment.