1*90c8c64dSAndroid Build Coastguard Worker/* 2*90c8c64dSAndroid Build Coastguard Worker * Copyright (C) 2023 The Android Open Source Project 3*90c8c64dSAndroid Build Coastguard Worker * 4*90c8c64dSAndroid Build Coastguard Worker * Licensed under the Apache License, Version 2.0 (the "License"); 5*90c8c64dSAndroid Build Coastguard Worker * you may not use this file except in compliance with the License. 6*90c8c64dSAndroid Build Coastguard Worker * You may obtain a copy of the License at 7*90c8c64dSAndroid Build Coastguard Worker * 8*90c8c64dSAndroid Build Coastguard Worker * http://www.apache.org/licenses/LICENSE-2.0 9*90c8c64dSAndroid Build Coastguard Worker * 10*90c8c64dSAndroid Build Coastguard Worker * Unless required by applicable law or agreed to in writing, software 11*90c8c64dSAndroid Build Coastguard Worker * distributed under the License is distributed on an "AS IS" BASIS, 12*90c8c64dSAndroid Build Coastguard Worker * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13*90c8c64dSAndroid Build Coastguard Worker * See the License for the specific language governing permissions and 14*90c8c64dSAndroid Build Coastguard Worker * limitations under the License. 15*90c8c64dSAndroid Build Coastguard Worker */ 16*90c8c64dSAndroid Build Coastguard Workerimport {assertTrue} from './assert_utils'; 17*90c8c64dSAndroid Build Coastguard Worker 18*90c8c64dSAndroid Build Coastguard Workerclass StringUtils { 19*90c8c64dSAndroid Build Coastguard Worker static parseBigIntStrippingUnit(s: string): bigint { 20*90c8c64dSAndroid Build Coastguard Worker const match = s.match(/^\s*(-?\d+)\D*.*$/); 21*90c8c64dSAndroid Build Coastguard Worker if (!match) { 22*90c8c64dSAndroid Build Coastguard Worker throw new Error(`Cannot parse '${s}' as bigint`); 23*90c8c64dSAndroid Build Coastguard Worker } 24*90c8c64dSAndroid Build Coastguard Worker return BigInt(match[1]); 25*90c8c64dSAndroid Build Coastguard Worker } 26*90c8c64dSAndroid Build Coastguard Worker 27*90c8c64dSAndroid Build Coastguard Worker static convertCamelToSnakeCase(s: string): string { 28*90c8c64dSAndroid Build Coastguard Worker const result: string[] = []; 29*90c8c64dSAndroid Build Coastguard Worker 30*90c8c64dSAndroid Build Coastguard Worker let prevChar: string | undefined; 31*90c8c64dSAndroid Build Coastguard Worker for (const currChar of s) { 32*90c8c64dSAndroid Build Coastguard Worker const prevCharCouldBeWordEnd = 33*90c8c64dSAndroid Build Coastguard Worker prevChar && 34*90c8c64dSAndroid Build Coastguard Worker (StringUtils.isDigit(prevChar) || StringUtils.isLowerCase(prevChar)); 35*90c8c64dSAndroid Build Coastguard Worker const currCharCouldBeWordStart = StringUtils.isUpperCase(currChar); 36*90c8c64dSAndroid Build Coastguard Worker if (prevCharCouldBeWordEnd && currCharCouldBeWordStart) { 37*90c8c64dSAndroid Build Coastguard Worker result.push('_'); 38*90c8c64dSAndroid Build Coastguard Worker result.push(currChar.toLowerCase()); 39*90c8c64dSAndroid Build Coastguard Worker } else { 40*90c8c64dSAndroid Build Coastguard Worker result.push(currChar); 41*90c8c64dSAndroid Build Coastguard Worker } 42*90c8c64dSAndroid Build Coastguard Worker prevChar = currChar; 43*90c8c64dSAndroid Build Coastguard Worker } 44*90c8c64dSAndroid Build Coastguard Worker 45*90c8c64dSAndroid Build Coastguard Worker return result.join(''); 46*90c8c64dSAndroid Build Coastguard Worker } 47*90c8c64dSAndroid Build Coastguard Worker 48*90c8c64dSAndroid Build Coastguard Worker static convertSnakeToCamelCase(s: string): string { 49*90c8c64dSAndroid Build Coastguard Worker const tokens = s.split('_').filter((token) => token.length > 0); 50*90c8c64dSAndroid Build Coastguard Worker const tokensCapitalized = tokens.map((token) => { 51*90c8c64dSAndroid Build Coastguard Worker return StringUtils.capitalizeFirstCharIfAlpha(token); 52*90c8c64dSAndroid Build Coastguard Worker }); 53*90c8c64dSAndroid Build Coastguard Worker 54*90c8c64dSAndroid Build Coastguard Worker const inputStartsWithUnderscore = s[0] === '_'; 55*90c8c64dSAndroid Build Coastguard Worker let result = inputStartsWithUnderscore ? '_' : ''; 56*90c8c64dSAndroid Build Coastguard Worker result += tokens[0]; 57*90c8c64dSAndroid Build Coastguard Worker for (const token of tokensCapitalized.slice(1)) { 58*90c8c64dSAndroid Build Coastguard Worker if (!StringUtils.isAlpha(token[0])) { 59*90c8c64dSAndroid Build Coastguard Worker result += '_'; 60*90c8c64dSAndroid Build Coastguard Worker } 61*90c8c64dSAndroid Build Coastguard Worker result += token; 62*90c8c64dSAndroid Build Coastguard Worker } 63*90c8c64dSAndroid Build Coastguard Worker 64*90c8c64dSAndroid Build Coastguard Worker return result; 65*90c8c64dSAndroid Build Coastguard Worker } 66*90c8c64dSAndroid Build Coastguard Worker 67*90c8c64dSAndroid Build Coastguard Worker static isAlpha(char: string): boolean { 68*90c8c64dSAndroid Build Coastguard Worker assertTrue(char.length === 1, () => 'Input must be a single character'); 69*90c8c64dSAndroid Build Coastguard Worker return char[0].toLowerCase() !== char[0].toUpperCase(); 70*90c8c64dSAndroid Build Coastguard Worker } 71*90c8c64dSAndroid Build Coastguard Worker 72*90c8c64dSAndroid Build Coastguard Worker static isDigit(char: string): boolean { 73*90c8c64dSAndroid Build Coastguard Worker assertTrue(char.length === 1, () => 'Input must be a single character'); 74*90c8c64dSAndroid Build Coastguard Worker return char >= '0' && char <= '9'; 75*90c8c64dSAndroid Build Coastguard Worker } 76*90c8c64dSAndroid Build Coastguard Worker 77*90c8c64dSAndroid Build Coastguard Worker static isLowerCase(char: string): boolean { 78*90c8c64dSAndroid Build Coastguard Worker assertTrue(char.length === 1, () => 'Input must be a single character'); 79*90c8c64dSAndroid Build Coastguard Worker return StringUtils.isAlpha(char) && char === char.toLowerCase(); 80*90c8c64dSAndroid Build Coastguard Worker } 81*90c8c64dSAndroid Build Coastguard Worker 82*90c8c64dSAndroid Build Coastguard Worker static isUpperCase(char: string): boolean { 83*90c8c64dSAndroid Build Coastguard Worker assertTrue(char.length === 1, () => 'Input must be a single character'); 84*90c8c64dSAndroid Build Coastguard Worker return StringUtils.isAlpha(char) && char === char.toUpperCase(); 85*90c8c64dSAndroid Build Coastguard Worker } 86*90c8c64dSAndroid Build Coastguard Worker 87*90c8c64dSAndroid Build Coastguard Worker static isBlank(str: string): boolean { 88*90c8c64dSAndroid Build Coastguard Worker return str.replace(/\s/g, '').length === 0; 89*90c8c64dSAndroid Build Coastguard Worker } 90*90c8c64dSAndroid Build Coastguard Worker 91*90c8c64dSAndroid Build Coastguard Worker static isNumeric(str: string): boolean { 92*90c8c64dSAndroid Build Coastguard Worker return Number(str).toString() === str; 93*90c8c64dSAndroid Build Coastguard Worker } 94*90c8c64dSAndroid Build Coastguard Worker 95*90c8c64dSAndroid Build Coastguard Worker private static capitalizeFirstCharIfAlpha(word: string): string { 96*90c8c64dSAndroid Build Coastguard Worker if (word.length === 0) { 97*90c8c64dSAndroid Build Coastguard Worker return word; 98*90c8c64dSAndroid Build Coastguard Worker } 99*90c8c64dSAndroid Build Coastguard Worker 100*90c8c64dSAndroid Build Coastguard Worker if (!StringUtils.isAlpha(word[0])) { 101*90c8c64dSAndroid Build Coastguard Worker return word; 102*90c8c64dSAndroid Build Coastguard Worker } 103*90c8c64dSAndroid Build Coastguard Worker return word[0].toUpperCase() + word.slice(1); 104*90c8c64dSAndroid Build Coastguard Worker } 105*90c8c64dSAndroid Build Coastguard Worker} 106*90c8c64dSAndroid Build Coastguard Worker 107*90c8c64dSAndroid Build Coastguard Workerexport {StringUtils}; 108