]> git-server-git.apps.pok.os.sepia.ceph.com Git - ceph.git/blob
c3be8b02a64ce04004c55d865f4927c48edab324
[ceph.git] /
1 <div class="col-sm-12 col-lg-6">
2   <form name="targetForm"
3         #formDir="ngForm"
4         [formGroup]="targetForm"
5         novalidate
6         *ngIf="targetForm">
7     <div class="card">
8       <div i18n="form title|Example: Create Pool@@formTitle"
9            class="card-header">{{ action | titlecase }} {{ resource | upperFirst }}</div>
10
11       <div class="card-body">
12         <!-- Target IQN -->
13         <div class="form-group row">
14           <label class="col-form-label col-sm-3"
15                  for="target_iqn">
16             <ng-container i18n>Target IQN</ng-container>
17             <span class="required"></span>
18           </label>
19           <div class="col-sm-9">
20             <div class="input-group">
21               <input class="form-control"
22                      type="text"
23                      id="target_iqn"
24                      name="target_iqn"
25                      formControlName="target_iqn" />
26               <span class="input-group-append">
27                 <button class="btn btn-light"
28                         id="ecp-info-button"
29                         type="button"
30                         (click)="targetSettingsModal()">
31                   <i [ngClass]="[icons.deepCheck]"
32                      aria-hidden="true"></i>
33                 </button>
34               </span>
35             </div>
36
37             <span class="invalid-feedback"
38                   *ngIf="targetForm.showError('target_iqn', formDir, 'required')"
39                   i18n>This field is required.</span>
40
41             <span class="invalid-feedback"
42                   *ngIf="targetForm.showError('target_iqn', formDir, 'pattern')"
43                   i18n>IQN has wrong pattern.</span>
44
45             <span class="invalid-feedback"
46                   *ngIf="targetForm.showError('target_iqn', formDir, 'iqn')">
47               <ng-container i18n>An IQN has the following notation
48                 'iqn.$year-$month.$reversedAddress:$definedName'</ng-container>
49               <br>
50               <ng-container i18n>For example: iqn.2016-06.org.dashboard:storage:disk.sn-a8675309</ng-container>
51               <br>
52               <a target="_blank"
53                  href="https://en.wikipedia.org/wiki/ISCSI#Addressing"
54                  i18n>More information</a>
55             </span>
56
57             <span class="form-text text-muted"
58                   *ngIf="hasAdvancedSettings(targetForm.getValue('target_controls'))"
59                   i18n>This target has modified advanced settings.</span>
60             <hr />
61           </div>
62         </div>
63
64         <!-- Portals -->
65         <div class="form-group row">
66           <label class="col-form-label col-sm-3"
67                  for="portals">
68             <ng-container i18n>Portals</ng-container>
69             <span class="required"></span>
70           </label>
71           <div class="col-sm-9">
72
73             <ng-container *ngFor="let portal of portals.value; let i = index">
74               <div class="input-group cd-mb">
75                 <input class="cd-form-control"
76                        type="text"
77                        [value]="portal"
78                        disabled />
79                 <span class="input-group-append">
80                   <button class="btn btn-light"
81                           type="button"
82                           (click)="removePortal(i, portal)">
83                     <i [ngClass]="[icons.destroy]"
84                        aria-hidden="true"></i>
85                   </button>
86                 </span>
87               </div>
88             </ng-container>
89
90             <div class="row">
91               <div class="col-md-12">
92                 <cd-select [data]="portals.value"
93                            [options]="portalsSelections"
94                            [messages]="messages.portals"
95                            (selection)="onPortalSelection($event)"
96                            elemClass="btn btn-light float-right">
97                   <i [ngClass]="[icons.add]"></i>
98                   <ng-container i18n>Add portal</ng-container>
99                 </cd-select>
100               </div>
101             </div>
102
103             <input class="form-control"
104                    type="hidden"
105                    id="portals"
106                    name="portals"
107                    formControlName="portals" />
108
109             <span class="invalid-feedback"
110                   *ngIf="targetForm.showError('portals', formDir, 'minGateways')"
111                   i18n>At least {{ minimum_gateways }} gateways are required.</span>
112
113             <hr />
114           </div>
115         </div>
116
117         <!-- Images -->
118         <div class="form-group row">
119           <label class="col-form-label col-sm-3"
120                  for="disks"
121                  i18n>Images</label>
122           <div class="col-sm-9">
123             <ng-container *ngFor="let image of targetForm.getValue('disks'); let i = index">
124               <div class="input-group cd-mb">
125                 <input class="cd-form-control"
126                        type="text"
127                        [value]="image"
128                        disabled />
129                 <span class="input-group-append">
130                   <button class="btn btn-light"
131                           type="button"
132                           (click)="imageSettingsModal(image)">
133                     <i [ngClass]="[icons.deepCheck]"
134                        aria-hidden="true"></i>
135                   </button>
136                   <button class="btn btn-light"
137                           type="button"
138                           (click)="removeImage(i, image)">
139                     <i [ngClass]="[icons.destroy]"
140                        aria-hidden="true"></i>
141                   </button>
142                 </span>
143
144               </div>
145
146               <span class="form-text text-muted">
147                 <ng-container *ngIf="backstores.length > 1"
148                               i18n>Backstore: {{ imagesSettings[image].backstore | iscsiBackstore }}.&nbsp;</ng-container>
149
150                 <ng-container *ngIf="hasAdvancedSettings(imagesSettings[image][imagesSettings[image].backstore])"
151                               i18n>This image has modified settings.</ng-container>
152               </span>
153             </ng-container>
154
155             <div class="row">
156               <div class="col-md-12">
157                 <cd-select [data]="disks.value"
158                            [options]="imagesSelections"
159                            [messages]="messages.images"
160                            (selection)="onImageSelection($event)"
161                            elemClass="btn btn-light float-right">
162                   <i [ngClass]="[icons.add]"></i>
163                   <ng-container i18n>Add image</ng-container>
164                 </cd-select>
165               </div>
166             </div>
167
168             <hr />
169           </div>
170         </div>
171
172         <!-- acl_enabled -->
173         <div class="form-group row">
174           <div class="offset-sm-3 col-sm-9">
175             <div class="custom-control custom-checkbox">
176               <input type="checkbox"
177                      class="custom-control-input"
178                      formControlName="acl_enabled"
179                      name="acl_enabled"
180                      id="acl_enabled">
181               <label for="acl_enabled"
182                      class="custom-control-label"
183                      i18n>ACL authentication</label>
184             </div>
185
186             <hr />
187           </div>
188         </div>
189
190         <!-- Target level authentication was introduced in ceph-iscsi config v11 -->
191         <div formGroupName="auth" *ngIf="cephIscsiConfigVersion > 10 && !targetForm.getValue('acl_enabled')">
192
193           <!-- Target user -->
194           <div class="form-group row">
195             <label class="col-form-label col-sm-3"
196                    for="target_user">
197               <ng-container i18n>User</ng-container>
198             </label>
199             <div class="col-sm-9">
200               <input class="form-control"
201                      type="text"
202                      id="target_user"
203                      name="target_user"
204                      formControlName="user" />
205
206               <span class="invalid-feedback"
207                     *ngIf="targetForm.showError('user', formDir, 'required')"
208                     i18n>This field is required.</span>
209
210               <span class="invalid-feedback"
211                     *ngIf="targetForm.showError('user', formDir, 'pattern')"
212                     i18n>Usernames must have a length of 8 to 64 characters and
213                 can only contain letters, '.', '@', '-', '_' or ':'.</span>
214             </div>
215           </div>
216
217           <!-- Target password -->
218           <div class="form-group row">
219             <label class="col-form-label col-sm-3"
220                    for="target_password">
221               <ng-container i18n>Password</ng-container>
222             </label>
223             <div class="col-sm-9">
224               <div class="input-group">
225                 <input class="form-control"
226                        type="password"
227                        autocomplete="new-password"
228                        id="target_password"
229                        name="target_password"
230                        formControlName="password" />
231
232                 <span class="input-group-append">
233                   <button type="button"
234                           class="btn btn-light"
235                           cdPasswordButton="target_password">
236                   </button>
237                   <button type="button"
238                           class="btn btn-light"
239                           cdCopy2ClipboardButton="target_password">
240                   </button>
241                 </span>
242               </div>
243
244               <span class="invalid-feedback"
245                     *ngIf="targetForm.showError('password', formDir, 'required')"
246                     i18n>This field is required.</span>
247
248               <span class="invalid-feedback"
249                     *ngIf="targetForm.showError('password', formDir, 'pattern')"
250                     i18n>Passwords must have a length of 12 to 16 characters
251                 and can only contain letters, '@', '-', '_' or '/'.</span>
252             </div>
253           </div>
254
255           <!-- Target mutual_user -->
256           <div class="form-group row">
257             <label class="col-form-label col-sm-3"
258                    for="target_mutual_user">
259               <ng-container i18n>Mutual User</ng-container>
260             </label>
261             <div class="col-sm-9">
262               <input class="form-control"
263                      type="text"
264                      id="target_mutual_user"
265                      name="target_mutual_user"
266                      formControlName="mutual_user" />
267
268               <span class="invalid-feedback"
269                     *ngIf="targetForm.showError('mutual_user', formDir, 'required')"
270                     i18n>This field is required.</span>
271
272               <span class="invalid-feedback"
273                     *ngIf="targetForm.showError('mutual_user', formDir, 'pattern')"
274                     i18n>Usernames must have a length of 8 to 64 characters and
275                 can only contain letters, '.', '@', '-', '_' or ':'.</span>
276             </div>
277           </div>
278
279           <!-- Target mutual_password -->
280           <div class="form-group row">
281             <label class="col-form-label col-sm-3"
282                    for="target_mutual_password">
283               <ng-container i18n>Mutual Password</ng-container>
284             </label>
285             <div class="col-sm-9">
286               <div class="input-group">
287                 <input class="form-control"
288                        type="password"
289                        autocomplete="new-password"
290                        id="target_mutual_password"
291                        name="target_mutual_password"
292                        formControlName="mutual_password" />
293
294                 <span class="input-group-append">
295                   <button type="button"
296                           class="btn btn-light"
297                           cdPasswordButton="target_mutual_password">
298                   </button>
299                   <button type="button"
300                           class="btn btn-light"
301                           cdCopy2ClipboardButton="target_mutual_password">
302                   </button>
303                 </span>
304               </div>
305
306               <span class="invalid-feedback"
307                     *ngIf="targetForm.showError('mutual_password', formDir, 'required')"
308                     i18n>This field is required.</span>
309
310               <span class="invalid-feedback"
311                     *ngIf="targetForm.showError('mutual_password', formDir, 'pattern')"
312                     i18n>Passwords must have a length of 12 to 16 characters
313                 and can only contain letters, '@', '-', '_' or '/'.</span>
314             </div>
315           </div>
316
317         </div>
318
319         <!-- Initiators -->
320         <div class="form-group row"
321              *ngIf="targetForm.getValue('acl_enabled')">
322           <label class="col-form-label col-sm-3"
323                  for="initiators"
324                  i18n>Initiators</label>
325           <div class="col-sm-9"
326                formArrayName="initiators">
327             <div class="card mb-2"
328                  *ngFor="let initiator of initiators.controls; let ii = index"
329                  [formGroupName]="ii">
330               <div class="card-header">
331                 <ng-container i18n>Initiator</ng-container>: {{ initiator.getValue('client_iqn') }}
332                 <button type="button"
333                         class="close"
334                         (click)="removeInitiator(ii)">
335                   <i [ngClass]="[icons.destroy]"></i>
336                 </button>
337               </div>
338               <div class="card-body">
339                 <!-- Initiator: Name -->
340                 <div class="form-group row">
341                   <label class="col-form-label col-sm-3"
342                          for="client_iqn">
343                     <ng-container i18n>Client IQN</ng-container>
344                     <span class="required"></span>
345                   </label>
346                   <div class="col-sm-9">
347                     <input class="form-control"
348                            type="text"
349                            formControlName="client_iqn"
350                            (blur)="updatedInitiatorSelector()">
351
352                     <span class="invalid-feedback"
353                           *ngIf="initiator.showError('client_iqn', formDir, 'notUnique')"
354                           i18n>Initiator IQN needs to be unique.</span>
355
356                     <span class="invalid-feedback"
357                           *ngIf="initiator.showError('client_iqn', formDir, 'required')"
358                           i18n>This field is required.</span>
359
360                     <span class="invalid-feedback"
361                           *ngIf="initiator.showError('client_iqn', formDir, 'pattern')"
362                           i18n>IQN has wrong pattern.</span>
363                   </div>
364                 </div>
365
366                 <ng-container formGroupName="auth">
367                   <!-- Initiator: User -->
368                   <div class="form-group row">
369                     <label class="col-form-label col-sm-3"
370                            for="user"
371                            i18n>User</label>
372                     <div class="col-sm-9">
373                       <input [id]="'user' + ii"
374                              class="form-control"
375                              formControlName="user"
376                              type="text">
377                       <span class="invalid-feedback"
378                             *ngIf="initiator.showError('user', formDir, 'required')"
379                             i18n>This field is required.</span>
380
381                       <span class="invalid-feedback"
382                             *ngIf="initiator.showError('user', formDir, 'pattern')"
383                             i18n>Usernames must have a length of 8 to 64 characters and
384                         can only contain letters, '.', '@', '-', '_' or ':'.</span>
385                     </div>
386                   </div>
387
388                   <!-- Initiator: Password -->
389                   <div class="form-group row">
390                     <label class="col-form-label col-sm-3"
391                            for="password"
392                            i18n>Password</label>
393                     <div class="col-sm-9">
394                       <div class="input-group">
395                         <input [id]="'password' + ii"
396                                class="form-control"
397                                formControlName="password"
398                                type="password">
399
400                         <span class="input-group-append">
401                           <button type="button"
402                                   class="btn btn-light"
403                                   [cdPasswordButton]="'password' + ii">
404                           </button>
405                           <button type="button"
406                                   class="btn btn-light"
407                                   [cdCopy2ClipboardButton]="'password' + ii">
408                           </button>
409                         </span>
410                       </div>
411                       <span class="invalid-feedback"
412                             *ngIf="initiator.showError('password', formDir, 'required')"
413                             i18n>This field is required.</span>
414
415                       <span class="invalid-feedback"
416                             *ngIf="initiator.showError('password', formDir, 'pattern')"
417                             i18n>Passwords must have a length of 12 to 16 characters
418                         and can only contain letters, '@', '-', '_' or '/'.</span>
419                     </div>
420                   </div>
421
422
423                   <!-- Initiator: mutual_user -->
424                   <div class="form-group row">
425                     <label class="col-form-label col-sm-3"
426                            for="mutual_user">
427                       <ng-container i18n>Mutual User</ng-container>
428                     </label>
429                     <div class="col-sm-9">
430                       <input [id]="'mutual_user' + ii"
431                              class="form-control"
432                              formControlName="mutual_user"
433                              type="text">
434
435                       <span class="invalid-feedback"
436                             *ngIf="initiator.showError('mutual_user', formDir, 'required')"
437                             i18n>This field is required.</span>
438
439                       <span class="invalid-feedback"
440                             *ngIf="initiator.showError('mutual_user', formDir, 'pattern')"
441                             i18n>Usernames must have a length of 8 to 64 characters and
442                         can only contain letters, '.', '@', '-', '_' or ':'.</span>
443                     </div>
444                   </div>
445
446                   <!-- Initiator: mutual_password -->
447                   <div class="form-group row">
448                     <label class="col-form-label col-sm-3"
449                            for="mutual_password"
450                            i18n>Mutual Password</label>
451                     <div class="col-sm-9">
452                       <div class="input-group">
453                         <input [id]="'mutual_password' + ii"
454                                class="form-control"
455                                formControlName="mutual_password"
456                                type="password">
457
458                         <span class="input-group-append">
459                           <button type="button"
460                                   class="btn btn-light"
461                                   [cdPasswordButton]="'mutual_password' + ii">
462                           </button>
463                           <button type="button"
464                                   class="btn btn-light"
465                                   [cdCopy2ClipboardButton]="'mutual_password' + ii">
466                           </button>
467                         </span>
468                       </div>
469                       <span class="invalid-feedback"
470                             *ngIf="initiator.showError('mutual_password', formDir, 'required')"
471                             i18n>This field is required.</span>
472
473                       <span class="invalid-feedback"
474                             *ngIf="initiator.showError('mutual_password', formDir, 'pattern')"
475                             i18n>Passwords must have a length of 12 to 16 characters and
476                         can only contain letters, '@', '-', '_' or '/'.</span>
477                     </div>
478                   </div>
479                 </ng-container>
480
481                 <!-- Initiator: Images -->
482                 <div class="form-group row">
483                   <label class="col-form-label col-sm-3"
484                          for="luns"
485                          i18n>Images</label>
486                   <div class="col-sm-9">
487                     <ng-container *ngFor="let image of initiator.getValue('luns'); let li = index">
488                       <div class="input-group cd-mb">
489                         <input class="cd-form-control"
490                                type="text"
491                                [value]="image"
492                                disabled />
493                         <span class="input-group-append">
494                           <button class="btn btn-light"
495                                   type="button"
496                                   (click)="removeInitiatorImage(initiator, li, ii, image)">
497                             <i [ngClass]="[icons.destroy]"
498                                aria-hidden="true"></i>
499                           </button>
500                         </span>
501                       </div>
502                     </ng-container>
503
504                     <span *ngIf="initiator.getValue('cdIsInGroup')"
505                           i18n>Initiator belongs to a group. Images will be configure in the group.</span>
506
507                     <div class="row"
508                          *ngIf="!initiator.getValue('cdIsInGroup')">
509                       <div class="col-md-12">
510                         <cd-select [data]="initiator.getValue('luns')"
511                                    [options]="imagesInitiatorSelections[ii]"
512                                    [messages]="messages.initiatorImage"
513                                    elemClass="btn btn-light float-right">
514                           <i [ngClass]="[icons.add]"></i>
515                           <ng-container i18n>Add image</ng-container>
516                         </cd-select>
517                       </div>
518                     </div>
519                   </div>
520                 </div>
521               </div>
522             </div>
523
524             <div class="row">
525               <div class="col-md-12">
526                 <span class="form-text text-muted"
527                       *ngIf="initiators.controls.length === 0"
528                       i18n>No items added.</span>
529
530                 <button (click)="addInitiator(); false"
531                         class="btn btn-light float-right">
532                   <i [ngClass]="[icons.add]"></i>
533                   <ng-container i18n>Add initiator</ng-container>
534                 </button>
535               </div>
536             </div>
537
538             <hr />
539           </div>
540         </div>
541
542         <!-- Groups -->
543         <div class="form-group row"
544              *ngIf="targetForm.getValue('acl_enabled')">
545           <label class="col-form-label col-sm-3"
546                  for="initiators"
547                  i18n>Groups</label>
548           <div class="col-sm-9"
549                formArrayName="groups">
550             <div class="card mb-2"
551                  *ngFor="let group of groups.controls; let gi = index"
552                  [formGroupName]="gi">
553               <div class="card-header">
554                 <ng-container i18n>Group</ng-container>: {{ group.getValue('group_id') }}
555                 <button type="button"
556                         class="close"
557                         (click)="groups.removeAt(gi)">
558                   <i [ngClass]="[icons.destroy]"></i>
559                 </button>
560               </div>
561               <div class="card-body">
562                 <!-- Group: group_id -->
563                 <div class="form-group row">
564                   <label class="col-form-label col-sm-3"
565                          for="group_id">
566                     <ng-container i18n>Name</ng-container>
567                     <span class="required"></span>
568                   </label>
569                   <div class="col-sm-9">
570                     <input class="form-control"
571                            type="text"
572                            formControlName="group_id">
573                   </div>
574                 </div>
575
576                 <!-- Group: members -->
577                 <div class="form-group row">
578                   <label class="col-form-label col-sm-3"
579                          for="members">
580                     <ng-container i18n>Initiators</ng-container>
581                   </label>
582                   <div class="col-sm-9">
583                     <ng-container *ngFor="let member of group.getValue('members'); let i = index">
584                       <div class="input-group cd-mb">
585                         <input class="cd-form-control"
586                                type="text"
587                                [value]="member"
588                                disabled />
589                         <span class="input-group-append">
590                           <button class="btn btn-light"
591                                   type="button"
592                                   (click)="removeGroupInitiator(group, i, gi)">
593                             <i [ngClass]="[icons.destroy]"
594                                aria-hidden="true"></i>
595                           </button>
596                         </span>
597                       </div>
598                     </ng-container>
599
600                     <div class="row">
601                       <div class="col-md-12">
602                         <cd-select [data]="group.getValue('members')"
603                                    [options]="groupMembersSelections[gi]"
604                                    [messages]="messages.groupInitiator"
605                                    (selection)="onGroupMemberSelection($event)"
606                                    elemClass="btn btn-light float-right">
607                           <i [ngClass]="[icons.add]"></i>
608                           <ng-container i18n>Add initiator</ng-container>
609                         </cd-select>
610                       </div>
611                     </div>
612
613                     <hr />
614                   </div>
615                 </div>
616
617                 <!-- Group: disks -->
618                 <div class="form-group row">
619                   <label class="col-form-label col-sm-3"
620                          for="disks">
621                     <ng-container i18n>Images</ng-container>
622                   </label>
623                   <div class="col-sm-9">
624                     <ng-container *ngFor="let disk of group.getValue('disks'); let i = index">
625                       <div class="input-group cd-mb">
626                         <input class="cd-form-control"
627                                type="text"
628                                [value]="disk"
629                                disabled />
630                         <span class="input-group-append">
631                           <button class="btn btn-light"
632                                   type="button"
633                                   (click)="removeGroupDisk(group, i, gi)">
634                             <i [ngClass]="[icons.destroy]"
635                                aria-hidden="true"></i>
636                           </button>
637                         </span>
638                       </div>
639                     </ng-container>
640
641                     <div class="row">
642                       <div class="col-md-12">
643                         <cd-select [data]="group.getValue('disks')"
644                                    [options]="groupDiskSelections[gi]"
645                                    [messages]="messages.initiatorImage"
646                                    elemClass="btn btn-light float-right">
647                           <i [ngClass]="[icons.add]"></i>
648                           <ng-container i18n>Add image</ng-container>
649                         </cd-select>
650                       </div>
651                     </div>
652
653                     <hr />
654                   </div>
655                 </div>
656               </div>
657             </div>
658
659             <div class="row">
660               <div class="col-md-12">
661                 <span class="form-text text-muted"
662                       *ngIf="groups.controls.length === 0"
663                       i18n>No items added.</span>
664
665                 <button (click)="addGroup(); false"
666                         class="btn btn-light float-right">
667                   <i [ngClass]="[icons.add]"></i>
668                   <ng-container i18n>Add group</ng-container>
669                 </button>
670               </div>
671             </div>
672           </div>
673         </div>
674
675       </div>
676       <div class="card-footer">
677         <div class="button-group text-right">
678           <cd-submit-button (submitAction)="submit()"
679                             i18n="form action button|Example: Create Pool@@formActionButton"
680                             [form]="formDir">{{ action | titlecase }} {{ resource | upperFirst }}</cd-submit-button>
681           <cd-back-button></cd-back-button>
682         </div>
683       </div>
684     </div>
685   </form>
686 </div>