ngx-transforms 0.1.0 → 0.2.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.
@@ -315,22 +315,6 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImpor
315
315
  * @param {boolean} [isReplace=true] - Whether to perform replacement (true) or only highlight matches (false).
316
316
  *
317
317
  * @returns {string | SafeHtml} - Returns the transformed string or SafeHtml with highlights.
318
- *
319
- * @example
320
- * {{ 'Hello World' | replace:'World':'Universe' }}
321
- * // Output: Hello Universe
322
- *
323
- * {{ 'test123' | replace:/\d+/g:'X':'highlight' }}
324
- * // Output: test<span class="highlight">X</span>
325
- *
326
- * {{ 'Angular is great' | replace:'great':'awesome':'highlight':true }}
327
- * // Output: Angular is <span class="highlight">awesome</span>
328
- *
329
- * {{ 'Angular is great' | replace:'great':'awesome':'highlight':false }}
330
- * // Output: Angular is <span class="highlight">great</span>
331
- *
332
- * <div [innerHTML]="'Angular is great' | replace:'great':'awesome':'highlight':false"></div>
333
- * // Renders: Angular is <span class="highlight">great</span>
334
318
  */
335
319
  class ReplacePipe {
336
320
  sanitizer = inject(DomSanitizer);
@@ -1204,6 +1188,179 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImpor
1204
1188
  }]
1205
1189
  }] });
1206
1190
 
