@nyaomaru/divider 1.9.18 → 1.9.19
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/README.md +13 -0
- package/dist/index.cjs +43 -2
- package/dist/index.d.cts +17 -1
- package/dist/index.d.ts +17 -1
- package/dist/index.js +41 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -209,9 +209,22 @@ Some common use cases are wrapped as presets for convenience.
|
|
|
209
209
|
| `emailDivider` | Divide email into [local-part, domain] (by '@') |
|
|
210
210
|
| `csvDivider` | Divide comma-separated strings, with quoted field support |
|
|
211
211
|
| `pathDivider` | Divide file paths by / or \| |
|
|
212
|
+
| `queryDivider` | Divide query strings into [key, value] pairs (URL-safe) |
|
|
212
213
|
|
|
213
214
|
[Presets detail](src/presets/README.md)
|
|
214
215
|
|
|
216
|
+
Example:
|
|
217
|
+
|
|
218
|
+
```ts
|
|
219
|
+
import { queryDivider } from '@nyaomaru/divider';
|
|
220
|
+
|
|
221
|
+
queryDivider('?q=hello+world');
|
|
222
|
+
// [['q', 'hello world']] // default: '+' treated as space and % decoded
|
|
223
|
+
|
|
224
|
+
queryDivider('q=hello+world', { mode: 'raw' });
|
|
225
|
+
// [['q', 'hello+world']] // raw mode keeps '+' and % as-is
|
|
226
|
+
```
|
|
227
|
+
|
|
215
228
|
## 🎯 General Options
|
|
216
229
|
|
|
217
230
|
| Option | Type | Default | Description |
|
package/dist/index.cjs
CHANGED
|
@@ -27,7 +27,8 @@ __export(index_exports, {
|
|
|
27
27
|
dividerLoop: () => dividerLoop,
|
|
28
28
|
dividerNumberString: () => dividerNumberString,
|
|
29
29
|
emailDivider: () => emailDivider,
|
|
30
|
-
pathDivider: () => pathDivider
|
|
30
|
+
pathDivider: () => pathDivider,
|
|
31
|
+
queryDivider: () => queryDivider
|
|
31
32
|
});
|
|
32
33
|
module.exports = __toCommonJS(index_exports);
|
|
33
34
|
|
|
@@ -509,6 +510,45 @@ function pathDivider(input, options = {}) {
|
|
|
509
510
|
const maybeTrimmed = trim ? segments.map((segment) => segment.trim()) : segments;
|
|
510
511
|
return collapse ? maybeTrimmed.filter((segment) => !isEmptyString(segment)) : maybeTrimmed;
|
|
511
512
|
}
|
|
513
|
+
|
|
514
|
+
// src/presets/query-divider.ts
|
|
515
|
+
function tryExtractQuery(input) {
|
|
516
|
+
try {
|
|
517
|
+
const url = new URL(input);
|
|
518
|
+
return url.search.startsWith("?") ? url.search.slice(1) : url.search;
|
|
519
|
+
} catch {
|
|
520
|
+
return input;
|
|
521
|
+
}
|
|
522
|
+
}
|
|
523
|
+
function stripLeadingQuestionMark(query) {
|
|
524
|
+
return query.startsWith("?") ? query.slice(1) : query;
|
|
525
|
+
}
|
|
526
|
+
function splitOnFirstEquals(part) {
|
|
527
|
+
const kv = dividePreserve(part, "=");
|
|
528
|
+
if (kv.length === 1) return [kv[0] ?? "", ""];
|
|
529
|
+
return [kv[0] ?? "", kv.slice(1).join("=")];
|
|
530
|
+
}
|
|
531
|
+
function decodeField(text, mode, trim) {
|
|
532
|
+
let t = text;
|
|
533
|
+
if (mode === "auto") {
|
|
534
|
+
t = t.replace(/\+/g, " ");
|
|
535
|
+
try {
|
|
536
|
+
t = decodeURIComponent(t);
|
|
537
|
+
} catch {
|
|
538
|
+
}
|
|
539
|
+
}
|
|
540
|
+
if (trim) t = t.trim();
|
|
541
|
+
return t;
|
|
542
|
+
}
|
|
543
|
+
function queryDivider(input, { mode = "auto", trim = false } = {}) {
|
|
544
|
+
if (input.length === 0) return [];
|
|
545
|
+
const query = stripLeadingQuestionMark(tryExtractQuery(input));
|
|
546
|
+
if (query.length === 0) return [];
|
|
547
|
+
return dividePreserve(query, "&").map((part) => {
|
|
548
|
+
const [key, value] = splitOnFirstEquals(part);
|
|
549
|
+
return [decodeField(key, mode, trim), decodeField(value, mode, trim)];
|
|
550
|
+
});
|
|
551
|
+
}
|
|
512
552
|
// Annotate the CommonJS export names for ESM import in node:
|
|
513
553
|
0 && (module.exports = {
|
|
514
554
|
csvDivider,
|
|
@@ -518,5 +558,6 @@ function pathDivider(input, options = {}) {
|
|
|
518
558
|
dividerLoop,
|
|
519
559
|
dividerNumberString,
|
|
520
560
|
emailDivider,
|
|
521
|
-
pathDivider
|
|
561
|
+
pathDivider,
|
|
562
|
+
queryDivider
|
|
522
563
|
});
|
package/dist/index.d.cts
CHANGED
|
@@ -158,6 +158,11 @@ type PathDividerOptions = Pick<DividerOptions, 'trim'> & {
|
|
|
158
158
|
/** Collapse empty segments produced by leading/trailing or repeated separators. */
|
|
159
159
|
collapse?: boolean;
|
|
160
160
|
};
|
|
161
|
+
type QueryDecodeMode = 'auto' | 'raw';
|
|
162
|
+
type QueryDividerOptions = Pick<DividerOptions, 'trim'> & {
|
|
163
|
+
/** Decoding mode: 'auto' applies standard URL decoding; 'raw' leaves values untouched. */
|
|
164
|
+
mode?: QueryDecodeMode;
|
|
165
|
+
};
|
|
161
166
|
|
|
162
167
|
/**
|
|
163
168
|
* Divides a CSV line into an array of fields, handling quoted values appropriately.
|
|
@@ -190,4 +195,15 @@ declare function emailDivider(input: string, options?: EmailDividerOptions): Div
|
|
|
190
195
|
*/
|
|
191
196
|
declare function pathDivider(input: string, options?: PathDividerOptions): DividerStringResult;
|
|
192
197
|
|
|
193
|
-
|
|
198
|
+
/**
|
|
199
|
+
* Divide a query string into key/value pairs.
|
|
200
|
+
* - Supports raw query (with or without leading '?').
|
|
201
|
+
* - Accepts full URLs (query extracted automatically).
|
|
202
|
+
* - Preserves empty keys/values and trailing separators.
|
|
203
|
+
* @param input Query string or full URL.
|
|
204
|
+
* @param options Parsing options: { mode?: 'auto' | 'raw'; trim?: boolean }.
|
|
205
|
+
* @returns Array of [key, value] string tuples in input order.
|
|
206
|
+
*/
|
|
207
|
+
declare function queryDivider(input: string, { mode, trim }?: QueryDividerOptions): DividerArrayResult;
|
|
208
|
+
|
|
209
|
+
export { type DividerArg, type DividerArgs, type DividerArrayResult, type DividerEmptyOptions, type DividerExcludeMode, type DividerInferredOptions, type DividerInput, type DividerLoopEmptyOptions, type DividerLoopOptions, type DividerLoopOptionsLike, type DividerOptions, type DividerResult, type DividerSeparator, type DividerSeparators, type DividerStringResult, type ExtractedDividerOptions, type NumericSeparator, type StringArrayInput, type StringInput, type StringSeparator, csvDivider, divider, dividerFirst, dividerLast, dividerLoop, dividerNumberString, emailDivider, pathDivider, queryDivider };
|
package/dist/index.d.ts
CHANGED
|
@@ -158,6 +158,11 @@ type PathDividerOptions = Pick<DividerOptions, 'trim'> & {
|
|
|
158
158
|
/** Collapse empty segments produced by leading/trailing or repeated separators. */
|
|
159
159
|
collapse?: boolean;
|
|
160
160
|
};
|
|
161
|
+
type QueryDecodeMode = 'auto' | 'raw';
|
|
162
|
+
type QueryDividerOptions = Pick<DividerOptions, 'trim'> & {
|
|
163
|
+
/** Decoding mode: 'auto' applies standard URL decoding; 'raw' leaves values untouched. */
|
|
164
|
+
mode?: QueryDecodeMode;
|
|
165
|
+
};
|
|
161
166
|
|
|
162
167
|
/**
|
|
163
168
|
* Divides a CSV line into an array of fields, handling quoted values appropriately.
|
|
@@ -190,4 +195,15 @@ declare function emailDivider(input: string, options?: EmailDividerOptions): Div
|
|
|
190
195
|
*/
|
|
191
196
|
declare function pathDivider(input: string, options?: PathDividerOptions): DividerStringResult;
|
|
192
197
|
|
|
193
|
-
|
|
198
|
+
/**
|
|
199
|
+
* Divide a query string into key/value pairs.
|
|
200
|
+
* - Supports raw query (with or without leading '?').
|
|
201
|
+
* - Accepts full URLs (query extracted automatically).
|
|
202
|
+
* - Preserves empty keys/values and trailing separators.
|
|
203
|
+
* @param input Query string or full URL.
|
|
204
|
+
* @param options Parsing options: { mode?: 'auto' | 'raw'; trim?: boolean }.
|
|
205
|
+
* @returns Array of [key, value] string tuples in input order.
|
|
206
|
+
*/
|
|
207
|
+
declare function queryDivider(input: string, { mode, trim }?: QueryDividerOptions): DividerArrayResult;
|
|
208
|
+
|
|
209
|
+
export { type DividerArg, type DividerArgs, type DividerArrayResult, type DividerEmptyOptions, type DividerExcludeMode, type DividerInferredOptions, type DividerInput, type DividerLoopEmptyOptions, type DividerLoopOptions, type DividerLoopOptionsLike, type DividerOptions, type DividerResult, type DividerSeparator, type DividerSeparators, type DividerStringResult, type ExtractedDividerOptions, type NumericSeparator, type StringArrayInput, type StringInput, type StringSeparator, csvDivider, divider, dividerFirst, dividerLast, dividerLoop, dividerNumberString, emailDivider, pathDivider, queryDivider };
|
package/dist/index.js
CHANGED
|
@@ -476,6 +476,45 @@ function pathDivider(input, options = {}) {
|
|
|
476
476
|
const maybeTrimmed = trim ? segments.map((segment) => segment.trim()) : segments;
|
|
477
477
|
return collapse ? maybeTrimmed.filter((segment) => !isEmptyString(segment)) : maybeTrimmed;
|
|
478
478
|
}
|
|
479
|
+
|
|
480
|
+
// src/presets/query-divider.ts
|
|
481
|
+
function tryExtractQuery(input) {
|
|
482
|
+
try {
|
|
483
|
+
const url = new URL(input);
|
|
484
|
+
return url.search.startsWith("?") ? url.search.slice(1) : url.search;
|
|
485
|
+
} catch {
|
|
486
|
+
return input;
|
|
487
|
+
}
|
|
488
|
+
}
|
|
489
|
+
function stripLeadingQuestionMark(query) {
|
|
490
|
+
return query.startsWith("?") ? query.slice(1) : query;
|
|
491
|
+
}
|
|
492
|
+
function splitOnFirstEquals(part) {
|
|
493
|
+
const kv = dividePreserve(part, "=");
|
|
494
|
+
if (kv.length === 1) return [kv[0] ?? "", ""];
|
|
495
|
+
return [kv[0] ?? "", kv.slice(1).join("=")];
|
|
496
|
+
}
|
|
497
|
+
function decodeField(text, mode, trim) {
|
|
498
|
+
let t = text;
|
|
499
|
+
if (mode === "auto") {
|
|
500
|
+
t = t.replace(/\+/g, " ");
|
|
501
|
+
try {
|
|
502
|
+
t = decodeURIComponent(t);
|
|
503
|
+
} catch {
|
|
504
|
+
}
|
|
505
|
+
}
|
|
506
|
+
if (trim) t = t.trim();
|
|
507
|
+
return t;
|
|
508
|
+
}
|
|
509
|
+
function queryDivider(input, { mode = "auto", trim = false } = {}) {
|
|
510
|
+
if (input.length === 0) return [];
|
|
511
|
+
const query = stripLeadingQuestionMark(tryExtractQuery(input));
|
|
512
|
+
if (query.length === 0) return [];
|
|
513
|
+
return dividePreserve(query, "&").map((part) => {
|
|
514
|
+
const [key, value] = splitOnFirstEquals(part);
|
|
515
|
+
return [decodeField(key, mode, trim), decodeField(value, mode, trim)];
|
|
516
|
+
});
|
|
517
|
+
}
|
|
479
518
|
export {
|
|
480
519
|
csvDivider,
|
|
481
520
|
divider,
|
|
@@ -484,5 +523,6 @@ export {
|
|
|
484
523
|
dividerLoop,
|
|
485
524
|
dividerNumberString,
|
|
486
525
|
emailDivider,
|
|
487
|
-
pathDivider
|
|
526
|
+
pathDivider,
|
|
527
|
+
queryDivider
|
|
488
528
|
};
|