Fix tag select bug in tag component

Signed-off-by: AllForNothing <sshijun@vmware.com>
This commit is contained in:
AllForNothing 2019-11-12 10:25:03 +08:00
parent 407417ce7b
commit 7f1201dec9
6 changed files with 36 additions and 32 deletions

View File

@ -55,10 +55,10 @@
<div class="col-lg-12 col-md-12 col-sm-12 col-xs-12">
<clr-datagrid [clrDgLoading]="loading" class="datagrid-top" [class.embeded-datagrid]="isEmbedded" [(clrDgSelected)]="selectedRow">
<clr-dg-action-bar>
<button [clrLoading]="scanBtnState" type="button" class="btn btn-sm btn-secondary" [disabled]="!(canScanNow(selectedRow) && selectedRow.length==1 && hasEnabledScanner)" (click)="scanNow(selectedRow)"><clr-icon shape="shield-check" size="16"></clr-icon>&nbsp;{{'VULNERABILITY.SCAN_NOW' | translate}}</button>
<button type="button" class="btn btn-sm btn-secondary" [disabled]="!(selectedRow.length==1)" (click)="showDigestId(selectedRow)"><clr-icon shape="copy" size="16"></clr-icon>&nbsp;{{'REPOSITORY.COPY_DIGEST_ID' | translate}}</button>
<button [clrLoading]="scanBtnState" type="button" class="btn btn-sm btn-secondary" [disabled]="!(canScanNow() && selectedRow.length==1 && hasEnabledScanner)" (click)="scanNow()"><clr-icon shape="shield-check" size="16"></clr-icon>&nbsp;{{'VULNERABILITY.SCAN_NOW' | translate}}</button>
<button type="button" class="btn btn-sm btn-secondary" [disabled]="!(selectedRow.length==1)" (click)="showDigestId()"><clr-icon shape="copy" size="16"></clr-icon>&nbsp;{{'REPOSITORY.COPY_DIGEST_ID' | translate}}</button>
<clr-dropdown *ngIf="!withAdmiral">
<button type="button" class="btn btn-sm btn-secondary" clrDropdownTrigger [disabled]="!(selectedRow.length==1)||!hasAddLabelImagePermission" (click)="addLabels(selectedRow)"><clr-icon shape="plus" size="16"></clr-icon>{{'REPOSITORY.ADD_LABELS' | translate}}</button>
<button type="button" class="btn btn-sm btn-secondary" clrDropdownTrigger [disabled]="!(selectedRow.length==1)||!hasAddLabelImagePermission" (click)="addLabels()"><clr-icon shape="plus" size="16"></clr-icon>{{'REPOSITORY.ADD_LABELS' | translate}}</button>
<clr-dropdown-menu clrPosition="bottom-left" *clrIfOpen>
<clr-dropdown>
<div class="filter-grid">
@ -75,8 +75,8 @@
</clr-dropdown>
</clr-dropdown-menu>
</clr-dropdown>
<button type="button" class="btn btn-sm btn-secondary" *ngIf="!withAdmiral" [disabled]="!(selectedRow.length===1)|| !hasRetagImagePermission" (click)="retag(selectedRow)"><clr-icon shape="copy" size="16"></clr-icon>&nbsp;{{'REPOSITORY.RETAG' | translate}}</button>
<button type="button" class="btn btn-sm btn-secondary" *ngIf="hasDeleteImagePermission" (click)="deleteTags(selectedRow)" [disabled]="!hasDeleteImagePermission||!selectedRow.length"><clr-icon shape="times" size="16"></clr-icon>&nbsp;{{'REPOSITORY.DELETE' | translate}}</button>
<button type="button" class="btn btn-sm btn-secondary" *ngIf="!withAdmiral" [disabled]="!(selectedRow.length===1)|| !hasRetagImagePermission" (click)="retag()"><clr-icon shape="copy" size="16"></clr-icon>&nbsp;{{'REPOSITORY.RETAG' | translate}}</button>
<button type="button" class="btn btn-sm btn-secondary" *ngIf="hasDeleteImagePermission" (click)="deleteTags()" [disabled]="!hasDeleteImagePermission||!selectedRow.length"><clr-icon shape="times" size="16"></clr-icon>&nbsp;{{'REPOSITORY.DELETE' | translate}}</button>
</clr-dg-action-bar>
<clr-dg-column class="flex-max-width" [clrDgField]="'name'">{{'REPOSITORY.TAG' | translate}}</clr-dg-column>
<clr-dg-column [clrDgField]="'size'">{{'REPOSITORY.SIZE' | translate}}</clr-dg-column>
@ -109,7 +109,7 @@
</clr-dg-cell>
<clr-dg-cell>
<div class="cell">
<hbr-vulnerability-bar [repoName]="repoName" [tagId]="t.name" [summary]="handleScanOverview(t.scan_overview)"></hbr-vulnerability-bar>
<hbr-vulnerability-bar (submitFinish)="submitFinish($event)" [repoName]="repoName" [tagId]="t.name" [summary]="handleScanOverview(t.scan_overview)"></hbr-vulnerability-bar>
</div>
</clr-dg-cell>
<clr-dg-cell *ngIf="withNotary" [ngSwitch]="t.signature !== null">

