ssh-handler 1.0.5__tar.gz → 1.0.6__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {ssh_handler-1.0.5/ssh_handler.egg-info → ssh_handler-1.0.6}/PKG-INFO +16 -1
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/README.md +15 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/pyproject.toml +5 -1
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/__init__.py +1 -1
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/cli.py +54 -0
- ssh_handler-1.0.6/ssh_handler/setup_openssh_server.ps1 +150 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6/ssh_handler.egg-info}/PKG-INFO +16 -1
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler.egg-info/SOURCES.txt +1 -0
- ssh_handler-1.0.6/ssh_handler.egg-info/entry_points.txt +3 -0
- ssh_handler-1.0.5/ssh_handler.egg-info/entry_points.txt +0 -2
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/LICENSE +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/setup.cfg +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/__main__.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/config.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/core.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/credentials.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/exceptions.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/ftp.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/pool.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/pyqt_worker.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/results.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler/winrm_bootstrap.py +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler.egg-info/dependency_links.txt +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler.egg-info/requires.txt +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/ssh_handler.egg-info/top_level.txt +0 -0
- {ssh_handler-1.0.5 → ssh_handler-1.0.6}/tests/test_offline.py +0 -0
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: ssh-handler
|
|
3
|
-
Version: 1.0.
|
|
3
|
+
Version: 1.0.6
|
|
4
4
|
Summary: Extensive SSH/SFTP/SCP/FTP handler built on Paramiko, for test automation, CLIs and PyQt5 tools.
|
|
5
5
|
Author: ssh-handler contributors
|
|
6
6
|
License-Expression: MIT
|
|
@@ -224,6 +224,21 @@ Requirements: `pip install "ssh-handler[winrm]"` (pulls in `pywinrm`; uses NTLM
|
|
|
224
224
|
domain creds work without Kerberos), and the account must be a **local
|
|
225
225
|
administrator** on the target. If SSH already works, this code path never runs.
|
|
226
226
|
|
|
227
|
+
### Set up OpenSSH Server on a machine (bundled installer)
|
|
228
|
+
|
|
229
|
+
Installing the package also gives you a one-command setup for the *local* Windows
|
|
230
|
+
machine — it ships inside the wheel, self-elevates to Administrator, installs &
|
|
231
|
+
starts OpenSSH Server, and opens the firewall:
|
|
232
|
+
|
|
233
|
+
```powershell
|
|
234
|
+
pip install ssh-handler
|
|
235
|
+
ssh-handler-setup # install + start sshd + firewall (self-elevates)
|
|
236
|
+
ssh-handler-setup --install-pip # also (re)install the package as admin
|
|
237
|
+
# equivalent: python -m ssh_handler setup-server
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
Run it on whichever machine you want to reach over SSH (e.g. the RDP jump box).
|
|
241
|
+
|
|
227
242
|
When a connection just fails, the error now self-diagnoses — it probes the SSH and
|
|
228
243
|
RDP ports and tells you *why* (e.g. "Port 22 is closed but RDP (3389) is open … no
|
|
229
244
|
SSH server listening"). Call `ssh.diagnose()` for a pre-flight reachability check.
|
|
@@ -193,6 +193,21 @@ Requirements: `pip install "ssh-handler[winrm]"` (pulls in `pywinrm`; uses NTLM
|
|
|
193
193
|
domain creds work without Kerberos), and the account must be a **local
|
|
194
194
|
administrator** on the target. If SSH already works, this code path never runs.
|
|
195
195
|
|
|
196
|
+
### Set up OpenSSH Server on a machine (bundled installer)
|
|
197
|
+
|
|
198
|
+
Installing the package also gives you a one-command setup for the *local* Windows
|
|
199
|
+
machine — it ships inside the wheel, self-elevates to Administrator, installs &
|
|
200
|
+
starts OpenSSH Server, and opens the firewall:
|
|
201
|
+
|
|
202
|
+
```powershell
|
|
203
|
+
pip install ssh-handler
|
|
204
|
+
ssh-handler-setup # install + start sshd + firewall (self-elevates)
|
|
205
|
+
ssh-handler-setup --install-pip # also (re)install the package as admin
|
|
206
|
+
# equivalent: python -m ssh_handler setup-server
|
|
207
|
+
```
|
|
208
|
+
|
|
209
|
+
Run it on whichever machine you want to reach over SSH (e.g. the RDP jump box).
|
|
210
|
+
|
|
196
211
|
When a connection just fails, the error now self-diagnoses — it probes the SSH and
|
|
197
212
|
RDP ports and tells you *why* (e.g. "Port 22 is closed but RDP (3389) is open … no
|
|
198
213
|
SSH server listening"). Call `ssh.diagnose()` for a pre-flight reachability check.
|
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "ssh-handler"
|
|
7
|
-
version = "1.0.
|
|
7
|
+
version = "1.0.6"
|
|
8
8
|
description = "Extensive SSH/SFTP/SCP/FTP handler built on Paramiko, for test automation, CLIs and PyQt5 tools."
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
requires-python = ">=3.8"
|
|
@@ -32,6 +32,10 @@ all = ["keyring>=23.0", "scp>=0.14", "PyQt5>=5.15", "pywinrm>=0.4.3"]
|
|
|
32
32
|
|
|
33
33
|
[project.scripts]
|
|
34
34
|
ssh-handler = "ssh_handler.cli:main"
|
|
35
|
+
ssh-handler-setup = "ssh_handler.cli:setup_server_main"
|
|
35
36
|
|
|
36
37
|
[tool.setuptools]
|
|
37
38
|
packages = ["ssh_handler"]
|
|
39
|
+
|
|
40
|
+
[tool.setuptools.package-data]
|
|
41
|
+
ssh_handler = ["*.ps1"]
|
|
@@ -15,9 +15,11 @@ Credentials (password never echoed, never stored in plaintext):
|
|
|
15
15
|
|
|
16
16
|
from __future__ import annotations
|
|
17
17
|
|
|
18
|
+
import os
|
|
18
19
|
import sys
|
|
19
20
|
import json
|
|
20
21
|
import argparse
|
|
22
|
+
import subprocess
|
|
21
23
|
|
|
22
24
|
from .config import SSHConfig
|
|
23
25
|
from .core import SSHHandler
|
|
@@ -26,6 +28,35 @@ from .exceptions import SSHError
|
|
|
26
28
|
from .results import CommandResult, TransferResult
|
|
27
29
|
|
|
28
30
|
|
|
31
|
+
def _setup_script_path() -> str:
|
|
32
|
+
"""Absolute path to the bundled OpenSSH setup PowerShell script."""
|
|
33
|
+
return os.path.join(os.path.dirname(__file__), "setup_openssh_server.ps1")
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
def setup_server_main(argv=None) -> int:
|
|
37
|
+
"""
|
|
38
|
+
Console entry point (`ssh-handler-setup`): run the bundled PowerShell script
|
|
39
|
+
that installs & starts OpenSSH Server, opens the firewall, and optionally
|
|
40
|
+
pip-installs the package. Self-elevates to Administrator. Windows only.
|
|
41
|
+
|
|
42
|
+
Any extra args are forwarded to the script, e.g.:
|
|
43
|
+
ssh-handler-setup --InstallPip --Port 22
|
|
44
|
+
"""
|
|
45
|
+
if os.name != "nt":
|
|
46
|
+
print("ssh-handler-setup only runs on Windows (it sets up OpenSSH Server).",
|
|
47
|
+
file=sys.stderr)
|
|
48
|
+
return 2
|
|
49
|
+
script = _setup_script_path()
|
|
50
|
+
if not os.path.exists(script):
|
|
51
|
+
print(f"Bundled setup script not found: {script}", file=sys.stderr)
|
|
52
|
+
return 1
|
|
53
|
+
extra = list(argv) if argv is not None else sys.argv[1:]
|
|
54
|
+
cmd = ["powershell", "-NoProfile", "-ExecutionPolicy", "Bypass",
|
|
55
|
+
"-File", script] + extra
|
|
56
|
+
print(f"Launching OpenSSH Server setup (will prompt for Administrator)...")
|
|
57
|
+
return subprocess.call(cmd)
|
|
58
|
+
|
|
59
|
+
|
|
29
60
|
def _add_conn_args(p: argparse.ArgumentParser) -> None:
|
|
30
61
|
p.add_argument("--host", required=True)
|
|
31
62
|
p.add_argument("--port", type=int, default=22)
|
|
@@ -107,6 +138,29 @@ def main(argv=None) -> int:
|
|
|
107
138
|
p_info = sub.add_parser("info", help="connect and report remote OS")
|
|
108
139
|
_add_conn_args(p_info)
|
|
109
140
|
|
|
141
|
+
p_setup = sub.add_parser("setup-server",
|
|
142
|
+
help="install & start OpenSSH Server on THIS Windows "
|
|
143
|
+
"machine (self-elevates to Administrator)")
|
|
144
|
+
p_setup.add_argument("--install-pip", action="store_true",
|
|
145
|
+
help="also pip-install ssh-handler[winrm]")
|
|
146
|
+
p_setup.add_argument("--port", type=int, default=22)
|
|
147
|
+
|
|
148
|
+
# setup-server takes no connection args and runs the bundled PowerShell script
|
|
149
|
+
if argv is None:
|
|
150
|
+
_argv = sys.argv[1:]
|
|
151
|
+
else:
|
|
152
|
+
_argv = list(argv)
|
|
153
|
+
if _argv and _argv[0] == "setup-server":
|
|
154
|
+
forward = []
|
|
155
|
+
rest = _argv[1:]
|
|
156
|
+
if "--install-pip" in rest:
|
|
157
|
+
forward.append("-InstallPip")
|
|
158
|
+
if "--port" in rest:
|
|
159
|
+
i = rest.index("--port")
|
|
160
|
+
if i + 1 < len(rest):
|
|
161
|
+
forward += ["-Port", rest[i + 1]]
|
|
162
|
+
return setup_server_main(forward)
|
|
163
|
+
|
|
110
164
|
args = parser.parse_args(argv)
|
|
111
165
|
|
|
112
166
|
# store-credential is handled without a connection
|
|
@@ -0,0 +1,150 @@
|
|
|
1
|
+
<#
|
|
2
|
+
.SYNOPSIS
|
|
3
|
+
One-shot setup for an SSH target / RDP jump machine:
|
|
4
|
+
installs & starts OpenSSH Server, opens the firewall, and (optionally)
|
|
5
|
+
pip-installs the ssh-handler package. Self-elevates to Administrator.
|
|
6
|
+
|
|
7
|
+
.DESCRIPTION
|
|
8
|
+
Run this once on a Windows machine that you want to reach over SSH (e.g. the
|
|
9
|
+
RDP box you tunnel through). It:
|
|
10
|
+
1. Re-launches itself elevated if not already running as Administrator.
|
|
11
|
+
2. Installs OpenSSH Server (Windows capability -> winget fallback).
|
|
12
|
+
3. Starts sshd, sets it to start automatically, opens TCP 22.
|
|
13
|
+
4. Optionally runs `pip install -U "ssh-handler[winrm]"`.
|
|
14
|
+
5. Verifies sshd is running and listening.
|
|
15
|
+
|
|
16
|
+
.PARAMETER InstallPip
|
|
17
|
+
Also install/upgrade the ssh-handler Python package (needs Python+pip on PATH).
|
|
18
|
+
|
|
19
|
+
.PARAMETER Port
|
|
20
|
+
SSH port to open in the firewall (default 22).
|
|
21
|
+
|
|
22
|
+
.EXAMPLE
|
|
23
|
+
powershell -ExecutionPolicy Bypass -File .\setup_openssh_server.ps1
|
|
24
|
+
|
|
25
|
+
.EXAMPLE
|
|
26
|
+
powershell -ExecutionPolicy Bypass -File .\setup_openssh_server.ps1 -InstallPip
|
|
27
|
+
#>
|
|
28
|
+
|
|
29
|
+
param(
|
|
30
|
+
[switch]$InstallPip,
|
|
31
|
+
[int]$Port = 22
|
|
32
|
+
)
|
|
33
|
+
|
|
34
|
+
$ErrorActionPreference = 'Stop'
|
|
35
|
+
$ProgressPreference = 'SilentlyContinue'
|
|
36
|
+
|
|
37
|
+
# --- 1. Self-elevate to Administrator -------------------------------------- #
|
|
38
|
+
$isAdmin = ([Security.Principal.WindowsPrincipal]`
|
|
39
|
+
[Security.Principal.WindowsIdentity]::GetCurrent()`
|
|
40
|
+
).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator)
|
|
41
|
+
|
|
42
|
+
if (-not $isAdmin) {
|
|
43
|
+
Write-Host "Elevating to Administrator..." -ForegroundColor Yellow
|
|
44
|
+
$argList = "-NoProfile -ExecutionPolicy Bypass -File `"$PSCommandPath`""
|
|
45
|
+
if ($InstallPip) { $argList += " -InstallPip" }
|
|
46
|
+
$argList += " -Port $Port"
|
|
47
|
+
Start-Process powershell -Verb RunAs -ArgumentList $argList
|
|
48
|
+
exit
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
Write-Host "=== OpenSSH Server setup (running as Administrator) ===" -ForegroundColor Cyan
|
|
52
|
+
|
|
53
|
+
# --- 2. Install OpenSSH Server --------------------------------------------- #
|
|
54
|
+
function Test-SshdPresent {
|
|
55
|
+
return [bool](Get-Service -Name sshd -ErrorAction SilentlyContinue)
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
if (Test-SshdPresent) {
|
|
59
|
+
Write-Host "OpenSSH Server already present." -ForegroundColor Green
|
|
60
|
+
}
|
|
61
|
+
else {
|
|
62
|
+
Write-Host "Installing OpenSSH Server..."
|
|
63
|
+
$installed = $false
|
|
64
|
+
|
|
65
|
+
# 2a. Windows capability (Features-on-Demand). May be slow on corporate nets.
|
|
66
|
+
try {
|
|
67
|
+
$cap = Get-WindowsCapability -Online -Name 'OpenSSH.Server*' |
|
|
68
|
+
Select-Object -First 1
|
|
69
|
+
if ($cap -and $cap.State -ne 'Installed') {
|
|
70
|
+
Write-Host " Trying Add-WindowsCapability (can take a few minutes)..."
|
|
71
|
+
Add-WindowsCapability -Online -Name $cap.Name | Out-Null
|
|
72
|
+
}
|
|
73
|
+
if (Test-SshdPresent) { $installed = $true }
|
|
74
|
+
}
|
|
75
|
+
catch {
|
|
76
|
+
Write-Host " Windows capability install failed: $($_.Exception.Message)" `
|
|
77
|
+
-ForegroundColor DarkYellow
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
# 2b. winget fallback
|
|
81
|
+
if (-not $installed) {
|
|
82
|
+
try {
|
|
83
|
+
Write-Host " Trying winget (Microsoft.OpenSSH.Beta)..."
|
|
84
|
+
winget install --id Microsoft.OpenSSH.Beta -e --silent `
|
|
85
|
+
--accept-source-agreements --accept-package-agreements | Out-Null
|
|
86
|
+
if (Test-SshdPresent) { $installed = $true }
|
|
87
|
+
}
|
|
88
|
+
catch {
|
|
89
|
+
Write-Host " winget not available or failed." -ForegroundColor DarkYellow
|
|
90
|
+
}
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
if (-not $installed -and -not (Test-SshdPresent)) {
|
|
94
|
+
Write-Warning @"
|
|
95
|
+
Could not auto-install OpenSSH Server (Windows Update / winget likely blocked).
|
|
96
|
+
Manual fallback:
|
|
97
|
+
1. On a machine with internet, download OpenSSH-Win64.zip from
|
|
98
|
+
https://github.com/PowerShell/Win32-OpenSSH/releases/latest
|
|
99
|
+
2. Copy it here, extract to 'C:\Program Files\OpenSSH'
|
|
100
|
+
3. Run: powershell -ExecutionPolicy Bypass -File 'C:\Program Files\OpenSSH\install-sshd.ps1'
|
|
101
|
+
Then re-run this script to finish service + firewall setup.
|
|
102
|
+
"@
|
|
103
|
+
exit 1
|
|
104
|
+
}
|
|
105
|
+
Write-Host "OpenSSH Server installed." -ForegroundColor Green
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
# --- 3. Service + firewall -------------------------------------------------- #
|
|
109
|
+
Write-Host "Configuring sshd service and firewall..."
|
|
110
|
+
Set-Service -Name sshd -StartupType Automatic
|
|
111
|
+
Start-Service sshd
|
|
112
|
+
|
|
113
|
+
$ruleName = "OpenSSH-Server-In-TCP"
|
|
114
|
+
if (-not (Get-NetFirewallRule -Name $ruleName -ErrorAction SilentlyContinue)) {
|
|
115
|
+
New-NetFirewallRule -Name $ruleName -DisplayName 'OpenSSH Server (sshd)' `
|
|
116
|
+
-Enabled True -Direction Inbound -Protocol TCP -Action Allow `
|
|
117
|
+
-LocalPort $Port | Out-Null
|
|
118
|
+
Write-Host " Firewall rule added for TCP $Port." -ForegroundColor Green
|
|
119
|
+
}
|
|
120
|
+
else {
|
|
121
|
+
Write-Host " Firewall rule already present." -ForegroundColor Green
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
# --- 4. Optional: pip install the package ---------------------------------- #
|
|
125
|
+
if ($InstallPip) {
|
|
126
|
+
Write-Host "Installing ssh-handler (pip)..."
|
|
127
|
+
try {
|
|
128
|
+
python -m pip install --upgrade pip | Out-Null
|
|
129
|
+
python -m pip install -U "ssh-handler[winrm]"
|
|
130
|
+
Write-Host " ssh-handler installed." -ForegroundColor Green
|
|
131
|
+
}
|
|
132
|
+
catch {
|
|
133
|
+
Write-Warning "pip install failed: $($_.Exception.Message)"
|
|
134
|
+
Write-Host " Ensure Python and pip are on PATH, then run: pip install -U ssh-handler"
|
|
135
|
+
}
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
# --- 5. Verify -------------------------------------------------------------- #
|
|
139
|
+
Write-Host "`n=== Verification ===" -ForegroundColor Cyan
|
|
140
|
+
$svc = Get-Service sshd
|
|
141
|
+
Write-Host ("sshd status : {0}" -f $svc.Status)
|
|
142
|
+
$test = Test-NetConnection localhost -Port $Port -WarningAction SilentlyContinue
|
|
143
|
+
Write-Host ("port {0} open : {1}" -f $Port, $test.TcpTestSucceeded)
|
|
144
|
+
|
|
145
|
+
if ($svc.Status -eq 'Running' -and $test.TcpTestSucceeded) {
|
|
146
|
+
Write-Host "`nDone. This machine now accepts SSH on port $Port." -ForegroundColor Green
|
|
147
|
+
}
|
|
148
|
+
else {
|
|
149
|
+
Write-Warning "Setup finished but sshd is not listening yet - check the messages above."
|
|
150
|
+
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: ssh-handler
|
|
3
|
-
Version: 1.0.
|
|
3
|
+
Version: 1.0.6
|
|
4
4
|
Summary: Extensive SSH/SFTP/SCP/FTP handler built on Paramiko, for test automation, CLIs and PyQt5 tools.
|
|
5
5
|
Author: ssh-handler contributors
|
|
6
6
|
License-Expression: MIT
|
|
@@ -224,6 +224,21 @@ Requirements: `pip install "ssh-handler[winrm]"` (pulls in `pywinrm`; uses NTLM
|
|
|
224
224
|
domain creds work without Kerberos), and the account must be a **local
|
|
225
225
|
administrator** on the target. If SSH already works, this code path never runs.
|
|
226
226
|
|
|
227
|
+
### Set up OpenSSH Server on a machine (bundled installer)
|
|
228
|
+
|
|
229
|
+
Installing the package also gives you a one-command setup for the *local* Windows
|
|
230
|
+
machine — it ships inside the wheel, self-elevates to Administrator, installs &
|
|
231
|
+
starts OpenSSH Server, and opens the firewall:
|
|
232
|
+
|
|
233
|
+
```powershell
|
|
234
|
+
pip install ssh-handler
|
|
235
|
+
ssh-handler-setup # install + start sshd + firewall (self-elevates)
|
|
236
|
+
ssh-handler-setup --install-pip # also (re)install the package as admin
|
|
237
|
+
# equivalent: python -m ssh_handler setup-server
|
|
238
|
+
```
|
|
239
|
+
|
|
240
|
+
Run it on whichever machine you want to reach over SSH (e.g. the RDP jump box).
|
|
241
|
+
|
|
227
242
|
When a connection just fails, the error now self-diagnoses — it probes the SSH and
|
|
228
243
|
RDP ports and tells you *why* (e.g. "Port 22 is closed but RDP (3389) is open … no
|
|
229
244
|
SSH server listening"). Call `ssh.diagnose()` for a pre-flight reachability check.
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|