@pcg/text-kit 1.0.0-alpha.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.turbo/turbo-build.log +15 -0
- package/README.md +243 -0
- package/dist/index.d.ts +243 -0
- package/dist/index.js +324 -0
- package/dist/index.js.map +1 -0
- package/eslint.config.cjs +14 -0
- package/package.json +26 -0
- package/src/cases.ts +317 -0
- package/src/declination.ts +23 -0
- package/src/entities.ts +41 -0
- package/src/generators.ts +16 -0
- package/src/index.ts +5 -0
- package/src/pluralize.ts +35 -0
- package/tests/cases.test.ts +196 -0
- package/tests/declination.test.ts +14 -0
- package/tests/entities.test.ts +47 -0
- package/tests/generators.test.ts +11 -0
- package/tests/pluralize.test.ts +28 -0
- package/tsconfig.json +9 -0
- package/tsconfig.lib.json +9 -0
- package/tsdown.config.ts +11 -0
- package/vitest.config.ts +19 -0
package/dist/index.js
ADDED
|
@@ -0,0 +1,324 @@
|
|
|
1
|
+
import * as cc from "change-case";
|
|
2
|
+
import cyrillicToTranslit from "cyrillic-to-translit-js";
|
|
3
|
+
import { customAlphabet } from "nanoid/non-secure";
|
|
4
|
+
import * as pluralize from "pluralize";
|
|
5
|
+
|
|
6
|
+
//#region src/generators.ts
|
|
7
|
+
const createRandomString = (size = 8) => {
|
|
8
|
+
return customAlphabet("0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz", size)();
|
|
9
|
+
};
|
|
10
|
+
const createRandomAbbreviationString = (size = 8) => {
|
|
11
|
+
return customAlphabet("ABCDEFGHIJKLMNOPQRSTUVWXYZ", size)();
|
|
12
|
+
};
|
|
13
|
+
const createNumericCode = (num, length) => {
|
|
14
|
+
return num.toString().padStart(length, "0");
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
//#endregion
|
|
18
|
+
//#region src/cases.ts
|
|
19
|
+
/**
|
|
20
|
+
* Convert a string to string with the first character in uppercase.
|
|
21
|
+
* @example
|
|
22
|
+
* ucfirst('hello world'); // Hello world
|
|
23
|
+
**/
|
|
24
|
+
const ucfirst = (input) => {
|
|
25
|
+
return input.charAt(0).toUpperCase() + input.substring(1);
|
|
26
|
+
};
|
|
27
|
+
/**
|
|
28
|
+
* Convert a string to string with the first character in lower case.
|
|
29
|
+
* @example
|
|
30
|
+
* lcfirst('Hello world'); // hello world
|
|
31
|
+
**/
|
|
32
|
+
const lcfirst = (input) => {
|
|
33
|
+
return input.charAt(0).toLowerCase() + input.substring(1);
|
|
34
|
+
};
|
|
35
|
+
/**
|
|
36
|
+
* Convert a string to PascalCase.
|
|
37
|
+
* @example
|
|
38
|
+
* pascalCase('foo bar'); //=> 'FooBar'
|
|
39
|
+
* pascalCase('foo_bar'); //=> 'FooBar'
|
|
40
|
+
* pascalCase('foo-bar'); //=> 'FooBar'
|
|
41
|
+
* pascalCase('foo.bar'); //=> 'FooBar'
|
|
42
|
+
* pascalCase('fooBar'); //=> 'FooBar'
|
|
43
|
+
**/
|
|
44
|
+
const pascalCase = (input) => {
|
|
45
|
+
return cc.pascalCase(input, { mergeAmbiguousCharacters: true });
|
|
46
|
+
};
|
|
47
|
+
/**
|
|
48
|
+
* Convert a string to camelCase.
|
|
49
|
+
* @example
|
|
50
|
+
* camelCase('foo bar'); //=> 'fooBar'
|
|
51
|
+
* camelCase('foo_bar'); //=> 'fooBar'
|
|
52
|
+
* camelCase('foo-bar'); //=> 'fooBar'
|
|
53
|
+
* camelCase('foo.bar'); //=> 'fooBar'
|
|
54
|
+
* camelCase('fooBar'); //=> 'fooBar'
|
|
55
|
+
* camelCase('FooBar'); //=> 'fooBar'
|
|
56
|
+
**/
|
|
57
|
+
const camelCase = (input) => {
|
|
58
|
+
return cc.camelCase(input);
|
|
59
|
+
};
|
|
60
|
+
/**
|
|
61
|
+
* Convert a string to param-case.
|
|
62
|
+
* @example
|
|
63
|
+
* paramCase('foo bar'); //=> 'foo-bar'
|
|
64
|
+
* paramCase('foo_bar'); //=> 'foo-bar'
|
|
65
|
+
* paramCase('foo-bar'); //=> 'foo-bar'
|
|
66
|
+
* paramCase('foo.bar'); //=> 'foo-bar'
|
|
67
|
+
* paramCase('fooBar'); //=> 'foo-bar'
|
|
68
|
+
* paramCase('FooBar'); //=> 'foo-bar'
|
|
69
|
+
**/
|
|
70
|
+
const paramCase = (input) => {
|
|
71
|
+
return cc.kebabCase(input);
|
|
72
|
+
};
|
|
73
|
+
/**
|
|
74
|
+
* Convert a string to "dot.case".
|
|
75
|
+
* @example
|
|
76
|
+
* dotCase('foo bar'); //=> 'foo.bar'
|
|
77
|
+
* dotCase('foo_bar'); //=> 'foo.bar'
|
|
78
|
+
* dotCase('foo-bar'); //=> 'foo.bar'
|
|
79
|
+
* dotCase('foo.bar'); //=> 'foo.bar'
|
|
80
|
+
* dotCase('fooBar'); //=> 'foo.bar'
|
|
81
|
+
* dotCase('FooBar'); //=> 'foo.bar'
|
|
82
|
+
**/
|
|
83
|
+
const dotCase = (input) => {
|
|
84
|
+
return cc.dotCase(input);
|
|
85
|
+
};
|
|
86
|
+
/**
|
|
87
|
+
* Convert a string to snake_case.
|
|
88
|
+
* @example
|
|
89
|
+
* snakeCase('foo bar'); //=> 'foo_bar'
|
|
90
|
+
* snakeCase('foo_bar'); //=> 'foo_bar'
|
|
91
|
+
* snakeCase('foo-bar'); //=> 'foo_bar'
|
|
92
|
+
* snakeCase('foo.bar'); //=> 'foo_bar'
|
|
93
|
+
* snakeCase('fooBar'); //=> 'foo_bar'
|
|
94
|
+
* snakeCase('FooBar'); //=> 'foo_bar'
|
|
95
|
+
**/
|
|
96
|
+
const snakeCase = (input) => {
|
|
97
|
+
return cc.snakeCase(input);
|
|
98
|
+
};
|
|
99
|
+
/**
|
|
100
|
+
* Convert a string to CONSTANT_CASE.
|
|
101
|
+
* @example
|
|
102
|
+
* constantCase('foo bar'); //=> 'FOO_BAR'
|
|
103
|
+
* constantCase('foo_bar'); //=> 'FOO_BAR'
|
|
104
|
+
* constantCase('foo-bar'); //=> 'FOO_BAR'
|
|
105
|
+
* constantCase('foo.bar'); //=> 'FOO_BAR'
|
|
106
|
+
* constantCase('fooBar'); //=> 'FOO_BAR'
|
|
107
|
+
* constantCase('FooBar'); //=> 'FOO_BAR'
|
|
108
|
+
**/
|
|
109
|
+
const constantCase = (input) => {
|
|
110
|
+
return cc.constantCase(input);
|
|
111
|
+
};
|
|
112
|
+
/**
|
|
113
|
+
* Convert a string to sentence.
|
|
114
|
+
* @deprecated use sentenceCase instead
|
|
115
|
+
* @example
|
|
116
|
+
* toSentence('foo bar'); //=> 'Foo bar'
|
|
117
|
+
* toSentence('foo_bar'); //=> 'Foo bar'
|
|
118
|
+
* toSentence('foo-bar'); //=> 'Foo bar'
|
|
119
|
+
* toSentence('foo.bar'); //=> 'Foo bar'
|
|
120
|
+
* toSentence('fooBar'); //=> 'Foo bar'
|
|
121
|
+
* toSentence('FooBar'); //=> 'Foo bar'
|
|
122
|
+
* toSentence('foo bar baz'); //=> 'Foo bar baz'
|
|
123
|
+
**/
|
|
124
|
+
const toSentence = (input) => {
|
|
125
|
+
return ucfirst(cc.noCase(input, { delimiter: " " }));
|
|
126
|
+
};
|
|
127
|
+
/**
|
|
128
|
+
* Convert a string to sentence.
|
|
129
|
+
* @example
|
|
130
|
+
* sentenceCase('foo bar'); //=> 'Foo bar'
|
|
131
|
+
* sentenceCase('foo_bar'); //=> 'Foo bar'
|
|
132
|
+
* sentenceCase('foo-bar'); //=> 'Foo bar'
|
|
133
|
+
* sentenceCase('foo.bar'); //=> 'Foo bar'
|
|
134
|
+
* sentenceCase('fooBar'); //=> 'Foo bar'
|
|
135
|
+
* sentenceCase('FooBar'); //=> 'Foo bar'
|
|
136
|
+
* sentenceCase('foo bar baz'); //=> 'Foo bar baz'
|
|
137
|
+
**/
|
|
138
|
+
const sentenceCase = (input) => {
|
|
139
|
+
return cc.sentenceCase(input);
|
|
140
|
+
};
|
|
141
|
+
/**
|
|
142
|
+
* Convert a string to upper cased sentence.
|
|
143
|
+
* @deprecated use capitalCase instead
|
|
144
|
+
* @example
|
|
145
|
+
* toUcSentence('foo bar'); //=> 'Foo Bar'
|
|
146
|
+
* toUcSentence('foo_bar'); //=> 'Foo Bar'
|
|
147
|
+
* toUcSentence('foo-bar'); //=> 'Foo Bar'
|
|
148
|
+
* toUcSentence('foo.bar'); //=> 'Foo Bar'
|
|
149
|
+
* toUcSentence('fooBar'); //=> 'Foo Bar'
|
|
150
|
+
* toUcSentence('FooBar'); //=> 'Foo Bar'
|
|
151
|
+
* toUcSentence('foo bar baz'); //=> 'Foo Bar Baz'
|
|
152
|
+
**/
|
|
153
|
+
const toUcSentence = (input) => {
|
|
154
|
+
return cc.capitalCase(input);
|
|
155
|
+
};
|
|
156
|
+
/**
|
|
157
|
+
* Convert a string to upper cased sentence.
|
|
158
|
+
* @example
|
|
159
|
+
* capitalCase('foo bar'); //=> 'Foo Bar'
|
|
160
|
+
* capitalCase('foo_bar'); //=> 'Foo Bar'
|
|
161
|
+
* capitalCase('foo-bar'); //=> 'Foo Bar'
|
|
162
|
+
* capitalCase('foo.bar'); //=> 'Foo Bar'
|
|
163
|
+
* capitalCase('fooBar'); //=> 'Foo Bar'
|
|
164
|
+
* capitalCase('FooBar'); //=> 'Foo Bar'
|
|
165
|
+
* capitalCase('foo bar baz'); //=> 'Foo Bar Baz'
|
|
166
|
+
**/
|
|
167
|
+
const capitalCase = (input) => {
|
|
168
|
+
return cc.capitalCase(input);
|
|
169
|
+
};
|
|
170
|
+
/**
|
|
171
|
+
* Alias to "toUcSentence"
|
|
172
|
+
* @deprecated use capitalCase instead
|
|
173
|
+
**/
|
|
174
|
+
const capitalize = (input) => toUcSentence(input);
|
|
175
|
+
/**
|
|
176
|
+
* Convert a string to lower cased sentence.
|
|
177
|
+
* @deprecated use lowerSentenceCase instead
|
|
178
|
+
* @example
|
|
179
|
+
* toLcSentence('foo bar'); //=> 'foo bar'
|
|
180
|
+
* toLcSentence('foo_bar'); //=> 'foo bar'
|
|
181
|
+
* toLcSentence('foo-bar'); //=> 'foo bar'
|
|
182
|
+
* toLcSentence('foo.bar'); //=> 'foo bar'
|
|
183
|
+
* toLcSentence('fooBar'); //=> 'foo bar'
|
|
184
|
+
* toLcSentence('FooBar'); //=> 'foo bar'
|
|
185
|
+
* toLcSentence('Foo bar baz'); //=> 'foo bar baz'
|
|
186
|
+
**/
|
|
187
|
+
const toLcSentence = (input) => {
|
|
188
|
+
return sentenceCase(input).toLowerCase();
|
|
189
|
+
};
|
|
190
|
+
/**
|
|
191
|
+
* Convert a string to lower cased sentence.
|
|
192
|
+
* @example
|
|
193
|
+
* lowerSentenceCase('foo bar'); //=> 'foo bar'
|
|
194
|
+
* lowerSentenceCase('foo_bar'); //=> 'foo bar'
|
|
195
|
+
* lowerSentenceCase('foo-bar'); //=> 'foo bar'
|
|
196
|
+
* lowerSentenceCase('foo.bar'); //=> 'foo bar'
|
|
197
|
+
* lowerSentenceCase('fooBar'); //=> 'foo bar'
|
|
198
|
+
* lowerSentenceCase('FooBar'); //=> 'foo bar'
|
|
199
|
+
* lowerSentenceCase('Foo bar baz'); //=> 'foo bar baz'
|
|
200
|
+
**/
|
|
201
|
+
const lowerSentenceCase = (input) => {
|
|
202
|
+
return sentenceCase(input).toLowerCase();
|
|
203
|
+
};
|
|
204
|
+
/**
|
|
205
|
+
* Convert a table name to sql alias.
|
|
206
|
+
* @example
|
|
207
|
+
* toSqlAlias('foo bar'); //=> 'fb'
|
|
208
|
+
* toSqlAlias('book'); //=> 'b'
|
|
209
|
+
* toSqlAlias('article-category'); //=> 'ac'
|
|
210
|
+
**/
|
|
211
|
+
const toSqlAlias = (input) => {
|
|
212
|
+
return snakeCase(input).split("_").reduce((acc, word) => acc.concat(word[0]), "");
|
|
213
|
+
};
|
|
214
|
+
/**
|
|
215
|
+
* Remove vowels from a word.
|
|
216
|
+
* @param word - word to remove vowels from
|
|
217
|
+
* @returns word without vowels
|
|
218
|
+
* @example
|
|
219
|
+
* removeVowels('foo'); //=> 'f'
|
|
220
|
+
*/
|
|
221
|
+
const removeVowels = (word) => {
|
|
222
|
+
return word.replace(/[aeiou]/gi, "");
|
|
223
|
+
};
|
|
224
|
+
/**
|
|
225
|
+
* Convert a string to abbreviation.
|
|
226
|
+
* @example
|
|
227
|
+
* toAbbreviation('Sabbath Schook'); //=> 'SB'
|
|
228
|
+
* toAbbreviation('Рожеві окуляри', {
|
|
229
|
+
* lang: 'uk',
|
|
230
|
+
* }); //=> 'RO'
|
|
231
|
+
* toAbbreviation('Удивительные факты', {
|
|
232
|
+
* lang: 'ru',
|
|
233
|
+
* }); //=> 'UF'
|
|
234
|
+
*/
|
|
235
|
+
const toAbbreviation = (input, opts) => {
|
|
236
|
+
const words = cyrillicToTranslit(opts?.lang ? { preset: opts.lang } : void 0).transform(input).toUpperCase().replace(/[^A-Z ]/g, "").split(" ").filter((word) => word.length > 0);
|
|
237
|
+
let abbreviation = "";
|
|
238
|
+
if (words.length > 1) abbreviation = words.reduce((acc, word) => {
|
|
239
|
+
if (word.length >= 1) acc += word[0];
|
|
240
|
+
return acc;
|
|
241
|
+
}, "");
|
|
242
|
+
else if (words.length === 1) {
|
|
243
|
+
const word = words[0];
|
|
244
|
+
if (word.length > 1) abbreviation = word.slice(0, 1) + removeVowels(word.slice(1));
|
|
245
|
+
else abbreviation = word;
|
|
246
|
+
}
|
|
247
|
+
if (opts?.maxLength && !opts?.iteration) abbreviation = abbreviation.slice(0, opts.maxLength);
|
|
248
|
+
if (opts?.minLength && abbreviation.length < opts.minLength) {
|
|
249
|
+
let charsNeeded = opts.minLength - abbreviation.length;
|
|
250
|
+
if (opts?.iteration && opts?.iteration > 0) charsNeeded -= 1;
|
|
251
|
+
if (charsNeeded > 0) abbreviation += createRandomAbbreviationString(charsNeeded).toUpperCase();
|
|
252
|
+
}
|
|
253
|
+
if (opts?.iteration) {
|
|
254
|
+
if (opts?.maxLength) {
|
|
255
|
+
const maxAbbrLength = opts.maxLength - 1;
|
|
256
|
+
abbreviation = abbreviation.slice(0, maxAbbrLength);
|
|
257
|
+
}
|
|
258
|
+
abbreviation += opts.iteration;
|
|
259
|
+
}
|
|
260
|
+
return abbreviation;
|
|
261
|
+
};
|
|
262
|
+
|
|
263
|
+
//#endregion
|
|
264
|
+
//#region src/declination.ts
|
|
265
|
+
/**
|
|
266
|
+
* Decline a noun based on a number.
|
|
267
|
+
* @example
|
|
268
|
+
* const words = ['элемент', 'элемента', 'элементов'];
|
|
269
|
+
*
|
|
270
|
+
* decline(0, words, false) // => 'элементов'
|
|
271
|
+
* decline(24, words, false) // => 'элемента'
|
|
272
|
+
* decline(21, words, false) // => 'элемент'
|
|
273
|
+
*
|
|
274
|
+
* decline(0, words) // => '0 элементов'
|
|
275
|
+
* decline(24, words) // => '24 элемента'
|
|
276
|
+
* decline(21, words) // => '21 элемент'
|
|
277
|
+
*/
|
|
278
|
+
const decline = (n, words, concat = true) => {
|
|
279
|
+
const word = words[n % 100 > 4 && n % 100 < 20 ? 2 : [
|
|
280
|
+
2,
|
|
281
|
+
0,
|
|
282
|
+
1,
|
|
283
|
+
1,
|
|
284
|
+
1,
|
|
285
|
+
2
|
|
286
|
+
][n % 10 < 5 ? n % 10 : 5]];
|
|
287
|
+
return concat ? `${n} ${word}` : word;
|
|
288
|
+
};
|
|
289
|
+
|
|
290
|
+
//#endregion
|
|
291
|
+
//#region src/pluralize.ts
|
|
292
|
+
/**
|
|
293
|
+
* Change the plural form of a word to its singular form.
|
|
294
|
+
* @example
|
|
295
|
+
* pluralToSingular('books'); //=> 'book'
|
|
296
|
+
*/
|
|
297
|
+
const singularToPlural = (input) => {
|
|
298
|
+
return pluralize.plural(input);
|
|
299
|
+
};
|
|
300
|
+
/**
|
|
301
|
+
* Change the singular form of a word to its plural form.
|
|
302
|
+
* @example
|
|
303
|
+
* singularToPlural('book'); //=> 'books'
|
|
304
|
+
*/
|
|
305
|
+
const pluralToSingular = (input) => {
|
|
306
|
+
return pluralize.singular(input);
|
|
307
|
+
};
|
|
308
|
+
/**
|
|
309
|
+
* Checks if a given word is in its plural form.
|
|
310
|
+
*
|
|
311
|
+
* @param word - The word to check for plural form
|
|
312
|
+
* @returns `true` if the word is plural, `false` if it's singular
|
|
313
|
+
*
|
|
314
|
+
* @example
|
|
315
|
+
* ```typescript
|
|
316
|
+
* isPlural("cats"); // true
|
|
317
|
+
* isPlural("cat"); // false
|
|
318
|
+
* ```
|
|
319
|
+
*/
|
|
320
|
+
const isPlural = (word) => singularToPlural(word) === word;
|
|
321
|
+
|
|
322
|
+
//#endregion
|
|
323
|
+
export { camelCase, capitalCase, capitalize, constantCase, createNumericCode, createRandomAbbreviationString, createRandomString, decline, dotCase, isPlural, lcfirst, lowerSentenceCase, paramCase, pascalCase, pluralToSingular, removeVowels, sentenceCase, singularToPlural, snakeCase, toAbbreviation, toLcSentence, toSentence, toSqlAlias, toUcSentence, ucfirst };
|
|
324
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","names":[],"sources":["../src/generators.ts","../src/cases.ts","../src/declination.ts","../src/pluralize.ts"],"sourcesContent":["import { customAlphabet } from 'nanoid/non-secure';\n\nexport const createRandomString = (size = 8) => {\n return customAlphabet('0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz', size)();\n};\n\nexport const createRandomAbbreviationString = (size = 8) => {\n return customAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ', size)();\n};\n\nexport const createNumericCode = (num: number, length: number): string => {\n // Add leading zeros if necessary using padStart\n const numberStr = num.toString().padStart(length, '0');\n\n return numberStr;\n};\n","import * as cc from 'change-case';\nimport { default as cyrillicToTranslit } from 'cyrillic-to-translit-js';\nimport { createRandomAbbreviationString } from './generators.js';\n\n/**\n * Convert a string to string with the first character in uppercase.\n * @example\n * ucfirst('hello world'); // Hello world\n**/\nexport const ucfirst = (input: string) => {\n return input.charAt(0).toUpperCase() + input.substring(1);\n};\n\n/**\n * Convert a string to string with the first character in lower case.\n * @example\n * lcfirst('Hello world'); // hello world\n **/\nexport const lcfirst = (input: string) => {\n return input.charAt(0).toLowerCase() + input.substring(1);\n};\n\n/**\n * Convert a string to PascalCase.\n * @example\n * pascalCase('foo bar'); //=> 'FooBar'\n * pascalCase('foo_bar'); //=> 'FooBar'\n * pascalCase('foo-bar'); //=> 'FooBar'\n * pascalCase('foo.bar'); //=> 'FooBar'\n * pascalCase('fooBar'); //=> 'FooBar'\n**/\nexport const pascalCase = (input: string) => {\n return cc.pascalCase(input, {\n mergeAmbiguousCharacters: true,\n });\n};\n\n/**\n * Convert a string to camelCase.\n * @example\n * camelCase('foo bar'); //=> 'fooBar'\n * camelCase('foo_bar'); //=> 'fooBar'\n * camelCase('foo-bar'); //=> 'fooBar'\n * camelCase('foo.bar'); //=> 'fooBar'\n * camelCase('fooBar'); //=> 'fooBar'\n * camelCase('FooBar'); //=> 'fooBar'\n**/\nexport const camelCase = (input: string) => {\n return cc.camelCase(input);\n};\n\n/**\n * Convert a string to param-case.\n * @example\n * paramCase('foo bar'); //=> 'foo-bar'\n * paramCase('foo_bar'); //=> 'foo-bar'\n * paramCase('foo-bar'); //=> 'foo-bar'\n * paramCase('foo.bar'); //=> 'foo-bar'\n * paramCase('fooBar'); //=> 'foo-bar'\n * paramCase('FooBar'); //=> 'foo-bar'\n**/\nexport const paramCase = (input: string) => {\n return cc.kebabCase(input);\n};\n\n/**\n * Convert a string to \"dot.case\".\n * @example\n * dotCase('foo bar'); //=> 'foo.bar'\n * dotCase('foo_bar'); //=> 'foo.bar'\n * dotCase('foo-bar'); //=> 'foo.bar'\n * dotCase('foo.bar'); //=> 'foo.bar'\n * dotCase('fooBar'); //=> 'foo.bar'\n * dotCase('FooBar'); //=> 'foo.bar'\n**/\nexport const dotCase = (input: string) => {\n return cc.dotCase(input);\n};\n\n/**\n * Convert a string to snake_case.\n * @example\n * snakeCase('foo bar'); //=> 'foo_bar'\n * snakeCase('foo_bar'); //=> 'foo_bar'\n * snakeCase('foo-bar'); //=> 'foo_bar'\n * snakeCase('foo.bar'); //=> 'foo_bar'\n * snakeCase('fooBar'); //=> 'foo_bar'\n * snakeCase('FooBar'); //=> 'foo_bar'\n**/\nexport const snakeCase = (input: string) => {\n return cc.snakeCase(input);\n};\n\n/**\n * Convert a string to CONSTANT_CASE.\n * @example\n * constantCase('foo bar'); //=> 'FOO_BAR'\n * constantCase('foo_bar'); //=> 'FOO_BAR'\n * constantCase('foo-bar'); //=> 'FOO_BAR'\n * constantCase('foo.bar'); //=> 'FOO_BAR'\n * constantCase('fooBar'); //=> 'FOO_BAR'\n * constantCase('FooBar'); //=> 'FOO_BAR'\n**/\nexport const constantCase = (input: string) => {\n return cc.constantCase(input);\n};\n\n/**\n * Convert a string to sentence.\n * @deprecated use sentenceCase instead\n * @example\n * toSentence('foo bar'); //=> 'Foo bar'\n * toSentence('foo_bar'); //=> 'Foo bar'\n * toSentence('foo-bar'); //=> 'Foo bar'\n * toSentence('foo.bar'); //=> 'Foo bar'\n * toSentence('fooBar'); //=> 'Foo bar'\n * toSentence('FooBar'); //=> 'Foo bar'\n * toSentence('foo bar baz'); //=> 'Foo bar baz'\n**/\nexport const toSentence = (input: string) => {\n return ucfirst(cc.noCase(input, {\n delimiter: ' ',\n }));\n};\n\n/**\n * Convert a string to sentence.\n * @example\n * sentenceCase('foo bar'); //=> 'Foo bar'\n * sentenceCase('foo_bar'); //=> 'Foo bar'\n * sentenceCase('foo-bar'); //=> 'Foo bar'\n * sentenceCase('foo.bar'); //=> 'Foo bar'\n * sentenceCase('fooBar'); //=> 'Foo bar'\n * sentenceCase('FooBar'); //=> 'Foo bar'\n * sentenceCase('foo bar baz'); //=> 'Foo bar baz'\n**/\nexport const sentenceCase = (input: string) => {\n return cc.sentenceCase(input);\n};\n\n/**\n * Convert a string to upper cased sentence.\n * @deprecated use capitalCase instead\n * @example\n * toUcSentence('foo bar'); //=> 'Foo Bar'\n * toUcSentence('foo_bar'); //=> 'Foo Bar'\n * toUcSentence('foo-bar'); //=> 'Foo Bar'\n * toUcSentence('foo.bar'); //=> 'Foo Bar'\n * toUcSentence('fooBar'); //=> 'Foo Bar'\n * toUcSentence('FooBar'); //=> 'Foo Bar'\n * toUcSentence('foo bar baz'); //=> 'Foo Bar Baz'\n**/\nexport const toUcSentence = (input: string) => {\n return cc.capitalCase(input);\n};\n\n/**\n * Convert a string to upper cased sentence.\n * @example\n * capitalCase('foo bar'); //=> 'Foo Bar'\n * capitalCase('foo_bar'); //=> 'Foo Bar'\n * capitalCase('foo-bar'); //=> 'Foo Bar'\n * capitalCase('foo.bar'); //=> 'Foo Bar'\n * capitalCase('fooBar'); //=> 'Foo Bar'\n * capitalCase('FooBar'); //=> 'Foo Bar'\n * capitalCase('foo bar baz'); //=> 'Foo Bar Baz'\n**/\nexport const capitalCase = (input: string) => {\n return cc.capitalCase(input);\n};\n\n/**\n * Alias to \"toUcSentence\"\n * @deprecated use capitalCase instead\n**/\nexport const capitalize = (input: string) => toUcSentence(input);\n\n/**\n * Convert a string to lower cased sentence.\n * @deprecated use lowerSentenceCase instead\n * @example\n * toLcSentence('foo bar'); //=> 'foo bar'\n * toLcSentence('foo_bar'); //=> 'foo bar'\n * toLcSentence('foo-bar'); //=> 'foo bar'\n * toLcSentence('foo.bar'); //=> 'foo bar'\n * toLcSentence('fooBar'); //=> 'foo bar'\n * toLcSentence('FooBar'); //=> 'foo bar'\n * toLcSentence('Foo bar baz'); //=> 'foo bar baz'\n**/\nexport const toLcSentence = (input: string) => {\n return sentenceCase(input).toLowerCase();\n};\n\n/**\n * Convert a string to lower cased sentence.\n * @example\n * lowerSentenceCase('foo bar'); //=> 'foo bar'\n * lowerSentenceCase('foo_bar'); //=> 'foo bar'\n * lowerSentenceCase('foo-bar'); //=> 'foo bar'\n * lowerSentenceCase('foo.bar'); //=> 'foo bar'\n * lowerSentenceCase('fooBar'); //=> 'foo bar'\n * lowerSentenceCase('FooBar'); //=> 'foo bar'\n * lowerSentenceCase('Foo bar baz'); //=> 'foo bar baz'\n**/\nexport const lowerSentenceCase = (input: string) => {\n return sentenceCase(input).toLowerCase();\n};\n\n/**\n * Convert a table name to sql alias.\n * @example\n * toSqlAlias('foo bar'); //=> 'fb'\n * toSqlAlias('book'); //=> 'b'\n * toSqlAlias('article-category'); //=> 'ac'\n**/\nexport const toSqlAlias = (input: string): string => {\n return snakeCase(input)\n .split('_')\n .reduce((acc, word) => acc.concat(word[0]), '');\n};\n\nexport interface ToAbbreviationOptions {\n maxLength?: number;\n minLength?: number;\n lang?: 'uk' | 'ru' | 'mn';\n iteration?: number;\n}\n\n/**\n * Remove vowels from a word.\n * @param word - word to remove vowels from\n * @returns word without vowels\n * @example\n * removeVowels('foo'); //=> 'f'\n */\nexport const removeVowels = (word: string) => {\n return word.replace(/[aeiou]/gi, '');\n};\n\n/**\n * Convert a string to abbreviation.\n * @example\n * toAbbreviation('Sabbath Schook'); //=> 'SB'\n * toAbbreviation('Рожеві окуляри', {\n * lang: 'uk',\n * }); //=> 'RO'\n * toAbbreviation('Удивительные факты', {\n * lang: 'ru',\n * }); //=> 'UF'\n */\nexport const toAbbreviation = (input: string, opts?: ToAbbreviationOptions): string => {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const transliterator = (cyrillicToTranslit as any)(opts?.lang ? {\n preset: opts.lang,\n } : undefined);\n\n const words = transliterator\n .transform(input)\n .toUpperCase()\n .replace(/[^A-Z ]/g, '')\n .split(' ')\n .filter((word: string) => word.length > 0);\n\n // .map((word) =>).toUpperCase());\n\n let abbreviation = '';\n\n // Sabbath School => SS\n if (words.length > 1) {\n abbreviation = words.reduce((acc: string, word: string) => {\n if (word.length >= 1) {\n acc += word[0];\n }\n\n return acc;\n }, '');\n } else if (words.length === 1) {\n const word = words[0];\n\n // Sabbath => SBBTH\n if (word.length > 1) {\n abbreviation = word.slice(0, 1) + removeVowels(word.slice(1));\n } else {\n abbreviation = word;\n }\n }\n\n // If the maxLength option is set, trim the abbreviation before adding random characters and appending digits\n if (opts?.maxLength && !opts?.iteration) {\n abbreviation = abbreviation.slice(0, opts.maxLength);\n }\n\n // If the minLength option is set, ensure the abbreviation meets the minimum length by appending random characters before appending digits\n if (opts?.minLength && abbreviation.length < opts.minLength) {\n let charsNeeded = opts.minLength - abbreviation.length;\n if (opts?.iteration && opts?.iteration > 0) {\n charsNeeded -= 1;\n }\n\n if (charsNeeded > 0) {\n abbreviation += createRandomAbbreviationString(charsNeeded).toUpperCase();\n }\n }\n\n // Append a number based on the iteration option\n if (opts?.iteration) {\n if (opts?.maxLength) {\n // Calculate the maximum length the abbreviation can be, considering the digits and random characters\n const maxAbbrLength = opts.maxLength - 1;\n abbreviation = abbreviation.slice(0, maxAbbrLength);\n }\n\n abbreviation += opts.iteration;\n }\n\n return abbreviation;\n};\n","/**\n * Decline a noun based on a number.\n * @example\n * const words = ['элемент', 'элемента', 'элементов'];\n *\n * decline(0, words, false) // => 'элементов'\n * decline(24, words, false) // => 'элемента'\n * decline(21, words, false) // => 'элемент'\n *\n * decline(0, words) // => '0 элементов'\n * decline(24, words) // => '24 элемента'\n * decline(21, words) // => '21 элемент'\n */\nexport const decline = (n: number, words: string[], concat = true) => {\n const word =\n words[\n n % 100 > 4 && n % 100 < 20\n ? 2\n : [2, 0, 1, 1, 1, 2][n % 10 < 5 ? n % 10 : 5]\n ];\n\n return concat ? `${n} ${word}` : word;\n};\n","import * as pluralize from 'pluralize';\n\n/**\n * Change the plural form of a word to its singular form.\n * @example\n * pluralToSingular('books'); //=> 'book'\n */\nexport const singularToPlural = (input: string): string => {\n return pluralize.plural(input);\n};\n\n/**\n * Change the singular form of a word to its plural form.\n * @example\n * singularToPlural('book'); //=> 'books'\n */\nexport const pluralToSingular = (input: string): string => {\n return pluralize.singular(input);\n};\n\n/**\n * Checks if a given word is in its plural form.\n *\n * @param word - The word to check for plural form\n * @returns `true` if the word is plural, `false` if it's singular\n *\n * @example\n * ```typescript\n * isPlural(\"cats\"); // true\n * isPlural(\"cat\"); // false\n * ```\n */\nexport const isPlural = (word: string): boolean =>\n singularToPlural(word) === word;\n\n"],"mappings":"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"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
//
|
|
2
|
+
// @pkg 📦 DeepVision ESLint Config [NestJS]
|
|
3
|
+
// @version 📍 1.0.0
|
|
4
|
+
// @author 🐳 DeepVision Team <code@deepvision.team>
|
|
5
|
+
//
|
|
6
|
+
// Documentation reference: https://eslint.org/docs/user-guide/configuring/
|
|
7
|
+
// ESLint versions: https://eslint.org/blog/
|
|
8
|
+
//
|
|
9
|
+
// eslint-disable-next-line @typescript-eslint/no-require-imports, node/no-unpublished-require
|
|
10
|
+
const deep = require('@deepvision/eslint-plugin');
|
|
11
|
+
|
|
12
|
+
module.exports = [
|
|
13
|
+
...deep.default.configs.node,
|
|
14
|
+
];
|
package/package.json
ADDED
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@pcg/text-kit",
|
|
3
|
+
"version": "1.0.0-alpha.0",
|
|
4
|
+
"description": "Helps you transform text and words programmatically",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"main": "dist/index.js",
|
|
7
|
+
"types": "dist/index.d.ts",
|
|
8
|
+
"dependencies": {
|
|
9
|
+
"change-case": "^5.4.4",
|
|
10
|
+
"cyrillic-to-translit-js": "^3.2.1",
|
|
11
|
+
"nanoid": "^5.1.6",
|
|
12
|
+
"pluralize": "^8.0.0"
|
|
13
|
+
},
|
|
14
|
+
"devDependencies": {
|
|
15
|
+
"@types/pluralize": "^0.0.33",
|
|
16
|
+
"@vitest/ui": "^3.2.4",
|
|
17
|
+
"vitest": "^3.2.4"
|
|
18
|
+
},
|
|
19
|
+
"scripts": {
|
|
20
|
+
"dev": "tsdown --watch",
|
|
21
|
+
"build": "tsdown",
|
|
22
|
+
"test": "vitest run",
|
|
23
|
+
"test:watch": "vitest",
|
|
24
|
+
"lint": "eslint \"src/**/*.ts\""
|
|
25
|
+
}
|
|
26
|
+
}
|