View File

@ -153,6 +153,7 @@ export class TagComponent implements OnInit, AfterViewInit {
hasScanImagePermission: boolean;
hasEnabledScanner: boolean;
scanBtnState: ClrLoadingState = ClrLoadingState.DEFAULT;
onSendingScanCommand: boolean;
constructor(
private errorHandler: ErrorHandler,
private tagService: TagService,
@ -318,11 +319,11 @@ export class TagComponent implements OnInit, AfterViewInit {
}
}
addLabels(tag: Tag[]): void {
addLabels(): void {
this.labelListOpen = true;
this.selectedTag = tag;
this.selectedTag = this.selectedRow;
this.stickName = '';
this.labelSelectedChange(tag);
this.labelSelectedChange(this.selectedRow);
}
stickLabel(labelInfo: LabelState): void {
@ -558,10 +559,10 @@ export class TagComponent implements OnInit, AfterViewInit {
}
}
retag(tags: Tag[]) {
if (tags && tags.length) {
retag() {
if (this.selectedRow && this.selectedRow.length) {
this.retagDialogOpened = true;
this.retagSrcImage = this.repoName + ":" + tags[0].digest;
this.retagSrcImage = this.repoName + ":" + this.selectedRow[0].digest;
} else {
this.errorHandler.error("One tag should be selected before retag.");
}
@ -588,10 +589,10 @@ export class TagComponent implements OnInit, AfterViewInit {
});
}
deleteTags(tags: Tag[]) {
if (tags && tags.length) {
deleteTags() {
if (this.selectedRow && this.selectedRow.length) {
let tagNames: string[] = [];
tags.forEach(tag => {
this.selectedRow.forEach(tag => {
tagNames.push(tag.name);
});
@ -604,7 +605,7 @@ export class TagComponent implements OnInit, AfterViewInit {
titleKey,
summaryKey,
content,
tags,
this.selectedRow,
ConfirmationTargets.TAG,
buttons);
this.confirmationDialog.open(message);
@ -670,10 +671,10 @@ export class TagComponent implements OnInit, AfterViewInit {
}
}
showDigestId(tag: Tag[]) {
if (tag && (tag.length === 1)) {
showDigestId() {
if (this.selectedRow && (this.selectedRow.length === 1)) {
this.manifestInfoTitle = "REPOSITORY.COPY_DIGEST_ID";
this.digestId = tag[0].digest;
this.digestId = this.selectedRow[0].digest;
this.showTagManifestOpened = true;
this.copyFailed = false;
}
@ -716,9 +717,10 @@ export class TagComponent implements OnInit, AfterViewInit {
return VULNERABILITY_SCAN_STATUS.NOT_SCANNED;
}
// Whether show the 'scan now' menu
canScanNow(t: Tag[]): boolean {
canScanNow(): boolean {
if (!this.hasScanImagePermission) { return false; }
let st: string = this.scanStatus(t[0]);
if (this.onSendingScanCommand) { return false; }
let st: string = this.scanStatus(this.selectedRow[0]);
return st !== VULNERABILITY_SCAN_STATUS.RUNNING;
}
getImagePermissionRule(projectId: number): void {
@ -742,15 +744,18 @@ export class TagComponent implements OnInit, AfterViewInit {
}, error => this.errorHandler.error(error));
}
// Trigger scan
scanNow(t: Tag[]): void {
if (t && t.length) {
t.forEach((data: any) => {
scanNow(): void {
if (this.selectedRow && this.selectedRow.length) {
this.selectedRow.forEach((data: any) => {
let tagId = data.name;
this.onSendingScanCommand = true;
this.channel.publishScanEvent(this.repoName + "/" + tagId);
});
}
}
submitFinish(e: boolean) {
this.onSendingScanCommand = e;
}
// pull command
onCpError($event: any): void {
this.copyInput.setPullCommendShow();

View File

@ -3,7 +3,7 @@ import {
Input,
OnInit,
OnDestroy,
ChangeDetectorRef,
ChangeDetectorRef, Output, EventEmitter,
} from '@angular/core';
import { Subscription , timer} from "rxjs";
@ -17,6 +17,7 @@ import {
import { ErrorHandler } from '../error-handler/index';
import { ChannelService } from '../channel/index';
import { JobLogService } from "../service/index";
import { finalize } from "rxjs/operators";
const STATE_CHECK_INTERVAL: number = 3000; // 3s
const RETRY_TIMES: number = 3;
@ -35,6 +36,8 @@ export class ResultBarChartComponent implements OnInit, OnDestroy {
stateCheckTimer: Subscription;
scanSubscription: Subscription;
timerHandler: any;
@Output()
submitFinish: EventEmitter<boolean> = new EventEmitter<boolean>();
constructor(
private tagService: TagService,
@ -114,6 +117,7 @@ export class ResultBarChartComponent implements OnInit, OnDestroy {
this.onSubmitting = true;
this.scanningService.startVulnerabilityScanning(this.repoName, this.tagId)
.pipe(finalize(() => this.submitFinish.emit(false)))
.subscribe(() => {
this.onSubmitting = false;

View File

@ -26,7 +26,7 @@
<span class="margin-left-10 font-weight-800 color-green font-size-12">{{fixableCount}}</span>
<span class="margin-left-5 color-green font-size-12">{{'SCANNER.FIXABLE' | translate}}</span>
</div>
<div *ngIf="isNone" class="margin-left-5 tip-wrapper bar-block-none shadow-none width-150">{{'VULNERABILITY.NO_VULNERABILITY' | translate }}</div>
<div *ngIf="isNone" class="pl-1 margin-left-5 tip-wrapper bar-block-none shadow-none width-150">{{'VULNERABILITY.NO_VULNERABILITY' | translate }}</div>
</div>
<clr-tooltip-content class="w-800" [clrPosition]="'right'" [clrSize]="'lg'" *clrIfOpen>
<div class="bar-tooltip-font-larger">

View File

@ -288,8 +288,6 @@ hr {
color: green;
}
.tip-block {
height: $thirty-pixel;
line-height: $thirty-pixel;
position: relative;
}
.font-size-14 {

View File

@ -1,6 +1,5 @@
.bar-wrapper {
width: 210px;
height: 15px;
}
.bar-state {
text-align: center !important;
@ -10,7 +9,6 @@
}
.bar-state-chart {
margin-top: 2px;
.loop-height {
height: 2px;
}
@ -18,7 +16,6 @@
.bar-state-error {
position: relative;
top: -4px;
}
.error-text {