Commit 6c631a9f146516fd7dbbc839928eb8ea8a74bce7

Authored by Vladyslav_Prykhodko
Committed by Andrew Shvayka
1 parent 3a7a97dd

UI: Add power mode settings in LwM2M device profile and refactoring lwm2m device…

… profile transport form
... ... @@ -141,7 +141,7 @@ import { DashboardImageDialogComponent } from '@home/components/dashboard-page/d
141 141 import { WidgetContainerComponent } from '@home/components/widget/widget-container.component';
142 142 import { SnmpDeviceProfileTransportModule } from '@home/components/profile/device/snpm/snmp-device-profile-transport.module';
143 143 import { DeviceCredentialsModule } from '@home/components/device/device-credentials.module';
144   -import { PowerModeSettingComponent } from '@home/components/profile/device/common/power-mode-setting.component';
  144 +import { DeviceProfileCommonModule } from '@home/components/profile/device/common/device-profile-common.module';
145 145
146 146 @NgModule({
147 147 declarations:
... ... @@ -260,8 +260,7 @@ import { PowerModeSettingComponent } from '@home/components/profile/device/commo
260 260 DashboardStateDialogComponent,
261 261 DashboardImageDialogComponent,
262 262 EmbedDashboardDialogComponent,
263   - DisplayWidgetTypesPanelComponent,
264   - PowerModeSettingComponent
  263 + DisplayWidgetTypesPanelComponent
265 264 ],
266 265 imports: [
267 266 CommonModule,
... ... @@ -270,7 +269,8 @@ import { PowerModeSettingComponent } from '@home/components/profile/device/commo
270 269 Lwm2mProfileComponentsModule,
271 270 SnmpDeviceProfileTransportModule,
272 271 StatesControllerModule,
273   - DeviceCredentialsModule
  272 + DeviceCredentialsModule,
  273 + DeviceProfileCommonModule
274 274 ],
275 275 exports: [
276 276 EntitiesTableComponent,
... ... @@ -371,8 +371,7 @@ import { PowerModeSettingComponent } from '@home/components/profile/device/commo
371 371 DashboardStateDialogComponent,
372 372 DashboardImageDialogComponent,
373 373 EmbedDashboardDialogComponent,
374   - DisplayWidgetTypesPanelComponent,
375   - PowerModeSettingComponent
  374 + DisplayWidgetTypesPanelComponent
376 375 ],
377 376 providers: [
378 377 WidgetComponentService,
... ...
  1 +///
  2 +/// Copyright © 2016-2021 The Thingsboard Authors
  3 +///
  4 +/// Licensed under the Apache License, Version 2.0 (the "License");
  5 +/// you may not use this file except in compliance with the License.
  6 +/// You may obtain a copy of the License at
  7 +///
  8 +/// http://www.apache.org/licenses/LICENSE-2.0
  9 +///
  10 +/// Unless required by applicable law or agreed to in writing, software
  11 +/// distributed under the License is distributed on an "AS IS" BASIS,
  12 +/// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
  13 +/// See the License for the specific language governing permissions and
  14 +/// limitations under the License.
  15 +///
  16 +
  17 +import { NgModule } from '@angular/core';
  18 +import { PowerModeSettingComponent } from '@home/components/profile/device/common/power-mode-setting.component';
  19 +import { SharedModule } from '@shared/shared.module';
  20 +import { CommonModule } from '@angular/common';
  21 +
  22 +@NgModule({
  23 + declarations: [
  24 + PowerModeSettingComponent
  25 + ],
  26 + imports: [
  27 + CommonModule,
  28 + SharedModule
  29 + ],
  30 + exports: [
  31 + PowerModeSettingComponent
  32 + ]
  33 +})
  34 +export class DeviceProfileCommonModule { }
... ...
... ... @@ -132,7 +132,7 @@
132 132 <mat-option [value]=3>{{ 'device-profile.lwm2m.fw-update-strategy-data' | translate }}</mat-option>
133 133 </mat-select>
134 134 </mat-form-field>
135   - <mat-form-field class="mat-block" fxFlex *ngIf="isFwUpdateStrategy">
  135 + <mat-form-field class="mat-block" fxFlex *ngIf="lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateStrategy').value === 2">
136 136 <mat-label>{{ 'device-profile.lwm2m.fw-update-resource' | translate }}</mat-label>
137 137 <input matInput formControlName="fwUpdateResource" required>
138 138 <mat-error *ngIf="lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource').hasError('required')">
... ... @@ -149,7 +149,7 @@
149 149 <mat-option [value]=2>{{ 'device-profile.lwm2m.sw-update-strategy-package-uri' | translate }}</mat-option>
150 150 </mat-select>
151 151 </mat-form-field>
152   - <mat-form-field class="mat-block" fxFlex *ngIf="isSwUpdateStrategy">
  152 + <mat-form-field class="mat-block" fxFlex *ngIf="lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateStrategy').value === 2">
153 153 <mat-label>{{ 'device-profile.lwm2m.sw-update-resource' | translate }}</mat-label>
154 154 <input matInput formControlName="swUpdateResource" required>
155 155 <mat-error *ngIf="lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource').hasError('required')">
... ... @@ -159,25 +159,8 @@
159 159 </fieldset>
160 160 <fieldset class="fields-group">
161 161 <legend class="group-title" translate>device-profile.power-saving-mode</legend>
162   - <mat-form-field class="mat-block" fxFlex>
163   - <mat-label> </mat-label>
164   - <mat-select formControlName="powerMode">
165   - <mat-option *ngFor="let powerMod of powerMods" [value]="powerMod">
166   - {{ powerModeTranslationMap.get(powerMod) | translate}}
167   - </mat-option>
168   - </mat-select>
169   - </mat-form-field>
170   - <mat-form-field class="mat-block" fxFlex *ngIf="lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.powerMode').value === 'E_DRX'">
171   - <mat-label>{{ 'device-profile.edrx-cycle' | translate }}</mat-label>
172   - <input matInput type="number" min="0" formControlName="edrxCycle" required>
173   - <mat-error *ngIf="lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').hasError('required')">
174   - {{ 'device-profile.edrx-cycle-required' | translate }}
175   - </mat-error>
176   - <mat-error *ngIf="lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').hasError('pattern') ||
177   - lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').hasError('min')">
178   - {{ 'device-profile.edrx-cycle-pattern' | translate }}
179   - </mat-error>
180   - </mat-form-field>
  162 + <tb-power-mode-settings [parentForm]="clientSettingsFormGroup">
  163 + </tb-power-mode-settings>
181 164 </fieldset>
182 165 <mat-slide-toggle class="mat-slider"
183 166 formControlName="compositeOperationsSupport">{{ 'device-profile.lwm2m.composite-operations-support' | translate }}</mat-slide-toggle>
... ...
... ... @@ -16,7 +16,15 @@
16 16
17 17 import { DeviceProfileTransportConfiguration } from '@shared/models/device.models';
18 18 import { Component, forwardRef, Input, OnDestroy } from '@angular/core';
19   -import { ControlValueAccessor, FormBuilder, FormGroup, NG_VALUE_ACCESSOR, Validators } from '@angular/forms';
  19 +import {
  20 + ControlValueAccessor,
  21 + FormBuilder,
  22 + FormGroup, NG_VALIDATORS,
  23 + NG_VALUE_ACCESSOR,
  24 + ValidationErrors,
  25 + Validator,
  26 + Validators
  27 +} from '@angular/forms';
20 28 import { coerceBooleanProperty } from '@angular/cdk/coercion';
21 29 import {
22 30 ATTRIBUTE,
... ... @@ -30,10 +38,7 @@ import {
30 38 DEFAULT_NOTIF_IF_DESIBLED,
31 39 DEFAULT_SW_UPDATE_RESOURCE,
32 40 getDefaultBootstrapServerSecurityConfig,
33   - getDefaultBootstrapServersSecurityConfig,
34 41 getDefaultLwM2MServerSecurityConfig,
35   - getDefaultProfileClientLwM2mSettingsConfig,
36   - getDefaultProfileObserveAttrConfig,
37 42 Instance,
38 43 INSTANCES,
39 44 KEY_NAME,
... ... @@ -41,7 +46,6 @@ import {
41 46 ObjectLwM2M,
42 47 OBSERVE,
43 48 PowerMode,
44   - PowerModeTranslationMap,
45 49 RESOURCES,
46 50 ServerSecurityConfig,
47 51 TELEMETRY
... ... @@ -58,13 +62,19 @@ import { takeUntil } from 'rxjs/operators';
58 62 selector: 'tb-profile-lwm2m-device-transport-configuration',
59 63 templateUrl: './lwm2m-device-profile-transport-configuration.component.html',
60 64 styleUrls: ['./lwm2m-device-profile-transport-configuration.component.scss'],
61   - providers: [{
62   - provide: NG_VALUE_ACCESSOR,
63   - useExisting: forwardRef(() => Lwm2mDeviceProfileTransportConfigurationComponent),
64   - multi: true
65   - }]
  65 + providers: [
  66 + {
  67 + provide: NG_VALUE_ACCESSOR,
  68 + useExisting: forwardRef(() => Lwm2mDeviceProfileTransportConfigurationComponent),
  69 + multi: true
  70 + },
  71 + {
  72 + provide: NG_VALIDATORS,
  73 + useExisting: forwardRef(() => Lwm2mDeviceProfileTransportConfigurationComponent),
  74 + multi: true
  75 + }]
66 76 })
67   -export class Lwm2mDeviceProfileTransportConfigurationComponent implements ControlValueAccessor, Validators, OnDestroy {
  77 +export class Lwm2mDeviceProfileTransportConfigurationComponent implements ControlValueAccessor, Validator, OnDestroy {
68 78
69 79 private configurationValue: Lwm2mProfileConfigModels;
70 80 private requiredValue: boolean;
... ... @@ -76,10 +86,6 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
76 86 lwm2mDeviceProfileFormGroup: FormGroup;
77 87 lwm2mDeviceConfigFormGroup: FormGroup;
78 88 sortFunction: (key: string, value: object) => object;
79   - isFwUpdateStrategy: boolean;
80   - isSwUpdateStrategy: boolean;
81   - powerMods = Object.values(PowerMode);
82   - powerModeTranslationMap = PowerModeTranslationMap;
83 89
84 90 get required(): boolean {
85 91 return this.requiredValue;
... ... @@ -116,7 +122,9 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
116 122 fwUpdateResource: [{value: '', disabled: true}, []],
117 123 swUpdateResource: [{value: '', disabled: true}, []],
118 124 powerMode: [PowerMode.DRX, Validators.required],
119   - edrxCycle: [0],
  125 + edrxCycle: [{disabled: true, value: 0}, [Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]],
  126 + psmActivityTimer: [{disabled: true, value: 0}, [Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]],
  127 + pagingTransmissionWindow: [{disabled: true, value: 0}, [Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]],
120 128 compositeOperationsSupport: [false]
121 129 })
122 130 });
... ... @@ -128,42 +136,22 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
128 136 ).subscribe((fwStrategy) => {
129 137 if (fwStrategy === 2) {
130 138 this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource').enable({emitEvent: false});
131   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource')
132   - .patchValue(DEFAULT_FW_UPDATE_RESOURCE, {emitEvent: false});
133   - this.isFwUpdateStrategy = true;
134 139 } else {
135 140 this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource').disable({emitEvent: false});
136   - this.isFwUpdateStrategy = false;
  141 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource')
  142 + .reset(DEFAULT_FW_UPDATE_RESOURCE, {emitEvent: false});
137 143 }
138   - this.otaUpdateFwStrategyValidate(true);
139 144 });
140 145 this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateStrategy').valueChanges.pipe(
141 146 takeUntil(this.destroy$)
142 147 ).subscribe((swStrategy) => {
143 148 if (swStrategy === 2) {
144 149 this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource').enable({emitEvent: false});
145   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource')
146   - .patchValue(DEFAULT_SW_UPDATE_RESOURCE, {emitEvent: false});
147   - this.isSwUpdateStrategy = true;
148 150 } else {
149   - this.isSwUpdateStrategy = false;
150 151 this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource').disable({emitEvent: false});
  152 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource')
  153 + .reset(DEFAULT_SW_UPDATE_RESOURCE, {emitEvent: false});
151 154 }
152   - this.otaUpdateSwStrategyValidate(true);
153   - });
154   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.powerMode').valueChanges.pipe(
155   - takeUntil(this.destroy$)
156   - ).subscribe((powerMode: PowerMode) => {
157   - if (powerMode === PowerMode.E_DRX) {
158   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').enable({emitEvent: false});
159   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').patchValue(0, {emitEvent: false});
160   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle')
161   - .setValidators([Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]);
162   - } else {
163   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').disable({emitEvent: false});
164   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').clearValidators();
165   - }
166   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.edrxCycle').updateValueAndValidity({emitEvent: false});
167 155 });
168 156 this.lwm2mDeviceProfileFormGroup.valueChanges.pipe(
169 157 takeUntil(this.destroy$)
... ... @@ -198,24 +186,33 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
198 186 } else {
199 187 this.lwm2mDeviceProfileFormGroup.enable({emitEvent: false});
200 188 this.lwm2mDeviceConfigFormGroup.enable({emitEvent: false});
  189 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.powerMode').updateValueAndValidity({onlySelf: true});
  190 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateStrategy').updateValueAndValidity({onlySelf: true});
  191 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateStrategy').updateValueAndValidity({onlySelf: true});
201 192 }
202 193 }
203 194
204 195 async writeValue(value: Lwm2mProfileConfigModels | null) {
205   - if (isDefinedAndNotNull(value)) {
206   - if (value?.clientLwM2mSettings || value?.observeAttr || value?.bootstrap) {
207   - this.configurationValue = value;
208   - } else {
209   - this.configurationValue = await this.defaultProfileConfig();
210   - }
  196 + if (isDefinedAndNotNull(value) && (value?.clientLwM2mSettings || value?.observeAttr || value?.bootstrap)) {
  197 + this.configurationValue = value;
  198 + const defaultFormSettings = !(value.observeAttr.attribute.length && value.observeAttr.telemetry.length);
211 199 this.lwm2mDeviceConfigFormGroup.patchValue({
212 200 configurationJson: this.configurationValue
213   - }, {emitEvent: false});
  201 + }, {emitEvent: defaultFormSettings});
  202 + if (defaultFormSettings) {
  203 + await this.defaultProfileConfig();
  204 + }
214 205 this.initWriteValue();
215 206 }
216 207 }
217 208
218   - private async defaultProfileConfig(): Promise<Lwm2mProfileConfigModels> {
  209 + validate(): ValidationErrors | null {
  210 + return this.lwm2mDeviceProfileFormGroup.valid ? null : {
  211 + lwm2mDeviceProfile: false
  212 + };
  213 + }
  214 +
  215 + private async defaultProfileConfig(): Promise<void> {
219 216 let bootstrap: ServerSecurityConfig;
220 217 let lwm2m: ServerSecurityConfig;
221 218 try {
... ... @@ -227,15 +224,15 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
227 224 bootstrap = getDefaultBootstrapServerSecurityConfig();
228 225 lwm2m = getDefaultLwM2MServerSecurityConfig();
229 226 }
230   - return {
231   - observeAttr: getDefaultProfileObserveAttrConfig(),
232   - bootstrap: {
233   - servers: getDefaultBootstrapServersSecurityConfig(),
234   - bootstrapServer: bootstrap,
235   - lwm2mServer: lwm2m
236   - },
237   - clientLwM2mSettings: getDefaultProfileClientLwM2mSettingsConfig()
238   - };
  227 +
  228 + this.configurationValue.bootstrap.bootstrapServer = bootstrap;
  229 + this.configurationValue.bootstrap.lwm2mServer = lwm2m;
  230 + this.lwm2mDeviceConfigFormGroup.patchValue({
  231 + configurationJson: this.configurationValue
  232 + }, {emitEvent: false});
  233 + this.lwm2mDeviceProfileFormGroup.patchValue({
  234 + bootstrap: this.configurationValue.bootstrap
  235 + }, {emitEvent: false});
239 236 }
240 237
241 238 private initWriteValue = (): void => {
... ... @@ -256,10 +253,6 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
256 253 }
257 254
258 255 private updateWriteValue = (value: ObjectLwM2M[]): void => {
259   - const fwResource = isDefinedAndNotNull(this.configurationValue.clientLwM2mSettings.fwUpdateResource) ?
260   - this.configurationValue.clientLwM2mSettings.fwUpdateResource : '';
261   - const swResource = isDefinedAndNotNull(this.configurationValue.clientLwM2mSettings.swUpdateResource) ?
262   - this.configurationValue.clientLwM2mSettings.swUpdateResource : '';
263 256 this.lwm2mDeviceProfileFormGroup.patchValue({
264 257 objectIds: value,
265 258 observeAttrTelemetry: this.getObserveAttrTelemetryObjects(value),
... ... @@ -268,22 +261,19 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
268 261 clientOnlyObserveAfterConnect: this.configurationValue.clientLwM2mSettings.clientOnlyObserveAfterConnect,
269 262 fwUpdateStrategy: this.configurationValue.clientLwM2mSettings.fwUpdateStrategy || 1,
270 263 swUpdateStrategy: this.configurationValue.clientLwM2mSettings.swUpdateStrategy || 1,
271   - fwUpdateResource: fwResource,
272   - swUpdateResource: swResource,
  264 + fwUpdateResource: this.configurationValue.clientLwM2mSettings.fwUpdateResource || '',
  265 + swUpdateResource: this.configurationValue.clientLwM2mSettings.swUpdateResource || '',
273 266 powerMode: this.configurationValue.clientLwM2mSettings.powerMode || PowerMode.DRX,
274 267 edrxCycle: this.configurationValue.clientLwM2mSettings.edrxCycle || 0,
275 268 compositeOperationsSupport: this.configurationValue.clientLwM2mSettings.compositeOperationsSupport || false
276 269 }
277 270 },
278 271 {emitEvent: false});
279   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.powerMode')
280   - .patchValue(this.configurationValue.clientLwM2mSettings.powerMode || PowerMode.DRX, {emitEvent: false, onlySelf: true});
281   - this.configurationValue.clientLwM2mSettings.fwUpdateResource = fwResource;
282   - this.configurationValue.clientLwM2mSettings.swUpdateResource = swResource;
283   - this.isFwUpdateStrategy = this.configurationValue.clientLwM2mSettings.fwUpdateStrategy === 2;
284   - this.isSwUpdateStrategy = this.configurationValue.clientLwM2mSettings.swUpdateStrategy === 2;
285   - this.otaUpdateSwStrategyValidate();
286   - this.otaUpdateFwStrategyValidate();
  272 + if (!this.disabled) {
  273 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.powerMode').updateValueAndValidity({onlySelf: true});
  274 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateStrategy').updateValueAndValidity({onlySelf: true});
  275 + this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateStrategy').updateValueAndValidity({onlySelf: true});
  276 + }
287 277 }
288 278
289 279 private updateModel = (): void => {
... ... @@ -576,22 +566,8 @@ export class Lwm2mDeviceProfileTransportConfigurationComponent implements Contro
576 566 });
577 567 }
578 568
579   - private otaUpdateFwStrategyValidate(updated = false): void {
580   - if (this.isFwUpdateStrategy) {
581   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource').setValidators([Validators.required]);
582   - } else {
583   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource').clearValidators();
584   - }
585   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.fwUpdateResource').updateValueAndValidity({emitEvent: updated});
586   - }
587   -
588   - private otaUpdateSwStrategyValidate(updated = false): void {
589   - if (this.isSwUpdateStrategy) {
590   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource').setValidators([Validators.required]);
591   - } else {
592   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource').clearValidators();
593   - }
594   - this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings.swUpdateResource').updateValueAndValidity({emitEvent: updated});
  569 + get clientSettingsFormGroup(): FormGroup {
  570 + return this.lwm2mDeviceProfileFormGroup.get('clientLwM2mSettings') as FormGroup;
595 571 }
596 572
597 573 }
... ...
... ... @@ -17,7 +17,7 @@
17 17 -->
18 18 <form [formGroup]="instancesFormGroup" (ngSubmit)="add()" style="min-width: 400px;">
19 19 <mat-toolbar fxLayout="row" color="primary">
20   - <b><i>{{data.objectName}}</i></b> (object <<b>{{data.objectId}}</b>>)
  20 + <span style="font-weight: 500">{{data.objectName}}</span>&nbsp;#{{data.objectId}}
