Skip to content

Commit 45a81a5

Browse files
committed
adjust connection settings
1 parent 47781c8 commit 45a81a5

4 files changed

Lines changed: 52 additions & 6 deletions

File tree

.github/workflows/benchmarks.yaml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -119,6 +119,8 @@ jobs:
119119
mkdir -p ~/.ssh
120120
echo "${{ secrets.HETZNER_SSH_PRIVATE_KEY }}" > ~/.ssh/hetzner_key
121121
chmod 600 ~/.ssh/hetzner_key
122+
# Generate public key from private key for Hetzner registration
123+
ssh-keygen -y -f ~/.ssh/hetzner_key > ~/.ssh/hetzner_key.pub
122124
123125
- name: Run benchmarks on Hetzner
124126
env:

csp_benchmarks/hetzner/cli.py

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,11 +31,16 @@ def run_benchmarks(args: argparse.Namespace) -> int:
3131
logger.error("Hetzner Cloud token required. Set HCLOUD_TOKEN or use --token")
3232
return 1
3333

34+
# Determine SSH key name - either explicit or derive from key file
35+
ssh_key_name = args.ssh_key_name
36+
if not ssh_key_name and args.ssh_key:
37+
ssh_key_name = "csp-benchmarks"
38+
3439
# Configure server
3540
server_config = ServerConfig(
3641
name=args.server_name,
3742
server_type=args.server_type,
38-
ssh_key_name=args.ssh_key_name,
43+
ssh_key_name=ssh_key_name,
3944
)
4045

4146
# Configure benchmarks
@@ -48,6 +53,24 @@ def run_benchmarks(args: argparse.Namespace) -> int:
4853
server = None
4954

5055
try:
56+
# Upload SSH public key to Hetzner if we have a private key
57+
if args.ssh_key and ssh_key_name:
58+
pub_key_path = args.ssh_key + ".pub"
59+
if os.path.exists(pub_key_path):
60+
with open(pub_key_path) as f:
61+
public_key = f.read().strip()
62+
manager.ensure_ssh_key(public_key, ssh_key_name)
63+
else:
64+
# Try to generate public key from private key
65+
import subprocess
66+
67+
result = subprocess.run(["ssh-keygen", "-y", "-f", args.ssh_key], capture_output=True, text=True)
68+
if result.returncode == 0:
69+
public_key = result.stdout.strip()
70+
manager.ensure_ssh_key(public_key, ssh_key_name)
71+
else:
72+
logger.warning(f"Could not extract public key from {args.ssh_key}")
73+
5174
# Check if server already exists
5275
server = manager.get_server()
5376
if server and not args.reuse:

csp_benchmarks/hetzner/runner.py

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -136,26 +136,29 @@ def _scp_from_server(self, remote_path: str, local_path: str) -> None:
136136

137137
subprocess.run(scp_args, check=True)
138138

139-
def _wait_for_ssh(self, timeout: int = 120, interval: int = 10) -> None:
139+
def _wait_for_ssh(self, timeout: int = 300, interval: int = 15) -> None:
140140
"""Wait for SSH to become available on the server."""
141141
import time
142142

143143
logger.info("Waiting for SSH to become available...")
144144
start_time = time.time()
145+
last_error = None
145146

146147
while time.time() - start_time < timeout:
147148
try:
148149
result = self._run_ssh_command("echo 'SSH ready'", check=False)
149150
if result.returncode == 0:
150151
logger.info("SSH connection established")
151152
return
152-
except Exception:
153-
pass
153+
last_error = f"exit code {result.returncode}: {result.stderr}"
154+
except Exception as e:
155+
last_error = str(e)
154156

155-
logger.debug(f"SSH not ready, retrying in {interval}s...")
157+
elapsed = int(time.time() - start_time)
158+
logger.info(f"SSH not ready after {elapsed}s, retrying... (last error: {last_error})")
156159
time.sleep(interval)
157160

158-
raise TimeoutError(f"SSH not available after {timeout} seconds")
161+
raise TimeoutError(f"SSH not available after {timeout} seconds. Last error: {last_error}")
159162

160163
def _setup_environment(self) -> None:
161164
"""Set up the benchmark environment on the remote server."""

csp_benchmarks/hetzner/server.py

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -140,6 +140,24 @@ def _wait_for_server_ready(self, server: BoundServer, timeout: int = 300) -> Non
140140

141141
raise TimeoutError(f"Server did not become ready within {timeout} seconds")
142142

143+
def ensure_ssh_key(self, public_key: str, key_name: str = "csp-benchmarks") -> None:
144+
"""
145+
Ensure an SSH public key exists in Hetzner Cloud.
146+
147+
Args:
148+
public_key: The SSH public key content
149+
key_name: Name for the key in Hetzner Cloud
150+
"""
151+
# Check if key already exists
152+
existing = self.client.ssh_keys.get_by_name(key_name)
153+
if existing:
154+
logger.info(f"SSH key '{key_name}' already exists in Hetzner Cloud")
155+
return
156+
157+
# Create the key
158+
logger.info(f"Creating SSH key '{key_name}' in Hetzner Cloud")
159+
self.client.ssh_keys.create(name=key_name, public_key=public_key)
160+
143161
def _get_cloud_init_script(self) -> str:
144162
"""Get the cloud-init script for server setup."""
145163
return """#cloud-config

0 commit comments

Comments
 (0)