mirror of
https://github.com/goharbor/harbor.git
synced 2024-11-22 02:05:41 +01:00
parent
c791b39a26
commit
dee73a44f3
@ -78,6 +78,7 @@ export const ACTION_RESOURCE_I18N_MAP = {
|
||||
log: 'ROBOT_ACCOUNT.LOG',
|
||||
'notification-policy': 'ROBOT_ACCOUNT.NOTIFICATION_POLICY',
|
||||
quota: 'ROBOT_ACCOUNT.QUOTA',
|
||||
sbom: 'ROBOT_ACCOUNT.SBOM',
|
||||
};
|
||||
|
||||
export function convertKey(key: string) {
|
||||
|
@ -13,10 +13,13 @@
|
||||
[clrIfActive]="currentTabLinkId === 'vulnerability'">
|
||||
<clr-tab-content id="vulnerability-content">
|
||||
<hbr-artifact-vulnerabilities
|
||||
*ngIf="currentTabLinkId === 'vulnerability'"
|
||||
[artifact]="artifact"
|
||||
[projectName]="projectName"
|
||||
[projectId]="projectId"
|
||||
[repoName]="repoName"
|
||||
[scanBtnState]="getScanBtnState()"
|
||||
[hasEnabledScanner]="hasEnabledScanner()"
|
||||
[digest]="digest"
|
||||
[vulnerabilitiesLink]="
|
||||
getVulnerability()
|
||||
@ -24,16 +27,18 @@
|
||||
</clr-tab-content>
|
||||
</ng-template>
|
||||
</clr-tab>
|
||||
<clr-tab *ngIf="getSbom()">
|
||||
<clr-tab *ngIf="hasScannerSupportSBOM()">
|
||||
<button clrTabLink id="sbom" (click)="actionTab('sbom')">
|
||||
{{ 'REPOSITORY.SBOM' | translate }}
|
||||
</button>
|
||||
<ng-template [clrIfActive]="currentTabLinkId === 'sbom'">
|
||||
<clr-tab-content id="sbom-content">
|
||||
<hbr-artifact-sbom
|
||||
*ngIf="currentTabLinkId === 'sbom'"
|
||||
[artifact]="artifact"
|
||||
[projectName]="projectName"
|
||||
[projectId]="projectId"
|
||||
[hasScannerSupportSBOM]="hasScannerSupportSBOM()"
|
||||
[repoName]="repoName"
|
||||
[sbomDigest]="sbomDigest"></hbr-artifact-sbom>
|
||||
</clr-tab-content>
|
||||
@ -50,6 +55,7 @@
|
||||
[clrIfActive]="currentTabLinkId === 'build-history'">
|
||||
<clr-tab-content>
|
||||
<hbr-artifact-build-history
|
||||
*ngIf="currentTabLinkId === 'build-history'"
|
||||
[buildHistoryLink]="
|
||||
getBuildHistory()
|
||||
"></hbr-artifact-build-history>
|
||||
@ -67,6 +73,7 @@
|
||||
[clrIfActive]="currentTabLinkId === 'summary-link'">
|
||||
<clr-tab-content id="summary-content">
|
||||
<hbr-artifact-summary
|
||||
*ngIf="currentTabLinkId === 'summary-link'"
|
||||
[summaryLink]="getSummary()"></hbr-artifact-summary>
|
||||
</clr-tab-content>
|
||||
</ng-template>
|
||||
@ -81,6 +88,7 @@
|
||||
<ng-template [clrIfActive]="currentTabLinkId === 'depend-link'">
|
||||
<clr-tab-content id="depend-content">
|
||||
<hbr-artifact-dependencies
|
||||
*ngIf="currentTabLinkId === 'depend-link'"
|
||||
[dependenciesLink]="
|
||||
getDependencies()
|
||||
"></hbr-artifact-dependencies>
|
||||
@ -97,6 +105,7 @@
|
||||
<ng-template [clrIfActive]="currentTabLinkId === 'value-link'">
|
||||
<clr-tab-content id="value-content">
|
||||
<hbr-artifact-values
|
||||
*ngIf="currentTabLinkId === 'value-link'"
|
||||
[valuesLink]="getValues()"></hbr-artifact-values>
|
||||
</clr-tab-content>
|
||||
</ng-template>
|
||||
|
@ -4,6 +4,8 @@ import { AdditionLinks } from '../../../../../../../ng-swagger-gen/models/additi
|
||||
import { CURRENT_BASE_HREF } from '../../../../../shared/units/utils';
|
||||
import { SharedTestingModule } from '../../../../../shared/shared.module';
|
||||
import { NO_ERRORS_SCHEMA } from '@angular/core';
|
||||
import { ArtifactListPageService } from '../artifact-list-page/artifact-list-page.service';
|
||||
import { ClrLoadingState } from '@clr/angular';
|
||||
|
||||
describe('ArtifactAdditionsComponent', () => {
|
||||
const mockedAdditionLinks: AdditionLinks = {
|
||||
@ -12,6 +14,18 @@ describe('ArtifactAdditionsComponent', () => {
|
||||
href: CURRENT_BASE_HREF + '/test',
|
||||
},
|
||||
};
|
||||
const mockedArtifactListPageService = {
|
||||
hasScannerSupportSBOM(): boolean {
|
||||
return true;
|
||||
},
|
||||
hasEnabledScanner(): boolean {
|
||||
return true;
|
||||
},
|
||||
getScanBtnState(): ClrLoadingState {
|
||||
return ClrLoadingState.SUCCESS;
|
||||
},
|
||||
init() {},
|
||||
};
|
||||
let component: ArtifactAdditionsComponent;
|
||||
let fixture: ComponentFixture<ArtifactAdditionsComponent>;
|
||||
|
||||
@ -20,6 +34,12 @@ describe('ArtifactAdditionsComponent', () => {
|
||||
imports: [SharedTestingModule],
|
||||
declarations: [ArtifactAdditionsComponent],
|
||||
schemas: [NO_ERRORS_SCHEMA],
|
||||
providers: [
|
||||
{
|
||||
provide: ArtifactListPageService,
|
||||
useValue: mockedArtifactListPageService,
|
||||
},
|
||||
],
|
||||
}).compileComponents();
|
||||
});
|
||||
|
||||
@ -27,6 +47,7 @@ describe('ArtifactAdditionsComponent', () => {
|
||||
fixture = TestBed.createComponent(ArtifactAdditionsComponent);
|
||||
component = fixture.componentInstance;
|
||||
component.additionLinks = mockedAdditionLinks;
|
||||
component.tab = 'vulnerability';
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
|
@ -10,7 +10,8 @@ import { ADDITIONS } from './models';
|
||||
import { AdditionLinks } from '../../../../../../../ng-swagger-gen/models/addition-links';
|
||||
import { AdditionLink } from '../../../../../../../ng-swagger-gen/models/addition-link';
|
||||
import { Artifact } from '../../../../../../../ng-swagger-gen/models/artifact';
|
||||
import { ClrTabs } from '@clr/angular';
|
||||
import { ClrLoadingState, ClrTabs } from '@clr/angular';
|
||||
import { ArtifactListPageService } from '../artifact-list-page/artifact-list-page.service';
|
||||
|
||||
@Component({
|
||||
selector: 'artifact-additions',
|
||||
@ -32,14 +33,21 @@ export class ArtifactAdditionsComponent implements AfterViewChecked, OnInit {
|
||||
@Input()
|
||||
tab: string;
|
||||
|
||||
@Input() currentTabLinkId: string = 'vulnerability';
|
||||
@Input() currentTabLinkId: string = '';
|
||||
activeTab: string = null;
|
||||
|
||||
@ViewChild('additionsTab') tabs: ClrTabs;
|
||||
constructor(private ref: ChangeDetectorRef) {}
|
||||
constructor(
|
||||
private ref: ChangeDetectorRef,
|
||||
private artifactListPageService: ArtifactListPageService
|
||||
) {}
|
||||
|
||||
ngOnInit(): void {
|
||||
this.activeTab = this.tab;
|
||||
if (!this.activeTab) {
|
||||
this.currentTabLinkId = 'vulnerability';
|
||||
}
|
||||
this.artifactListPageService.init(this.projectId);
|
||||
}
|
||||
|
||||
ngAfterViewChecked() {
|
||||
@ -50,6 +58,10 @@ export class ArtifactAdditionsComponent implements AfterViewChecked, OnInit {
|
||||
this.ref.detectChanges();
|
||||
}
|
||||
|
||||
hasScannerSupportSBOM(): boolean {
|
||||
return this.artifactListPageService.hasScannerSupportSBOM();
|
||||
}
|
||||
|
||||
getVulnerability(): AdditionLink {
|
||||
if (
|
||||
this.additionLinks &&
|
||||
@ -59,12 +71,7 @@ export class ArtifactAdditionsComponent implements AfterViewChecked, OnInit {
|
||||
}
|
||||
return null;
|
||||
}
|
||||
getSbom(): AdditionLink {
|
||||
if (this.additionLinks && this.additionLinks[ADDITIONS.SBOMS]) {
|
||||
return this.additionLinks[ADDITIONS.SBOMS];
|
||||
}
|
||||
return {};
|
||||
}
|
||||
|
||||
getBuildHistory(): AdditionLink {
|
||||
if (this.additionLinks && this.additionLinks[ADDITIONS.BUILD_HISTORY]) {
|
||||
return this.additionLinks[ADDITIONS.BUILD_HISTORY];
|
||||
@ -93,4 +100,12 @@ export class ArtifactAdditionsComponent implements AfterViewChecked, OnInit {
|
||||
actionTab(tab: string): void {
|
||||
this.currentTabLinkId = tab;
|
||||
}
|
||||
|
||||
getScanBtnState(): ClrLoadingState {
|
||||
return this.artifactListPageService.getScanBtnState();
|
||||
}
|
||||
|
||||
hasEnabledScanner(): boolean {
|
||||
return this.artifactListPageService.hasEnabledScanner();
|
||||
}
|
||||
}
|
||||
|
@ -32,12 +32,18 @@
|
||||
</div>
|
||||
</div>
|
||||
</clr-dg-action-bar>
|
||||
<clr-dg-column [clrDgField]="'package'" class="package-medium">{{
|
||||
'SBOM.GRID.COLUMN_PACKAGE' | translate
|
||||
}}</clr-dg-column>
|
||||
<clr-dg-column [clrDgField]="'version'" class="version-medium">{{
|
||||
'SBOM.GRID.COLUMN_VERSION' | translate
|
||||
}}</clr-dg-column>
|
||||
<clr-dg-column
|
||||
[clrDgSortBy]="'name'"
|
||||
[clrDgField]="'name'"
|
||||
class="package-medium"
|
||||
>{{ 'SBOM.GRID.COLUMN_PACKAGE' | translate }}</clr-dg-column
|
||||
>
|
||||
<clr-dg-column
|
||||
[clrDgSortBy]="'versionInfo'"
|
||||
[clrDgField]="'versionInfo'"
|
||||
class="version-medium"
|
||||
>{{ 'SBOM.GRID.COLUMN_VERSION' | translate }}</clr-dg-column
|
||||
>
|
||||
<clr-dg-column>{{
|
||||
'SBOM.GRID.COLUMN_LICENSE' | translate
|
||||
}}</clr-dg-column>
|
||||
|
@ -10,7 +10,6 @@ import {
|
||||
} from '@ngx-translate/core';
|
||||
import { BrowserAnimationsModule } from '@angular/platform-browser/animations';
|
||||
import { UserPermissionService } from '../../../../../../shared/services';
|
||||
import { AdditionLink } from '../../../../../../../../ng-swagger-gen/models/addition-link';
|
||||
import { ErrorHandler } from '../../../../../../shared/units/error-handler';
|
||||
import { SessionService } from '../../../../../../shared/services/session.service';
|
||||
import { SessionUser } from '../../../../../../shared/entities/session-user';
|
||||
|
@ -1,13 +1,6 @@
|
||||
import {
|
||||
AfterViewInit,
|
||||
Component,
|
||||
Input,
|
||||
OnDestroy,
|
||||
OnInit,
|
||||
} from '@angular/core';
|
||||
import { Component, Input, OnDestroy, OnInit } from '@angular/core';
|
||||
import { ClrDatagridStateInterface, ClrLoadingState } from '@clr/angular';
|
||||
import { finalize } from 'rxjs/operators';
|
||||
import { AdditionLink } from '../../../../../../../../ng-swagger-gen/models/addition-link';
|
||||
import {
|
||||
ScannerVo,
|
||||
UserPermissionService,
|
||||
@ -30,7 +23,6 @@ import {
|
||||
HarborEvent,
|
||||
} from '../../../../../../services/event-service/event.service';
|
||||
import { severityText } from '../../../../../left-side-nav/interrogation-services/vulnerability-database/security-hub.interface';
|
||||
import { AppConfigService } from 'src/app/services/app-config.service';
|
||||
|
||||
import {
|
||||
ArtifactSbom,
|
||||
@ -38,8 +30,7 @@ import {
|
||||
getArtifactSbom,
|
||||
} from '../../artifact';
|
||||
import { ArtifactService } from 'ng-swagger-gen/services';
|
||||
import { ScanTypes } from 'src/app/shared/entities/shared.const';
|
||||
import { ArtifactListPageService } from '../../artifact-list-page/artifact-list-page.service';
|
||||
import { ScanTypes } from '../../../../../../shared/entities/shared.const';
|
||||
|
||||
@Component({
|
||||
selector: 'hbr-artifact-sbom',
|
||||
@ -56,13 +47,12 @@ export class ArtifactSbomComponent implements OnInit, OnDestroy {
|
||||
@Input()
|
||||
sbomDigest: string;
|
||||
@Input() artifact: Artifact;
|
||||
@Input() hasScannerSupportSBOM: boolean = false;
|
||||
|
||||
artifactSbom: ArtifactSbom;
|
||||
loading: boolean = false;
|
||||
hasScannerSupportSBOM: boolean = false;
|
||||
downloadSbomBtnState: ClrLoadingState = ClrLoadingState.DEFAULT;
|
||||
hasSbomPermission: boolean = false;
|
||||
|
||||
hasShowLoading: boolean = false;
|
||||
sub: Subscription;
|
||||
hasViewInitWithDelay: boolean = false;
|
||||
@ -73,16 +63,13 @@ export class ArtifactSbomComponent implements OnInit, OnDestroy {
|
||||
readonly severityText = severityText;
|
||||
constructor(
|
||||
private errorHandler: ErrorHandler,
|
||||
private appConfigService: AppConfigService,
|
||||
private artifactService: ArtifactService,
|
||||
private artifactListPageService: ArtifactListPageService,
|
||||
private userPermissionService: UserPermissionService,
|
||||
private eventService: EventService,
|
||||
private session: SessionService
|
||||
) {}
|
||||
|
||||
ngOnInit() {
|
||||
this.artifactListPageService.init(this.projectId);
|
||||
this.getSbom();
|
||||
this.getSbomPermission();
|
||||
if (!this.sub) {
|
||||
@ -222,8 +209,6 @@ export class ArtifactSbomComponent implements OnInit, OnDestroy {
|
||||
}
|
||||
|
||||
canDownloadSbom(): boolean {
|
||||
this.hasScannerSupportSBOM =
|
||||
this.artifactListPageService.hasScannerSupportSBOM();
|
||||
return (
|
||||
this.hasScannerSupportSBOM &&
|
||||
//this.hasSbomPermission &&
|
||||
@ -234,7 +219,12 @@ export class ArtifactSbomComponent implements OnInit, OnDestroy {
|
||||
}
|
||||
|
||||
artifactSbomPackages(): ArtifactSbomPackageItem[] {
|
||||
return this.artifactSbom?.sbomPackage?.packages ?? [];
|
||||
return (
|
||||
this.artifactSbom?.sbomPackage?.packages?.filter(
|
||||
item =>
|
||||
item?.name || item?.versionInfo || item?.licenseConcluded
|
||||
) ?? []
|
||||
);
|
||||
}
|
||||
|
||||
load(state: ClrDatagridStateInterface) {
|
||||
|
@ -50,14 +50,13 @@ export class ArtifactVulnerabilitiesComponent implements OnInit, OnDestroy {
|
||||
@Input()
|
||||
digest: string;
|
||||
@Input() artifact: Artifact;
|
||||
@Input() scanBtnState: ClrLoadingState = ClrLoadingState.DEFAULT;
|
||||
@Input() hasEnabledScanner: boolean = false;
|
||||
scan_overview: any;
|
||||
scanner: ScannerVo;
|
||||
projectScanner: ScannerVo;
|
||||
|
||||
scanningResults: VulnerabilityItem[] = [];
|
||||
loading: boolean = false;
|
||||
hasEnabledScanner: boolean = false;
|
||||
scanBtnState: ClrLoadingState = ClrLoadingState.DEFAULT;
|
||||
severitySort: ClrDatagridComparatorInterface<VulnerabilityItem>;
|
||||
cvssSort: ClrDatagridComparatorInterface<VulnerabilityItem>;
|
||||
hasScanningPermission: boolean = false;
|
||||
@ -112,7 +111,6 @@ export class ArtifactVulnerabilitiesComponent implements OnInit, OnDestroy {
|
||||
ngOnInit() {
|
||||
this.getVulnerabilities();
|
||||
this.getScanningPermission();
|
||||
this.getProjectScanner();
|
||||
if (!this.sub) {
|
||||
this.sub = this.eventService.subscribe(
|
||||
HarborEvent.UPDATE_VULNERABILITY_INFO,
|
||||
@ -203,30 +201,6 @@ export class ArtifactVulnerabilitiesComponent implements OnInit, OnDestroy {
|
||||
);
|
||||
}
|
||||
|
||||
getProjectScanner(): void {
|
||||
this.hasEnabledScanner = false;
|
||||
this.scanBtnState = ClrLoadingState.LOADING;
|
||||
this.scanningService.getProjectScanner(this.projectId).subscribe(
|
||||
response => {
|
||||
if (
|
||||
response &&
|
||||
'{}' !== JSON.stringify(response) &&
|
||||
!response.disabled &&
|
||||
response.health === 'healthy'
|
||||
) {
|
||||
this.scanBtnState = ClrLoadingState.SUCCESS;
|
||||
this.hasEnabledScanner = true;
|
||||
} else {
|
||||
this.scanBtnState = ClrLoadingState.ERROR;
|
||||
}
|
||||
this.projectScanner = response;
|
||||
},
|
||||
error => {
|
||||
this.scanBtnState = ClrLoadingState.ERROR;
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
getLevel(v: VulnerabilityItem): number {
|
||||
if (v && v.severity && SEVERITY_LEVEL_MAP[v.severity]) {
|
||||
return SEVERITY_LEVEL_MAP[v.severity];
|
||||
|
@ -65,10 +65,6 @@
|
||||
class="action-dropdown"
|
||||
clrPosition="bottom-left"
|
||||
*clrIfOpen>
|
||||
<div
|
||||
class="dropdown-divider"
|
||||
role="separator"
|
||||
aria-hidden="true"></div>
|
||||
<button
|
||||
clrDropdownItem
|
||||
id="stop-scan"
|
||||
|
@ -1099,7 +1099,7 @@ export class ArtifactListTabComponent implements OnInit, OnDestroy {
|
||||
res?.filter(
|
||||
item =>
|
||||
item.type === AccessoryType.SBOM
|
||||
)?.[0]?.digest ?? null;
|
||||
)?.[0]?.digest ?? undefined;
|
||||
}
|
||||
},
|
||||
error: err => {
|
||||
|
@ -76,7 +76,7 @@ export enum AccessoryType {
|
||||
COSIGN = 'signature.cosign',
|
||||
NOTATION = 'signature.notation',
|
||||
NYDUS = 'accelerator.nydus',
|
||||
SBOM = 'harbor.sbom',
|
||||
SBOM = 'sbom.harbor',
|
||||
}
|
||||
|
||||
export enum ArtifactType {
|
||||
|
@ -68,9 +68,7 @@ export class SbomTipHistogramComponent {
|
||||
}
|
||||
|
||||
get noSbom(): boolean {
|
||||
return (
|
||||
this.sbomSummary.scan_status === SBOM_SCAN_STATUS.NOT_GENERATED_SBOM
|
||||
);
|
||||
return this.sbomDigest === undefined || this.sbomDigest === '';
|
||||
}
|
||||
|
||||
isThemeLight() {
|
||||
|
@ -142,7 +142,16 @@ export const errorHandler = function (error: any): string {
|
||||
}
|
||||
// Not a standard error return Basically not used cover unknown error
|
||||
try {
|
||||
return JSON.parse(error.error).message;
|
||||
const jsonError = JSON.parse(error.error);
|
||||
if (jsonError.errors && jsonError.errors instanceof Array) {
|
||||
return (
|
||||
jsonError.errors?.map(error => error.message) ?? [
|
||||
'UNKNOWN_ERROR',
|
||||
]
|
||||
).join(',');
|
||||
} else {
|
||||
return JSON.parse(error.error).message;
|
||||
}
|
||||
} catch (err) {}
|
||||
// Not a standard error return Basically not used cover unknown error
|
||||
if (typeof error.error === 'string') {
|
||||
|
@ -406,6 +406,7 @@
|
||||
"REPOSITORY": "Repository",
|
||||
"ARTIFACT": "Artifact",
|
||||
"SCAN": "Scan",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "Accessory",
|
||||
"ARTIFACT_ADDITION": "Artifact Addition",
|
||||
@ -1061,7 +1062,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -406,6 +406,7 @@
|
||||
"REPOSITORY": "Repository",
|
||||
"ARTIFACT": "Artifact",
|
||||
"SCAN": "Scan",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "Accessory",
|
||||
"ARTIFACT_ADDITION": "Artifact Addition",
|
||||
@ -1062,7 +1063,7 @@
|
||||
"GENERATE": "Generate SBOM ",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -407,6 +407,7 @@
|
||||
"REPOSITORY": "Repository",
|
||||
"ARTIFACT": "Artifact",
|
||||
"SCAN": "Scan",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "Accessory",
|
||||
"ARTIFACT_ADDITION": "Artifact Addition",
|
||||
@ -1060,7 +1061,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -406,6 +406,7 @@
|
||||
"REPOSITORY": "Dépôt",
|
||||
"ARTIFACT": "Artefact",
|
||||
"SCAN": "Scan",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "Accessoire",
|
||||
"ARTIFACT_ADDITION": "Artefact Addition",
|
||||
@ -1060,7 +1061,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -403,6 +403,7 @@
|
||||
"REPOSITORY": "저장소",
|
||||
"ARTIFACT": "아티팩트",
|
||||
"SCAN": "스캔",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "태그",
|
||||
"ACCESSORY": "액세서리",
|
||||
"ARTIFACT_ADDITION": "아티팩트 추가",
|
||||
@ -1059,7 +1060,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -404,6 +404,7 @@
|
||||
"REPOSITORY": "Repository",
|
||||
"ARTIFACT": "Artifact",
|
||||
"SCAN": "Scan",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "Accessory",
|
||||
"ARTIFACT_ADDITION": "Artifact Addition",
|
||||
@ -1058,7 +1059,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -406,6 +406,7 @@
|
||||
"REPOSITORY": "Repository",
|
||||
"ARTIFACT": "Artifact",
|
||||
"SCAN": "Scan",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "Accessory",
|
||||
"ARTIFACT_ADDITION": "Artifact Addition",
|
||||
@ -1061,7 +1062,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -405,6 +405,7 @@
|
||||
"REPOSITORY": "仓库",
|
||||
"ARTIFACT": "Artifact",
|
||||
"SCAN": "扫描",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "附件",
|
||||
"ARTIFACT_ADDITION": "Artifact 额外信息",
|
||||
@ -1059,7 +1060,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
@ -405,6 +405,7 @@
|
||||
"REPOSITORY": "Repository",
|
||||
"ARTIFACT": "Artifact",
|
||||
"SCAN": "Scan",
|
||||
"SBOM": "SBOM",
|
||||
"TAG": "Tag",
|
||||
"ACCESSORY": "Accessory",
|
||||
"ARTIFACT_ADDITION": "Artifact Addition",
|
||||
@ -1058,7 +1059,7 @@
|
||||
"GENERATE": "Generate SBOM",
|
||||
"DOWNLOAD": "Download SBOM",
|
||||
"Details": "SBOM details",
|
||||
"STOP": "Stop SBOM",
|
||||
"STOP": "Stop Generate SBOM",
|
||||
"TRIGGER_STOP_SUCCESS": "Trigger stopping SBOM generation successfully"
|
||||
},
|
||||
"VULNERABILITY": {
|
||||
|
Loading…
Reference in New Issue
Block a user