فهرست منبع

refactor(admin-ui): Use variables to store reused permission arrays

Michael Bromley 4 سال پیش
والد
کامیت
4a7cc57694
22فایلهای تغییر یافته به همراه106 افزوده شده و 88 حذف شده
  1. 7 7
      packages/admin-ui/src/lib/catalog/src/components/collection-detail/collection-detail.component.html
  2. 2 1
      packages/admin-ui/src/lib/catalog/src/components/collection-detail/collection-detail.component.ts
  3. 7 7
      packages/admin-ui/src/lib/catalog/src/components/facet-detail/facet-detail.component.html
  4. 2 0
      packages/admin-ui/src/lib/catalog/src/components/facet-detail/facet-detail.component.ts
  5. 17 17
      packages/admin-ui/src/lib/catalog/src/components/product-variants-list/product-variants-list.component.html
  6. 2 0
      packages/admin-ui/src/lib/catalog/src/components/product-variants-list/product-variants-list.component.ts
  7. 6 6
      packages/admin-ui/src/lib/catalog/src/components/product-variants-table/product-variants-table.component.html
  8. 2 1
      packages/admin-ui/src/lib/catalog/src/components/product-variants-table/product-variants-table.component.ts
  9. 7 7
      packages/admin-ui/src/lib/settings/src/components/channel-detail/channel-detail.component.html
  10. 2 1
      packages/admin-ui/src/lib/settings/src/components/channel-detail/channel-detail.component.ts
  11. 4 4
      packages/admin-ui/src/lib/settings/src/components/country-detail/country-detail.component.html
  12. 2 0
      packages/admin-ui/src/lib/settings/src/components/country-detail/country-detail.component.ts
  13. 3 3
      packages/admin-ui/src/lib/settings/src/components/global-settings/global-settings.component.html
  14. 1 0
      packages/admin-ui/src/lib/settings/src/components/global-settings/global-settings.component.ts
  15. 8 8
      packages/admin-ui/src/lib/settings/src/components/payment-method-detail/payment-method-detail.component.html
  16. 2 0
      packages/admin-ui/src/lib/settings/src/components/payment-method-detail/payment-method-detail.component.ts
  17. 8 8
      packages/admin-ui/src/lib/settings/src/components/shipping-method-detail/shipping-method-detail.component.html
  18. 2 0
      packages/admin-ui/src/lib/settings/src/components/shipping-method-detail/shipping-method-detail.component.ts
  19. 3 3
      packages/admin-ui/src/lib/settings/src/components/tax-category-detail/tax-category-detail.component.html
  20. 2 1
      packages/admin-ui/src/lib/settings/src/components/tax-category-detail/tax-category-detail.component.ts
  21. 6 6
      packages/admin-ui/src/lib/settings/src/components/tax-rate-detail/tax-rate-detail.component.html
  22. 11 8
      packages/admin-ui/src/lib/settings/src/components/tax-rate-detail/tax-rate-detail.component.ts

+ 7 - 7
packages/admin-ui/src/lib/catalog/src/components/collection-detail/collection-detail.component.html

@@ -21,7 +21,7 @@
         </button>
         <ng-template #updateButton>
             <button
-                *vdrIfPermissions="['UpdateCatalog', 'UpdateCollection']"
+                *vdrIfPermissions="updatePermission"
                 class="btn btn-primary"
                 (click)="save()"
                 [disabled]="(detailForm.invalid || detailForm.pristine) && !assetsChanged()"
@@ -42,7 +42,7 @@
                         clrToggle
                         formControlName="visible"
                         id="visibility"
-                        [vdrDisabled]="!(['UpdateCatalog', 'UpdateCollection'] | hasPermission)"
+                        [vdrDisabled]="!(updatePermission | hasPermission)"
                     />
                     <label class="visible-toggle">
                         <ng-container *ngIf="detailForm.value.visible; else private">{{ 'catalog.public' | translate }}</ng-container>
@@ -55,7 +55,7 @@
                     id="name"
                     type="text"
                     formControlName="name"
-                    [readonly]="!(['UpdateCatalog', 'UpdateCollection'] | hasPermission)"
+                    [readonly]="!(updatePermission | hasPermission)"
                     (input)="updateSlug($event.target.value)"
                 />
             </vdr-form-field>
@@ -68,13 +68,13 @@
                     id="slug"
                     type="text"
                     formControlName="slug"
-                    [readonly]="!(['UpdateCatalog', 'UpdateCollection'] | hasPermission)"
+                    [readonly]="!(updatePermission | hasPermission)"
                     pattern="[a-z0-9_-]+"
                 />
             </vdr-form-field>
             <vdr-rich-text-editor
                 formControlName="description"
-                [readonly]="!(['UpdateCatalog', 'UpdateCollection'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
                 [label]="'common.description' | translate"
             ></vdr-rich-text-editor>
 
@@ -107,11 +107,11 @@
                     [operation]="filter"
                     [operationDefinition]="getFilterDefinition(filter)"
                     [formControlName]="i"
-                    [readonly]="!(['UpdateCatalog', 'UpdateCollection'] | hasPermission)"
+                    [readonly]="!(updatePermission | hasPermission)"
                 ></vdr-configurable-input>
             </ng-container>
 
-            <div *vdrIfPermissions="['UpdateCatalog', 'UpdateCollection']">
+            <div *vdrIfPermissions="updatePermission">
                 <vdr-dropdown>
                     <button class="btn btn-outline" vdrDropdownTrigger>
                         <clr-icon shape="plus"></clr-icon>

