on ea25a45 help sign in
bridge/src/form/formatters.ts
127 lines 2.8 kB history raw
1import { compose, strSplice } from 'lib/lib';
2import { convertToInt } from 'lib/convertToInt';
4const HEX_PREFIX = '0x';
5const SIG_PREFIX = '~';
6const TICKET_MAX_BYTE_LEN = 32; // tickets can be as large as 32 bytes
7const PAT_BLOCK_CHAR_LENGTH = 6; // pat{p,q} blocks are 6 characters long
9interface Formatter {
10 (s?: string | undefined): string | undefined;
13export const buildFormatter = (formatters: Array<Formatter> = []) =>
14 compose(...formatters.reverse());
16/**
17 * inserts a ~ or - before every pat block
18 */
19export const ensurePatFormat = (s?: string) => {
20 // bail if falsy or empty string, nothing to do
21 if (!s || s.length === 0) {
22 return s || '';
23 }
25 // ensure there's a dash every 6 + 1 characters
26 const dashAt = (i: number) => i * (PAT_BLOCK_CHAR_LENGTH + 1);
27 const maxBlocks = TICKET_MAX_BYTE_LEN / 2;
29 // for every index that may need a separator
30 for (let i = 0; i !== maxBlocks; i++) {
31 const dashIndex = dashAt(i);
33 // if the string is too short to have a separator here, we're done
34 if (s.length - 1 < dashIndex) {
35 return s;
36 }
38 // insert the separator at the correct index if not already there
39 const sep = i === 0 ? '~' : '-';
40 if (s.charAt(dashIndex) !== sep) {
41 s = strSplice(s, dashIndex, sep);
42 }
43 }
45 return s;
46};
48export const ensureHexPrefix = (s?: string) => {
49 if (!s || s.length < HEX_PREFIX.length) {
50 return s || '';
51 }
53 return s.indexOf(HEX_PREFIX) !== 0 ? `${HEX_PREFIX}${s}` : s;
54};
56export const convertToNumber = (s?: string) => {
57 if (!s) {
58 return s || '';
59 }
61 try {
62 return convertToInt(s, 10);
63 } catch {
64 return 0;
65 }
66};
68export const downcase = (s?: string) => {
69 if (!s) {
70 return s;
71 }
73 return s.toLowerCase();
74};
76export const stripHexPrefix = (s?: string) => {
77 if (!s) {
78 return s;
79 }
81 return s.toLowerCase().indexOf(HEX_PREFIX) === 0
82 ? s.slice(HEX_PREFIX.length)
83 : s;
84};
86export const ensureSigPrefix = (s?: string) => {
87 if (!s || s.length < SIG_PREFIX.length) {
88 return s || '';
89 }
91 return s.indexOf(SIG_PREFIX) !== 0 ? `${SIG_PREFIX}${s}` : s;
92};
94export const stripSigPrefix = (s: string) => {
95 if (!s) {
96 return s;
97 }
99 return s.toLowerCase().indexOf(SIG_PREFIX) === 0
100 ? s.slice(SIG_PREFIX.length)
101 : s;
102};
104export const ticketToSegments = (ticket: string): string[] => {
105 return stripSigPrefix(ticket).split('-');
106};
108export const ticketFromSegments = (segments: string[]): string => {
109 return ensureSigPrefix(segments.join('-'));
110};
112export const capitalize = (s: string) => {
113 if (!s || s === '') {
114 return s;
115 }
117 return s.charAt(0).toUpperCase() + s.slice(1);
118};
120export const titleize = (s?: string): string => {
121 return s
122 ? s
123 .split(' ')
124 .map(_s => capitalize(_s))
125 .join(' ')
126 : '';
127};