1191
+ /**
1192
+ * DiffPipe: Returns elements present in the first array but not in the second.
1193
+ *
1194
+ * Supports primitives and objects by property key with dot notation.
1195
+ *
1196
+ * @param {unknown[]} value - The source array.
1197
+ * @param {unknown[]} compared - The array to compare against.
1198
+ * @param {string} [key] - Optional property path for object comparison (supports dot notation).
1199
+ *
1200
+ * @returns {unknown[]} - Elements in value that are not in compared.
1201
+ *
1202
+ * @example
1203
+ * {{ [1, 2, 3, 4, 5] | diff:[3, 4, 5, 6] }} // [1, 2]
1204
+ * {{ allUsers | diff:activeUsers:'id' }} // inactive users
1205
+ * {{ orders | diff:shipped:'meta.trackingId' }} // unshipped orders
1206
+ */
1207
+ class DiffPipe {
1208
+ transform(value, compared, key) {
1209
+ if (!Array.isArray(value)) {
1210
+ return [];
1211
+ }
1212
+ if (!Array.isArray(compared) || compared.length === 0) {
1213
+ return [...value];
1214
+ }
1215
+ if (!key) {
1216
+ const comparedSet = new Set(compared);
1217
+ return value.filter(item => !comparedSet.has(item));
1218
+ }
1219
+ const comparedSet = new Set(compared.map(item => this.getNestedValue(item, key)));
1220
+ return value.filter(item => {
1221
+ const val = this.getNestedValue(item, key);
1222
+ return !comparedSet.has(val);
1223
+ });
1224
+ }
1225
+ getNestedValue(obj, path) {
1226
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1227
+ }
1228
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: DiffPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1229
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: DiffPipe, isStandalone: true, name: "diff" });
1230
+ }
1231
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: DiffPipe, decorators: [{
1232
+ type: Pipe,
1233
+ args: [{
1234
+ name: 'diff',
1235
+ standalone: true,
1236
+ }]
1237
+ }] });
1238
+
1239
+ /**
1240
+ * EveryPipe: Checks if all elements in an array satisfy a condition.
1241
+ *
1242
+ * Supports primitives (equality check) and objects by property key with dot notation.
1243
+ *
1244
+ * @param {unknown[]} value - The array to check.
1245
+ * @param {unknown} match - The value to match against.
1246
+ * @param {string} [key] - Optional property path to check (supports dot notation).
1247
+ *
1248
+ * @returns {boolean} - True if all elements match, false otherwise.
1249
+ *
1250
+ * @example
1251
+ * {{ [true, true, true] | every:true }} // true
1252
+ * {{ users | every:'active':'status' }} // are all users active?
1253
+ * {{ orders | every:'shipped':'meta.state' }} // are all orders shipped?
1254
+ */
1255
+ class EveryPipe {
1256
+ transform(value, match, key) {
1257
+ if (!Array.isArray(value) || value.length === 0) {
1258
+ return false;
1259
+ }
1260
+ if (!key) {
1261
+ return value.every(item => item === match);
1262
+ }
1263
+ return value.every(item => this.getNestedValue(item, key) === match);
1264
+ }
1265
+ getNestedValue(obj, path) {
1266
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1267
+ }
1268
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: EveryPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1269
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: EveryPipe, isStandalone: true, name: "every" });
1270
+ }
1271
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: EveryPipe, decorators: [{
1272
+ type: Pipe,
1273
+ args: [{
1274
+ name: 'every',
1275
+ standalone: true,
1276
+ }]
1277
+ }] });
1278
+
1279
+ /**
1280
+ * IntersectionPipe: Returns elements common to both arrays.
1281
+ *
1282
+ * Supports primitives and objects by property key with dot notation.
1283
+ *
1284
+ * @param {unknown[]} value - The first array.
1285
+ * @param {unknown[]} compared - The second array.
1286
+ * @param {string} [key] - Optional property path for object comparison (supports dot notation).
1287
+ *
1288
+ * @returns {unknown[]} - Elements present in both arrays.
1289
+ *
1290
+ * @example
1291
+ * {{ [1, 2, 3, 4] | intersection:[3, 4, 5, 6] }} // [3, 4]
1292
+ * {{ teamA | intersection:teamB:'id' }} // shared members
1293
+ * {{ required | intersection:granted:'meta.scope' }} // matched permissions
1294
+ */
1295
+ class IntersectionPipe {
1296
+ transform(value, compared, key) {
1297
+ if (!Array.isArray(value)) {
1298
+ return [];
1299
+ }
1300
+ if (!Array.isArray(compared) || compared.length === 0) {
1301
+ return [];
1302
+ }
1303
+ if (!key) {
1304
+ const comparedSet = new Set(compared);
1305
+ return value.filter(item => comparedSet.has(item));
1306
+ }
1307
+ const comparedSet = new Set(compared.map(item => this.getNestedValue(item, key)));
1308
+ return value.filter(item => {
1309
+ const val = this.getNestedValue(item, key);
1310
+ return comparedSet.has(val);
1311
+ });
1312
+ }
1313
+ getNestedValue(obj, path) {
1314
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1315
+ }
1316
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: IntersectionPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1317
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: IntersectionPipe, isStandalone: true, name: "intersection" });
1318
+ }
1319
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: IntersectionPipe, decorators: [{
1320
+ type: Pipe,
1321
+ args: [{
1322
+ name: 'intersection',
1323
+ standalone: true,
1324
+ }]
1325
+ }] });
1326
+
1327
+ /**
1328
+ * ChunkPipe: Splits an array into smaller arrays of a specified size.
1329
+ *
1330
+ * @param {unknown[]} value - The array to split.
1331
+ * @param {number} [size=1] - The size of each chunk.
1332
+ *
1333
+ * @returns {unknown[][]} - An array of chunks.
1334
+ *
1335
+ * @example
1336
+ * {{ [1, 2, 3, 4, 5] | chunk:2 }} // [[1, 2], [3, 4], [5]]
1337
+ * {{ [1, 2, 3, 4, 5, 6] | chunk:3 }} // [[1, 2, 3], [4, 5, 6]]
1338
+ */
1339
+ class ChunkPipe {
1340
+ transform(value, size = 1) {
1341
+ if (!Array.isArray(value) || value.length === 0) {
1342
+ return [];
1343
+ }
1344
+ if (size <= 0) {
1345
+ return [];
1346
+ }
1347
+ const result = [];
1348
+ for (let i = 0; i < value.length; i += size) {
1349
+ result.push(value.slice(i, i + size));
1350
+ }
1351
+ return result;
1352
+ }
1353
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: ChunkPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1354
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: ChunkPipe, isStandalone: true, name: "chunk" });
1355
+ }
1356
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: ChunkPipe, decorators: [{
1357
+ type: Pipe,
1358
+ args: [{
1359
+ name: 'chunk',
1360
+ standalone: true
1361
+ }]
1362
+ }] });
1363
+
1207
1364
  /**
1208
1365
  * FlattenPipe: Flattens nested arrays to a specified depth.
1209
1366
  *
@@ -1235,6 +1392,46 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImpor
1235
1392
  }]
1236
1393
  }] });
1237
1394
 
1395
+ /**
1396
+ * GroupByPipe: Groups array elements by a property value.
1397
+ *
1398
+ * @param {unknown[]} value - The array to group.
1399
+ * @param {string} key - Property path to group by (supports dot notation).
1400
+ *
1401
+ * @returns {Record<string, unknown[]>} - An object where keys are group names and values are arrays.
1402
+ *
1403
+ * @example
1404
+ * {{ users | groupBy:'role' }} // { admin: [...], editor: [...] }
1405
+ * {{ orders | groupBy:'customer.city' }} // { 'New York': [...], 'London': [...] }
1406
+ */
1407
+ class GroupByPipe {
1408
+ transform(value, key) {
1409
+ if (!Array.isArray(value) || !key) {
1410
+ return {};
1411
+ }
1412
+ return value.reduce((groups, item) => {
1413
+ const groupKey = String(this.getNestedValue(item, key) ?? 'undefined');
1414
+ if (!groups[groupKey]) {
1415
+ groups[groupKey] = [];
1416
+ }
1417
+ groups[groupKey].push(item);
1418
+ return groups;
1419
+ }, {});
1420
+ }
1421
+ getNestedValue(obj, path) {
1422
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1423
+ }
1424
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: GroupByPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1425
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: GroupByPipe, isStandalone: true, name: "groupBy" });
1426
+ }
1427
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: GroupByPipe, decorators: [{
1428
+ type: Pipe,
1429
+ args: [{
1430
+ name: 'groupBy',
1431
+ standalone: true,
1432
+ }]
1433
+ }] });
1434
+
1238
1435
  /**
1239
1436
  * InitialPipe: Returns all elements except the last n.
1240
1437
  *
@@ -1272,6 +1469,130 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImpor
1272
1469
  }]
1273
1470
  }] });
1274
1471
 
1472
+ /**
1473
+ * OrderByPipe: Sorts an array by a property value.
1474
+ *
1475
+ * @param {unknown[]} value - The array to sort.
1476
+ * @param {string} key - Property path to sort by (supports dot notation).
1477
+ * @param {string} [direction='asc'] - Sort direction: 'asc' or 'desc'.
1478
+ *
1479
+ * @returns {unknown[]} - A new sorted array.
1480
+ *
1481
+ * @example
1482
+ * {{ users | orderBy:'name' }} // sorted A-Z
1483
+ * {{ users | orderBy:'name':'desc' }} // sorted Z-A
1484
+ * {{ users | orderBy:'age':'asc' }} // sorted by age
1485
+ */
1486
+ class OrderByPipe {
1487
+ transform(value, key, direction = 'asc') {
1488
+ if (!Array.isArray(value) || value.length <= 1 || !key) {
1489
+ return Array.isArray(value) ? [...value] : [];
1490
+ }
1491
+ const dir = direction === 'desc' ? -1 : 1;
1492
+ return [...value].sort((a, b) => {
1493
+ const valA = this.getNestedValue(a, key);
1494
+ const valB = this.getNestedValue(b, key);
1495
+ if (valA === valB)
1496
+ return 0;
1497
+ if (valA === null || valA === undefined)
1498
+ return 1;
1499
+ if (valB === null || valB === undefined)
1500
+ return -1;
1501
+ if (typeof valA === 'string' && typeof valB === 'string') {
1502
+ return valA.localeCompare(valB) * dir;
1503
+ }
1504
+ if (typeof valA === 'number' && typeof valB === 'number') {
1505
+ return (valA - valB) * dir;
1506
+ }
1507
+ return String(valA).localeCompare(String(valB)) * dir;
1508
+ });
1509
+ }
1510
+ getNestedValue(obj, path) {
1511
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1512
+ }
1513
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: OrderByPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1514
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: OrderByPipe, isStandalone: true, name: "orderBy" });
1515
+ }
1516
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: OrderByPipe, decorators: [{
1517
+ type: Pipe,
1518
+ args: [{
1519
+ name: 'orderBy',
1520
+ standalone: true,
1521
+ }]
1522
+ }] });
1523
+
1524
+ /**
1525
+ * PluckPipe: Extracts a property value from every object in an array.
1526
+ *
1527
+ * @param {unknown[]} value - The array of objects.
1528
+ * @param {string} key - Property path to extract (supports dot notation).
1529
+ *
1530
+ * @returns {unknown[]} - An array of the extracted values.
1531
+ *
1532
+ * @example
1533
+ * {{ users | pluck:'name' }} // ['Alice', 'Bob', 'Carol']
1534
+ * {{ orders | pluck:'customer.email' }} // ['a@test.com', 'b@test.com']
1535
+ */
1536
+ class PluckPipe {
1537
+ transform(value, key) {
1538
+ if (!Array.isArray(value) || !key) {
1539
+ return [];
1540
+ }
1541
+ return value.map(item => this.getNestedValue(item, key));
1542
+ }
1543
+ getNestedValue(obj, path) {
1544
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1545
+ }
1546
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: PluckPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1547
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: PluckPipe, isStandalone: true, name: "pluck" });
1548
+ }
1549
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: PluckPipe, decorators: [{
1550
+ type: Pipe,
1551
+ args: [{
1552
+ name: 'pluck',
1553
+ standalone: true,
1554
+ }]
1555
+ }] });
1556
+
1557
+ /**
1558
+ * RangePipe: Generates a numeric sequence array.
1559
+ *
1560
+ * @param {number} value - The number of items to generate (or the end value when start is provided).
1561
+ * @param {number} [start=0] - The starting number.
1562
+ * @param {number} [step=1] - The increment between each number.
1563
+ *
1564
+ * @returns {number[]} - An array of sequential numbers.
1565
+ *
1566
+ * @example
1567
+ * {{ 5 | range }} // [0, 1, 2, 3, 4]
1568
+ * {{ 5 | range:1 }} // [1, 2, 3, 4, 5]
1569
+ * {{ 10 | range:0:2 }} // [0, 2, 4, 6, 8]
1570
+ */
1571
+ class RangePipe {
1572
+ transform(value, start = 0, step = 1) {
1573
+ if (typeof value !== 'number' || isNaN(value) || value <= 0) {
1574
+ return [];
1575
+ }
1576
+ if (step === 0) {
1577
+ return [];
1578
+ }
1579
+ const result = [];
1580
+ for (let i = 0; i < value; i++) {
1581
+ result.push(start + i * step);
1582
+ }
1583
+ return result;
1584
+ }
1585
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: RangePipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1586
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: RangePipe, isStandalone: true, name: "range" });
1587
+ }
1588
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: RangePipe, decorators: [{
1589
+ type: Pipe,
1590
+ args: [{
1591
+ name: 'range',
1592
+ standalone: true,
1593
+ }]
1594
+ }] });
1595
+
1275
1596
  /**
1276
1597
  * ReversePipe: Reverses the characters in a string.
1277
1598
  *
@@ -1512,6 +1833,216 @@ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImpor
1512
1833
  }]
1513
1834
  }] });
1514
1835
 
1836
+ /**
1837
+ * WithoutPipe: Excludes specified elements from an array.
1838
+ *
1839
+ * Supports primitives and objects by property key with dot notation.
1840
+ *
1841
+ * @param {unknown[]} value - The array to filter.
1842
+ * @param {unknown[]} excludes - Values to exclude.
1843
+ * @param {string} [key] - Optional property path for object comparison (supports dot notation).
1844
+ *
1845
+ * @returns {unknown[]} - A new array without the excluded elements.
1846
+ *
1847
+ * @example
1848
+ * {{ [1, 2, 3, 4, 5] | without:[2, 4] }} // [1, 3, 5]
1849
+ * {{ users | without:['banned']:'status' }} // active users
1850
+ * {{ orders | without:['cancelled']:'meta.status' }} // non-cancelled orders
1851
+ */
1852
+ class WithoutPipe {
1853
+ transform(value, excludes, key) {
1854
+ if (!Array.isArray(value)) {
1855
+ return [];
1856
+ }
1857
+ if (!Array.isArray(excludes) || excludes.length === 0) {
1858
+ return [...value];
1859
+ }
1860
+ const excludeSet = new Set(excludes);
1861
+ if (!key) {
1862
+ return value.filter(item => !excludeSet.has(item));
1863
+ }
1864
+ return value.filter(item => {
1865
+ const val = this.getNestedValue(item, key);
1866
+ return !excludeSet.has(val);
1867
+ });
1868
+ }
1869
+ getNestedValue(obj, path) {
1870
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1871
+ }
1872
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: WithoutPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1873
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: WithoutPipe, isStandalone: true, name: "without" });
1874
+ }
1875
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: WithoutPipe, decorators: [{
1876
+ type: Pipe,
1877
+ args: [{
1878
+ name: 'without',
1879
+ standalone: true,
1880
+ }]
1881
+ }] });
1882
+
1883
+ /**
1884
+ * SomePipe: Checks if at least one element in an array satisfies a condition.
1885
+ *
1886
+ * Supports primitives (equality check) and objects by property key with dot notation.
1887
+ *
1888
+ * @param {unknown[]} value - The array to check.
1889
+ * @param {unknown} match - The value to match against.
1890
+ * @param {string} [key] - Optional property path to check (supports dot notation).
1891
+ *
1892
+ * @returns {boolean} - True if at least one element matches, false otherwise.
1893
+ *
1894
+ * @example
1895
+ * {{ [false, false, true] | some:true }} // true
1896
+ * {{ users | some:'admin':'role' }} // any admins?
1897
+ * {{ orders | some:'failed':'meta.status' }} // any failures?
1898
+ */
1899
+ class SomePipe {
1900
+ transform(value, match, key) {
1901
+ if (!Array.isArray(value) || value.length === 0) {
1902
+ return false;
1903
+ }
1904
+ if (!key) {
1905
+ return value.some(item => item === match);
1906
+ }
1907
+ return value.some(item => this.getNestedValue(item, key) === match);
1908
+ }
1909
+ getNestedValue(obj, path) {
1910
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1911
+ }
1912
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: SomePipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1913
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: SomePipe, isStandalone: true, name: "some" });
1914
+ }
1915
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: SomePipe, decorators: [{
1916
+ type: Pipe,
1917
+ args: [{
1918
+ name: 'some',
1919
+ standalone: true,
1920
+ }]
1921
+ }] });
1922
+
1923
+ /**
1924
+ * UnionPipe: Combines two arrays, keeping only unique elements.
1925
+ *
1926
+ * Supports primitives and objects by property key with dot notation.
1927
+ *
1928
+ * @param {unknown[]} value - The first array.
1929
+ * @param {unknown[]} other - The second array.
1930
+ * @param {string} [key] - Optional property path for uniqueness check (supports dot notation).
1931
+ *
1932
+ * @returns {unknown[]} - A merged array with duplicates removed.
1933
+ *
1934
+ * @example
1935
+ * {{ [1, 2, 3] | union:[3, 4, 5] }} // [1, 2, 3, 4, 5]
1936
+ * {{ admins | union:editors:'id' }} // all unique users
1937
+ * {{ local | union:remote:'meta.uuid' }} // merged records
1938
+ */
1939
+ class UnionPipe {
1940
+ transform(value, other, key) {
1941
+ if (!Array.isArray(value) && !Array.isArray(other)) {
1942
+ return [];
1943
+ }
1944
+ const first = Array.isArray(value) ? value : [];
1945
+ const second = Array.isArray(other) ? other : [];
1946
+ if (!key) {
1947
+ const seen = new Set();
1948
+ const result = [];
1949
+ for (const item of [...first, ...second]) {
1950
+ if (!seen.has(item)) {
1951
+ seen.add(item);
1952
+ result.push(item);
1953
+ }
1954
+ }
1955
+ return result;
1956
+ }
1957
+ const seen = new Set();
1958
+ const result = [];
1959
+ for (const item of [...first, ...second]) {
1960
+ const val = this.getNestedValue(item, key);
1961
+ if (!seen.has(val)) {
1962
+ seen.add(val);
1963
+ result.push(item);
1964
+ }
1965
+ }
1966
+ return result;
1967
+ }
1968
+ getNestedValue(obj, path) {
1969
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
1970
+ }
1971
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: UnionPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
1972
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: UnionPipe, isStandalone: true, name: "union" });
1973
+ }
1974
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: UnionPipe, decorators: [{
1975
+ type: Pipe,
1976
+ args: [{
1977
+ name: 'union',
1978
+ standalone: true,
1979
+ }]
1980
+ }] });
1981
+
1982
+ /**
1983
+ * FilterByPipe: Filters an array by matching a search term against object
1984
+ properties.
1985
+ *
1986
+ * @param {unknown[]} value - The array to filter.
1987
+ * @param {string} search - The search term.
1988
+ * @param {string} [key] - Property to search in. If omitted, searches all string
1989
+ properties.
1990
+ *
1991
+ * @returns {unknown[]} - Filtered array with matching items.
1992
+ *
1993
+ * @example
1994
+ * {{ users | filterBy:'alice':'name' }} // users with 'alice' in name
1995
+ * {{ users | filterBy:'admin':'role' }} // users with role 'admin'
1996
+ * {{ users | filterBy:'bob' }} // search all properties for 'bob'
1997
+ */
1998
+ class FilterByPipe {
1999
+ transform(value, search, key) {
2000
+ if (!Array.isArray(value) || !search) {
2001
+ return Array.isArray(value) ? [...value] : [];
2002
+ }
2003
+ const term = String(search).toLowerCase();
2004
+ if (key) {
2005
+ return value.filter(item => {
2006
+ const val = this.getNestedValue(item, key);
2007
+ return val !== undefined && val !== null
2008
+ && String(val).toLowerCase().includes(term);
2009
+ });
2010
+ }
2011
+ return value.filter(item => {
2012
+ if (typeof item === 'object' && item !== null) {
2013
+ return this.searchObject(item, term);
2014
+ }
2015
+ return String(item).toLowerCase().includes(term);
2016
+ });
2017
+ }
2018
+ searchObject(obj, term) {
2019
+ return Object.values(obj).some(val => {
2020
+ if (typeof val === 'string') {
2021
+ return val.toLowerCase().includes(term);
2022
+ }
2023
+ if (typeof val === 'number' || typeof val === 'boolean') {
2024
+ return String(val).toLowerCase().includes(term);
2025
+ }
2026
+ if (typeof val === 'object' && val !== null) {
2027
+ return this.searchObject(val, term);
2028
+ }
2029
+ return false;
2030
+ });
2031
+ }
2032
+ getNestedValue(obj, path) {
2033
+ return path.split('.').reduce((current, segment) => current?.[segment], obj);
2034
+ }
2035
+ static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: FilterByPipe, deps: [], target: i0.ɵɵFactoryTarget.Pipe });
2036
+ static ɵpipe = i0.ɵɵngDeclarePipe({ minVersion: "14.0.0", version: "21.1.3", ngImport: i0, type: FilterByPipe, isStandalone: true, name: "filterBy" });
2037
+ }
2038
+ i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "21.1.3", ngImport: i0, type: FilterByPipe, decorators: [{
2039
+ type: Pipe,
2040
+ args: [{
2041
+ name: 'filterBy',
2042
+ standalone: true,
2043
+ }]
2044
+ }] });
2045
+
1515
2046
  // Text