21 21 <span fxFlex></span>
22 22 <button mat-button mat-icon-button
23 23 (click)="cancel()"
... ... @@ -31,6 +31,7 @@
31 31 <div mat-dialog-content>
32 32 <fieldset [disabled]="isLoading$ | async">
33 33 <tb-profile-lwm2m-object-add-instances-list
  34 + required
34 35 formControlName="instancesIds">
35 36 </tb-profile-lwm2m-object-add-instances-list>
36 37 </fieldset>
... ...
... ... @@ -18,40 +18,32 @@
18 18 <section [formGroup]="instancesListFormGroup" class="lwm2m-instances-list">
19 19 <mat-form-field class="mat-block">
20 20 <mat-label>{{ 'device-profile.lwm2m.instances-list' | translate }}</mat-label>
21   - <mat-chip-list>
  21 + <mat-chip-list #chipList formControlName="instanceList" [required]="required" (focus)="onFocus()">
22 22 <mat-chip
23 23 *ngFor="let instanceId of instancesId"
24   - [selectable]="true"
25   - [removable]="true"
  24 + [selectable]="!disabled"
  25 + [removable]="!disabled"
26 26 (removed)="remove(instanceId)">
27 27 {{instanceId}}
28   - <mat-icon matChipRemove>close</mat-icon>
  28 + <mat-icon matChipRemove *ngIf="!disabled">close</mat-icon>
