Skip to content

Commit e618981

Browse files
add method to issue ssh commands
Signed-off-by: Olamide Ojo <[email protected]>
1 parent 91366a0 commit e618981

File tree

45 files changed

+742
-136
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

45 files changed

+742
-136
lines changed

.vscode/settings.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,8 @@
1212
"./src/zos_files",
1313
"./src/zos_jobs",
1414
"./src/zos_tso",
15-
"./src/zosmf"
15+
"./src/zosmf",
16+
"./src/zos_uss"
1617
],
1718
"python.testing.pytestArgs": ["tests"],
1819
"python.testing.pytestEnabled": true,

CHANGELOG.md

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,10 @@
22

33
All notable changes to the Zowe Client Python SDK will be documented in this file.
44

5+
## Recent Changes
6+
7+
- Add method to issue SSH commands. [#253](https://github.com/zowe/zowe-client-python-sdk/issues/253)
8+
59
## `1.0.0-dev22`
610

711
### Enhancements

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ jsonschema
5454
pyyaml
5555
requests>=2.22
5656
urllib3
57+
paramiko
5758
```
5859

5960
It also has an optional dependency on the Zowe Secrets SDK for storing client secrets which can be installed with the `secrets` extra:

docs/README.md

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -26,3 +26,13 @@ These steps should help you to build the documentation
2626
- `npm run doc:install`
2727
5. Build and open the documentation:
2828
- `npm run doc:dev`
29+
30+
## Best practices
31+
32+
When using paramiko to interact with z/OS UNIX System Services (USS), it's important to consider encoding and special character handling.
33+
Since z/OS uses EBCDIC-based encodings (e.g., IBM-1047, IBM-037, etc.), some commands may return unexpected results when processed in a UTF-8 environment. This is because by default, paramiko reads responses in UTF-8, but z/OS USS may return data in an EBCDIC codepage.
34+
Certain special characters, such as ööö, 👍, or 🔟, may not be correctly interpreted if the encoding is mismatched.
35+
If you experience unexpected characters in output, check the terminal's encoding settings (local command on Linux).
36+
Some commands may alter the terminal's codepage, affecting subsequent outputs.
37+
For example, switching between ASCII and EBCDIC on mainframes can impact character interpretation.
38+
If a command affects encoding, reset it after execution.

docs/source/_ext/zowe_autodoc.py

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,11 @@ def main():
5858
if len(class_names) == 1:
5959
rst_name = f"{py_name[:-3]}.rst"
6060
rst_contents = render_template(
61-
CLASS_TEMPLATE, {"fullname": f"{sdk_name}.{pkg_name}.{class_names[0]}", "header": class_names[0]}
61+
CLASS_TEMPLATE,
62+
{
63+
"fullname": f"{sdk_name}.{pkg_name}.{class_names[0]}",
64+
"header": class_names[0],
65+
},
6266
)
6367
with open(f"docs/source/classes/{sdk_name}/{rst_name}", "w", encoding="utf-8") as f:
6468
f.write(rst_contents)
@@ -71,9 +75,16 @@ def main():
7175
rst_name = f"{class_name.lower()}.rst"
7276
rst_contents = render_template(
7377
CLASS_TEMPLATE,
74-
{"fullname": f"{sdk_name}.{pkg_name}.{module_name}.{class_name}", "header": class_name},
78+
{
79+
"fullname": f"{sdk_name}.{pkg_name}.{module_name}.{class_name}",
80+
"header": class_name,
81+
},
7582
)
76-
with open(f"docs/source/classes/{sdk_name}/{module_name}/{rst_name}", "w", encoding="utf-8") as f:
83+
with open(
84+
f"docs/source/classes/{sdk_name}/{module_name}/{rst_name}",
85+
"w",
86+
encoding="utf-8",
87+
) as f:
7788
f.write(rst_contents)
7889
child_rst_names.append(rst_name)
7990
rst_name = f"{module_name}/index.rst"
@@ -104,7 +115,11 @@ def main():
104115

105116
rst_contents = render_template(
106117
INDEX_TEMPLATE,
107-
{"filelist": "\n ".join(f"{name}/index" for name in sdk_names), "header": "Classes", "maxdepth": 3},
118+
{
119+
"filelist": "\n ".join(f"{name}/index" for name in sdk_names),
120+
"header": "Classes",
121+
"maxdepth": 3,
122+
},
108123
)
109124
with open(f"docs/source/classes/index.rst", "w", encoding="utf-8") as f:
110125
f.write(rst_contents)

docs/source/packages/files.rst

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -18,3 +18,27 @@ Reference
1818
:maxdepth: 2
1919

2020
../classes/zos_files/index
21+
22+
Interaction with USS via z/OSMF
23+
===============================
24+
25+
The Zowe Client Python SDK leverages the z/OS Management Facility (z/OSMF) REST interface to interact with Unix System Services (USS) on z/OS.
26+
Rather than connecting directly to USS, our implementation uses z/OSMF as a standardized conduit for file operations and other USS functionalities.
27+
This design offers several benefits:
28+
29+
- **Standardization:** z/OSMF provides a consistent REST API for interacting with various z/OS components, including USS.
30+
- **Security & Maintainability:** By utilizing z/OSMF, we benefit from its built-in authentication, logging, and error-handling mechanisms, making integration more robust.
31+
- **Simplified Integration:** The REST-based approach reduces the complexity of direct USS interactions, allowing for easier maintenance and future enhancements.
32+
33+
In summary, while it might appear that all USS functionality is routed through z/OSMF, this approach is intentional, providing a secure and manageable interface to z/OS USS.
34+
35+
Paramiko and Encoding Considerations
36+
======================================
37+
38+
When using Paramiko to interact with z/OS UNIX System Services (USS), it is important to consider encoding and the handling of special characters.
39+
By default, Paramiko decodes responses using UTF-8, but z/OS USS may return data in an EBCDIC codepage (e.g., IBM-1047, IBM-037, etc.).
40+
This mismatch can result in unexpected output, particularly with special characters like ``ööö``, ``👍``, or ``🔟``.
41+
42+
If you experience unexpected characters in your output, please check your terminal's encoding settings (for example, using ``locale`` on Linux).
43+
Note that certain commands may change the terminal's codepage, which can affect subsequent outputs.
44+
In such cases, resetting the terminal's encoding after command execution is recommended.

requirements.txt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ deepmerge==1.1.0
33
jsonschema==4.17.3
44
PyYAML==6.0.1
55
requests==2.32.0
6+
paramiko==3.5.0
67

78
# Dev deps
89
black
@@ -24,3 +25,4 @@ wheel
2425
-e ./src/zos_jobs
2526
-e ./src/zos_tso
2627
-e ./src/zosmf
28+
-e ./src/zos_uss

src/core/zowe/core_for_zowe_sdk/config_file.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
1010
Copyright Contributors to the Zowe Project.
1111
"""
12+
1213
import json
1314
import os.path
1415
import re

src/core/zowe/core_for_zowe_sdk/credential_manager.py

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,9 @@ def save_secure_props() -> None:
7979
# Delete the existing credential
8080
CredentialManager._delete_credential(constants["ZoweServiceName"], constants["ZoweAccountName"])
8181
CredentialManager._set_credential(
82-
constants["ZoweServiceName"], constants["ZoweAccountName"], encoded_credential
82+
constants["ZoweServiceName"],
83+
constants["ZoweAccountName"],
84+
encoded_credential,
8385
)
8486

8587
@staticmethod

src/core/zowe/core_for_zowe_sdk/logger.py

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,10 @@ class Log:
3939
file_handler: logging.FileHandler = logging.FileHandler(os.path.join(dirname, "python_sdk_logs.log"))
4040
file_handler.setLevel(logging.INFO)
4141
file_handler.setFormatter(
42-
logging.Formatter("[%(asctime)s] [%(levelname)s] [%(name)s] - %(message)s", "%m/%d/%Y %I:%M:%S %p")
42+
logging.Formatter(
43+
"[%(asctime)s] [%(levelname)s] [%(name)s] - %(message)s",
44+
"%m/%d/%Y %I:%M:%S %p",
45+
)
4346
)
4447
console_handler: logging.StreamHandler = logging.StreamHandler()
4548

0 commit comments

Comments
 (0)