pub struct SqlmapEngine { /* private fields */ }Expand description
Manages the sqlmapapi lifecycle and provides access to its REST API.
When the engine is dropped, the daemon subprocess (if locally spawned) is killed automatically via RAII.
Implementations§
Source§impl SqlmapEngine
impl SqlmapEngine
Sourcepub async fn new(
port: u16,
spawn_local: bool,
binary_path: Option<&str>,
) -> Result<Self, SqlmapError>
pub async fn new( port: u16, spawn_local: bool, binary_path: Option<&str>, ) -> Result<Self, SqlmapError>
Launches a local sqlmapapi daemon or connects to an existing remote one.
§Arguments
port— TCP port for the daemon. If0is passed withspawn_local, the OS assigns an ephemeral port (not yet supported by sqlmapapi).spawn_local— If true, spawns a localsqlmapapisubprocess.binary_path— Override thesqlmapapibinary location.
§Errors
Returns SqlmapError::ProcessError if the daemon fails to spawn,
or SqlmapError::ApiError if it doesn’t become responsive within 5 seconds.
Examples found in repository?
13async fn main() -> Result<(), Box<dyn std::error::Error>> {
14 // ── 1. Check availability ────────────────────────────
15 if !SqlmapEngine::is_available() {
16 eprintln!("ERROR: sqlmapapi not found in PATH");
17 eprintln!("Quick fix:");
18 eprintln!(" conda env create -f environment.yml");
19 eprintln!(" conda activate sqlmap-env");
20 eprintln!(" # OR: ./setup.sh");
21 std::process::exit(1);
22 }
23
24 // ── 2. Boot the daemon ───────────────────────────────
25 println!("Booting sqlmapapi daemon on port 8775...");
26 let engine = SqlmapEngine::new(8775, true, None).await?;
27 println!("Daemon ready at {}", engine.api_url());
28
29 // ── 3. Configure scan with builder ───────────────────
30 let target = std::env::args()
31 .nth(1)
32 .unwrap_or_else(|| "http://testphp.vulnweb.com/listproducts.php?cat=1".to_string());
33
34 println!("Target: {target}");
35
36 let opts = SqlmapOptions::builder()
37 .url(&target)
38 .level(3)
39 .risk(2)
40 .batch(true)
41 .threads(4)
42 .random_agent(true)
43 .build();
44
45 // ── 4. Create and run task ───────────────────────────
46 let task = engine.create_task(&opts).await?;
47 println!("Task created: {}", task.task_id());
48
49 task.start().await?;
50 println!("Scan started, polling for completion...");
51
52 // ── 5. Monitor execution ─────────────────────────────
53 task.wait_for_completion(300).await?;
54 println!("Scan complete!");
55
56 // ── 6. Fetch and display logs ────────────────────────
57 match task.fetch_log().await {
58 Ok(log_resp) => {
59 if let Some(logs) = &log_resp.log {
60 println!("\n=== Scan Log ({} entries) ===", logs.len());
61 for entry in logs.iter().rev().take(10) {
62 println!(" [{}] {}: {}", entry.time, entry.level, entry.message);
63 }
64 if logs.len() > 10 {
65 println!(" ... and {} more entries", logs.len() - 10);
66 }
67 }
68 }
69 Err(err) => eprintln!("Could not fetch log: {err}"),
70 }
71
72 // ── 7. Fetch results ─────────────────────────────────
73 let data = task.fetch_data().await?;
74 let findings = data.findings();
75
76 println!("\n=== Results ===");
77 println!(" Findings: {}", findings.len());
78
79 if findings.is_empty() {
80 println!(" No SQL injection vulnerabilities detected.");
81 } else {
82 // ── 8. Multi-format output ───────────────────────
83 println!("\n{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Plain));
84
85 println!("=== JSON ===");
86 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::JsonPretty));
87
88 println!("=== CSV ===");
89 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Csv));
90
91 println!("=== Markdown ===");
92 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Markdown));
93 }
94
95 // ── 9. Inspect configured options ────────────────────
96 match task.list_options().await {
97 Ok(options) => {
98 println!("\n=== Active Options ===");
99 println!("{}", serde_json::to_string_pretty(&options)?);
100 }
101 Err(err) => eprintln!("Could not fetch options: {err}"),
102 }
103
104 // Task is auto-deleted from daemon on drop.
105 // Engine daemon is auto-killed on drop.
106 println!("\nDone. Task and daemon will be cleaned up automatically.");
107
108 Ok(())
109}Sourcepub async fn with_config(
port: u16,
spawn_local: bool,
binary_path: Option<&str>,
request_timeout: Duration,
poll_interval: Duration,
) -> Result<Self, SqlmapError>
pub async fn with_config( port: u16, spawn_local: bool, binary_path: Option<&str>, request_timeout: Duration, poll_interval: Duration, ) -> Result<Self, SqlmapError>
Launches a daemon with custom HTTP timeout and polling interval.
§Arguments
request_timeout— HTTP request timeout for API calls.poll_interval— Interval between status polls inwait_for_completion.
Sourcepub async fn create_task(
&self,
options: &SqlmapOptions,
) -> Result<SqlmapTask<'_>, SqlmapError>
pub async fn create_task( &self, options: &SqlmapOptions, ) -> Result<SqlmapTask<'_>, SqlmapError>
Creates and configures a new scanning task, returning an RAII wrapper.
The task is automatically deleted from the daemon when dropped.
Examples found in repository?
13async fn main() -> Result<(), Box<dyn std::error::Error>> {
14 // ── 1. Check availability ────────────────────────────
15 if !SqlmapEngine::is_available() {
16 eprintln!("ERROR: sqlmapapi not found in PATH");
17 eprintln!("Quick fix:");
18 eprintln!(" conda env create -f environment.yml");
19 eprintln!(" conda activate sqlmap-env");
20 eprintln!(" # OR: ./setup.sh");
21 std::process::exit(1);
22 }
23
24 // ── 2. Boot the daemon ───────────────────────────────
25 println!("Booting sqlmapapi daemon on port 8775...");
26 let engine = SqlmapEngine::new(8775, true, None).await?;
27 println!("Daemon ready at {}", engine.api_url());
28
29 // ── 3. Configure scan with builder ───────────────────
30 let target = std::env::args()
31 .nth(1)
32 .unwrap_or_else(|| "http://testphp.vulnweb.com/listproducts.php?cat=1".to_string());
33
34 println!("Target: {target}");
35
36 let opts = SqlmapOptions::builder()
37 .url(&target)
38 .level(3)
39 .risk(2)
40 .batch(true)
41 .threads(4)
42 .random_agent(true)
43 .build();
44
45 // ── 4. Create and run task ───────────────────────────
46 let task = engine.create_task(&opts).await?;
47 println!("Task created: {}", task.task_id());
48
49 task.start().await?;
50 println!("Scan started, polling for completion...");
51
52 // ── 5. Monitor execution ─────────────────────────────
53 task.wait_for_completion(300).await?;
54 println!("Scan complete!");
55
56 // ── 6. Fetch and display logs ────────────────────────
57 match task.fetch_log().await {
58 Ok(log_resp) => {
59 if let Some(logs) = &log_resp.log {
60 println!("\n=== Scan Log ({} entries) ===", logs.len());
61 for entry in logs.iter().rev().take(10) {
62 println!(" [{}] {}: {}", entry.time, entry.level, entry.message);
63 }
64 if logs.len() > 10 {
65 println!(" ... and {} more entries", logs.len() - 10);
66 }
67 }
68 }
69 Err(err) => eprintln!("Could not fetch log: {err}"),
70 }
71
72 // ── 7. Fetch results ─────────────────────────────────
73 let data = task.fetch_data().await?;
74 let findings = data.findings();
75
76 println!("\n=== Results ===");
77 println!(" Findings: {}", findings.len());
78
79 if findings.is_empty() {
80 println!(" No SQL injection vulnerabilities detected.");
81 } else {
82 // ── 8. Multi-format output ───────────────────────
83 println!("\n{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Plain));
84
85 println!("=== JSON ===");
86 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::JsonPretty));
87
88 println!("=== CSV ===");
89 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Csv));
90
91 println!("=== Markdown ===");
92 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Markdown));
93 }
94
95 // ── 9. Inspect configured options ────────────────────
96 match task.list_options().await {
97 Ok(options) => {
98 println!("\n=== Active Options ===");
99 println!("{}", serde_json::to_string_pretty(&options)?);
100 }
101 Err(err) => eprintln!("Could not fetch options: {err}"),
102 }
103
104 // Task is auto-deleted from daemon on drop.
105 // Engine daemon is auto-killed on drop.
106 println!("\nDone. Task and daemon will be cleaned up automatically.");
107
108 Ok(())
109}Sourcepub fn is_available() -> bool
pub fn is_available() -> bool
Check if sqlmapapi is available on this system.
Tests that the sqlmapapi binary exists and is executable.
Does NOT fall back to python3 -c "import sqlmap" since that
doesn’t guarantee the REST API server is available.
Examples found in repository?
13async fn main() -> Result<(), Box<dyn std::error::Error>> {
14 // ── 1. Check availability ────────────────────────────
15 if !SqlmapEngine::is_available() {
16 eprintln!("ERROR: sqlmapapi not found in PATH");
17 eprintln!("Quick fix:");
18 eprintln!(" conda env create -f environment.yml");
19 eprintln!(" conda activate sqlmap-env");
20 eprintln!(" # OR: ./setup.sh");
21 std::process::exit(1);
22 }
23
24 // ── 2. Boot the daemon ───────────────────────────────
25 println!("Booting sqlmapapi daemon on port 8775...");
26 let engine = SqlmapEngine::new(8775, true, None).await?;
27 println!("Daemon ready at {}", engine.api_url());
28
29 // ── 3. Configure scan with builder ───────────────────
30 let target = std::env::args()
31 .nth(1)
32 .unwrap_or_else(|| "http://testphp.vulnweb.com/listproducts.php?cat=1".to_string());
33
34 println!("Target: {target}");
35
36 let opts = SqlmapOptions::builder()
37 .url(&target)
38 .level(3)
39 .risk(2)
40 .batch(true)
41 .threads(4)
42 .random_agent(true)
43 .build();
44
45 // ── 4. Create and run task ───────────────────────────
46 let task = engine.create_task(&opts).await?;
47 println!("Task created: {}", task.task_id());
48
49 task.start().await?;
50 println!("Scan started, polling for completion...");
51
52 // ── 5. Monitor execution ─────────────────────────────
53 task.wait_for_completion(300).await?;
54 println!("Scan complete!");
55
56 // ── 6. Fetch and display logs ────────────────────────
57 match task.fetch_log().await {
58 Ok(log_resp) => {
59 if let Some(logs) = &log_resp.log {
60 println!("\n=== Scan Log ({} entries) ===", logs.len());
61 for entry in logs.iter().rev().take(10) {
62 println!(" [{}] {}: {}", entry.time, entry.level, entry.message);
63 }
64 if logs.len() > 10 {
65 println!(" ... and {} more entries", logs.len() - 10);
66 }
67 }
68 }
69 Err(err) => eprintln!("Could not fetch log: {err}"),
70 }
71
72 // ── 7. Fetch results ─────────────────────────────────
73 let data = task.fetch_data().await?;
74 let findings = data.findings();
75
76 println!("\n=== Results ===");
77 println!(" Findings: {}", findings.len());
78
79 if findings.is_empty() {
80 println!(" No SQL injection vulnerabilities detected.");
81 } else {
82 // ── 8. Multi-format output ───────────────────────
83 println!("\n{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Plain));
84
85 println!("=== JSON ===");
86 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::JsonPretty));
87
88 println!("=== CSV ===");
89 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Csv));
90
91 println!("=== Markdown ===");
92 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Markdown));
93 }
94
95 // ── 9. Inspect configured options ────────────────────
96 match task.list_options().await {
97 Ok(options) => {
98 println!("\n=== Active Options ===");
99 println!("{}", serde_json::to_string_pretty(&options)?);
100 }
101 Err(err) => eprintln!("Could not fetch options: {err}"),
102 }
103
104 // Task is auto-deleted from daemon on drop.
105 // Engine daemon is auto-killed on drop.
106 println!("\nDone. Task and daemon will be cleaned up automatically.");
107
108 Ok(())
109}Sourcepub fn is_available_at(binary_path: &str) -> bool
pub fn is_available_at(binary_path: &str) -> bool
Check if sqlmapapi is available, trying the provided binary path first.
Sourcepub fn api_url(&self) -> &str
pub fn api_url(&self) -> &str
Returns the base API URL for this engine.
Examples found in repository?
13async fn main() -> Result<(), Box<dyn std::error::Error>> {
14 // ── 1. Check availability ────────────────────────────
15 if !SqlmapEngine::is_available() {
16 eprintln!("ERROR: sqlmapapi not found in PATH");
17 eprintln!("Quick fix:");
18 eprintln!(" conda env create -f environment.yml");
19 eprintln!(" conda activate sqlmap-env");
20 eprintln!(" # OR: ./setup.sh");
21 std::process::exit(1);
22 }
23
24 // ── 2. Boot the daemon ───────────────────────────────
25 println!("Booting sqlmapapi daemon on port 8775...");
26 let engine = SqlmapEngine::new(8775, true, None).await?;
27 println!("Daemon ready at {}", engine.api_url());
28
29 // ── 3. Configure scan with builder ───────────────────
30 let target = std::env::args()
31 .nth(1)
32 .unwrap_or_else(|| "http://testphp.vulnweb.com/listproducts.php?cat=1".to_string());
33
34 println!("Target: {target}");
35
36 let opts = SqlmapOptions::builder()
37 .url(&target)
38 .level(3)
39 .risk(2)
40 .batch(true)
41 .threads(4)
42 .random_agent(true)
43 .build();
44
45 // ── 4. Create and run task ───────────────────────────
46 let task = engine.create_task(&opts).await?;
47 println!("Task created: {}", task.task_id());
48
49 task.start().await?;
50 println!("Scan started, polling for completion...");
51
52 // ── 5. Monitor execution ─────────────────────────────
53 task.wait_for_completion(300).await?;
54 println!("Scan complete!");
55
56 // ── 6. Fetch and display logs ────────────────────────
57 match task.fetch_log().await {
58 Ok(log_resp) => {
59 if let Some(logs) = &log_resp.log {
60 println!("\n=== Scan Log ({} entries) ===", logs.len());
61 for entry in logs.iter().rev().take(10) {
62 println!(" [{}] {}: {}", entry.time, entry.level, entry.message);
63 }
64 if logs.len() > 10 {
65 println!(" ... and {} more entries", logs.len() - 10);
66 }
67 }
68 }
69 Err(err) => eprintln!("Could not fetch log: {err}"),
70 }
71
72 // ── 7. Fetch results ─────────────────────────────────
73 let data = task.fetch_data().await?;
74 let findings = data.findings();
75
76 println!("\n=== Results ===");
77 println!(" Findings: {}", findings.len());
78
79 if findings.is_empty() {
80 println!(" No SQL injection vulnerabilities detected.");
81 } else {
82 // ── 8. Multi-format output ───────────────────────
83 println!("\n{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Plain));
84
85 println!("=== JSON ===");
86 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::JsonPretty));
87
88 println!("=== CSV ===");
89 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Csv));
90
91 println!("=== Markdown ===");
92 println!("{}", sqlmap_rs::types::format_findings(&findings, OutputFormat::Markdown));
93 }
94
95 // ── 9. Inspect configured options ────────────────────
96 match task.list_options().await {
97 Ok(options) => {
98 println!("\n=== Active Options ===");
99 println!("{}", serde_json::to_string_pretty(&options)?);
100 }
101 Err(err) => eprintln!("Could not fetch options: {err}"),
102 }
103
104 // Task is auto-deleted from daemon on drop.
105 // Engine daemon is auto-killed on drop.
106 println!("\nDone. Task and daemon will be cleaned up automatically.");
107
108 Ok(())
109}