From 4a50c54d9ae9c989b7df01288162c58b5a8e02d8 Mon Sep 17 00:00:00 2001 From: David Laine Date: Tue, 20 Aug 2024 12:28:21 -0500 Subject: [PATCH 1/3] CASMCMS-8979 - add status endpoint to cray ims remote-build-nodes. --- cray/modules/ims/openapi.yaml | 87 ++++++- cray/modules/ims/swagger3.json | 350 +++++++++++++++++++++++++++- cray/tests/test_modules/test_ims.py | 34 +++ 3 files changed, 459 insertions(+), 12 deletions(-) diff --git a/cray/modules/ims/openapi.yaml b/cray/modules/ims/openapi.yaml index 983f1e0..b7f048e 100644 --- a/cray/modules/ims/openapi.yaml +++ b/cray/modules/ims/openapi.yaml @@ -629,6 +629,46 @@ paths: $ref: '#/components/responses/NotFound' '500': $ref: '#/components/responses/InternalServerError' + /v3/remote-build-nodes/status/{remote_build_node_xname}: + parameters: + - $ref: '#/components/parameters/remote_build_node_xname' + get: + summary: List remote build node status objects + operationId: get_all_v3_remote_build_status + tags: + - remote build node status + - v3 + description: Retrieve the status of all remote build nodes that are registered with IMS. + responses: + '200': + description: A collection of the status of each remote build node + content: + application/json: + schema: + items: + $ref: '#/components/schemas/RemoteBuildNodeStatus' + type: array + '500': + $ref: '#/components/responses/InternalServerError' + /v3/remote-build-nodes/status: + get: + summary: List remote build node status objects + operationId: get_all_v3_remote_build_status + tags: + - remote build node status + - v3 + description: Retrieve the status of all remote build nodes that are registered with IMS. + responses: + '200': + description: A collection of the status of each remote build node + content: + application/json: + schema: + items: + $ref: '#/components/schemas/RemoteBuildNodeStatus' + type: array + '500': + $ref: '#/components/responses/InternalServerError' /v3/jobs: get: summary: Retrieve a list of JobRecords that are registered with IMS @@ -2072,6 +2112,42 @@ components: example: x3000c1s10b1n0 type: string minLength: 1 + RemoteBuildNodeStatus: + description: A Remote Build Node Status + type: object + required: + - xname + properties: + xname: + description: Xname of the remote build node + example: x3000c1s10b1n0 + type: string + minLength: 1 + nodeArch: + description: Architecture of the remote build node + example: x86_64 + type: string + minLength: 1 + numCurrentJobs: + description: Number of current jobs running on the remote build node + example: 15 + type: integer + minLength: 1 + podmanStatus: + description: Status of the podman executable on the remote build node + example: Podman present at /usr/bin/podman + type: string + minLength: 1 + sshStatus: + description: Status of the ssh connection to the remote build node + example: SSH connection established + type: string + minLength: 1 + ableToRunJobs: + description: If the node is able to run new jobs + example: True + type: boolean + minLength: 1 ArtifactLinkRecord: description: An Artifact Link Record type: object @@ -2363,10 +2439,17 @@ components: - x86_64 type: string metadata: - description: List of key/value pairs to associate with an Image + description: User supplied annotations about an image type: object properties: - $ref: '#/components/schemas/ImageMetadataAnnotationKeyValuePair' + key: + description: Template variable to associate with the IMS image + example: includes_additional_packages + type: string + value: + description: Value variable to associate with the IMS image + example: "foo,bar,baz" + type: string JobRecord: description: A Job Record type: object diff --git a/cray/modules/ims/swagger3.json b/cray/modules/ims/swagger3.json index 740b9a2..d482d03 100644 --- a/cray/modules/ims/swagger3.json +++ b/cray/modules/ims/swagger3.json @@ -3686,6 +3686,236 @@ } } }, + "/v3/remote-build-nodes/status/{remote_build_node_xname}": { + "parameters": [ + { + "description": "The unique xname of a remote build node", + "in": "path", + "name": "remote_build_node_xname", + "required": true, + "schema": { + "type": "string" + }, + "example": "x3000c1s10b1n0" + } + ], + "get": { + "summary": "List remote build node status objects", + "operationId": "get_all_v3_remote_build_status", + "tags": [ + "remote build node status", + "v3" + ], + "description": "Retrieve the status of all remote build nodes that are registered with IMS.", + "responses": { + "200": { + "description": "A collection of the status of each remote build node", + "content": { + "application/json": { + "schema": { + "items": { + "description": "A Remote Build Node Status", + "type": "object", + "required": [ + "xname" + ], + "properties": { + "xname": { + "description": "Xname of the remote build node", + "example": "x3000c1s10b1n0", + "type": "string", + "minLength": 1 + }, + "nodeArch": { + "description": "Architecture of the remote build node", + "example": "x86_64", + "type": "string", + "minLength": 1 + }, + "numCurrentJobs": { + "description": "Number of current jobs running on the remote build node", + "example": 15, + "type": "integer", + "minLength": 1 + }, + "podmanStatus": { + "description": "Status of the podman executable on the remote build node", + "example": "Podman present at /usr/bin/podman", + "type": "string", + "minLength": 1 + }, + "sshStatus": { + "description": "Status of the ssh connection to the remote build node", + "example": "SSH connection established", + "type": "string", + "minLength": 1 + }, + "ableToRunJobs": { + "description": "If the node is able to run new jobs", + "example": true, + "type": "boolean", + "minLength": 1 + } + } + }, + "type": "array" + } + } + } + }, + "500": { + "description": "An internal error occurred. Re-running the request may or may not succeed.", + "content": { + "application/json": { + "schema": { + "description": "An error response for RFC 7807 problem details.", + "type": "object", + "properties": { + "detail": { + "description": "A human-readable explanation specific to this occurrence of the problem. Focus on helping correct the problem, rather than giving debugging information.", + "type": "string" + }, + "errors": { + "description": "An object denoting field-specific errors. Only present on error responses when field input is specified for the request.", + "type": "object" + }, + "instance": { + "description": "A relative URI reference that identifies the specific occurrence of the problem", + "format": "uri", + "type": "string" + }, + "status": { + "description": "HTTP status code", + "example": 400, + "type": "integer" + }, + "title": { + "description": "Short, human-readable summary of the problem, should not change by occurrence.", + "type": "string" + }, + "type": { + "default": "about:blank", + "description": "Relative URI reference to the type of problem which includes human-readable documentation.", + "format": "uri", + "type": "string" + } + } + } + } + } + } + } + } + }, + "/v3/remote-build-nodes/status": { + "get": { + "summary": "List remote build node status objects", + "operationId": "get_all_v3_remote_build_status", + "tags": [ + "remote build node status", + "v3" + ], + "description": "Retrieve the status of all remote build nodes that are registered with IMS.", + "responses": { + "200": { + "description": "A collection of the status of each remote build node", + "content": { + "application/json": { + "schema": { + "items": { + "description": "A Remote Build Node Status", + "type": "object", + "required": [ + "xname" + ], + "properties": { + "xname": { + "description": "Xname of the remote build node", + "example": "x3000c1s10b1n0", + "type": "string", + "minLength": 1 + }, + "nodeArch": { + "description": "Architecture of the remote build node", + "example": "x86_64", + "type": "string", + "minLength": 1 + }, + "numCurrentJobs": { + "description": "Number of current jobs running on the remote build node", + "example": 15, + "type": "integer", + "minLength": 1 + }, + "podmanStatus": { + "description": "Status of the podman executable on the remote build node", + "example": "Podman present at /usr/bin/podman", + "type": "string", + "minLength": 1 + }, + "sshStatus": { + "description": "Status of the ssh connection to the remote build node", + "example": "SSH connection established", + "type": "string", + "minLength": 1 + }, + "ableToRunJobs": { + "description": "If the node is able to run new jobs", + "example": true, + "type": "boolean", + "minLength": 1 + } + } + }, + "type": "array" + } + } + } + }, + "500": { + "description": "An internal error occurred. Re-running the request may or may not succeed.", + "content": { + "application/json": { + "schema": { + "description": "An error response for RFC 7807 problem details.", + "type": "object", + "properties": { + "detail": { + "description": "A human-readable explanation specific to this occurrence of the problem. Focus on helping correct the problem, rather than giving debugging information.", + "type": "string" + }, + "errors": { + "description": "An object denoting field-specific errors. Only present on error responses when field input is specified for the request.", + "type": "object" + }, + "instance": { + "description": "A relative URI reference that identifies the specific occurrence of the problem", + "format": "uri", + "type": "string" + }, + "status": { + "description": "HTTP status code", + "example": 400, + "type": "integer" + }, + "title": { + "description": "Short, human-readable summary of the problem, should not change by occurrence.", + "type": "string" + }, + "type": { + "default": "about:blank", + "description": "Relative URI reference to the type of problem which includes human-readable documentation.", + "format": "uri", + "type": "string" + } + } + } + } + } + } + } + } + }, "/v3/jobs": { "get": { "summary": "Retrieve a list of JobRecords that are registered with IMS", @@ -6438,9 +6668,20 @@ "type": "string" }, "metadata": { - "description": "List of key/value pairs to associate with an Image", + "description": "User supplied annotations about an image", "type": "object", - "properties": false + "properties": { + "key": { + "description": "Template variable to associate with the IMS image", + "example": "includes_additional_packages", + "type": "string" + }, + "value": { + "description": "Value variable to associate with the IMS image", + "example": "foo,bar,baz", + "type": "string" + } + } } } }, @@ -6885,9 +7126,20 @@ "type": "string" }, "metadata": { - "description": "List of key/value pairs to associate with an Image", + "description": "User supplied annotations about an image", "type": "object", - "properties": false + "properties": { + "key": { + "description": "Template variable to associate with the IMS image", + "example": "includes_additional_packages", + "type": "string" + }, + "value": { + "description": "Value variable to associate with the IMS image", + "example": "foo,bar,baz", + "type": "string" + } + } } } } @@ -9846,9 +10098,20 @@ "type": "string" }, "metadata": { - "description": "List of key/value pairs to associate with an Image", + "description": "User supplied annotations about an image", "type": "object", - "properties": false + "properties": { + "key": { + "description": "Template variable to associate with the IMS image", + "example": "includes_additional_packages", + "type": "string" + }, + "value": { + "description": "Value variable to associate with the IMS image", + "example": "foo,bar,baz", + "type": "string" + } + } } } } @@ -14691,9 +14954,20 @@ "type": "string" }, "metadata": { - "description": "List of key/value pairs to associate with an Image", + "description": "User supplied annotations about an image", "type": "object", - "properties": false + "properties": { + "key": { + "description": "Template variable to associate with the IMS image", + "example": "includes_additional_packages", + "type": "string" + }, + "value": { + "description": "Value variable to associate with the IMS image", + "example": "foo,bar,baz", + "type": "string" + } + } } } } @@ -19062,6 +19336,51 @@ } } }, + "RemoteBuildNodeStatus": { + "description": "A Remote Build Node Status", + "type": "object", + "required": [ + "xname" + ], + "properties": { + "xname": { + "description": "Xname of the remote build node", + "example": "x3000c1s10b1n0", + "type": "string", + "minLength": 1 + }, + "nodeArch": { + "description": "Architecture of the remote build node", + "example": "x86_64", + "type": "string", + "minLength": 1 + }, + "numCurrentJobs": { + "description": "Number of current jobs running on the remote build node", + "example": 15, + "type": "integer", + "minLength": 1 + }, + "podmanStatus": { + "description": "Status of the podman executable on the remote build node", + "example": "Podman present at /usr/bin/podman", + "type": "string", + "minLength": 1 + }, + "sshStatus": { + "description": "Status of the ssh connection to the remote build node", + "example": "SSH connection established", + "type": "string", + "minLength": 1 + }, + "ableToRunJobs": { + "description": "If the node is able to run new jobs", + "example": true, + "type": "boolean", + "minLength": 1 + } + } + }, "ArtifactLinkRecord": { "description": "An Artifact Link Record", "type": "object", @@ -19599,9 +19918,20 @@ "type": "string" }, "metadata": { - "description": "List of key/value pairs to associate with an Image", + "description": "User supplied annotations about an image", "type": "object", - "properties": false + "properties": { + "key": { + "description": "Template variable to associate with the IMS image", + "example": "includes_additional_packages", + "type": "string" + }, + "value": { + "description": "Value variable to associate with the IMS image", + "example": "foo,bar,baz", + "type": "string" + } + } } } }, diff --git a/cray/tests/test_modules/test_ims.py b/cray/tests/test_modules/test_ims.py index c293c9a..68bcfc0 100644 --- a/cray/tests/test_modules/test_ims.py +++ b/cray/tests/test_modules/test_ims.py @@ -175,6 +175,7 @@ def test_cray_ims_public_keys_create_missing_required(cli_runner, rest_mock): assert result.exit_code == 2 assert '--public-key' in result.output + def test_cray_ims_remote_build_nodes_base(cli_runner, rest_mock): """ Test cray ims remote-build-nodes base command """ runner, cli, _ = cli_runner @@ -262,6 +263,39 @@ def test_cray_ims_remote_build_nodes_create_missing_required(cli_runner, rest_mo assert '--xname' in result.output +def test_cray_ims_remote_build_nodes_status(cli_runner, rest_mock): + """ Test cray ims remote-build-nodes base command """ + runner, cli, _ = cli_runner + result = runner.invoke(cli, ['ims', 'remote-build-nodes', 'status']) + assert result.exit_code == 0 + + outputs = [ + "describe", + "list", + ] + + compare_output(outputs, result.output) + +def test_cray_ims_remote_build_nodes_status_list(cli_runner, rest_mock): + """ Test cray ims public_keys list """ + runner, cli, config = cli_runner + result = runner.invoke(cli, ['ims', 'remote-build-nodes', 'status', 'list']) + assert result.exit_code == 0 + data = json.loads(result.output) + assert data['method'] == 'GET' + assert data['url'] == f'{config["default"]["hostname"]}/apis/ims/v3/remote-build-nodes/status' + + +def test_cray_ims_remote_build_nodes_status_describe(cli_runner, rest_mock): + """ Test cray ims public_keys describe """ + runner, cli, config = cli_runner + result = runner.invoke(cli, ['ims', 'remote-build-nodes', 'status', 'describe', 'foo']) + assert result.exit_code == 0 + data = json.loads(result.output) + assert data['method'] == 'GET' + assert data['url'] == f'{config["default"]["hostname"]}/apis/ims/v3/remote-build-nodes/status/foo' + + def test_cray_ims_deleted_public_keys_base(cli_runner, rest_mock): """ Test cray ims public-keys base command """ runner, cli, _ = cli_runner From dddd06338f84bf9ed0d6abdffced9bca74c24e82 Mon Sep 17 00:00:00 2001 From: David Laine Date: Wed, 21 Aug 2024 11:38:46 -0500 Subject: [PATCH 2/3] Fix line too long. --- cray/tests/test_modules/test_ims.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/cray/tests/test_modules/test_ims.py b/cray/tests/test_modules/test_ims.py index 68bcfc0..e434a10 100644 --- a/cray/tests/test_modules/test_ims.py +++ b/cray/tests/test_modules/test_ims.py @@ -293,7 +293,8 @@ def test_cray_ims_remote_build_nodes_status_describe(cli_runner, rest_mock): assert result.exit_code == 0 data = json.loads(result.output) assert data['method'] == 'GET' - assert data['url'] == f'{config["default"]["hostname"]}/apis/ims/v3/remote-build-nodes/status/foo' + assert data['url'] == f'{config["default"]["hostname"]}/apis/ims/v3/\ + remote-build-nodes/status/foo' def test_cray_ims_deleted_public_keys_base(cli_runner, rest_mock): From 57add7f02fc8a408e84944c6643f2dd568299d12 Mon Sep 17 00:00:00 2001 From: David Laine Date: Wed, 21 Aug 2024 11:45:49 -0500 Subject: [PATCH 3/3] Fix line too long - take 2. --- cray/tests/test_modules/test_ims.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cray/tests/test_modules/test_ims.py b/cray/tests/test_modules/test_ims.py index e434a10..a180f4d 100644 --- a/cray/tests/test_modules/test_ims.py +++ b/cray/tests/test_modules/test_ims.py @@ -293,8 +293,8 @@ def test_cray_ims_remote_build_nodes_status_describe(cli_runner, rest_mock): assert result.exit_code == 0 data = json.loads(result.output) assert data['method'] == 'GET' - assert data['url'] == f'{config["default"]["hostname"]}/apis/ims/v3/\ - remote-build-nodes/status/foo' + testurl = f'{config["default"]["hostname"]}/apis/ims/v3/remote-build-nodes/status/foo' + assert data['url'] == testurl def test_cray_ims_deleted_public_keys_base(cli_runner, rest_mock):