29 29 </mat-chip>
  30 + <input matInput type="text"
  31 + #instanceId
  32 + style="max-width: 70px;"
  33 + formControlName="instanceId"
  34 + [matChipInputFor]="chipList"
  35 + [matChipInputSeparatorKeyCodes]="separatorKeysCodes"
  36 + matChipInputAddOnBlur
  37 + (matChipInputTokenEnd)="add($event)">
30 38 </mat-chip-list>
31   - </mat-form-field>
32   - <mat-form-field class="mat-block">
33   - <mat-label>{{ 'device-profile.lwm2m.instances-input' | translate }}</mat-label>
34   - <input fxFlexFill matInput type='text'
35   - placeholder="{{'device-profile.lwm2m.instances-input-holder' | translate}}"
36   - formControlName="instanceIdInput">
37   - <button mat-icon-button matSuffix
38   - (click)="add()" type="button">
39   - <mat-icon>add</mat-icon>
40   - </button>
41   - <mat-error *ngIf="instancesListFormGroup.get('instanceIdInput').hasError('min')">
42   - {{ 'device-profile.lwm2m.valid-id-instance' | translate: {
43   - count: 2, instance: instanceId, min: instanceIdValueMin
44   - } }}
  39 + <mat-error *ngIf="instancesListFormGroup.get('instanceList').hasError('required')">
  40 + {{ 'device-profile.lwm2m.instances-list-required' | translate }}
