diff --git a/app/scripts/modules/core/src/artifact/ArtifactIconService.ts b/app/scripts/modules/core/src/artifact/ArtifactIconService.ts
new file mode 100644
index 00000000000..40c895f9129
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/ArtifactIconService.ts
@@ -0,0 +1,29 @@
+const unknownArtifactPath = require('./icons/unknown-type-artifact.svg');
+
+interface IArtifactIcon {
+ type: RegExp;
+ path: string;
+}
+
+export class ArtifactIconService {
+ private static icons: IArtifactIcon[] = [];
+
+ public static registerType(type: RegExp, path: string) {
+ ArtifactIconService.icons.push({ type, path });
+ }
+
+ public static getPath(type: string) {
+ const icon = ArtifactIconService.icons.find(entry => entry.type.test(type));
+ if (icon === undefined) {
+ return unknownArtifactPath;
+ }
+ return icon.path;
+ }
+}
+
+ArtifactIconService.registerType(/docker\/image/, require('./icons/docker-image-artifact.svg'));
+ArtifactIconService.registerType(/kubernetes\/.*/, require('./icons/kubernetes-artifact.svg'));
+ArtifactIconService.registerType(/embedded\/base64/, require('./icons/embedded-base64-artifact.svg'));
+ArtifactIconService.registerType(/gcs\/object/, require('./icons/gcs-file-artifact.svg'));
+ArtifactIconService.registerType(/github\/file/, require('./icons/github-file-artifact.svg'));
+ArtifactIconService.registerType(/s3\/object/, require('./icons/s3-object-artifact.svg'));
diff --git a/app/scripts/modules/core/src/artifact/artifactIconList.ts b/app/scripts/modules/core/src/artifact/artifactIconList.ts
new file mode 100644
index 00000000000..8aac02ec80f
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/artifactIconList.ts
@@ -0,0 +1,30 @@
+import { IComponentOptions, IController, module } from 'angular';
+import { ArtifactIconService } from '@spinnaker/core';
+
+class ArtifactIconListController implements IController {
+ public artifacts: any[];
+
+ public iconPath(type: string): string {
+ return ArtifactIconService.getPath(type);
+ }
+}
+
+class ArtifactIconListComponent implements IComponentOptions {
+ public bindings: any = { artifacts: '<' };
+ public controller: any = ArtifactIconListController;
+ public controllerAs = 'ctrl';
+ public template = `
+
+
{{ artifact.name }} - {{ artifact.version }}
+
+ `;
+}
+
+export const ARTIFACT_ICON_LIST = 'spinnaker.kubernetes.v2.kubernetes.artifact.iconList';
+module(ARTIFACT_ICON_LIST, []).component('artifactIconList', new ArtifactIconListComponent());
diff --git a/app/scripts/modules/core/src/artifact/icons/docker-image-artifact.svg b/app/scripts/modules/core/src/artifact/icons/docker-image-artifact.svg
new file mode 100644
index 00000000000..3389ea5be4b
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/icons/docker-image-artifact.svg
@@ -0,0 +1,36 @@
+
+
\ No newline at end of file
diff --git a/app/scripts/modules/core/src/artifact/icons/embedded-base64-artifact.svg b/app/scripts/modules/core/src/artifact/icons/embedded-base64-artifact.svg
new file mode 100644
index 00000000000..ef62fca189b
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/icons/embedded-base64-artifact.svg
@@ -0,0 +1,20 @@
+
+
diff --git a/app/scripts/modules/core/src/artifact/icons/gcs-file-artifact.svg b/app/scripts/modules/core/src/artifact/icons/gcs-file-artifact.svg
new file mode 100644
index 00000000000..55e2d81f499
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/icons/gcs-file-artifact.svg
@@ -0,0 +1,11 @@
+
diff --git a/app/scripts/modules/core/src/artifact/icons/github-file-artifact.svg b/app/scripts/modules/core/src/artifact/icons/github-file-artifact.svg
new file mode 100644
index 00000000000..fade3fdc147
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/icons/github-file-artifact.svg
@@ -0,0 +1,2 @@
+
+
diff --git a/app/scripts/modules/core/src/artifact/icons/kubernetes-artifact.svg b/app/scripts/modules/core/src/artifact/icons/kubernetes-artifact.svg
new file mode 100644
index 00000000000..bedd3b88e43
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/icons/kubernetes-artifact.svg
@@ -0,0 +1,84 @@
+
+
+
+
diff --git a/app/scripts/modules/core/src/artifact/icons/s3-object-artifact.svg b/app/scripts/modules/core/src/artifact/icons/s3-object-artifact.svg
new file mode 100644
index 00000000000..f761e3b4eab
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/icons/s3-object-artifact.svg
@@ -0,0 +1,17 @@
+
diff --git a/app/scripts/modules/core/src/artifact/icons/unknown-type-artifact.svg b/app/scripts/modules/core/src/artifact/icons/unknown-type-artifact.svg
new file mode 100644
index 00000000000..7b801e9bb0d
--- /dev/null
+++ b/app/scripts/modules/core/src/artifact/icons/unknown-type-artifact.svg
@@ -0,0 +1,18 @@
+
+
diff --git a/app/scripts/modules/core/src/artifact/index.ts b/app/scripts/modules/core/src/artifact/index.ts
index 790276021c8..24048b2bab6 100644
--- a/app/scripts/modules/core/src/artifact/index.ts
+++ b/app/scripts/modules/core/src/artifact/index.ts
@@ -2,3 +2,5 @@ export * from './expectedArtifactSelector.component';
export * from './expectedArtifact.service';
export * from './imageSourceSelector.component';
export * from './ArtifactReferenceService';
+export * from './ArtifactIconService';
+export * from './artifactIconList';
diff --git a/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/artifactTab.less b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/artifactTab.less
new file mode 100644
index 00000000000..98d282339b8
--- /dev/null
+++ b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/artifactTab.less
@@ -0,0 +1,34 @@
+.execution-artifacts {
+ background: var(--color-alabaster);
+ display: flex;
+ margin-right: 0;
+ padding: 6px;
+}
+
+.artifact-list-container {
+ background: white;
+ padding: 8px 6px 6px;
+
+ > h5 {
+ margin-top: 0;
+ }
+}
+
+.artifact-list-item {
+ height: 28px;
+ position: relative;
+ line-height: 28px;
+ overflow: hidden;
+ white-space: nowrap;
+ text-overflow: ellipsis;
+ margin-bottom: 0.1em;
+}
+
+.artifact-list-item-icon {
+ position: absolute;
+ top: 4px;
+}
+
+.artifact-list-item-name {
+ padding-left: 24px;
+}
diff --git a/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/artifactTab.ts b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/artifactTab.ts
new file mode 100644
index 00000000000..c7ff7ed2e3d
--- /dev/null
+++ b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/artifactTab.ts
@@ -0,0 +1,79 @@
+import { IComponentOptions, IController, module } from 'angular';
+import { get, includes } from 'lodash';
+import { ARTIFACT_ICON_LIST } from '@spinnaker/core';
+
+import './artifactTab.less';
+
+class KubernetesExecutionArtifactTabController implements IController {
+ private _stage: any;
+ private _execution: any;
+
+ public consumedArtifacts: any[] = [];
+ public producedArtifacts: any[] = [];
+
+ get stage(): any {
+ return this._stage;
+ }
+
+ set stage(stage: any) {
+ this._stage = stage;
+ this.populateArtifactLists();
+ }
+
+ get execution(): any {
+ return this._execution;
+ }
+
+ set execution(execution: any) {
+ this._execution = execution;
+ this.populateArtifactLists();
+ }
+
+ public populateArtifactLists() {
+ const requiredArtifactIds = get(this.stage, ['context', 'requiredArtifactIds'], []);
+ const manifestArtifactId = get(this.stage, ['context', 'manifestArtifactId'], null);
+ const resolvedExpectedArtifacts = get(this.execution, ['trigger', 'resolvedExpectedArtifacts'], []);
+
+ const consumedIds = requiredArtifactIds.slice();
+ if (manifestArtifactId) {
+ consumedIds.push(manifestArtifactId);
+ }
+
+ this.consumedArtifacts = resolvedExpectedArtifacts
+ .filter(rea => includes(consumedIds, rea.id))
+ .map(rea => rea.boundArtifact)
+ .filter(({ name, type }) => name && type);
+
+ this.producedArtifacts = get(this.stage, ['outputs', 'artifacts'], []).slice();
+ }
+}
+
+class KubernetesExecutionArtifactTabComponent implements IComponentOptions {
+ public bindings: any = { stage: '<', execution: '<' };
+ public controller: any = KubernetesExecutionArtifactTabController;
+ public controllerAs = 'ctrl';
+ public template = `
+
+`;
+}
+
+export const KUBERNETES_EXECUTION_ARTIFACT_TAB =
+ 'spinnaker.kubernetes.v2.kubernetes.deployManifest.artifactTab.component';
+
+module(KUBERNETES_EXECUTION_ARTIFACT_TAB, [ARTIFACT_ICON_LIST]).component(
+ 'kubernetesExecutionArtifactTab',
+ new KubernetesExecutionArtifactTabComponent(),
+);
diff --git a/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestExecutionDetails.html b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestExecutionDetails.html
index 62df7b69ba4..668d9a15814 100644
--- a/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestExecutionDetails.html
+++ b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestExecutionDetails.html
@@ -24,4 +24,8 @@
+
+
+
+
diff --git a/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestStage.ts b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestStage.ts
index 7ce6b13a1a5..8dadfc6d235 100644
--- a/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestStage.ts
+++ b/app/scripts/modules/kubernetes/src/v2/pipelines/stages/deployManifest/deployManifestStage.ts
@@ -10,6 +10,7 @@ import {
import { KubernetesV2DeployManifestConfigCtrl } from './deployManifestConfig.controller';
import { KUBERNETES_MANIFEST_COMMAND_BUILDER } from '../../../manifest/manifestCommandBuilder.service';
import { KUBERNETES_DEPLOY_MANIFEST_DEPLOY_STATUS_MANIFEST_SUMMARY } from './deployStatusManifestSummary';
+import { KUBERNETES_EXECUTION_ARTIFACT_TAB } from './artifactTab';
export const KUBERNETES_DEPLOY_MANIFEST_STAGE = 'spinnaker.kubernetes.v2.pipeline.stage.deployManifestStage';
@@ -17,6 +18,7 @@ module(KUBERNETES_DEPLOY_MANIFEST_STAGE, [
PIPELINE_CONFIG_PROVIDER,
KUBERNETES_MANIFEST_COMMAND_BUILDER,
KUBERNETES_DEPLOY_MANIFEST_DEPLOY_STATUS_MANIFEST_SUMMARY,
+ KUBERNETES_EXECUTION_ARTIFACT_TAB,
])
.config(
(
@@ -34,7 +36,7 @@ module(KUBERNETES_DEPLOY_MANIFEST_STAGE, [
controller: 'KubernetesV2DeployManifestConfigCtrl',
controllerAs: 'ctrl',
executionDetailsUrl: require('./deployManifestExecutionDetails.html'),
- executionConfigSections: ['deployStatus', 'taskStatus'],
+ executionConfigSections: ['deployStatus', 'taskStatus', 'artifactStatus'],
producesArtifacts: true,
defaultTimeoutMs: 30 * 60 * 1000, // 30 minutes
validators: [],