Merge pull request #6469 from zhoumeina/fix_scan_log_viewer

fix #6432 modify scan log to use popup window
This commit is contained in:
Mia ZHOU 2018-12-06 15:11:03 +08:00 committed by GitHub
commit 657ee8a150
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
17 changed files with 13 additions and 214 deletions

View File

@ -36,7 +36,6 @@ import {
ProjectDefaultService,
ProjectService
} from "../service/project.service";
import { JobLogViewerComponent } from "../job-log-viewer/job-log-viewer.component";
import { OperationService } from "../operation/operation.service";
import {FilterLabelComponent} from "./filter-label.component";
import {LabelService} from "../service/label.service";
@ -242,7 +241,6 @@ describe("CreateEditRuleComponent (inline template)", () => {
DatePickerComponent,
FilterComponent,
InlineAlertComponent,
JobLogViewerComponent,
FilterLabelComponent,
LabelPieceComponent
],

View File

@ -20,7 +20,6 @@ import { DATETIME_PICKER_DIRECTIVES } from './datetime-picker/index';
import { VULNERABILITY_DIRECTIVES } from './vulnerability-scanning/index';
import { PUSH_IMAGE_BUTTON_DIRECTIVES } from './push-image/index';
import { CONFIGURATION_DIRECTIVES } from './config/index';
import { JOB_LOG_VIEWER_DIRECTIVES } from './job-log-viewer/index';
import { PROJECT_POLICY_CONFIG_DIRECTIVES } from './project-policy-config/index';
import { HBR_GRIDVIEW_DIRECTIVES } from './gridview/index';
import { REPOSITORY_GRIDVIEW_DIRECTIVES } from './repository-gridview/index';
@ -191,7 +190,6 @@ export function initConfig(translateInitializer: TranslateServiceInitializer, co
VULNERABILITY_DIRECTIVES,
PUSH_IMAGE_BUTTON_DIRECTIVES,
CONFIGURATION_DIRECTIVES,
JOB_LOG_VIEWER_DIRECTIVES,
PROJECT_POLICY_CONFIG_DIRECTIVES,
LABEL_DIRECTIVES,
CREATE_EDIT_LABEL_DIRECTIVES,
@ -218,7 +216,6 @@ export function initConfig(translateInitializer: TranslateServiceInitializer, co
VULNERABILITY_DIRECTIVES,
PUSH_IMAGE_BUTTON_DIRECTIVES,
CONFIGURATION_DIRECTIVES,
JOB_LOG_VIEWER_DIRECTIVES,
TranslateModule,
PROJECT_POLICY_CONFIG_DIRECTIVES,
LABEL_DIRECTIVES,

View File

@ -17,7 +17,6 @@ export * from './i18n/index';
export * from './push-image/index';
export * from './third-party/index';
export * from './config/index';
export * from './job-log-viewer/index';
export * from './channel/index';
export * from './project-policy-config/index';
export * from './label/index';

View File

@ -1,9 +0,0 @@
import { Type } from '@angular/core';
import { JobLogViewerComponent } from './job-log-viewer.component';
export * from './job-log-viewer.component';
export const JOB_LOG_VIEWER_DIRECTIVES: Type<any>[] = [
JobLogViewerComponent
];

View File

@ -1,14 +0,0 @@
<clr-modal [(clrModalOpen)]="opened" [clrModalStaticBackdrop]="true" [clrModalSize]="'xl'">
<h3 class="modal-title" class="log-viewer-title" style="margin-top: 0px;">{{title | translate }}</h3>
<div class="modal-body">
<div class="loading-back" [hidden]="!onGoing">
<span class="spinner spinner-md"></span>
</div>
<pre [hidden]="onGoing">
<code>{{log}}</code>
</pre>
</div>
<div class="modal-footer">
<button type="button" class="btn btn-primary" (click)="close()">{{ 'BUTTON.CLOSE' | translate}}</button>
</div>
</clr-modal>

View File

@ -1,12 +0,0 @@
.log-viewer-title {
line-height: 24px;
color: #000000;
font-size: 22px;
}
.loading-back {
height: 358px;
display: flex;
align-items: center;
justify-content: center;
}

View File

@ -1,58 +0,0 @@
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
// tslint:disable-next-line:no-unused-variable
import { Observable } from "rxjs";
import { JobLogService, JobLogDefaultService } from '../service/index';
import { JobLogViewerComponent } from './job-log-viewer.component';
import { SERVICE_CONFIG, IServiceConfig } from '../service.config';
import { ErrorHandler } from '../error-handler/index';
import { SharedModule } from '../shared/shared.module';
describe('JobLogViewerComponent (inline template)', () => {
let component: JobLogViewerComponent;
let fixture: ComponentFixture<JobLogViewerComponent>;
let serviceConfig: IServiceConfig;
let jobLogService: JobLogDefaultService;
let spy: jasmine.Spy;
let testConfig: IServiceConfig = {
replicationJobEndpoint: "/api/jobs/replication/testing"
};
beforeEach(async(() => {
TestBed.configureTestingModule({
imports: [
SharedModule,
BrowserAnimationsModule
],
declarations: [JobLogViewerComponent],
providers: [
ErrorHandler,
{ provide: SERVICE_CONFIG, useValue: testConfig },
{ provide: JobLogService, useClass: JobLogDefaultService }
]
});
}));
beforeEach(() => {
fixture = TestBed.createComponent(JobLogViewerComponent);
component = fixture.componentInstance;
serviceConfig = TestBed.get(SERVICE_CONFIG);
jobLogService = fixture.debugElement.injector.get(JobLogService);
spy = spyOn(jobLogService, 'getJobLog')
.and.returnValue(Promise.resolve("job log text"));
fixture.detectChanges();
});
it('should be created', () => {
fixture.detectChanges();
expect(component).toBeTruthy();
expect(serviceConfig).toBeTruthy();
expect(serviceConfig.replicationJobEndpoint).toEqual("/api/jobs/replication/testing");
component.open(16);
});
});

View File

@ -1,90 +0,0 @@
// Copyright Project Harbor Authors
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
import {
ChangeDetectionStrategy,
ChangeDetectorRef,
Component,
Input
} from "@angular/core";
import { JobLogService } from "../service/index";
import { ErrorHandler } from "../error-handler/index";
import { toPromise } from "../utils";
const supportSet: string[] = ["replication", "scan"];
@Component({
selector: "job-log-viewer",
templateUrl: "./job-log-viewer.component.html",
styleUrls: ["./job-log-viewer.component.scss"],
changeDetection: ChangeDetectionStrategy.OnPush
})
export class JobLogViewerComponent {
_jobType: string = "replication";
opened: boolean = false;
log: string = "";
onGoing: boolean = true;
@Input()
get jobType(): string {
return this._jobType;
}
set jobType(v: string) {
if (supportSet.find((t: string) => t === v)) {
this._jobType = v;
}
}
get title(): string {
if (this.jobType === "scan") {
return "VULNERABILITY.JOB_LOG_VIEWER";
}
return "REPLICATION.JOB_LOG_VIEWER";
}
constructor(
private jobLogService: JobLogService,
private errorHandler: ErrorHandler,
private ref: ChangeDetectorRef
) {}
open(jobId: number | string): void {
this.opened = true;
this.load(jobId);
}
close(): void {
this.opened = false;
this.log = "";
}
load(jobId: number | string): void {
this.onGoing = true;
toPromise<string>(this.jobLogService.getJobLog(this.jobType, jobId))
.then((log: string) => {
this.onGoing = false;
this.log = log;
})
.catch(error => {
this.onGoing = false;
this.errorHandler.error(error);
});
let hnd = setInterval(() => this.ref.markForCheck(), 100);
setTimeout(() => clearInterval(hnd), 2000);
}
}

View File

@ -17,7 +17,6 @@ import { ErrorHandler } from '../error-handler/error-handler';
import { SERVICE_CONFIG, IServiceConfig } from '../service.config';
import { ReplicationService, ReplicationDefaultService } from '../service/replication.service';
import { EndpointService, EndpointDefaultService } from '../service/endpoint.service';
import { JobLogViewerComponent } from '../job-log-viewer/job-log-viewer.component';
import { JobLogService, JobLogDefaultService, ReplicationJobItem } from '../service/index';
import {ProjectDefaultService, ProjectService} from "../service/project.service";
import {OperationService} from "../operation/operation.service";
@ -226,7 +225,6 @@ describe('Replication Component (inline template)', () => {
DatePickerComponent,
FilterComponent,
InlineAlertComponent,
JobLogViewerComponent,
FilterLabelComponent,
LabelPieceComponent
],

View File

@ -21,7 +21,6 @@ import { VULNERABILITY_DIRECTIVES } from '../vulnerability-scanning/index';
import { HBR_GRIDVIEW_DIRECTIVES } from '../gridview/index';
import { PUSH_IMAGE_BUTTON_DIRECTIVES } from '../push-image/index';
import { INLINE_ALERT_DIRECTIVES } from '../inline-alert/index';
import { JobLogViewerComponent } from '../job-log-viewer/index';
import { LabelPieceComponent } from "../label-piece/label-piece.component";
import { OperationService } from "../operation/operation.service";
import {ProjectDefaultService, ProjectService, RetagDefaultService, RetagService} from "../service";
@ -112,7 +111,6 @@ describe('RepositoryComponentGridview (inline template)', () => {
PUSH_IMAGE_BUTTON_DIRECTIVES,
INLINE_ALERT_DIRECTIVES,
HBR_GRIDVIEW_DIRECTIVES,
JobLogViewerComponent
],
providers: [
ErrorHandler,

View File

@ -14,7 +14,6 @@ import { TagComponent } from '../tag/tag.component';
import { VULNERABILITY_DIRECTIVES } from '../vulnerability-scanning/index';
import { PUSH_IMAGE_BUTTON_DIRECTIVES } from '../push-image/index';
import { INLINE_ALERT_DIRECTIVES } from '../inline-alert/index';
import { JobLogViewerComponent } from '../job-log-viewer/index';
import { ErrorHandler } from '../error-handler/error-handler';
@ -168,7 +167,6 @@ describe('RepositoryComponent (inline template)', () => {
VULNERABILITY_DIRECTIVES,
PUSH_IMAGE_BUTTON_DIRECTIVES,
INLINE_ALERT_DIRECTIVES,
JobLogViewerComponent,
],
providers: [
ErrorHandler,

View File

@ -21,6 +21,8 @@ export abstract class JobLogService {
* returns {(Observable<string> | Promise<string> | string)}
* @memberof JobLogService
*/
abstract getScanJobBaseUrl(): string;
abstract getJobLog(
jobType: string,
jobId: number | string
@ -70,6 +72,10 @@ export class JobLogDefaultService extends JobLogService {
return false;
}
public getScanJobBaseUrl() {
return this._scanningJobBaseUrl;
}
public getJobLog(
jobType: string,
jobId: number | string

View File

@ -24,7 +24,6 @@ import { FilterComponent } from "../filter/index";
import { VULNERABILITY_SCAN_STATUS } from "../utils";
import { VULNERABILITY_DIRECTIVES } from "../vulnerability-scanning/index";
import { LabelPieceComponent } from "../label-piece/label-piece.component";
import { JobLogViewerComponent } from "../job-log-viewer/job-log-viewer.component";
import { ChannelService } from "../channel/channel.service";
import {
JobLogService,
@ -99,7 +98,6 @@ describe("TagDetailComponent (inline template)", () => {
ResultGridComponent,
VULNERABILITY_DIRECTIVES,
LabelPieceComponent,
JobLogViewerComponent,
FilterComponent
],
providers: [

View File

@ -17,7 +17,6 @@ import { VULNERABILITY_DIRECTIVES } from "../vulnerability-scanning/index";
import { FILTER_DIRECTIVES } from "../filter/index";
import { ChannelService } from "../channel/index";
import { JobLogViewerComponent } from "../job-log-viewer/index";
import { CopyInputComponent } from "../push-image/copy-input.component";
import { LabelPieceComponent } from "../label-piece/label-piece.component";
import { LabelDefaultService, LabelService } from "../service/label.service";
@ -108,7 +107,6 @@ describe("TagComponent (inline template)", () => {
ImageNameInputComponent,
VULNERABILITY_DIRECTIVES,
FILTER_DIRECTIVES,
JobLogViewerComponent,
CopyInputComponent
],
providers: [

View File

@ -6,7 +6,7 @@
<span class="label label-orange">{{'VULNERABILITY.STATE.QUEUED' | translate}}</span>
</div>
<div *ngIf="error" class="bar-state bar-state-error">
<a href="javascript:void(0);" class="error-text" (click)="viewLog()">
<a class="error-text" target="_blank" [href]="viewLog()">
<clr-icon shape="error" class="is-error" size="24"></clr-icon>
{{'VULNERABILITY.STATE.ERROR' | translate}}
</a>
@ -22,5 +22,4 @@
<clr-icon shape="warning" class="is-warning" size="24"></clr-icon>
<span style="margin-left:-5px;">{{'VULNERABILITY.STATE.UNKNOWN' | translate}}</span>
</div>
<job-log-viewer #scanningLogViewer [jobType]="'scan'"></job-log-viewer>
</div>

View File

@ -16,7 +16,6 @@ import { ErrorHandler } from '../error-handler/index';
import { SharedModule } from '../shared/shared.module';
import { VULNERABILITY_SCAN_STATUS } from '../utils';
import { ChannelService } from '../channel/index';
import { JobLogViewerComponent } from '../job-log-viewer/index';
describe('ResultBarChartComponent (inline template)', () => {
let component: ResultBarChartComponent;
@ -54,8 +53,7 @@ describe('ResultBarChartComponent (inline template)', () => {
],
declarations: [
ResultBarChartComponent,
ResultTipComponent,
JobLogViewerComponent],
ResultTipComponent],
providers: [
ErrorHandler,
ChannelService,

View File

@ -18,7 +18,7 @@ import {
import { ErrorHandler } from '../error-handler/index';
import { toPromise } from '../utils';
import { ChannelService } from '../channel/index';
import { JobLogViewerComponent } from '../job-log-viewer/index';
import { JobLogService } from "../service/index";
const STATE_CHECK_INTERVAL: number = 2000; // 2s
const RETRY_TIMES: number = 3;
@ -38,15 +38,13 @@ export class ResultBarChartComponent implements OnInit, OnDestroy {
scanSubscription: Subscription;
timerHandler: any;
@ViewChild("scanningLogViewer")
scanningJobLogViewer: JobLogViewerComponent;
constructor(
private tagService: TagService,
private scanningService: ScanningResultService,
private errorHandler: ErrorHandler,
private channel: ChannelService,
private ref: ChangeDetectorRef
private ref: ChangeDetectorRef,
private jobLogService: JobLogService,
) { }
ngOnInit(): void {
@ -200,10 +198,7 @@ export class ResultBarChartComponent implements OnInit, OnDestroy {
}, duration);
}
// Check error log
viewLog(): void {
if (this.summary && this.summary.job_id) {
this.scanningJobLogViewer.open(this.summary.job_id);
}
viewLog(): string {
return this.jobLogService.getScanJobBaseUrl() + "/" + this.summary.job_id + "/log";
}
}