+ 2 - 1
packages/admin-ui/src/lib/catalog/src/components/collection-detail/collection-detail.component.ts

@@ -14,7 +14,6 @@ import {
     BaseDetailComponent,
     Collection,
     ConfigurableOperation,
-    ConfigurableOperationDef,
     ConfigurableOperationDefinition,
     ConfigurableOperationInput,
     CreateCollectionInput,
@@ -27,6 +26,7 @@ import {
     LanguageCode,
     ModalService,
     NotificationService,
+    Permission,
     ServerConfigService,
     UpdateCollectionInput,
 } from '@vendure/admin-ui/core';
@@ -50,6 +50,7 @@ export class CollectionDetailComponent
     assetChanges: { assets?: Asset[]; featuredAsset?: Asset } = {};
     filters: ConfigurableOperation[] = [];
     allFilters: ConfigurableOperationDefinition[] = [];
+    readonly updatePermission = [Permission.UpdateCatalog, Permission.UpdateCollection];
     @ViewChild('collectionContents') contentsComponent: CollectionContentsComponent;
 
     constructor(

+ 7 - 7
packages/admin-ui/src/lib/catalog/src/components/facet-detail/facet-detail.component.html

@@ -21,7 +21,7 @@
         </button>
         <ng-template #updateButton>
             <button
-                *vdrIfPermissions="['UpdateCatalog', 'UpdateFacet']"
+                *vdrIfPermissions="updatePermission"
                 class="btn btn-primary"
                 (click)="save()"
                 [disabled]="detailForm.invalid || detailForm.pristine"
@@ -39,7 +39,7 @@
                 <input
                     type="checkbox"
                     clrToggle
-                    [vdrDisabled]="!(['UpdateCatalog', 'UpdateFacet'] | hasPermission)"
+                    [vdrDisabled]="!(updatePermission | hasPermission)"
                     formControlName="visible"
                     id="visibility"
                 />
@@ -54,19 +54,19 @@
                 id="name"
                 type="text"
                 formControlName="name"
-                [readonly]="!(['UpdateCatalog', 'UpdateFacet'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
                 (input)="updateCode(facet.code, $event.target.value)"
             />
         </vdr-form-field>
         <vdr-form-field
             [label]="'common.code' | translate"
             for="code"
-            [readOnlyToggle]="['UpdateCatalog', 'UpdateFacet'] | hasPermission"
+            [readOnlyToggle]="updatePermission | hasPermission"
         >
             <input
                 id="code"
                 type="text"
-                [readonly]="!(['UpdateCatalog', 'UpdateFacet'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
                 formControlName="code"
             />
         </vdr-form-field>
@@ -112,7 +112,7 @@
                         <input
                             type="text"
                             formControlName="name"
-                            [readonly]="!(['UpdateCatalog', 'UpdateFacet'] | hasPermission)"
+                            [readonly]="!(updatePermission | hasPermission)"
                             (input)="updateValueCode(facet.values[i]?.code, $event.target.value, i)"
                         />
                     </td>
@@ -139,7 +139,7 @@
                                     type="button"
                                     class="delete-button"
                                     (click)="deleteFacetValue(facet.values[i]?.id, i)"
-                                    [disabled]="!(['UpdateCatalog', 'UpdateFacet'] | hasPermission)"
+                                    [disabled]="!(updatePermission | hasPermission)"
                                     vdrDropdownItem
                                 >
                                     <clr-icon shape="trash" class="is-danger"></clr-icon>

+ 2 - 0
packages/admin-ui/src/lib/catalog/src/components/facet-detail/facet-detail.component.ts

@@ -15,6 +15,7 @@ import {
     LanguageCode,
     ModalService,
     NotificationService,
+    Permission,
     ServerConfigService,
     UpdateFacetInput,
     UpdateFacetValueInput,
@@ -37,6 +38,7 @@ export class FacetDetailComponent
     customValueFields: CustomFieldConfig[];
     detailForm: FormGroup;
     values: Array<FacetWithValues.Values | { name: string; code: string }>;
+    readonly updatePermission = [Permission.UpdateCatalog, Permission.UpdateFacet];
 
     constructor(
         router: Router,

+ 17 - 17
packages/admin-ui/src/lib/catalog/src/components/product-variants-list/product-variants-list.component.html

@@ -7,31 +7,31 @@
         <ng-container *ngIf="formGroupMap.get(variant.id) as formGroup" [formGroup]="formGroup">
             <div class="card-block header-row">
                 <div class="details">
-                    <vdr-title-input class="sku" [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)">
+                    <vdr-title-input class="sku" [readonly]="!(updatePermission | hasPermission)">
                         <clr-input-container>
                             <input
                                 clrInput
                                 type="text"
                                 formControlName="sku"
-                                [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                                [readonly]="!(updatePermission | hasPermission)"
                                 [placeholder]="'catalog.sku' | translate"
                             />
                         </clr-input-container>
                     </vdr-title-input>
-                    <vdr-title-input class="name" [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)">
+                    <vdr-title-input class="name" [readonly]="!(updatePermission | hasPermission)">
                         <clr-input-container>
                             <input
                                 clrInput
                                 type="text"
                                 formControlName="name"
-                                [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                                [readonly]="!(updatePermission | hasPermission)"
                                 [placeholder]="'common.name' | translate"
                             />
                         </clr-input-container>
                     </vdr-title-input>
                 </div>
                 <div class="right-controls">
-                    <clr-toggle-wrapper *vdrIfPermissions="['UpdateCatalog', 'UpdateProduct']">
+                    <clr-toggle-wrapper *vdrIfPermissions="updatePermission">
                         <input type="checkbox" clrToggle name="enabled" formControlName="enabled" />
                         <label>{{ 'common.enabled' | translate }}</label>
                     </clr-toggle-wrapper>
@@ -52,7 +52,7 @@
                             <div class="variant-form-input-row">
                                 <div class="tax-category">
                                     <clr-select-container
-                                        *vdrIfPermissions="['UpdateCatalog', 'UpdateProduct']; else taxCategoryLabel"
+                                        *vdrIfPermissions="updatePermission; else taxCategoryLabel"
                                     >
                                         <label>{{ 'catalog.tax-category' | translate }}</label>
                                         <select clrSelect name="options" formControlName="taxCategoryId">
@@ -80,14 +80,14 @@
                                             *ngIf="!channelPriceIncludesTax"
                                             clrInput
                                             [currencyCode]="variant.currencyCode"
-                                            [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                                            [readonly]="!(updatePermission | hasPermission)"
                                             formControlName="price"
                                         ></vdr-currency-input>
                                         <vdr-currency-input
                                             *ngIf="channelPriceIncludesTax"
                                             clrInput
                                             [currencyCode]="variant.currencyCode"
-                                            [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                                            [readonly]="!(updatePermission | hasPermission)"
                                             formControlName="priceWithTax"
                                         ></vdr-currency-input>
                                     </clr-input-container>
@@ -100,7 +100,7 @@
                                 ></vdr-variant-price-detail>
                             </div>
                             <div class="variant-form-input-row">
-                                <clr-select-container *vdrIfPermissions="['UpdateCatalog', 'UpdateProduct']">
+                                <clr-select-container *vdrIfPermissions="updatePermission">
                                     <label
                                         >{{ 'catalog.track-inventory' | translate }}
                                         <vdr-help-tooltip
@@ -133,7 +133,7 @@
                                         min="0"
                                         step="1"
                                         formControlName="stockOnHand"
-                                        [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                                        [readonly]="!(updatePermission | hasPermission)"
                                         [vdrDisabled]="inventoryIsNotTracked(formGroup)"
                                     />
                                 </clr-input-container>
@@ -178,7 +178,7 @@
                                                 clrInput
                                                 type="number"
                                                 [formControl]="formGroup.get('outOfStockThreshold')"
-                                                [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                                                [readonly]="!(updatePermission | hasPermission)"
                                                 [vdrDisabled]="
                                                     formGroup.get('useGlobalOutOfStockThreshold')?.value !==
                                                         false || inventoryIsNotTracked(formGroup)
@@ -192,7 +192,7 @@
                                                 name="useGlobalOutOfStockThreshold"
                                                 formControlName="useGlobalOutOfStockThreshold"
                                                 [vdrDisabled]="
-                                                    !(['UpdateCatalog', 'UpdateProduct'] | hasPermission) ||
+                                                    !(updatePermission | hasPermission) ||
                                                     inventoryIsNotTracked(formGroup)
                                                 "
                                             />
@@ -216,7 +216,7 @@
                                             entityName="ProductVariant"
                                             [compact]="true"
                                             [customFieldsFormGroup]="formGroup.get('customFields')"
-                                            [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                                            [readonly]="!(updatePermission | hasPermission)"
                                             [customField]="customField"
                                         ></vdr-custom-field-control>
                                     </ng-container>
@@ -236,7 +236,7 @@
                                 [colorFrom]="optionGroupName(option.groupId)"
                                 [invert]="true"
                                 (iconClick)="editOption(option)"
-                                [icon]="(['UpdateCatalog', 'UpdateProduct'] | hasPermission) && 'pencil'"
+                                [icon]="(updatePermission | hasPermission) && 'pencil'"
                             >
                                 <span class="option-group-name">{{ optionGroupName(option.groupId) }}</span>
                                 {{ optionName(option) }}
@@ -248,17 +248,17 @@
                         <vdr-facet-value-chip
                             *ngFor="let facetValue of existingFacetValues(variant)"
                             [facetValue]="facetValue"
-                            [removable]="['UpdateCatalog', 'UpdateProduct'] | hasPermission"
+                            [removable]="updatePermission | hasPermission"
                             (remove)="removeFacetValue(variant, facetValue.id)"
                         ></vdr-facet-value-chip>
                         <vdr-facet-value-chip
                             *ngFor="let facetValue of pendingFacetValues(variant)"
                             [facetValue]="facetValue"
-                            [removable]="['UpdateCatalog', 'UpdateProduct'] | hasPermission"
+                            [removable]="updatePermission | hasPermission"
                             (remove)="removeFacetValue(variant, facetValue.id)"
                         ></vdr-facet-value-chip>
                         <button
-                            *vdrIfPermissions="['UpdateCatalog', 'UpdateProduct']"
+                            *vdrIfPermissions="updatePermission"
                             class="btn btn-sm btn-secondary"
                             (click)="selectFacetValueClick.emit([variant.id])"
                         >

+ 2 - 0
packages/admin-ui/src/lib/catalog/src/components/product-variants-list/product-variants-list.component.ts

@@ -20,6 +20,7 @@ import {
     GlobalFlag,
     LanguageCode,
     ModalService,
+    Permission,
     ProductOptionFragment,
     ProductVariant,
     ProductWithVariants,
@@ -75,6 +76,7 @@ export class ProductVariantsListComponent implements OnChanges, OnInit, OnDestro
     GlobalFlag = GlobalFlag;
     globalTrackInventory: boolean;
     globalOutOfStockThreshold: number;
+    readonly updatePermission = [Permission.UpdateCatalog, Permission.UpdateProduct];
     private facetValues: FacetValue.Fragment[];
     private subscription: Subscription;
 

+ 6 - 6
packages/admin-ui/src/lib/catalog/src/components/product-variants-table/product-variants-table.component.html

@@ -31,7 +31,7 @@
                         clrInput
                         type="text"
                         formControlName="name"
-                        [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                        [readonly]="!(updatePermission | hasPermission)"
                         [placeholder]="'common.name' | translate"
                     />
                 </clr-input-container>
@@ -42,7 +42,7 @@
                         clrInput
                         type="text"
                         formControlName="sku"
-                        [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                        [readonly]="!(updatePermission | hasPermission)"
                         [placeholder]="'catalog.sku' | translate"
                     />
                 </clr-input-container>
@@ -62,14 +62,14 @@
                         *ngIf="!channelPriceIncludesTax"
                         clrInput
                         [currencyCode]="variant.currencyCode"
-                        [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                        [readonly]="!(updatePermission | hasPermission)"
                         formControlName="price"
                     ></vdr-currency-input>
                     <vdr-currency-input
                         *ngIf="channelPriceIncludesTax"
                         clrInput
                         [currencyCode]="variant.currencyCode"
-                        [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                        [readonly]="!(updatePermission | hasPermission)"
                         formControlName="priceWithTax"
                     ></vdr-currency-input>
                 </clr-input-container>
@@ -82,7 +82,7 @@
                         min="0"
                         step="1"
                         formControlName="stockOnHand"
-                        [readonly]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                        [readonly]="!(updatePermission | hasPermission)"
                     />
                 </clr-input-container>
             </td>
@@ -93,7 +93,7 @@
                         clrToggle
                         name="enabled"
                         formControlName="enabled"
-                        [vdrDisabled]="!(['UpdateCatalog', 'UpdateProduct'] | hasPermission)"
+                        [vdrDisabled]="!(updatePermission | hasPermission)"
                     />
                 </clr-toggle-wrapper>
             </td>

+ 2 - 1
packages/admin-ui/src/lib/catalog/src/components/product-variants-table/product-variants-table.component.ts

@@ -7,7 +7,7 @@ import {
     OnInit,
 } from '@angular/core';
 import { FormArray, FormGroup } from '@angular/forms';
-import { ProductWithVariants } from '@vendure/admin-ui/core';
+import { Permission, ProductWithVariants } from '@vendure/admin-ui/core';
 import { Subscription } from 'rxjs';
 import { debounceTime, distinctUntilChanged, map } from 'rxjs/operators';
 
@@ -26,6 +26,7 @@ export class ProductVariantsTableComponent implements OnInit, OnDestroy {
     @Input() optionGroups: ProductWithVariants.OptionGroups[];
     @Input() pendingAssetChanges: { [variantId: string]: SelectedAssets };
     formGroupMap = new Map<string, FormGroup>();
+    readonly updatePermission = [Permission.UpdateCatalog, Permission.UpdateProduct];
     private subscription: Subscription;
 
     constructor(private changeDetector: ChangeDetectorRef) {}

+ 7 - 7
packages/admin-ui/src/lib/settings/src/components/channel-detail/channel-detail.component.html

@@ -28,17 +28,17 @@
 
 <form class="form" [formGroup]="detailForm">
     <vdr-form-field [label]="'common.code' | translate" for="code">
-        <input id="code" type="text" [readonly]="!(['SuperAdmin', 'UpdateChannel', 'CreateChannel'] | hasPermission)" formControlName="code" />
+        <input id="code" type="text" [readonly]="!(updatePermission | hasPermission)" formControlName="code" />
     </vdr-form-field>
     <vdr-form-field [label]="'settings.channel-token' | translate" for="token">
-        <input id="token" type="text" [readonly]="!(['SuperAdmin', 'UpdateChannel', 'CreateChannel'] | hasPermission)" formControlName="token" />
+        <input id="token" type="text" [readonly]="!(updatePermission | hasPermission)" formControlName="token" />
     </vdr-form-field>
     <vdr-form-field [label]="'settings.currency' | translate" for="defaultTaxZoneId">
         <select
             clrSelect
             name="currencyCode"
             formControlName="currencyCode"
-            [vdrDisabled]="!(['SuperAdmin', 'UpdateChannel', 'CreateChannel'] | hasPermission)"
+            [vdrDisabled]="!(updatePermission | hasPermission)"
         >
             <option *ngFor="let code of currencyCodes" [value]="code">{{ code | localeCurrencyName }}</option>
         </select>
@@ -48,7 +48,7 @@
             clrSelect
             name="defaultLanguageCode"
             formControlName="defaultLanguageCode"
-            [vdrDisabled]="!(['SuperAdmin', 'UpdateChannel', 'CreateChannel'] | hasPermission)"
+            [vdrDisabled]="!(updatePermission | hasPermission)"
         >
             <option *ngFor="let languageCode of availableLanguageCodes$ | async" [value]="languageCode">
                 {{ 'lang.' + languageCode | translate }} ({{ languageCode | uppercase }})
@@ -62,7 +62,7 @@
                 clrToggle
                 id="pricesIncludeTax"
                 formControlName="pricesIncludeTax"
-                [vdrDisabled]="!(['SuperAdmin', 'UpdateChannel', 'CreateChannel'] | hasPermission)"
+                [vdrDisabled]="!(updatePermission | hasPermission)"
             />
         </clr-toggle-wrapper>
     </vdr-form-field>
@@ -71,7 +71,7 @@
             clrSelect
             name="defaultTaxZoneId"
             formControlName="defaultTaxZoneId"
-            [vdrDisabled]="!(['SuperAdmin', 'UpdateChannel', 'CreateChannel'] | hasPermission)"
+            [vdrDisabled]="!(updatePermission | hasPermission)"
         >
             <option *ngFor="let zone of zones$ | async" [value]="zone.id">{{ zone.name }}</option>
         </select>
@@ -93,7 +93,7 @@
             clrSelect
             name="defaultShippingZoneId"
             formControlName="defaultShippingZoneId"
-            [vdrDisabled]="!(['SuperAdmin', 'UpdateChannel', 'CreateChannel'] | hasPermission)"
+            [vdrDisabled]="!(updatePermission | hasPermission)"
         >
             <option *ngFor="let zone of zones$ | async" [value]="zone.id">{{ zone.name }}</option>
         </select>

+ 2 - 1
packages/admin-ui/src/lib/settings/src/components/channel-detail/channel-detail.component.ts

@@ -2,7 +2,7 @@ import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnDestroy, OnIni
 import { FormBuilder, FormGroup, Validators } from '@angular/forms';
 import { ActivatedRoute, Router } from '@angular/router';
 import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
-import { BaseDetailComponent, CustomFieldConfig } from '@vendure/admin-ui/core';
+import { BaseDetailComponent, CustomFieldConfig, Permission } from '@vendure/admin-ui/core';
 import {
     Channel,
     CreateChannelInput,
@@ -32,6 +32,7 @@ export class ChannelDetailComponent
     detailForm: FormGroup;
     currencyCodes = Object.values(CurrencyCode);
     availableLanguageCodes$: Observable<LanguageCode[]>;
+    readonly updatePermission = [Permission.SuperAdmin, Permission.UpdateChannel, Permission.CreateChannel];
 
     constructor(
         router: Router,

+ 4 - 4
packages/admin-ui/src/lib/settings/src/components/country-detail/country-detail.component.html

@@ -21,7 +21,7 @@
         <ng-template #updateButton>
             <button
                 class="btn btn-primary"
-                *vdrIfPermissions="['UpdateSettings', 'UpdateCountry']"
+                *vdrIfPermissions="updatePermission"
                 (click)="save()"
                 [disabled]="detailForm.invalid || detailForm.pristine"
             >
@@ -37,7 +37,7 @@
             id="code"
             type="text"
             formControlName="code"
-            [readonly]="!(['UpdateSettings', 'UpdateCountry'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
         />
     </vdr-form-field>
     <vdr-form-field [label]="'common.name' | translate" for="name">
@@ -45,7 +45,7 @@
             id="name"
             type="text"
             formControlName="name"
-            [readonly]="!(['UpdateSettings', 'UpdateCountry'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
         />
     </vdr-form-field>
     <vdr-form-field [label]="'common.enabled' | translate" for="enabled">
@@ -55,7 +55,7 @@
                 clrToggle
                 id="enabled"
                 formControlName="enabled"
-                [vdrDisabled]="!(['UpdateSettings', 'UpdateCountry'] | hasPermission)"
+                [vdrDisabled]="!(updatePermission | hasPermission)"
             />
         </clr-toggle-wrapper>
     </vdr-form-field>

+ 2 - 0
packages/admin-ui/src/lib/settings/src/components/country-detail/country-detail.component.ts

@@ -11,6 +11,7 @@ import {
     findTranslation,
     LanguageCode,
     NotificationService,
+    Permission,
     ServerConfigService,
     UpdateCountryInput,
 } from '@vendure/admin-ui/core';
@@ -27,6 +28,7 @@ export class CountryDetailComponent
     implements OnInit, OnDestroy {
     country$: Observable<Country.Fragment>;
     detailForm: FormGroup;
+    readonly updatePermission = [Permission.UpdateSettings, Permission.UpdateCountry];
 
     constructor(
         router: Router,

+ 3 - 3
packages/admin-ui/src/lib/settings/src/components/global-settings/global-settings.component.html

@@ -4,7 +4,7 @@
         <button
             class="btn btn-primary"
             (click)="save()"
-            *vdrIfPermissions="['UpdateSettings', 'UpdateGlobalSettings']"
+            *vdrIfPermissions="updatePermission"
             [disabled]="detailForm.invalid || detailForm.pristine"
         >
             {{ 'common.update' | translate }}
@@ -42,7 +42,7 @@
             id="outOfStockThreshold"
             type="number"
             formControlName="outOfStockThreshold"
-            [readonly]="!(['UpdateSettings', 'UpdateGlobalSettings'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
         />
     </vdr-form-field>
     <vdr-form-field
@@ -56,7 +56,7 @@
                 clrToggle
                 name="enabled"
                 formControlName="trackInventory"
-                [vdrDisabled]="!(['UpdateSettings', 'UpdateGlobalSettings'] | hasPermission)"
+                [vdrDisabled]="!(updatePermission | hasPermission)"
             />
         </clr-toggle-wrapper>
     </vdr-form-field>

+ 1 - 0
packages/admin-ui/src/lib/settings/src/components/global-settings/global-settings.component.ts

@@ -19,6 +19,7 @@ export class GlobalSettingsComponent extends BaseDetailComponent<GlobalSettings>
     detailForm: FormGroup;
     customFields: CustomFieldConfig[];
     languageCodes = Object.values(LanguageCode);
+    readonly updatePermission = [Permission.UpdateSettings, Permission.UpdateGlobalSettings];
 
     constructor(
         router: Router,

+ 8 - 8
packages/admin-ui/src/lib/settings/src/components/payment-method-detail/payment-method-detail.component.html

@@ -15,7 +15,7 @@
         </button>
         <ng-template #updateButton>
             <button
-                *vdrIfPermissions="['UpdateSettings', 'UpdatePaymentMethod']"
+                *vdrIfPermissions="updatePermission"
                 class="btn btn-primary"
                 (click)="save()"
                 [disabled]="detailForm.pristine || detailForm.invalid || !selectedHandler"
@@ -32,25 +32,25 @@
             id="name"
             type="text"
             formControlName="name"
-            [readonly]="!(['UpdateSettings', 'UpdatePaymentMethod'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
             (input)="updateCode(paymentMethod.code, $event.target.value)"
         />
     </vdr-form-field>
     <vdr-form-field
         [label]="'common.code' | translate"
         for="code"
-        [readOnlyToggle]="['UpdateSettings', 'UpdatePaymentMethod'] | hasPermission"
+        [readOnlyToggle]="updatePermission | hasPermission"
     >
         <input
             id="code"
             type="text"
             formControlName="code"
-            [readonly]="!(['UpdateSettings', 'UpdatePaymentMethod'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
         />
     </vdr-form-field>
     <vdr-rich-text-editor
         formControlName="description"
-        [readonly]="!(['UpdateSettings', 'UpdatePaymentMethod'] | hasPermission)"
+        [readonly]="!(updatePermission | hasPermission)"
         [label]="'common.description' | translate"
     ></vdr-rich-text-editor>
     <vdr-form-field [label]="'common.enabled' | translate" for="description">
@@ -59,7 +59,7 @@
                 type="checkbox"
                 clrToggle
                 id="enabled"
-                [vdrDisabled]="!(['UpdateSettings', 'UpdatePaymentMethod'] | hasPermission)"
+                [vdrDisabled]="!(updatePermission | hasPermission)"
                 formControlName="enabled"
             />
         </clr-toggle-wrapper>
@@ -72,7 +72,7 @@
                 *ngIf="selectedChecker && selectedCheckerDefinition"
                 [operation]="selectedChecker"
                 [operationDefinition]="selectedCheckerDefinition"
-                [readonly]="!(['UpdateSettings', 'UpdatePaymentMethod'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
                 (remove)="removeChecker()"
                 formControlName="checker"
             ></vdr-configurable-input>
@@ -101,7 +101,7 @@
                 *ngIf="selectedHandler && selectedHandlerDefinition"
                 [operation]="selectedHandler"
                 [operationDefinition]="selectedHandlerDefinition"
-                [readonly]="!(['UpdateSettings', 'UpdatePaymentMethod'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
                 (remove)="removeHandler()"
                 formControlName="handler"
             ></vdr-configurable-input>

+ 2 - 0
packages/admin-ui/src/lib/settings/src/components/payment-method-detail/payment-method-detail.component.ts

@@ -14,6 +14,7 @@ import {
     getConfigArgValue,
     NotificationService,
     PaymentMethod,
+    Permission,
     ServerConfigService,
     toConfigurableOperationInput,
     UpdatePaymentMethodInput,
@@ -38,6 +39,7 @@ export class PaymentMethodDetailComponent
     selectedCheckerDefinition?: ConfigurableOperationDefinition;
     selectedHandler?: ConfigurableOperation | null;
     selectedHandlerDefinition?: ConfigurableOperationDefinition;
+    readonly updatePermission = [Permission.UpdateSettings, Permission.UpdatePaymentMethod];
 
     constructor(
         router: Router,

+ 8 - 8
packages/admin-ui/src/lib/settings/src/components/shipping-method-detail/shipping-method-detail.component.html

@@ -23,7 +23,7 @@
             <button
                 class="btn btn-primary"
                 (click)="save()"
-                *vdrIfPermissions="['UpdateSettings', 'UpdateShippingMethod']"
+                *vdrIfPermissions="updatePermission"
                 [disabled]="
                     detailForm.pristine || detailForm.invalid || !selectedChecker || !selectedCalculator
                 "
@@ -40,32 +40,32 @@
             id="name"
             type="text"
             formControlName="name"
-            [readonly]="!(['UpdateSettings', 'UpdateShippingMethod'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
             (input)="updateCode(shippingMethod.code, $event.target.value)"
         />
     </vdr-form-field>
     <vdr-form-field
         [label]="'common.code' | translate"
         for="code"
-        [readOnlyToggle]="['UpdateSettings', 'UpdateShippingMethod'] | hasPermission"
+        [readOnlyToggle]="updatePermission | hasPermission"
     >
         <input
             id="code"
             type="text"
             formControlName="code"
-            [readonly]="!(['UpdateSettings', 'UpdateShippingMethod'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
         />
     </vdr-form-field>
     <vdr-rich-text-editor
         formControlName="description"
-        [readonly]="!(['UpdateSettings', 'UpdateShippingMethod'] | hasPermission)"
+        [readonly]="!(updatePermission | hasPermission)"
         [label]="'common.description' | translate"
     ></vdr-rich-text-editor>
     <vdr-form-field [label]="'settings.fulfillment-handler' | translate" for="fulfillmentHandler" class="mb2">
         <select
             name="fulfillmentHandler"
             formControlName="fulfillmentHandler"
-            [vdrDisabled]="!(['UpdateSettings', 'UpdateShippingMethod'] | hasPermission)"
+            [vdrDisabled]="!(updatePermission | hasPermission)"
         >
             <option *ngFor="let handler of fulfillmentHandlers" [value]="handler.code">
                 {{ handler.code }}: {{ handler.description }}
@@ -92,7 +92,7 @@
                 *ngIf="selectedChecker && selectedCheckerDefinition"
                 [operation]="selectedChecker"
                 [operationDefinition]="selectedCheckerDefinition"
-                [readonly]="!(['UpdateSettings', 'UpdateShippingMethod'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
                 (remove)="selectedChecker = null"
                 formControlName="checker"
             ></vdr-configurable-input>
@@ -121,7 +121,7 @@
                 *ngIf="selectedCalculator && selectedCalculatorDefinition"
                 [operation]="selectedCalculator"
                 [operationDefinition]="selectedCalculatorDefinition"
-                [readonly]="!(['UpdateSettings', 'UpdateShippingMethod'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
                 (remove)="selectedCalculator = null"
                 formControlName="calculator"
             ></vdr-configurable-input>

+ 2 - 0
packages/admin-ui/src/lib/settings/src/components/shipping-method-detail/shipping-method-detail.component.ts

@@ -16,6 +16,7 @@ import {
     getConfigArgValue,
     LanguageCode,
     NotificationService,
+    Permission,
     ServerConfigService,
     ShippingMethod,
     TestShippingMethodInput,
@@ -53,6 +54,7 @@ export class ShippingMethodDetailComponent
     testDataUpdated = false;
     testResult$: Observable<TestShippingMethodResult | undefined>;
     customFields: CustomFieldConfig[];
+    readonly updatePermission = [Permission.UpdateSettings, Permission.UpdateShippingMethod];
     private fetchTestResult$ = new Subject<[TestAddress, TestOrderLine[]]>();
 
     constructor(

+ 3 - 3
packages/admin-ui/src/lib/settings/src/components/tax-category-detail/tax-category-detail.component.html

@@ -18,7 +18,7 @@
                 class="btn btn-primary"
                 (click)="save()"
                 [disabled]="!saveButtonEnabled()"
-                *vdrIfPermissions="['UpdateSettings', 'UpdateTaxCategory']"
+                *vdrIfPermissions="updatePermission"
             >
                 {{ 'common.update' | translate }}
             </button>
@@ -32,7 +32,7 @@
             id="name"
             type="text"
             formControlName="name"
-            [readonly]="!(['UpdateSettings', 'UpdateTaxCategory'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
         />
     </vdr-form-field>
     <vdr-form-field [label]="'common.default-tax-category' | translate" for="isDefault">
@@ -41,7 +41,7 @@
                 type="checkbox"
                 clrToggle
                 id="isDefault"
-                [vdrDisabled]="!(['UpdateSettings', 'UpdateTaxCategory'] | hasPermission)"
+                [vdrDisabled]="!(updatePermission | hasPermission)"
                 formControlName="isDefault"
             />
         </clr-toggle-wrapper>

+ 2 - 1
packages/admin-ui/src/lib/settings/src/components/tax-category-detail/tax-category-detail.component.ts

@@ -2,7 +2,7 @@ import { ChangeDetectionStrategy, ChangeDetectorRef, Component, OnDestroy, OnIni
 import { FormBuilder, FormGroup, Validators } from '@angular/forms';
 import { ActivatedRoute, Router } from '@angular/router';
 import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
-import { BaseDetailComponent } from '@vendure/admin-ui/core';
+import { BaseDetailComponent, Permission } from '@vendure/admin-ui/core';
 import {
     ConfigurableOperation,
     CreateTaxCategoryInput,
@@ -27,6 +27,7 @@ export class TaxCategoryDetailComponent
     implements OnInit, OnDestroy {
     taxCategory$: Observable<TaxCategory.Fragment>;
     detailForm: FormGroup;
+    readonly updatePermission = [Permission.UpdateSettings, Permission.UpdateTaxCategory];
 
     private taxCondition: ConfigurableOperation;
     private taxAction: ConfigurableOperation;

+ 6 - 6
packages/admin-ui/src/lib/settings/src/components/tax-rate-detail/tax-rate-detail.component.html

@@ -18,7 +18,7 @@
                 class="btn btn-primary"
                 (click)="save()"
                 [disabled]="!saveButtonEnabled()"
-                *vdrIfPermissions="['UpdateSettings', 'UpdateTaxRate']"
+                *vdrIfPermissions="updatePermission"
             >
                 {{ 'common.update' | translate }}
             </button>
@@ -32,7 +32,7 @@
             id="name"
             type="text"
             formControlName="name"
-            [readonly]="!(['UpdateSettings', 'UpdateTaxRate'] | hasPermission)"
+            [readonly]="!(updatePermission | hasPermission)"
         />
     </vdr-form-field>
     <vdr-form-field [label]="'common.enabled' | translate" for="enabled">
@@ -42,7 +42,7 @@
                 clrToggle
                 id="enabled"
                 formControlName="enabled"
-                [vdrDisabled]="!(['UpdateSettings', 'UpdateTaxRate'] | hasPermission)"
+                [vdrDisabled]="!(updatePermission | hasPermission)"
             />
         </clr-toggle-wrapper>
     </vdr-form-field>
@@ -53,7 +53,7 @@
                 type="number"
                 step="0.1"
                 formControlName="value"
-                [readonly]="!(['UpdateSettings', 'UpdateTaxRate'] | hasPermission)"
+                [readonly]="!(updatePermission | hasPermission)"
             />
         </vdr-affixed-input>
     </vdr-form-field>
@@ -62,7 +62,7 @@
             clrSelect
             name="taxCategoryId"
             formControlName="taxCategoryId"
-            [vdrDisabled]="!(['UpdateSettings', 'UpdateTaxRate'] | hasPermission)"
+            [vdrDisabled]="!(updatePermission | hasPermission)"
         >
             <option *ngFor="let taxCategory of taxCategories$ | async" [value]="taxCategory.id">
                 {{ taxCategory.name }}
@@ -74,7 +74,7 @@
             clrSelect
             name="zoneId"
             formControlName="zoneId"
-            [vdrDisabled]="!(['UpdateSettings', 'UpdateTaxRate'] | hasPermission)"
+            [vdrDisabled]="!(updatePermission | hasPermission)"
         >
             <option *ngFor="let zone of zones$ | async" [value]="zone.id">{{ zone.name }}</option>
         </select>

+ 11 - 8
packages/admin-ui/src/lib/settings/src/components/tax-rate-detail/tax-rate-detail.component.ts

@@ -10,6 +10,7 @@ import {
     GetZones,
     LanguageCode,
     NotificationService,
+    Permission,
     ServerConfigService,
     TaxCategory,
     TaxRate,
@@ -24,12 +25,14 @@ import { mergeMap, take } from 'rxjs/operators';
     styleUrls: ['./tax-rate-detail.component.scss'],
     changeDetection: ChangeDetectionStrategy.OnPush,
 })
-export class TaxRateDetailComponent extends BaseDetailComponent<TaxRate.Fragment>
+export class TaxRateDetailComponent
+    extends BaseDetailComponent<TaxRate.Fragment>
     implements OnInit, OnDestroy {
     taxCategories$: Observable<TaxCategory.Fragment[]>;
     zones$: Observable<GetZones.Zones[]>;
     groups$: Observable<CustomerGroup[]>;
     detailForm: FormGroup;
+    readonly updatePermission = [Permission.UpdateSettings, Permission.UpdateTaxRate];
 
     constructor(
         router: Router,
@@ -55,8 +58,8 @@ export class TaxRateDetailComponent extends BaseDetailComponent<TaxRate.Fragment
         this.init();
         this.taxCategories$ = this.dataService.settings
             .getTaxCategories()
-            .mapSingle((data) => data.taxCategories);
-        this.zones$ = this.dataService.settings.getZones().mapSingle((data) => data.zones);
+            .mapSingle(data => data.taxCategories);
+        this.zones$ = this.dataService.settings.getZones().mapSingle(data => data.zones);
     }
 
     ngOnDestroy() {
@@ -81,7 +84,7 @@ export class TaxRateDetailComponent extends BaseDetailComponent<TaxRate.Fragment
             customerGroupId: formValue.customerGroupId,
         } as CreateTaxRateInput;
         this.dataService.settings.createTaxRate(input).subscribe(
-            (data) => {
+            data => {
                 this.notificationService.success(_('common.notify-create-success'), {
                     entity: 'TaxRate',
                 });
@@ -89,7 +92,7 @@ export class TaxRateDetailComponent extends BaseDetailComponent<TaxRate.Fragment
                 this.changeDetector.markForCheck();
                 this.router.navigate(['../', data.createTaxRate.id], { relativeTo: this.route });
             },
-            (err) => {
+            err => {
                 this.notificationService.error(_('common.notify-create-error'), {
                     entity: 'TaxRate',
                 });
@@ -105,7 +108,7 @@ export class TaxRateDetailComponent extends BaseDetailComponent<TaxRate.Fragment
         this.entity$
             .pipe(
                 take(1),
-                mergeMap((taxRate) => {
+                mergeMap(taxRate => {
                     const input = {
                         id: taxRate.id,
                         name: formValue.name,
@@ -119,14 +122,14 @@ export class TaxRateDetailComponent extends BaseDetailComponent<TaxRate.Fragment
                 }),
             )
             .subscribe(
-                (data) => {
+                data => {
                     this.notificationService.success(_('common.notify-update-success'), {
                         entity: 'TaxRate',
                     });
                     this.detailForm.markAsPristine();
                     this.changeDetector.markForCheck();
                 },
-                (err) => {
+                err => {
                     this.notificationService.error(_('common.notify-update-error'), {
                         entity: 'TaxRate',
                     });