added SSH key injection for rescue mode
This commit is contained in:
		
							
								
								
									
										22
									
								
								README.md
									
									
									
									
									
								
							
							
						
						
									
										22
									
								
								README.md
									
									
									
									
									
								
							| @@ -72,6 +72,28 @@ client.disable_rescue_mode(test_server.id); | ||||
| print(`Rebooting server with ID: ${test_server.id}`); | ||||
| client.reboot(test_server.id); | ||||
| ``` | ||||
| #### Injecting SSH Keys into Rescue Mode | ||||
|  | ||||
| You can also inject SSH keys into the rescue image. The `enable_rescue_mode` function accepts an optional SSH key ID (integer) or an array of SSH key IDs. | ||||
|  | ||||
| **Important:** The SSH keys must already exist in your Hetzner Cloud project. You can add them in the [Hetzner Cloud Console](https://console.hetzner.cloud/). For more details, refer to the [official documentation on enabling rescue mode](https://docs.hetzner.cloud/reference/cloud#server-actions-enable-rescue-mode-for-a-server). | ||||
|  | ||||
| Here are some examples of how to use this feature in your Rhai script: | ||||
|  | ||||
| ```rust | ||||
| // A single SSH key ID | ||||
| client.enable_rescue_mode(test_server.id, 1337); | ||||
|  | ||||
| // An array of SSH key IDs | ||||
| let ssh_keys = [123, 456, 789]; | ||||
| client.enable_rescue_mode(test_server.id, ssh_keys); | ||||
|  | ||||
| // Reading an SSH key from an environment variable | ||||
| let ssh_key_from_env = get_env("SSH_KEY_ID"); | ||||
| if ssh_key_from_env != "" { | ||||
|     client.enable_rescue_mode(test_server.id, ssh_key_from_env.parse_int()); | ||||
| } | ||||
| ``` | ||||
|  | ||||
| ### 4. Example Output (from `test.rhai` script) | ||||
|  | ||||
|   | ||||
| @@ -9,7 +9,7 @@ pub enum Request { | ||||
|     GetServer(HetznerClient, i64), | ||||
|     RebootServer(HetznerClient, i64), | ||||
|     ResetServer(HetznerClient, i64), | ||||
|     EnableRescueMode(HetznerClient, i64), | ||||
|     EnableRescueMode(HetznerClient, i64, Vec<i64>), | ||||
|     DisableRescueMode(HetznerClient, i64), | ||||
| } | ||||
|  | ||||
| @@ -55,8 +55,8 @@ pub fn run_worker( | ||||
|                     let result = rt.block_on(client.reset_server(server_id)).map_err(|e| e.to_string()); | ||||
|                     Response::ResetServer(result) | ||||
|                 } | ||||
|                 Request::EnableRescueMode(client, server_id) => { | ||||
|                     let result = rt.block_on(client.enable_rescue_mode_for_server(server_id)).map_err(|e| e.to_string()); | ||||
|                 Request::EnableRescueMode(client, server_id, ssh_keys) => { | ||||
|                     let result = rt.block_on(client.enable_rescue_mode_for_server(server_id, ssh_keys)).map_err(|e| e.to_string()); | ||||
|                     Response::EnableRescueMode(result) | ||||
|                 } | ||||
|                 Request::DisableRescueMode(client, server_id) => { | ||||
|   | ||||
| @@ -94,11 +94,11 @@ impl HetznerClient { | ||||
|         servers_api::reset_server(&self.configuration, params).await?; | ||||
|         Ok(()) | ||||
|     } | ||||
|     pub async fn enable_rescue_mode_for_server(&self, server_id: i64) -> Result<String, Box<dyn std::error::Error>> { | ||||
|     pub async fn enable_rescue_mode_for_server(&self, server_id: i64, ssh_keys: Vec<i64>) -> Result<String, Box<dyn std::error::Error>> { | ||||
|         let params = EnableRescueModeForServerParams { | ||||
|             id: server_id, | ||||
|             enable_rescue_mode_for_server_request: Some(EnableRescueModeForServerRequest { | ||||
|                 ssh_keys: None, | ||||
|                 ssh_keys: if ssh_keys.is_empty() { None } else { Some(ssh_keys) }, | ||||
|                 r#type: Some(hcloud::models::enable_rescue_mode_for_server_request::Type::Linux64), | ||||
|             }), | ||||
|         }; | ||||
|   | ||||
| @@ -2,6 +2,7 @@ use crate::async_handler::Response; | ||||
| use crate::async_handler::Request; | ||||
| use crate::hetzner_api::{HetznerClient, WrappedServer}; | ||||
| use rhai::{Engine, EvalAltResult}; | ||||
| use std::env; | ||||
| use std::sync::{mpsc::{Receiver, Sender}, Arc, Mutex}; | ||||
| use prettytable::{Table, Row, Cell}; | ||||
|  | ||||
| @@ -110,7 +111,30 @@ pub fn register_hetzner_api( | ||||
|         .register_fn("enable_rescue_mode", { | ||||
|             let bridge = api_bridge.clone(); | ||||
|             move |client: &mut HetznerClient, server_id: i64| { | ||||
|                 bridge.call(Request::EnableRescueMode(client.clone(), server_id), |response| { | ||||
|                 bridge.call(Request::EnableRescueMode(client.clone(), server_id, Vec::new()), |response| { | ||||
|                     match response { | ||||
|                         Response::EnableRescueMode(result) => result.map_err(|e| e.into()), | ||||
|                         _ => Err("Unexpected response".into()), | ||||
|                     } | ||||
|                 }) | ||||
|             } | ||||
|         }) | ||||
|         .register_fn("enable_rescue_mode", { | ||||
|             let bridge = api_bridge.clone(); | ||||
|             move |client: &mut HetznerClient, server_id: i64, ssh_key: i64| { | ||||
|                 bridge.call(Request::EnableRescueMode(client.clone(), server_id, vec![ssh_key]), |response| { | ||||
|                     match response { | ||||
|                         Response::EnableRescueMode(result) => result.map_err(|e| e.into()), | ||||
|                         _ => Err("Unexpected response".into()), | ||||
|                     } | ||||
|                 }) | ||||
|             } | ||||
|         }) | ||||
|         .register_fn("enable_rescue_mode", { | ||||
|             let bridge = api_bridge.clone(); | ||||
|             move |client: &mut HetznerClient, server_id: i64, ssh_keys: rhai::Array| { | ||||
|                 let keys: Vec<i64> = ssh_keys.into_iter().map(|k| k.as_int().unwrap_or(0)).collect(); | ||||
|                 bridge.call(Request::EnableRescueMode(client.clone(), server_id, keys), |response| { | ||||
|                     match response { | ||||
|                         Response::EnableRescueMode(result) => result.map_err(|e| e.into()), | ||||
|                         _ => Err("Unexpected response".into()), | ||||
| @@ -169,4 +193,8 @@ pub fn register_hetzner_api( | ||||
|  | ||||
|             Ok(table.to_string()) | ||||
|         }); | ||||
|  | ||||
|     engine.register_fn("get_env", |key: &str| -> String { | ||||
|         env::var(key).unwrap_or("".to_string()) | ||||
|     }); | ||||
| } | ||||
							
								
								
									
										12
									
								
								test.rhai
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								test.rhai
									
									
									
									
									
								
							| @@ -13,9 +13,19 @@ print(test_server.show_details()); | ||||
|  | ||||
| // Enable rescue mode flag on server  | ||||
| print(`Enabling rescue mode on server with ID: ${test_server.id}`); | ||||
| let root_password = client.enable_rescue_mode(test_server.id); | ||||
| let root_password = client.enable_rescue_mode(test_server.id, 1337); | ||||
| print(`Root password is: ${root_password}`); | ||||
|  | ||||
| // Enable rescue mode with multiple keys from array | ||||
| let ssh_keys = [123, 456, 789]; | ||||
| let root_password = client.enable_rescue_mode(test_server.id, ssh_keys); | ||||
|  | ||||
| // read SSH key from env var | ||||
| let ssh_key_from_env = get_env("SSH_KEY_ID"); | ||||
| if ssh_key_from_env != "" { | ||||
|     client.enable_rescue_mode(test_server.id, ssh_key_from_env.parse_int()); | ||||
| } | ||||
|  | ||||
| // Disable rescue mode flag on server | ||||
| print(`Disabling rescue mode on server with ID: ${test_server.id}`); | ||||
| client.disable_rescue_mode(test_server.id); | ||||
|   | ||||
		Reference in New Issue
	
	Block a user