45 41 </mat-error>
46   - <mat-error *ngIf="instancesListFormGroup.get('instanceIdInput').hasError('max')">
47   - {{ 'device-profile.lwm2m.valid-id-instance' | translate: {
48   - count: 1, instance: instanceId, max: instanceIdValueMax
49   - } }}
  42 + <mat-error *ngIf="instancesListFormGroup.get('instanceId').hasError('pattern')">
  43 + {{ 'device-profile.lwm2m.instance-id-pattern' | translate }}
50 44 </mat-error>
51   - <mat-error *ngIf="instancesListFormGroup.get('instanceIdInput').hasError('pattern')">
52   - {{ 'device-profile.lwm2m.valid-id-instance' | translate: {
53   - count: 0, instance: instanceId, max: instanceIdValueMax
54   - } }}
  45 + <mat-error *ngIf="instancesListFormGroup.get('instanceId').hasError('max')">
  46 + {{ 'device-profile.lwm2m.instance-id-max' | translate: {max: instanceIdValueMax} }}
55 47 </mat-error>
56 48 </mat-form-field>
57 49 </section>
... ...
... ... @@ -14,37 +14,76 @@
14 14 /// limitations under the License.
15 15 ///
16 16
17   -import { Component, forwardRef } from '@angular/core';
18   -import { ControlValueAccessor, FormBuilder, FormGroup, NG_VALUE_ACCESSOR, Validators } from '@angular/forms';
19   -import { INSTANCES_ID_VALUE_MAX, INSTANCES_ID_VALUE_MIN, KEY_REGEXP_NUMBER } from './lwm2m-profile-config.models';
  17 +import { Component, ElementRef, forwardRef, Input, ViewChild } from '@angular/core';
  18 +import {
  19 + ControlValueAccessor,
  20 + FormBuilder,
  21 + FormGroup,
  22 + NG_VALIDATORS,
  23 + NG_VALUE_ACCESSOR, ValidationErrors, Validator,
  24 + Validators
  25 +} from '@angular/forms';
  26 +import { INSTANCES_ID_VALUE_MAX, INSTANCES_ID_VALUE_MIN } from './lwm2m-profile-config.models';
  27 +import { coerceBooleanProperty } from '@angular/cdk/coercion';
  28 +import { COMMA, ENTER, SEMICOLON } from '@angular/cdk/keycodes';
  29 +import { MatChipInputEvent } from '@angular/material/chips';
