Skip to content

Commit

Permalink
Block users from importing argo workflows in pipeline import modal (#…
Browse files Browse the repository at this point in the history
  • Loading branch information
dpanshug authored Jul 30, 2024
1 parent 8b1da65 commit 8e17ae3
Show file tree
Hide file tree
Showing 31 changed files with 949 additions and 301 deletions.
117 changes: 111 additions & 6 deletions frontend/src/__mocks__/mockPipelineVersionsProxy.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,19 @@
/* eslint-disable camelcase */
import {
ArgoWorkflowPipelineVersion,
ArtifactType,
InputDefinitionParameterType,
PipelineKFCallCommon,
PipelineVersionKF,
PipelineVersionKFv2,
RelationshipKF,
ResourceTypeKF,
} from '~/concepts/pipelines/kfTypes';

export type BuildMockPipelinveVersionsType = PipelineKFCallCommon<{
pipeline_versions: (PipelineVersionKFv2 | ArgoWorkflowPipelineVersion)[];
}>;

/**
* @deprecated Use `mockPipelineVersionsListV2` instead.
*/
Expand Down Expand Up @@ -732,14 +738,13 @@ export const buildMockPipelineVersions = (
});

export const buildMockPipelineVersionsV2 = (
pipeline_versions: PipelineVersionKFv2[] = mockPipelineVersionsListV2,
pipeline_versions: (
| PipelineVersionKFv2
| ArgoWorkflowPipelineVersion
)[] = mockPipelineVersionsListV2,
totalSize?: number,
nextPageToken?: string,
): {
total_size?: number | undefined;
next_page_token?: string | undefined;
pipeline_versions: PipelineVersionKFv2[];
} => ({
): BuildMockPipelinveVersionsType => ({
pipeline_versions,
total_size: totalSize || pipeline_versions.length,
next_page_token: nextPageToken,
Expand All @@ -764,3 +769,103 @@ export const mockPipelineVersionsListSearch = (
.slice(0, 10);
return buildMockPipelineVersions(filteredVersions, filteredVersions.length);
};

type MockArgoWorkflowPipelineVersionType = {
pipelineId?: string;
pipelineVersionId?: string;
};

export const mockArgoWorkflowPipelineVersion = ({
pipelineId = 'test-pipeline',
pipelineVersionId = 'test-pipeline-version',
}: MockArgoWorkflowPipelineVersionType): ArgoWorkflowPipelineVersion => ({
pipeline_id: pipelineId,
pipeline_version_id: pipelineVersionId,
display_name: 'argo unsupported',
created_at: '2024-07-12T11:34:36Z',
pipeline_spec: {
apiVersion: 'argoproj.io/v1alpha1',
kind: 'Workflow',
metadata: {
annotations: {
'pipelines.kubeflow.org/kfp_sdk_version': '1.8.22',
'pipelines.kubeflow.org/pipeline_compilation_time': '2023-09-26T08:36:45.160091',
'pipelines.kubeflow.org/pipeline_spec':
'{"description": "A sample pipeline to generate Confusion Matrix for UI visualization.", "name": "confusion-matrix-pipeline"}',
},
generateName: 'confusion-matrix-pipeline-',
labels: {
'pipelines.kubeflow.org/kfp_sdk_version': '1.8.22',
},
},
spec: {
arguments: {},
entrypoint: 'confusion-matrix-pipeline',
serviceAccountName: 'pipeline-runner',
templates: [
{
dag: {
tasks: [
{
arguments: {},
name: 'confusion-visualization',
template: 'confusion-visualization',
},
],
},
inputs: {},
metadata: {},
name: 'confusion-matrix-pipeline',
outputs: {},
},
{
container: {
args: [
'--matrix-uri',
'https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv',
'----output-paths',
'/tmp/outputs/mlpipeline_ui_metadata/data',
],
command: [
'sh',
'-ec',
'program_path=$(mktemp)\nprintf "%s" "$0" > "$program_path"\npython3 -u "$program_path" "$@"\n',
"def confusion_visualization(matrix_uri = 'https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv'):\n \"\"\"Provide confusion matrix csv file to visualize as metrics.\"\"\"\n import json\n\n metadata = {\n 'outputs' : [{\n 'type': 'confusion_matrix',\n 'format': 'csv',\n 'schema': [\n {'name': 'target', 'type': 'CATEGORY'},\n {'name': 'predicted', 'type': 'CATEGORY'},\n {'name': 'count', 'type': 'NUMBER'},\n ],\n 'source': matrix_uri,\n 'labels': ['rose', 'lily', 'iris'],\n }]\n }\n\n from collections import namedtuple\n visualization_output = namedtuple('VisualizationOutput', [\n 'mlpipeline_ui_metadata'])\n return visualization_output(json.dumps(metadata))\n\nimport argparse\n_parser = argparse.ArgumentParser(prog='Confusion visualization', description='Provide confusion matrix csv file to visualize as metrics.')\n_parser.add_argument(\"--matrix-uri\", dest=\"matrix_uri\", type=str, required=False, default=argparse.SUPPRESS)\n_parser.add_argument(\"----output-paths\", dest=\"_output_paths\", type=str, nargs=1)\n_parsed_args = vars(_parser.parse_args())\n_output_files = _parsed_args.pop(\"_output_paths\", [])\n\n_outputs = confusion_visualization(**_parsed_args)\n\n_output_serializers = [\n str,\n\n]\n\nimport os\nfor idx, output_file in enumerate(_output_files):\n try:\n os.makedirs(os.path.dirname(output_file))\n except OSError:\n pass\n with open(output_file, 'w') as f:\n f.write(_output_serializers[idx](_outputs[idx]))\n",
],
image: 'python:3.7',
name: '',
resources: {},
},
inputs: {},
metadata: {
annotations: {
'pipelines.kubeflow.org/arguments.parameters':
'{"matrix_uri": "https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv"}',
'pipelines.kubeflow.org/component_ref': '{}',
'pipelines.kubeflow.org/component_spec':
'{"description": "Provide confusion matrix csv file to visualize as metrics.", "implementation": {"container": {"args": [{"if": {"cond": {"isPresent": "matrix_uri"}, "then": ["--matrix-uri", {"inputValue": "matrix_uri"}]}}, "----output-paths", {"outputPath": "mlpipeline_ui_metadata"}], "command": ["sh", "-ec", "program_path=$(mktemp)\\nprintf \\"%s\\" \\"$0\\" > \\"$program_path\\"\\npython3 -u \\"$program_path\\" \\"$@\\"\\n", "def confusion_visualization(matrix_uri = \'https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv\'):\\n \\"\\"\\"Provide confusion matrix csv file to visualize as metrics.\\"\\"\\"\\n import json\\n\\n metadata = {\\n \'outputs\' : [{\\n \'type\': \'confusion_matrix\',\\n \'format\': \'csv\',\\n \'schema\': [\\n {\'name\': \'target\', \'type\': \'CATEGORY\'},\\n {\'name\': \'predicted\', \'type\': \'CATEGORY\'},\\n {\'name\': \'count\', \'type\': \'NUMBER\'},\\n ],\\n \'source\': matrix_uri,\\n \'labels\': [\'rose\', \'lily\', \'iris\'],\\n }]\\n }\\n\\n from collections import namedtuple\\n visualization_output = namedtuple(\'VisualizationOutput\', [\\n \'mlpipeline_ui_metadata\'])\\n return visualization_output(json.dumps(metadata))\\n\\nimport argparse\\n_parser = argparse.ArgumentParser(prog=\'Confusion visualization\', description=\'Provide confusion matrix csv file to visualize as metrics.\')\\n_parser.add_argument(\\"--matrix-uri\\", dest=\\"matrix_uri\\", type=str, required=False, default=argparse.SUPPRESS)\\n_parser.add_argument(\\"----output-paths\\", dest=\\"_output_paths\\", type=str, nargs=1)\\n_parsed_args = vars(_parser.parse_args())\\n_output_files = _parsed_args.pop(\\"_output_paths\\", [])\\n\\n_outputs = confusion_visualization(**_parsed_args)\\n\\n_output_serializers = [\\n str,\\n\\n]\\n\\nimport os\\nfor idx, output_file in enumerate(_output_files):\\n try:\\n os.makedirs(os.path.dirname(output_file))\\n except OSError:\\n pass\\n with open(output_file, \'w\') as f:\\n f.write(_output_serializers[idx](_outputs[idx]))\\n"], "image": "python:3.7"}}, "inputs": [{"default": "https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv", "name": "matrix_uri", "optional": true, "type": "String"}], "name": "Confusion visualization", "outputs": [{"name": "mlpipeline_ui_metadata", "type": "UI_metadata"}]}',
},
labels: {
'pipelines.kubeflow.org/enable_caching': 'true',
'pipelines.kubeflow.org/kfp_sdk_version': '1.8.22',
'pipelines.kubeflow.org/pipeline-sdk-type': 'kfp',
},
},
name: 'confusion-visualization',
outputs: {
artifacts: [
{
name: 'mlpipeline-ui-metadata',
path: '/tmp/outputs/mlpipeline_ui_metadata/data',
},
],
},
},
],
},
status: {
finishedAt: null,
startedAt: null,
},
},
});
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
/* eslint-disable camelcase */
import {
type ExperimentKFv2,
type PipelineKFv2,
type PipelineRecurringRunKFv2,
type PipelineRunKFv2,
type PipelineVersionKFv2,
import type {
ArgoWorkflowPipelineVersion,
ExperimentKFv2,
PipelineKFv2,
PipelineRecurringRunKFv2,
PipelineRunKFv2,
PipelineVersionKFv2,
} from '~/concepts/pipelines/kfTypes';
import { buildMockRunKF } from '~/__mocks__';
import { buildMockPipelines } from '~/__mocks__/mockPipelinesProxy';
Expand Down Expand Up @@ -59,6 +60,13 @@ export class CreateRunPage {
return this.find().findByTestId('pipeline-version-toggle-button');
}

findPipelineVersionByName(name: string): Cypress.Chainable<JQuery<HTMLTableCellElement>> {
return this.find()
.findByTestId('pipeline-version-selector-table-list')
.find('td')
.contains(name);
}

findScheduledRunTypeSelector(): Cypress.Chainable<JQuery<HTMLElement>> {
return this.find().findByTestId('triggerTypeSelector');
}
Expand Down Expand Up @@ -226,7 +234,7 @@ export class CreateRunPage {

mockGetPipelineVersions(
namespace: string,
versions: PipelineVersionKFv2[],
versions: (PipelineVersionKFv2 | ArgoWorkflowPipelineVersion)[],
pipelineId: string,
): Cypress.Chainable<null> {
return cy.interceptOdh(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,10 @@ class PipelineImportModal extends Modal {
return this.find().findByTestId('pipeline-file-upload-error');
}

findImportModalError() {
return this.find().findByTestId('import-modal-error');
}

mockCreatePipelineAndVersion(params: CreatePipelineAndVersionKFData, namespace: string) {
return cy.interceptOdh(
'POST /api/service/pipelines/:namespace/:serviceName/apis/v2beta1/pipelines/create',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,10 @@ class PipelineImportModal extends Modal {
return this.find().findByTestId('code-source-input');
}

findImportModalError() {
return this.find().findByTestId('import-modal-error');
}

selectPipelineByName(name: string) {
this.findPipelineSelect()
.click()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,19 +35,20 @@ import type {
SubscriptionStatusData,
} from '~/types';
import type {
ArgoWorkflowPipelineVersion,
ExperimentKFv2,
GoogleRpcStatusKF,
ListExperimentsResponseKF,
ListPipelineRecurringRunsResourceKF,
ListPipelineRunsResourceKF,
ListPipelineVersionsKF,
ListPipelinesResponseKF,
PipelineKFv2,
PipelineRecurringRunKFv2,
PipelineRunKFv2,
PipelineVersionKFv2,
} from '~/concepts/pipelines/kfTypes';
import type { GrpcResponse } from '~/__mocks__/mlmd/utils';
import type { BuildMockPipelinveVersionsType } from '~/__mocks__';

type SuccessErrorResponse = {
success: boolean;
Expand Down Expand Up @@ -346,7 +347,9 @@ declare global {
pipelineVersionId: string;
};
},
response: OdhResponse<PipelineVersionKFv2 | GoogleRpcStatusKF>,
response: OdhResponse<
PipelineVersionKFv2 | ArgoWorkflowPipelineVersion | GoogleRpcStatusKF
>,
) => Cypress.Chainable<null>) &
((
type: `DELETE /api/service/pipelines/:namespace/:serviceName/apis/v2beta1/pipelines/:pipelineId/versions/:pipelineVersionId`,
Expand Down Expand Up @@ -393,7 +396,7 @@ declare global {
path: { namespace: string; serviceName: string; pipelineId: string };
times?: number;
},
response: OdhResponse<ListPipelineVersionsKF | GoogleRpcStatusKF>,
response: OdhResponse<BuildMockPipelinveVersionsType | GoogleRpcStatusKF>,
) => Cypress.Chainable<null>) &
((
type: `GET /api/service/pipelines/:namespace/:serviceName/apis/v2beta1/pipelines`,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
---
apiVersion: argoproj.io/v1alpha1
kind: Workflow
metadata:
annotations:
pipelines.kubeflow.org/kfp_sdk_version: 1.8.22
pipelines.kubeflow.org/pipeline_compilation_time: '2023-09-26T08:36:45.160091'
pipelines.kubeflow.org/pipeline_spec: '{"description": "A sample pipeline to generate
Confusion Matrix for UI visualization.", "name": "confusion-matrix-pipeline"}'
creationTimestamp:
generateName: confusion-matrix-pipeline-
labels:
pipelines.kubeflow.org/kfp_sdk_version: 1.8.22
spec:
arguments: {}
entrypoint: confusion-matrix-pipeline
serviceAccountName: pipeline-runner
templates:
- dag:
tasks:
- arguments: {}
name: confusion-visualization
template: confusion-visualization
inputs: {}
metadata: {}
name: confusion-matrix-pipeline
outputs: {}
- container:
args:
- "--matrix-uri"
- https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv
- "----output-paths"
- "/tmp/outputs/mlpipeline_ui_metadata/data"
command:
- sh
- "-ec"
- |
program_path=$(mktemp)
printf "%s" "$0" > "$program_path"
python3 -u "$program_path" "$@"
- |
def confusion_visualization(matrix_uri = 'https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv'):
"""Provide confusion matrix csv file to visualize as metrics."""
import json
metadata = {
'outputs' : [{
'type': 'confusion_matrix',
'format': 'csv',
'schema': [
{'name': 'target', 'type': 'CATEGORY'},
{'name': 'predicted', 'type': 'CATEGORY'},
{'name': 'count', 'type': 'NUMBER'},
],
'source': matrix_uri,
'labels': ['rose', 'lily', 'iris'],
}]
}
from collections import namedtuple
visualization_output = namedtuple('VisualizationOutput', [
'mlpipeline_ui_metadata'])
return visualization_output(json.dumps(metadata))
import argparse
_parser = argparse.ArgumentParser(prog='Confusion visualization', description='Provide confusion matrix csv file to visualize as metrics.')
_parser.add_argument("--matrix-uri", dest="matrix_uri", type=str, required=False, default=argparse.SUPPRESS)
_parser.add_argument("----output-paths", dest="_output_paths", type=str, nargs=1)
_parsed_args = vars(_parser.parse_args())
_output_files = _parsed_args.pop("_output_paths", [])
_outputs = confusion_visualization(**_parsed_args)
_output_serializers = [
str,
]
import os
for idx, output_file in enumerate(_output_files):
try:
os.makedirs(os.path.dirname(output_file))
except OSError:
pass
with open(output_file, 'w') as f:
f.write(_output_serializers[idx](_outputs[idx]))
image: python:3.7
name: ''
resources: {}
inputs: {}
metadata:
annotations:
pipelines.kubeflow.org/arguments.parameters: '{"matrix_uri": "https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv"}'
pipelines.kubeflow.org/component_ref: "{}"
pipelines.kubeflow.org/component_spec: '{"description": "Provide confusion
matrix csv file to visualize as metrics.", "implementation": {"container":
{"args": [{"if": {"cond": {"isPresent": "matrix_uri"}, "then": ["--matrix-uri",
{"inputValue": "matrix_uri"}]}}, "----output-paths", {"outputPath": "mlpipeline_ui_metadata"}],
"command": ["sh", "-ec", "program_path=$(mktemp)\nprintf \"%s\" \"$0\" >
\"$program_path\"\npython3 -u \"$program_path\" \"$@\"\n", "def confusion_visualization(matrix_uri
= ''https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv''):\n \"\"\"Provide
confusion matrix csv file to visualize as metrics.\"\"\"\n import json\n\n metadata
= {\n ''outputs'' : [{\n ''type'': ''confusion_matrix'',\n ''format'':
''csv'',\n ''schema'': [\n {''name'': ''target'', ''type'':
''CATEGORY''},\n {''name'': ''predicted'', ''type'': ''CATEGORY''},\n {''name'':
''count'', ''type'': ''NUMBER''},\n ],\n ''source'': matrix_uri,\n ''labels'':
[''rose'', ''lily'', ''iris''],\n }]\n }\n\n from collections
import namedtuple\n visualization_output = namedtuple(''VisualizationOutput'',
[\n ''mlpipeline_ui_metadata''])\n return visualization_output(json.dumps(metadata))\n\nimport
argparse\n_parser = argparse.ArgumentParser(prog=''Confusion visualization'',
description=''Provide confusion matrix csv file to visualize as metrics.'')\n_parser.add_argument(\"--matrix-uri\",
dest=\"matrix_uri\", type=str, required=False, default=argparse.SUPPRESS)\n_parser.add_argument(\"----output-paths\",
dest=\"_output_paths\", type=str, nargs=1)\n_parsed_args = vars(_parser.parse_args())\n_output_files
= _parsed_args.pop(\"_output_paths\", [])\n\n_outputs = confusion_visualization(**_parsed_args)\n\n_output_serializers
= [\n str,\n\n]\n\nimport os\nfor idx, output_file in enumerate(_output_files):\n try:\n os.makedirs(os.path.dirname(output_file))\n except
OSError:\n pass\n with open(output_file, ''w'') as f:\n f.write(_output_serializers[idx](_outputs[idx]))\n"],
"image": "python:3.7"}}, "inputs": [{"default": "https://raw.githubusercontent.com/kubeflow/pipelines/master/samples/core/visualization/confusion_matrix.csv",
"name": "matrix_uri", "optional": true, "type": "String"}], "name": "Confusion
visualization", "outputs": [{"name": "mlpipeline_ui_metadata", "type": "UI_metadata"}]}'
labels:
pipelines.kubeflow.org/enable_caching: 'true'
pipelines.kubeflow.org/kfp_sdk_version: 1.8.22
pipelines.kubeflow.org/pipeline-sdk-type: kfp
name: confusion-visualization
outputs:
artifacts:
- name: mlpipeline-ui-metadata
path: "/tmp/outputs/mlpipeline_ui_metadata/data"
status:
finishedAt:
startedAt:
Loading

0 comments on commit 8e17ae3

Please sign in to comment.