1516
2047
  const ALL_PIPES = [
1517
2048
  // Text
@@ -1543,14 +2074,26 @@ const ALL_PIPES = [
1543
2074
  TextToSpeechPipe,
1544
2075
  TimeAgoPipePipe,
1545
2076
  // Array
2077
+ ChunkPipe,
2078
+ DiffPipe,
2079
+ EveryPipe,
2080
+ IntersectionPipe,
1546
2081
  Flatten,
2082
+ GroupByPipe,
1547
2083
  InitialPipe,
2084
+ OrderByPipe,
2085
+ PluckPipe,
2086
+ RangePipe,
1548
2087
  ReversePipe,
1549
2088
  SamplePipe,
1550
2089
  ShufflePipe,
1551
2090
  TailPipe,
1552
2091
  TruthifyPipe,
1553
2092
  UniquePipe,
2093
+ WithoutPipe,
2094
+ SomePipe,
2095
+ UnionPipe,
2096
+ FilterByPipe
1554
2097
  ];
1555
2098
 
1556
2099
  // Text
@@ -1559,5 +2102,5 @@ const ALL_PIPES = [
1559
2102
  * Generated bundle index. Do not edit.
1560
2103
  */
1561
2104
 
1562
- export { ALL_PIPES, AsciiArtPipe, BarcodePipe, CamelCasePipe, ColorConvertPipe, CountPipe, CreditCardMaskPipe, DeviceTypePipe, EmailMaskPipe, Flatten, GravatarPipe, HighlightPipe, HtmlEscapePipe, HtmlSanitizePipe, InitialPipe, InitialsPipe, IpAddressMaskPipe, JsonPrettyPipe, KebabCasePipe, MorseCodePipe, QrCodePipe, ReplacePipe, ReversePipe, SamplePipe, ShufflePipe, SnakeCasePipe, TailPipe, TextToSpeechPipe, TimeAgoPipePipe, TitleCasePipe, TruncatePipe, TruthifyPipe, UniquePipe };
2105
+ export { ALL_PIPES, AsciiArtPipe, BarcodePipe, CamelCasePipe, ChunkPipe, ColorConvertPipe, CountPipe, CreditCardMaskPipe, DeviceTypePipe, DiffPipe, EmailMaskPipe, EveryPipe, FilterByPipe, Flatten, GravatarPipe, GroupByPipe, HighlightPipe, HtmlEscapePipe, HtmlSanitizePipe, InitialPipe, InitialsPipe, IntersectionPipe, IpAddressMaskPipe, JsonPrettyPipe, KebabCasePipe, MorseCodePipe, OrderByPipe, PluckPipe, QrCodePipe, RangePipe, ReplacePipe, ReversePipe, SamplePipe, ShufflePipe, SnakeCasePipe, SomePipe, TailPipe, TextToSpeechPipe, TimeAgoPipePipe, TitleCasePipe, TruncatePipe, TruthifyPipe, UnionPipe, UniquePipe, WithoutPipe };
1563
2106
  //# sourceMappingURL=ngx-transforms.mjs.map