20 30
21 31 @Component({
22 32 selector: 'tb-profile-lwm2m-object-add-instances-list',
23 33 templateUrl: './lwm2m-object-add-instances-list.component.html',
24   - providers: [{
25   - provide: NG_VALUE_ACCESSOR,
26   - useExisting: forwardRef(() => Lwm2mObjectAddInstancesListComponent),
27   - multi: true
28   - }]
  34 + providers: [
  35 + {
  36 + provide: NG_VALUE_ACCESSOR,
  37 + useExisting: forwardRef(() => Lwm2mObjectAddInstancesListComponent),
  38 + multi: true
  39 + },
  40 + {
  41 + provide: NG_VALIDATORS,
  42 + useExisting: forwardRef(() => Lwm2mObjectAddInstancesListComponent),
  43 + multi: true
  44 + }]
29 45 })
30   -export class Lwm2mObjectAddInstancesListComponent implements ControlValueAccessor {
  46 +export class Lwm2mObjectAddInstancesListComponent implements ControlValueAccessor, Validator {
31 47
32   - private disabled = false;
33   - private dirty = false;
  48 + private requiredValue: boolean;
  49 +
  50 + @Input()
  51 + disabled: boolean;
  52 +
  53 + get required(): boolean {
  54 + return this.requiredValue;
  55 + }
  56 +
  57 + @Input()
  58 + set required(value: boolean) {
  59 + this.requiredValue = coerceBooleanProperty(value);
  60 + this.updateValidators();
  61 + }
  62 +
  63 + @ViewChild('instanceId') instanceId: ElementRef<HTMLInputElement>;
34 64
35 65 instancesListFormGroup: FormGroup;
36 66 instancesId = new Set<number>();
37   - instanceIdValueMin = INSTANCES_ID_VALUE_MIN;
  67 + separatorKeysCodes = [ENTER, COMMA, SEMICOLON];
38 68 instanceIdValueMax = INSTANCES_ID_VALUE_MAX;
39 69
40 70 private propagateChange = (v: any) => { };
41 71
42 72 constructor(private fb: FormBuilder) {
43 73 this.instancesListFormGroup = this.fb.group({
44   - instanceIdInput: [null, [
45   - Validators.min(this.instanceIdValueMin),
46   - Validators.max(this.instanceIdValueMax),
47   - Validators.pattern(KEY_REGEXP_NUMBER)]]
  74 + instanceList: [null],
  75 + instanceId: [null, [
  76 + Validators.min(INSTANCES_ID_VALUE_MIN),
  77 + Validators.max(INSTANCES_ID_VALUE_MAX),
  78 + Validators.pattern('[0-9]*')]]
  79 + });
  80 + this.instancesListFormGroup.get('instanceId').statusChanges.subscribe((value) => {
  81 + if (value === 'INVALID') {
  82 + const errors = this.instancesListFormGroup.get('instanceId').errors;
  83 + this.instancesListFormGroup.get('instanceList').setErrors(errors);
  84 + } else {
  85 + this.instancesListFormGroup.get('instanceList').updateValueAndValidity({onlySelf: true});
  86 + }
48 87 });
49 88 }
50 89
... ... @@ -67,26 +106,41 @@ export class Lwm2mObjectAddInstancesListComponent implements ControlValueAccesso
67 106 writeValue(value: Set<number>): void {
68 107 if (value && value.size) {
69 108 this.instancesId = value;
  109 + this.instancesListFormGroup.patchValue({instanceList: Array.from(this.instancesId)}, {emitEvent: false});
70 110 }
71   - this.dirty = false;
72 111 }
73 112
74   - add = (): void => {
75   - if (this.instancesListFormGroup.get('instanceIdInput').valid && Number.isFinite(Number(this.instanceId))) {
76   - this.instancesId.add(Number(this.instanceId));
77   - this.instancesListFormGroup.get('instanceIdInput').setValue(null);
  113 + validate(): ValidationErrors | null {
  114 + return this.instancesListFormGroup.valid ? null : {
  115 + instancesListForm: false
  116 + };
  117 + }
  118 +
  119 + add = (event: MatChipInputEvent): void => {
  120 + const value = event.value;
  121 + if (this.instancesListFormGroup.get('instanceId').valid && value !== '' && Number.isFinite(Number(value))) {
  122 + this.instancesId.add(Number(value));
  123 + this.instancesListFormGroup.patchValue({instanceList: Array.from(this.instancesId)}, {emitEvent: false});
  124 + this.instancesListFormGroup.get('instanceId').setValue(null, {emitEvent: false});
78 125 this.propagateChange(this.instancesId);
79   - this.dirty = true;
80 126 }
81 127 }
82 128
83 129 remove = (object: number): void => {
84 130 this.instancesId.delete(object);
  131 + this.instancesListFormGroup.patchValue({instanceList: Array.from(this.instancesId)}, {emitEvent: false});
85 132 this.propagateChange(this.instancesId);
86   - this.dirty = true;
87 133 }
88 134
89   - get instanceId(): number {
90   - return this.instancesListFormGroup.get('instanceIdInput').value;
  135 + onFocus() {
  136 + setTimeout(() => {
  137 + this.instanceId.nativeElement.blur();
  138 + this.instanceId.nativeElement.focus();
  139 + }, 0);
  140 + }
  141 +
  142 + private updateValidators() {
  143 + this.instancesListFormGroup.get('instanceList').setValidators(this.required ? [Validators.required] : []);
  144 + this.instancesListFormGroup.get('instanceList').updateValueAndValidity({emitEvent: false});
91 145 }
92 146 }
... ...
... ... @@ -16,7 +16,8 @@
16 16
17 17 -->
18 18 <mat-form-field appearance="standard" [formGroup]="lwm2mListFormGroup" class="mat-block">
19   - <mat-chip-list #chipList formControlName="objectsList">
  19 + <mat-label translate>device-profile.lwm2m.object-list</mat-label>
  20 + <mat-chip-list #chipList formControlName="objectsList" [required]="required">
20 21 <mat-chip
21 22 *ngFor="let objectLwm2m of objectsList"
22 23 [selectable]="!disabled"
... ... @@ -25,7 +26,7 @@
25 26 {{objectLwm2m.name}} #{{objectLwm2m.keyId}}
26 27 <mat-icon matChipRemove *ngIf="!disabled">close</mat-icon>
27 28 </mat-chip>
28   - <input matInput type="text" placeholder="{{ !disabled ? ('device-profile.lwm2m.object-list' | translate) : '' }}"
  29 + <input matInput type="text"
29 30 style="max-width: 200px;"
30 31 #objectInput
31 32 (focusin)="onFocus()"
... ...
... ... @@ -131,7 +131,7 @@ export class Lwm2mObjectListComponent implements ControlValueAccessor, OnInit, V
131 131 if (isDisabled) {
132 132 this.lwm2mListFormGroup.disable({emitEvent: false});
133 133 if (isDefined(this.objectInput)) {
134   - this.clear();
  134 + this.clear('', false);
135 135 }
136 136 } else {
137 137 this.lwm2mListFormGroup.enable({emitEvent: false});
... ... @@ -196,12 +196,14 @@ export class Lwm2mObjectListComponent implements ControlValueAccessor, OnInit, V
196 196 }
197 197 }
198 198
199   - private clear(value: string = '') {
  199 + private clear(value = '', emitEvent = true) {
200 200 this.objectInput.nativeElement.value = value;
201   - this.lwm2mListFormGroup.get('objectLwm2m').patchValue(value);
202   - setTimeout(() => {
203   - this.objectInput.nativeElement.blur();
204   - this.objectInput.nativeElement.focus();
205   - }, 0);
  201 + this.lwm2mListFormGroup.get('objectLwm2m').patchValue(value, {emitEvent});
  202 + if (emitEvent) {
  203 + setTimeout(() => {
  204 + this.objectInput.nativeElement.blur();
  205 + this.objectInput.nativeElement.focus();
  206 + }, 0);
  207 + }
206 208 }
207 209 }
... ...
... ... @@ -28,6 +28,7 @@ import { Lwm2mObjectAddInstancesListComponent } from './lwm2m-object-add-instanc
28 28 import { CommonModule } from '@angular/common';
29 29 import { SharedModule } from '@app/shared/shared.module';
30 30 import { Lwm2mObserveAttrTelemetryInstancesComponent } from './lwm2m-observe-attr-telemetry-instances.component';
  31 +import { DeviceProfileCommonModule } from '@home/components/profile/device/common/device-profile-common.module';
31 32
32 33 @NgModule({
33 34 declarations:
... ... @@ -46,7 +47,8 @@ import { Lwm2mObserveAttrTelemetryInstancesComponent } from './lwm2m-observe-att
46 47 ],
47 48 imports: [
48 49 CommonModule,
49   - SharedModule
  50 + SharedModule,
  51 + DeviceProfileCommonModule
50 52 ],
51 53 exports: [
52 54 Lwm2mDeviceProfileTransportConfigurationComponent,
... ...
... ... @@ -18,7 +18,6 @@ import { ValidatorFn, Validators } from '@angular/forms';
18 18
19 19 export const PAGE_SIZE_LIMIT = 50;
20 20 export const INSTANCES = 'instances';
21   -export const INSTANCE = 'instance';
22 21 export const RESOURCES = 'resources';
23 22 export const OBSERVE = 'observe';
24 23 export const ATTRIBUTE = 'attribute';
... ... @@ -38,7 +37,6 @@ export const DEFAULT_BOOTSTRAP_SERVER_ACCOUNT_TIME_OUT = 0;
38 37 export const LEN_MAX_PUBLIC_KEY_RPK = 182;
39 38 export const LEN_MAX_PUBLIC_KEY_X509 = 3000;
40 39 export const KEY_REGEXP_HEX_DEC = /^[-+]?[0-9A-Fa-f]+\.?[0-9A-Fa-f]*?$/;
41   -export const KEY_REGEXP_NUMBER = /^(-?|\+?)\d*$/;
42 40 export const INSTANCES_ID_VALUE_MIN = 0;
43 41 export const INSTANCES_ID_VALUE_MAX = 65535;
44 42 export const DEFAULT_OTA_UPDATE_PROTOCOL = 'coap://';
... ... @@ -170,6 +168,8 @@ export interface ClientLwM2mSettings {
170 168 swUpdateResource: string;
171 169 powerMode: PowerMode;
172 170 edrxCycle?: number;
  171 + pagingTransmissionWindow?: number;
  172 + psmActivityTimer?: number;
173 173 compositeOperationsSupport: boolean;
174 174 }
175 175
... ...
... ... @@ -16,24 +16,6 @@
16 16
17 17 -->
18 18 <form [formGroup]="lwm2mDeviceTransportConfigurationFormGroup" style="padding-bottom: 16px;">
19   - <mat-form-field class="mat-block" fxFlex>
20   - <mat-label translate>device-profile.power-saving-mode</mat-label>
21   - <mat-select formControlName="powerMode">
22   - <mat-option [value]="null">{{ "device-profile.power-saving-mode-type.default" | translate }}</mat-option>
23   - <mat-option *ngFor="let powerMod of powerMods" [value]="powerMod">
24   - {{ powerModeTranslationMap.get(powerMod) | translate }}
25   - </mat-option>
26   - </mat-select>
27   - </mat-form-field>
28   - <mat-form-field class="mat-block" fxFlex *ngIf="lwm2mDeviceTransportConfigurationFormGroup.get('powerMode').value === 'E_DRX'">
29   - <mat-label>{{ 'device-profile.edrx-cycle' | translate }}</mat-label>
30   - <input matInput type="number" min="0" formControlName="edrxCycle" required>
31   - <mat-error *ngIf="lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').hasError('required')">
32   - {{ 'device-profile.edrx-cycle-required' | translate }}
33   - </mat-error>
34   - <mat-error *ngIf="lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').hasError('pattern') ||
35   - lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').hasError('min')">
36   - {{ 'device-profile.edrx-cycle-pattern' | translate }}
37   - </mat-error>
38   - </mat-form-field>
  19 + <tb-power-mode-settings [parentForm]="lwm2mDeviceTransportConfigurationFormGroup" [isDeviceSetting]="true">
  20 + </tb-power-mode-settings>
39 21 </form>
... ...
... ... @@ -19,8 +19,11 @@ import { ControlValueAccessor, FormBuilder, FormGroup, NG_VALUE_ACCESSOR, Valida
19 19 import { Store } from '@ngrx/store';
20 20 import { AppState } from '@app/core/core.state';
21 21 import { coerceBooleanProperty } from '@angular/cdk/coercion';
22   -import { DeviceTransportConfiguration, Lwm2mDeviceTransportConfiguration } from '@shared/models/device.models';
23   -import { PowerMode, PowerModeTranslationMap } from '@home/components/profile/device/lwm2m/lwm2m-profile-config.models';
  22 +import {
  23 + DeviceTransportConfiguration,
  24 + DeviceTransportType,
  25 + Lwm2mDeviceTransportConfiguration
  26 +} from '@shared/models/device.models';
24 27 import { takeUntil } from 'rxjs/operators';
25 28 import { Subject } from 'rxjs';
26 29 import { isDefinedAndNotNull } from '@core/utils';
... ... @@ -38,8 +41,6 @@ import { isDefinedAndNotNull } from '@core/utils';
38 41 export class Lwm2mDeviceTransportConfigurationComponent implements ControlValueAccessor, OnInit, OnDestroy {
39 42
40 43 lwm2mDeviceTransportConfigurationFormGroup: FormGroup;
41   - powerMods = Object.values(PowerMode);
42   - powerModeTranslationMap = PowerModeTranslationMap;
43 44
44 45 private requiredValue: boolean;
45 46 get required(): boolean {
... ... @@ -70,21 +71,9 @@ export class Lwm2mDeviceTransportConfigurationComponent implements ControlValueA
70 71 ngOnInit() {
71 72 this.lwm2mDeviceTransportConfigurationFormGroup = this.fb.group({
72 73 powerMode: [null],
73   - edrxCycle: [0]
74   - });
75   - this.lwm2mDeviceTransportConfigurationFormGroup.get('powerMode').valueChanges.pipe(
76   - takeUntil(this.destroy$)
77   - ).subscribe((powerMode: PowerMode) => {
78   - if (powerMode === PowerMode.E_DRX) {
79   - this.lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').enable({emitEvent: false});
80   - this.lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').patchValue(0, {emitEvent: false});
81   - this.lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle')
82   - .setValidators([Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]);
83   - } else {
84   - this.lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').disable({emitEvent: false});
85   - this.lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').clearValidators();
86   - }
87   - this.lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').updateValueAndValidity({emitEvent: false});
  74 + edrxCycle: [{disabled: true, value: 0}, [Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]],
  75 + psmActivityTimer: [{disabled: true, value: 0}, [Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]],
  76 + pagingTransmissionWindow: [{disabled: true, value: 0}, [Validators.required, Validators.min(0), Validators.pattern('[0-9]*')]]
88 77 });
89 78 this.lwm2mDeviceTransportConfigurationFormGroup.valueChanges.pipe(
90 79 takeUntil(this.destroy$)
... ... @@ -104,15 +93,18 @@ export class Lwm2mDeviceTransportConfigurationComponent implements ControlValueA
104 93 this.lwm2mDeviceTransportConfigurationFormGroup.disable({emitEvent: false});
105 94 } else {
106 95 this.lwm2mDeviceTransportConfigurationFormGroup.enable({emitEvent: false});
  96 + this.lwm2mDeviceTransportConfigurationFormGroup.get('powerMode').updateValueAndValidity({onlySelf: true});
107 97 }
108 98 }
109 99
110 100 writeValue(value: Lwm2mDeviceTransportConfiguration | null): void {
111 101 if (isDefinedAndNotNull(value)) {
112   - this.lwm2mDeviceTransportConfigurationFormGroup.get('powerMode').patchValue(value.powerMode, {emitEvent: false, onlySelf: true});
113   - this.lwm2mDeviceTransportConfigurationFormGroup.get('edrxCycle').patchValue(value.edrxCycle || 0, {emitEvent: false});
  102 + this.lwm2mDeviceTransportConfigurationFormGroup.patchValue(value, {emitEvent: false});
114 103 } else {
115   - this.lwm2mDeviceTransportConfigurationFormGroup.patchValue({powerMode: null, edrxCycle: 0}, {emitEvent: false});
  104 + this.lwm2mDeviceTransportConfigurationFormGroup.get('powerMode').patchValue(null, {emitEvent: false});
  105 + }
  106 + if (!this.disabled) {
  107 + this.lwm2mDeviceTransportConfigurationFormGroup.get('powerMode').updateValueAndValidity({onlySelf: true});
116 108 }
117 109 }
118 110
... ... @@ -120,7 +112,7 @@ export class Lwm2mDeviceTransportConfigurationComponent implements ControlValueA
120 112 let configuration: DeviceTransportConfiguration = null;
121 113 if (this.lwm2mDeviceTransportConfigurationFormGroup.valid) {
122 114 configuration = this.lwm2mDeviceTransportConfigurationFormGroup.value;
123   - // configuration.type = DeviceTransportType.LWM2M;
  115 + configuration.type = DeviceTransportType.LWM2M;
124 116 }
125 117 this.propagateChange(configuration);
126 118 }
... ...
... ... @@ -34,6 +34,7 @@ import { CoapDeviceTransportConfigurationComponent } from './data/coap-device-tr
34 34 import { Lwm2mDeviceTransportConfigurationComponent } from './data/lwm2m-device-transport-configuration.component';
35 35 import { SnmpDeviceTransportConfigurationComponent } from './data/snmp-device-transport-configuration.component';
36 36 import { DeviceCredentialsModule } from '@home/components/device/device-credentials.module';
  37 +import { DeviceProfileCommonModule } from '@home/components/profile/device/common/device-profile-common.module';
37 38
38 39 @NgModule({
39 40 declarations: [
... ... @@ -57,6 +58,7 @@ import { DeviceCredentialsModule } from '@home/components/device/device-credenti
57 58 HomeComponentsModule,
58 59 HomeDialogsModule,
59 60 DeviceCredentialsModule,
  61 + DeviceProfileCommonModule,
60 62 DeviceRoutingModule
61 63 ]
62 64 })
... ...
... ... @@ -30,7 +30,14 @@ import { AbstractControl, ValidationErrors } from '@angular/forms';
30 30 import { OtaPackageId } from '@shared/models/id/ota-package-id';
31 31 import { DashboardId } from '@shared/models/id/dashboard-id';
32 32 import { DataType } from '@shared/models/constants';
33   -import { PowerMode } from '@home/components/profile/device/lwm2m/lwm2m-profile-config.models';
  33 +import {
  34 + getDefaultBootstrapServerSecurityConfig,
  35 + getDefaultBootstrapServersSecurityConfig,
  36 + getDefaultLwM2MServerSecurityConfig,
  37 + getDefaultProfileClientLwM2mSettingsConfig,
  38 + getDefaultProfileObserveAttrConfig,
  39 + PowerMode
  40 +} from '@home/components/profile/device/lwm2m/lwm2m-profile-config.models';
34 41
35 42 export enum DeviceProfileType {
36 43 DEFAULT = 'DEFAULT',
... ... @@ -369,7 +376,15 @@ export function createDeviceProfileTransportConfiguration(type: DeviceTransportT
369 376 transportConfiguration = {...coapTransportConfiguration, type: DeviceTransportType.COAP};
370 377 break;
371 378 case DeviceTransportType.LWM2M:
372   - const lwm2mTransportConfiguration: Lwm2mDeviceProfileTransportConfiguration = {};
  379 + const lwm2mTransportConfiguration: Lwm2mDeviceProfileTransportConfiguration = {
  380 + observeAttr: getDefaultProfileObserveAttrConfig(),
  381 + bootstrap: {
  382 + servers: getDefaultBootstrapServersSecurityConfig(),
  383 + bootstrapServer: getDefaultBootstrapServerSecurityConfig(),
  384 + lwm2mServer: getDefaultLwM2MServerSecurityConfig()
  385 + },
  386 + clientLwM2mSettings: getDefaultProfileClientLwM2mSettingsConfig()
  387 + };
373 388 transportConfiguration = {...lwm2mTransportConfiguration, type: DeviceTransportType.LWM2M};
374 389 break;
375 390 case DeviceTransportType.SNMP:
... ... @@ -404,7 +419,9 @@ export function createDeviceTransportConfiguration(type: DeviceTransportType): D
404 419 transportConfiguration = {...coapTransportConfiguration, type: DeviceTransportType.COAP};
405 420 break;
406 421 case DeviceTransportType.LWM2M:
407   - const lwm2mTransportConfiguration: Lwm2mDeviceTransportConfiguration = {};
  422 + const lwm2mTransportConfiguration: Lwm2mDeviceTransportConfiguration = {
  423 + powerMode: null
  424 + };
408 425 transportConfiguration = {...lwm2mTransportConfiguration, type: DeviceTransportType.LWM2M};
409 426 break;
410 427 case DeviceTransportType.SNMP:
... ... @@ -592,7 +609,8 @@ export interface CoapDeviceTransportConfiguration {
592 609 export interface Lwm2mDeviceTransportConfiguration {
593 610 powerMode?: PowerMode | null;
594 611 edrxCycle?: number;
595   - [key: string]: any;
  612 + pagingTransmissionWindow?: number;
  613 + psmActivityTimer?: number;
596 614 }
597 615
598 616 export enum SnmpDeviceProtocolVersion {
... ...
... ... @@ -1242,14 +1242,12 @@
1242 1242 "object-list": "Object list",
1243 1243 "object-list-empty": "No objects selected.",
1244 1244 "no-objects-matching": "No objects matching '{{object}}' were found.",
1245   - "valid-id-instance-no-min": "Instance number '{{instance}}' no validated. Min value='{{min}}'",
1246   - "valid-id-instance-no-max": "Instance number '{{instance}}' no validated. Max value='{{max}}'",
1247   - "valid-id-instance": "Instance number '{{instance}}' no validated. { count, plural, 1 {Max value='{{max}}'} 2 {Min value='{{min}}'} other {Must be only number} }",
1248 1245 "model-tab": "LWM2M Model",
1249 1246 "add-new-instances": "Add new instances",
1250 1247 "instances-list": "Instances list",
1251   - "instances-input": "Input Instance Id value",
1252   - "instances-input-holder": "Input Instance number...",
  1248 + "instances-list-required": "Instances list is required.",
  1249 + "instance-id-pattern": "Instance id must be a positive integer.",
  1250 + "instance-id-max": "Maximum instance id value {{max}}.",
1253 1251 "instance": "Instance",
1254 1252 "resource-label": "#ID Resource name",
1255 1253 "observe-label": "Observe",
... ...