Skip to content

Commit

Permalink
feat(danrevah#19): Add support for multiple fields & deep property
Browse files Browse the repository at this point in the history
  • Loading branch information
danrevah committed Jan 26, 2017
1 parent 376cff7 commit 60b5844
Show file tree
Hide file tree
Showing 3 changed files with 77 additions and 10 deletions.
27 changes: 23 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -578,16 +578,35 @@ Returns sample items randomly from array

### groupBy

Returns object of grouped by items by discriminator
Returns object of grouped by items by discriminator, and supports nested properties.

**Usage:** `array | groupBy: [string | Function]`
**Usage:** `array | groupBy: [string[] | string | Function]`

```typescript
this.arrayObject = [{elm: 'foo', value: 0}, {elm: 'bar', value: 1}, {elm: 'foo', value: 2}];
this.arrayObject = [
{id: 1, elm: 'foo', value: 0},
{id: 2, elm: 'bar', value: 1},
{id: 3, elm: 'foo', value: 2},
{id: 4, elm: 'foo', value: 2}
];

this.arrayNestedObject = [
{id: 1, prop: { deep: 'foo' }},
{id: 2, prop: { deep: 'bar' }},
{id: 3, prop: { deep: 'foo' }},
{id: 4, prop: { deep: 'bar' }}
];
```

```html
<p>{{ arrayObject | groupBy: 'elm' }}</p> <!-- Output: "{foo: [{elm: 'foo', value: 0}, {elm: 'foo', value: 2}], bar: [{elm: 'bar', value: 1}]}" -->
<p>{{ arrayObject | groupBy: 'elm' }}</p>
<!-- Output: "{foo: [{id: 1, elm: 'foo', value: 0}, {id: 3, elm: 'foo', value: 2}, {id: 4, elm: 'foo', value: 2}], bar: [{id: 2, elm: 'bar', value: 1}]}" -->

<p>{{ arrayObject | groupBy: ['elm', 'value'] }}</p>
<!-- Output: "{foo_0: [{elm: foo, value: 0}], bar_1: [{elm:bar,value: 1}], foo_2: [{elm:foo, value: 2}], bar_3: [{elm:bar, value: 3}]}" -->

<p>{{ arrayNestedObject | groupBy: 'prop.deep' }}</p>
<!-- Output:{foo: [{id: 1, prop: {deep: foo}}, {id: 3, prop: {deep: foo}}], bar: [{id: 2, prop: {deep: bar}}, {id: 4, prop: {deep: bar}}]}" -->
```

### filterBy
Expand Down
43 changes: 43 additions & 0 deletions src/app/pipes/array/group-by.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ describe('GroupByPipe', () => {
bar: [{key: 'bar'}, {key: 'bar'}]
});
});

it('allow function to be used as discriminator', () => {
const arrayWithDiscriminator = [{key: 'foo'}, {key: 'bar'}, {key: 'foo'}, {key: 'bar'}];
const result = pipe.transform(arrayWithDiscriminator, _ => _['key']);
Expand All @@ -36,4 +37,46 @@ describe('GroupByPipe', () => {
bar: [{key: 'bar'}, {key: 'bar'}]
});
});

it('group on multiple discriminator', () => {
const arrayWithDiscriminator = [
{id: 1, key: 'foo', type: 1},
{id: 2, key: 'foo', type: 2},
{id: 3, key: 'foo', type: 1},
{id: 4, key: 'foo', type: 2}
];
const result = pipe.transform(arrayWithDiscriminator, ['key', 'type']);
expect(result).toEqual({
foo_1: [{id: 1, key: 'foo', type: 1}, {id: 3, key: 'foo', type: 1}],
foo_2: [{id: 2, key: 'foo', type: 2}, {id: 4, key: 'foo', type: 2}]
});
});

it('group on deep property discriminator', () => {
const arrayWithDiscriminator = [
{id: 1, prop: { deep: 'foo' }},
{id: 2, prop: { deep: 'bar' }},
{id: 3, prop: { deep: 'foo' }},
{id: 4, prop: { deep: 'bar' }}
];
const result = pipe.transform(arrayWithDiscriminator, 'prop.deep');
expect(result).toEqual({
foo: [{id: 1, prop: { deep: 'foo' }}, {id: 3, prop: { deep: 'foo' }}],
bar: [{id: 2, prop: { deep: 'bar' }}, {id: 4, prop: { deep: 'bar' }}]
});
});

it('group on multiple deep property discriminator', () => {
const arrayWithDiscriminator = [
{id: 1, prop: { deep: 'foo', type: 1 }},
{id: 2, prop: { deep: 'foo', type: 2 }},
{id: 3, prop: { deep: 'foo', type: 1 }},
{id: 4, prop: { deep: 'foo', type: 2 }}
];
const result = pipe.transform(arrayWithDiscriminator, ['prop.deep', 'prop.type']);
expect(result).toEqual({
foo_1: [{id: 1, prop: { deep: 'foo', type: 1 }}, {id: 3, prop: { deep: 'foo', type: 1 }}],
foo_2: [{id: 2, prop: { deep: 'foo', type: 2 }}, {id: 4, prop: { deep: 'foo', type: 2 }}]
});
});
});
17 changes: 11 additions & 6 deletions src/app/pipes/array/group-by.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,19 +4,24 @@ import GeneralHelper from '../helpers/helpers';
@Pipe({name: 'groupBy'})
export class GroupByPipe implements PipeTransform {

transform(arr: any, ...args: any[]): any {
transform(arr: any, discriminator: any = []): any {
if (!Array.isArray(arr)) {
return arr;
}

return this.groupBy(arr, args[0]);
return this.groupBy(arr, discriminator);
}

private groupBy(list: any[], discriminator: Function | string) {
private groupBy(list: any[], discriminator: any) {
return list.reduce((acc, payload) => {
const key = GeneralHelper.isFunction(discriminator)
? (<Function>discriminator)(payload)
: payload[<string>discriminator];
let key;
if (GeneralHelper.isFunction(discriminator)) {
key = (<Function>discriminator)(payload);
} else if (Array.isArray(discriminator)) {
key = discriminator.map(k => GeneralHelper.extractDeepPropertyByMapKey(payload, k)).join('_');
} else {
key = GeneralHelper.extractDeepPropertyByMapKey(payload, <string>discriminator);
}

return acc[key] = Array.isArray(acc[key])
? acc[key].concat([payload])
Expand Down

0 comments on commit 60b5844

Please sign in to comment.