</tr>
<tr *ngIf="selection.lifecycle_progress?.length > 0">
<td i18n
- class="bold w-25">Lifecycle Progress</td>
+ class="bold w-25">
+ Lifecycle progress
+ </td>
<td>
- <cds-tooltip [description]="lifecycleProgressMap.get(lifecycleProgress)?.description"
+ <cds-tooltip [description]="lifecycleProgressMap.get(lifecycleProgress.status)?.description"
[align]="'top'">
<cds-tag size="md"
- [type]="lifecycleProgressMap.get(lifecycleProgress)?.color">
- {{ lifecycleProgress }}
+ [type]="lifecycleProgressMap.get(lifecycleProgress.status)?.color">
+ {{ lifecycleProgress.status }}
</cds-tag>
</cds-tooltip>
+ <div *ngIf="lifecycleProgress?.status !== 'UNINITIAL'"
+ class="spacing-left">{{lifecycleProgress?.started}}</div>
</td>
</tr>
<tr>
<a ngbNavLink
i18n>Tiering</a>
<ng-template ngbNavContent>
- <cd-rgw-bucket-lifecycle-list [bucket]="selection"></cd-rgw-bucket-lifecycle-list>
+ <cd-rgw-bucket-lifecycle-list [bucket]="selection"
+ (updateBucketDetails)="updateBucketDetails(extractLifecycleDetails.bind(this))"></cd-rgw-bucket-lifecycle-list>
</ng-template>
</ng-container>
</nav>
+@use '@carbon/layout';
+
table {
table-layout: fixed;
}
max-height: 50vh;
overflow: auto;
}
+
+.spacing-left {
+ margin-left: layout.$spacing-03;
+}
rgwBucketServiceGetSpy.and.returnValue(of(bucket));
component.selection = { bid: 'bucket' };
component.lifecycleFormat = 'json';
- component.ngOnChanges();
+ component.extraxtDetailsfromResponse();
expect(component.selection.lifecycle).toEqual({});
});
const rateLimit = { bucket_ratelimit: { max_size: 1000 } };
spyOn(rgwBucketService, 'getBucketRateLimit').and.returnValue(of(rateLimit));
component.selection = { bid: 'bucket' };
- component.ngOnChanges();
+ component.extraxtDetailsfromResponse();
expect(component.bucketRateLimit).toEqual(rateLimit.bucket_ratelimit);
});
export class RgwBucketDetailsComponent implements OnChanges {
@Input()
selection: any;
- lifecycleProgress: string;
+ lifecycleProgress: { bucket: string; status: string; started: string };
lifecycleProgressMap = new Map<string, { description: string; color: string }>([
['UNINITIAL', { description: $localize`The process has not run yet`, color: 'cool-gray' }],
['PROCESSING', { description: $localize`The process is currently running`, color: 'cyan' }],
constructor(private rgwBucketService: RgwBucketService) {}
ngOnChanges() {
- if (this.selection) {
- this.rgwBucketService.get(this.selection.bid).subscribe((bucket: object) => {
- bucket['lock_retention_period_days'] = this.rgwBucketService.getLockDays(bucket);
- this.selection = bucket;
- if (this.lifecycleFormat === 'json' && !this.selection.lifecycle) {
- this.selection.lifecycle = {};
- }
- this.aclPermissions = this.parseXmlAcl(this.selection.acl, this.selection.owner);
- if (this.selection.replication?.['Rule']?.['Status']) {
- this.replicationStatus = this.selection.replication?.['Rule']?.['Status'];
- }
- if (this.selection.lifecycle_progress?.length > 0) {
- this.selection.lifecycle_progress.forEach(
- (progress: { bucket: string; status: string; started: string }) => {
- if (progress.bucket.includes(this.selection.bucket)) {
- this.lifecycleProgress = progress.status;
- }
- }
- );
- }
- });
- this.rgwBucketService.getBucketRateLimit(this.selection.bid).subscribe((resp: any) => {
- if (resp && resp.bucket_ratelimit !== undefined) {
- this.bucketRateLimit = resp.bucket_ratelimit;
- }
- });
- }
+ this.updateBucketDetails(this.extraxtDetailsfromResponse.bind(this));
}
parseXmlAcl(xml: any, bucketOwner: string): Record<string, string[]> {
});
return data;
}
+
+ updateBucketDetails(cbFn: Function) {
+ if (this.selection) {
+ this.rgwBucketService.get(this.selection.bid).subscribe((bucket: object) => {
+ bucket['lock_retention_period_days'] = this.rgwBucketService.getLockDays(bucket);
+ this.selection = bucket;
+ cbFn();
+ });
+ }
+ }
+
+ extraxtDetailsfromResponse() {
+ this.aclPermissions = this.parseXmlAcl(this.selection.acl, this.selection.owner);
+ if (this.selection.replication?.['Rule']?.['Status']) {
+ this.replicationStatus = this.selection.replication?.['Rule']?.['Status'];
+ }
+ this.rgwBucketService.getBucketRateLimit(this.selection.bid).subscribe((resp: any) => {
+ if (resp && resp.bucket_ratelimit !== undefined) {
+ this.bucketRateLimit = resp.bucket_ratelimit;
+ }
+ });
+ this.extractLifecycleDetails();
+ }
+
+ extractLifecycleDetails() {
+ if (this.lifecycleFormat === 'json' && !this.selection.lifecycle) {
+ this.selection.lifecycle = {};
+ }
+ if (this.selection.lifecycle_progress?.length > 0) {
+ this.selection.lifecycle_progress.forEach(
+ (progress: { bucket: string; status: string; started: string }) => {
+ if (progress.bucket.includes(this.selection.bucket)) {
+ this.lifecycleProgress = progress;
+ }
+ }
+ );
+ }
+ }
}
-import { Component, Input, OnInit, ViewChild } from '@angular/core';
+import { Component, EventEmitter, Input, OnInit, Output, ViewChild } from '@angular/core';
import { Bucket } from '../models/rgw-bucket';
import { RgwBucketService } from '~/app/shared/api/rgw-bucket.service';
import { AuthStorageService } from '~/app/shared/services/auth-storage.service';
})
export class RgwBucketLifecycleListComponent implements OnInit {
@Input() bucket: Bucket;
+ @Output() updateBucketDetails = new EventEmitter();
@ViewChild(TableComponent, { static: true })
table: TableComponent;
permission: Permission;
}
openTieringModal(type: string) {
- this.modalService.show(RgwBucketTieringFormComponent, {
+ const modalRef = this.modalService.show(RgwBucketTieringFormComponent, {
bucket: this.bucket,
selectedLifecycle: this.selection.first(),
editing: type === this.actionLabels.EDIT ? true : false
});
+ modalRef?.close?.subscribe(() => this.updateBucketDetails.emit());
}
updateSelection(selection: CdTableSelection) {
NotificationType.success,
$localize`Lifecycle rule deleted successfully`
);
+ this.updateBucketDetails.emit();
},
error: () => {
this.modalRef.componentInstance.stopLoadingSpinner();
expect(tableActions).toEqual({
'create,update,delete': {
- actions: ['Create', 'Edit', 'Delete', 'Tiering'],
+ actions: ['Create', 'Edit', 'Tiering', 'Delete'],
primary: {
multiple: 'Create',
executing: 'Create',
}
},
'update,delete': {
- actions: ['Edit', 'Delete', 'Tiering'],
+ actions: ['Edit', 'Tiering', 'Delete'],
primary: {
multiple: '',
executing: '',
disable: () => !this.selection.hasSelection,
name: this.actionLabels.TIERING
};
- this.tableActions = [addAction, editAction, deleteAction, tieringAction];
+ this.tableActions = [addAction, editAction, tieringAction, deleteAction];
this.setTableRefreshTimeout();
}