Browse Source

feat(admin-ui): Enable deletion of Customers from customer list

Closes #360
Michael Bromley 5 years ago
parent
commit
d1b0b9e043

+ 19 - 0
packages/admin-ui/src/lib/core/src/common/generated-types.ts

@@ -4266,6 +4266,19 @@ export type UpdateCustomerMutation = (
   ) }
 );
 
+export type DeleteCustomerMutationVariables = {
+  id: Scalars['ID'];
+};
+
+
+export type DeleteCustomerMutation = (
+  { __typename?: 'Mutation' }
+  & { deleteCustomer: (
+    { __typename?: 'DeletionResponse' }
+    & Pick<DeletionResponse, 'result' | 'message'>
+  ) }
+);
+
 export type CreateCustomerAddressMutationVariables = {
   customerId: Scalars['ID'];
   input: CreateAddressInput;
@@ -6652,6 +6665,12 @@ export namespace UpdateCustomer {
   export type UpdateCustomer = CustomerFragment;
 }
 
+export namespace DeleteCustomer {
+  export type Variables = DeleteCustomerMutationVariables;
+  export type Mutation = DeleteCustomerMutation;
+  export type DeleteCustomer = DeleteCustomerMutation['deleteCustomer'];
+}
+
 export namespace CreateCustomerAddress {
   export type Variables = CreateCustomerAddressMutationVariables;
   export type Mutation = CreateCustomerAddressMutation;

+ 9 - 0
packages/admin-ui/src/lib/core/src/data/definitions/customer-definitions.ts

@@ -103,6 +103,15 @@ export const UPDATE_CUSTOMER = gql`
     ${CUSTOMER_FRAGMENT}
 `;
 
+export const DELETE_CUSTOMER = gql`
+    mutation DeleteCustomer($id: ID!) {
+        deleteCustomer(id: $id) {
+            result
+            message
+        }
+    }
+`;
+
 export const CREATE_CUSTOMER_ADDRESS = gql`
     mutation CreateCustomerAddress($customerId: ID!, $input: CreateAddressInput!) {
         createCustomerAddress(customerId: $customerId, input: $input) {

+ 9 - 0
packages/admin-ui/src/lib/core/src/data/providers/customer-data.service.ts

@@ -3,6 +3,7 @@ import {
     CreateCustomer,
     CreateCustomerAddress,
     CreateCustomerInput,
+    DeleteCustomer,
     GetCustomer,
     GetCustomerList,
     OrderListOptions,
@@ -14,6 +15,7 @@ import {
 import {
     CREATE_CUSTOMER,
     CREATE_CUSTOMER_ADDRESS,
+    DELETE_CUSTOMER,
     GET_CUSTOMER,
     GET_CUSTOMER_LIST,
     UPDATE_CUSTOMER,
@@ -63,6 +65,13 @@ export class CustomerDataService {
         );
     }
 
+    deleteCustomer(id: string) {
+        return this.baseDataService.mutate<DeleteCustomer.Mutation, DeleteCustomer.Variables>(
+            DELETE_CUSTOMER,
+            { id },
+        );
+    }
+
     createCustomerAddress(customerId: string, input: CreateAddressInput) {
         return this.baseDataService.mutate<CreateCustomerAddress.Mutation, CreateCustomerAddress.Variables>(
             CREATE_CUSTOMER_ADDRESS,

+ 21 - 0
packages/admin-ui/src/lib/customer/src/components/customer-list/customer-list.component.html

@@ -29,6 +29,7 @@
     <vdr-dt-column [expand]="true">{{ 'customer.email-address' | translate }}</vdr-dt-column>
     <vdr-dt-column>{{ 'customer.customer-type' | translate }}</vdr-dt-column>
     <vdr-dt-column></vdr-dt-column>
+    <vdr-dt-column></vdr-dt-column>
     <ng-template let-customer="item">
         <td class="left align-middle">
             {{ customer.title }} {{ customer.firstName }} {{ customer.lastName }}
@@ -44,5 +45,25 @@
                 [linkTo]="['./', customer.id]"
             ></vdr-table-row-action>
         </td>
+        <td>
+            <vdr-dropdown>
+                <button type="button" class="btn btn-link btn-sm" vdrDropdownTrigger>
+                    {{ 'common.actions' | translate }}
+                    <clr-icon shape="caret down"></clr-icon>
+                </button>
+                <vdr-dropdown-menu vdrPosition="bottom-right">
+                    <button
+                        type="button"
+                        class="delete-button"
+                        (click)="deleteCustomer(customer)"
+                        [disabled]="!('DeleteCustomer' | hasPermission)"
+                        vdrDropdownItem
+                    >
+                        <clr-icon shape="trash" class="is-danger"></clr-icon>
+                        {{ 'common.delete' | translate }}
+                    </button>
+                </vdr-dropdown-menu>
+            </vdr-dropdown>
+        </td>
     </ng-template>
 </vdr-data-table>

+ 45 - 11
packages/admin-ui/src/lib/customer/src/components/customer-list/customer-list.component.ts

@@ -1,12 +1,17 @@
 import { Component, OnInit } from '@angular/core';
 import { FormControl } from '@angular/forms';
 import { ActivatedRoute, Router } from '@angular/router';
+import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
+import {
+    BaseListComponent,
+    DataService,
+    GetCustomerList,
+    ModalService,
+    NotificationService,
+} from '@vendure/admin-ui/core';
 import { SortOrder } from '@vendure/common/lib/generated-shop-types';
-import { debounceTime, takeUntil } from 'rxjs/operators';
-
-import { BaseListComponent } from '@vendure/admin-ui/core';
-import { GetCustomerList } from '@vendure/admin-ui/core';
-import { DataService } from '@vendure/admin-ui/core';
+import { EMPTY } from 'rxjs';
+import { debounceTime, switchMap, takeUntil } from 'rxjs/operators';
 
 @Component({
     selector: 'vdr-customer-list',
@@ -16,11 +21,17 @@ import { DataService } from '@vendure/admin-ui/core';
 export class CustomerListComponent extends BaseListComponent<GetCustomerList.Query, GetCustomerList.Items>
     implements OnInit {
     searchTerm = new FormControl('');
-    constructor(private dataService: DataService, router: Router, route: ActivatedRoute) {
+    constructor(
+        private dataService: DataService,
+        router: Router,
+        route: ActivatedRoute,
+        private modalService: ModalService,
+        private notificationService: NotificationService,
+    ) {
         super(router, route);
         super.setQueryFn(
             (...args: any[]) => this.dataService.customer.getCustomerList(...args),
-            data => data.customers,
+            (data) => data.customers,
             (skip, take) => ({
                 options: {
                     skip,
@@ -41,10 +52,33 @@ export class CustomerListComponent extends BaseListComponent<GetCustomerList.Que
     ngOnInit() {
         super.ngOnInit();
         this.searchTerm.valueChanges
-            .pipe(
-                debounceTime(250),
-                takeUntil(this.destroy$),
-            )
+            .pipe(debounceTime(250), takeUntil(this.destroy$))
             .subscribe(() => this.refresh());
     }
+
+    deleteCustomer(customer: GetCustomerList.Items) {
+        return this.modalService
+            .dialog({
+                title: _('catalog.confirm-delete-customer'),
+                body: `${customer.firstName} ${customer.lastName}`,
+                buttons: [
+                    { type: 'secondary', label: _('common.cancel') },
+                    { type: 'danger', label: _('common.delete'), returnValue: true },
+                ],
+            })
+            .pipe(switchMap((res) => (res ? this.dataService.customer.deleteCustomer(customer.id) : EMPTY)))
+            .subscribe(
+                () => {
+                    this.notificationService.success(_('common.notify-delete-success'), {
+                        entity: 'Customer',
+                    });
+                    this.refresh();
+                },
+                (err) => {
+                    this.notificationService.error(_('common.notify-delete-error'), {
+                        entity: 'Customer',
+                    });
+                },
+            );
+    }
 }

+ 1 - 0
packages/admin-ui/src/lib/static/i18n-messages/en.json

@@ -64,6 +64,7 @@
     "confirm-delete-collection": "Delete collection?",
     "confirm-delete-collection-and-children-body": "Deleting this collection will also delete all child collections",
     "confirm-delete-country": "Delete country?",
+    "confirm-delete-customer": "Delete customer?",
     "confirm-delete-facet": "Delete facet?",
     "confirm-delete-facet-value": "Delete facet value?",
     "confirm-delete-product": "Delete product?",