corgea-cli 1.8.0__tar.gz → 1.8.2__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.
- corgea_cli-1.8.2/.github/workflows/test.yml +26 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/Cargo.lock +1 -1
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/Cargo.toml +1 -1
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/PKG-INFO +1 -1
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/authorize.rs +204 -20
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/main.rs +12 -6
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scan.rs +12 -13
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scanners/fortify.rs +2 -2
- corgea_cli-1.8.0/.github/workflows/homebrew-bump.yml +0 -45
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/.github/workflows/npm-publish.yml +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/.github/workflows/release-binaries.yml +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/.github/workflows/release.yml +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/.github/workflows/update_docs..yml +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/.gitignore +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/LICENSE +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/README.md +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/bin/corgea.js +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/build_release.sh +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/package.json +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/pyproject.toml +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/scripts/npm/bundle-binaries.js +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/cicd.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/config.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/inspect.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/list.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/log.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scanners/blast.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scanners/parsers/checkmarx.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scanners/parsers/coverity.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scanners/parsers/mod.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scanners/parsers/sarif.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/scanners/parsers/semgrep.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/setup_hooks.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/targets.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/utils/api.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/utils/generic.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/utils/terminal.rs +0 -0
- {corgea_cli-1.8.0 → corgea_cli-1.8.2}/src/wait.rs +0 -0
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
name: Test
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches:
|
|
6
|
+
- main
|
|
7
|
+
- master
|
|
8
|
+
pull_request:
|
|
9
|
+
|
|
10
|
+
jobs:
|
|
11
|
+
rust-tests:
|
|
12
|
+
runs-on: ubuntu-latest
|
|
13
|
+
|
|
14
|
+
steps:
|
|
15
|
+
- name: Checkout
|
|
16
|
+
uses: actions/checkout@v4
|
|
17
|
+
|
|
18
|
+
- name: Setup Rust
|
|
19
|
+
uses: dtolnay/rust-toolchain@stable
|
|
20
|
+
|
|
21
|
+
- name: Cache cargo
|
|
22
|
+
uses: Swatinem/rust-cache@v2
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
- name: Run unit tests
|
|
26
|
+
run: cargo test
|
|
@@ -137,32 +137,36 @@ async fn start_callback_server(
|
|
|
137
137
|
};
|
|
138
138
|
|
|
139
139
|
loop {
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
140
|
+
tokio::select! {
|
|
141
|
+
accept_result = listener.accept() => {
|
|
142
|
+
let (stream, _) = accept_result?;
|
|
143
|
+
let io = TokioIo::new(stream);
|
|
144
|
+
let auth_code_clone = auth_code.clone();
|
|
145
|
+
|
|
146
|
+
let service = service_fn(move |req| {
|
|
147
|
+
handle_callback(req, auth_code_clone.clone())
|
|
148
|
+
});
|
|
149
|
+
|
|
150
|
+
tokio::task::spawn(async move {
|
|
151
|
+
if let Err(err) = hyper::server::conn::http1::Builder::new()
|
|
152
|
+
.serve_connection(io, service)
|
|
153
|
+
.await
|
|
154
|
+
{
|
|
155
|
+
eprintln!("Error serving connection: {:?}", err);
|
|
156
|
+
}
|
|
157
|
+
});
|
|
154
158
|
}
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
159
|
+
_ = tokio::time::sleep(Duration::from_millis(100)) => {}
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
// Check if we got the code.
|
|
163
|
+
// We must do this outside of `accept()` blocking so we don't miss a code
|
|
164
|
+
// that was set by the request task after a single callback request.
|
|
158
165
|
if let Ok(code_guard) = auth_code.lock() {
|
|
159
166
|
if let Some(code) = code_guard.as_ref() {
|
|
160
167
|
return Ok(code.clone());
|
|
161
168
|
}
|
|
162
169
|
}
|
|
163
|
-
|
|
164
|
-
// Add a small delay to prevent busy waiting
|
|
165
|
-
tokio::time::sleep(Duration::from_millis(100)).await;
|
|
166
170
|
}
|
|
167
171
|
}
|
|
168
172
|
|
|
@@ -523,3 +527,183 @@ fn parse_query_params(query: &str) -> HashMap<String, String> {
|
|
|
523
527
|
}
|
|
524
528
|
|
|
525
529
|
|
|
530
|
+
|
|
531
|
+
#[cfg(test)]
|
|
532
|
+
mod tests {
|
|
533
|
+
use super::*;
|
|
534
|
+
use std::io::{Read, Write};
|
|
535
|
+
use std::net::{TcpListener as StdTcpListener, TcpStream};
|
|
536
|
+
use std::sync::mpsc;
|
|
537
|
+
use std::thread;
|
|
538
|
+
use std::time::Duration as StdDuration;
|
|
539
|
+
use tokio::runtime::Runtime;
|
|
540
|
+
use tokio::time::{timeout, Duration};
|
|
541
|
+
|
|
542
|
+
fn reserve_ephemeral_port() -> u16 {
|
|
543
|
+
let listener = StdTcpListener::bind("127.0.0.1:0").expect("failed to bind ephemeral port");
|
|
544
|
+
listener.local_addr().expect("failed to get local addr").port()
|
|
545
|
+
}
|
|
546
|
+
|
|
547
|
+
fn spawn_callback_server(
|
|
548
|
+
port: u16,
|
|
549
|
+
auth_code: Arc<Mutex<Option<String>>>,
|
|
550
|
+
) -> mpsc::Receiver<Result<String, String>> {
|
|
551
|
+
let (tx, rx) = mpsc::channel();
|
|
552
|
+
thread::spawn(move || {
|
|
553
|
+
let runtime = Runtime::new().expect("failed to create tokio runtime");
|
|
554
|
+
let result = runtime
|
|
555
|
+
.block_on(start_callback_server(port, auth_code))
|
|
556
|
+
.map_err(|e| e.to_string());
|
|
557
|
+
tx.send(result).expect("failed to send callback result");
|
|
558
|
+
});
|
|
559
|
+
|
|
560
|
+
rx
|
|
561
|
+
}
|
|
562
|
+
|
|
563
|
+
fn send_http_get(port: u16, path: &str) -> (u16, String) {
|
|
564
|
+
let mut stream = None;
|
|
565
|
+
|
|
566
|
+
for _ in 0..50 {
|
|
567
|
+
match TcpStream::connect(("127.0.0.1", port)) {
|
|
568
|
+
Ok(s) => {
|
|
569
|
+
stream = Some(s);
|
|
570
|
+
break;
|
|
571
|
+
}
|
|
572
|
+
Err(_) => thread::sleep(StdDuration::from_millis(20)),
|
|
573
|
+
}
|
|
574
|
+
}
|
|
575
|
+
|
|
576
|
+
let mut stream = stream.expect("failed to connect to callback server");
|
|
577
|
+
let request = format!("GET {} HTTP/1.0\r\n\r\n", path);
|
|
578
|
+
|
|
579
|
+
stream
|
|
580
|
+
.write_all(request.as_bytes())
|
|
581
|
+
.expect("failed to write request");
|
|
582
|
+
|
|
583
|
+
let mut raw_response = String::new();
|
|
584
|
+
stream
|
|
585
|
+
.read_to_string(&mut raw_response)
|
|
586
|
+
.expect("failed to read response");
|
|
587
|
+
|
|
588
|
+
let mut sections = raw_response.splitn(2, "\r\n\r\n");
|
|
589
|
+
let headers = sections.next().expect("response headers missing");
|
|
590
|
+
let body = sections.next().unwrap_or_default().to_string();
|
|
591
|
+
let status_line = headers.lines().next().expect("status line missing");
|
|
592
|
+
let status = status_line
|
|
593
|
+
.split_whitespace()
|
|
594
|
+
.nth(1)
|
|
595
|
+
.expect("status code missing")
|
|
596
|
+
.parse::<u16>()
|
|
597
|
+
.expect("invalid status code");
|
|
598
|
+
|
|
599
|
+
(status, body)
|
|
600
|
+
}
|
|
601
|
+
|
|
602
|
+
#[test]
|
|
603
|
+
fn parse_query_params_decodes_values() {
|
|
604
|
+
let params = parse_query_params("code=a%20b&error_description=needs%2Blogin");
|
|
605
|
+
|
|
606
|
+
assert_eq!(params.get("code"), Some(&"a b".to_string()));
|
|
607
|
+
assert_eq!(params.get("error_description"), Some(&"needs+login".to_string()));
|
|
608
|
+
}
|
|
609
|
+
|
|
610
|
+
#[test]
|
|
611
|
+
fn parse_query_params_ignores_malformed_pairs() {
|
|
612
|
+
let params = parse_query_params("valid=ok&invalid&also_invalid=");
|
|
613
|
+
|
|
614
|
+
assert_eq!(params.get("valid"), Some(&"ok".to_string()));
|
|
615
|
+
assert_eq!(params.get("invalid"), None);
|
|
616
|
+
assert_eq!(params.get("also_invalid"), Some(&"".to_string()));
|
|
617
|
+
}
|
|
618
|
+
|
|
619
|
+
#[test]
|
|
620
|
+
fn port_is_available_reflects_current_port_usage() {
|
|
621
|
+
let listener = StdTcpListener::bind("127.0.0.1:0").expect("failed to bind ephemeral port");
|
|
622
|
+
let port = listener
|
|
623
|
+
.local_addr()
|
|
624
|
+
.expect("failed to get listener addr")
|
|
625
|
+
.port();
|
|
626
|
+
|
|
627
|
+
assert!(!port_is_available(port));
|
|
628
|
+
drop(listener);
|
|
629
|
+
assert!(port_is_available(port));
|
|
630
|
+
}
|
|
631
|
+
|
|
632
|
+
#[test]
|
|
633
|
+
fn find_available_port_skips_ports_that_are_in_use() {
|
|
634
|
+
let listener = StdTcpListener::bind("127.0.0.1:0").expect("failed to bind ephemeral port");
|
|
635
|
+
let occupied_port = listener
|
|
636
|
+
.local_addr()
|
|
637
|
+
.expect("failed to get listener addr")
|
|
638
|
+
.port();
|
|
639
|
+
|
|
640
|
+
let found_port = find_available_port(occupied_port).expect("should find an available port");
|
|
641
|
+
|
|
642
|
+
assert_ne!(found_port, occupied_port);
|
|
643
|
+
}
|
|
644
|
+
|
|
645
|
+
#[tokio::test]
|
|
646
|
+
async fn start_callback_server_returns_without_waiting_for_second_connection() {
|
|
647
|
+
let port = reserve_ephemeral_port();
|
|
648
|
+
let auth_code = Arc::new(Mutex::new(Some("test-code".to_string())));
|
|
649
|
+
|
|
650
|
+
let returned_code = timeout(
|
|
651
|
+
Duration::from_millis(300),
|
|
652
|
+
start_callback_server(port, auth_code),
|
|
653
|
+
)
|
|
654
|
+
.await
|
|
655
|
+
.expect("callback server timed out")
|
|
656
|
+
.expect("callback server should return code");
|
|
657
|
+
|
|
658
|
+
assert_eq!(returned_code, "test-code");
|
|
659
|
+
}
|
|
660
|
+
|
|
661
|
+
#[test]
|
|
662
|
+
fn start_callback_server_returns_bind_error_if_port_is_occupied() {
|
|
663
|
+
let listener = StdTcpListener::bind("127.0.0.1:0").expect("failed to bind ephemeral port");
|
|
664
|
+
let occupied_port = listener
|
|
665
|
+
.local_addr()
|
|
666
|
+
.expect("failed to get listener addr")
|
|
667
|
+
.port();
|
|
668
|
+
|
|
669
|
+
let runtime = Runtime::new().expect("failed to create runtime");
|
|
670
|
+
let result = runtime.block_on(start_callback_server(
|
|
671
|
+
occupied_port,
|
|
672
|
+
Arc::new(Mutex::new(None::<String>)),
|
|
673
|
+
));
|
|
674
|
+
|
|
675
|
+
assert!(result.is_err());
|
|
676
|
+
let error = result.err().expect("expected bind error").to_string();
|
|
677
|
+
assert!(error.contains("Failed to bind"));
|
|
678
|
+
}
|
|
679
|
+
|
|
680
|
+
#[test]
|
|
681
|
+
fn callback_server_serves_waiting_error_and_success_pages_then_returns_code() {
|
|
682
|
+
let port = reserve_ephemeral_port();
|
|
683
|
+
let auth_code = Arc::new(Mutex::new(None::<String>));
|
|
684
|
+
let result_rx = spawn_callback_server(port, auth_code);
|
|
685
|
+
|
|
686
|
+
let (waiting_status, waiting_body) = send_http_get(port, "/");
|
|
687
|
+
assert_eq!(waiting_status, 200);
|
|
688
|
+
assert!(waiting_body.contains("Waiting for Authorization"));
|
|
689
|
+
|
|
690
|
+
let (error_status, error_body) = send_http_get(
|
|
691
|
+
port,
|
|
692
|
+
"/?error=access_denied&error_description=user%20cancelled",
|
|
693
|
+
);
|
|
694
|
+
assert_eq!(error_status, 400);
|
|
695
|
+
assert!(error_body.contains("Authorization Failed"));
|
|
696
|
+
assert!(error_body.contains("access_denied"));
|
|
697
|
+
|
|
698
|
+
let (success_status, success_body) = send_http_get(port, "/?code=abc123");
|
|
699
|
+
assert_eq!(success_status, 200);
|
|
700
|
+
assert!(success_body.contains("Successfully Signed In"));
|
|
701
|
+
|
|
702
|
+
let returned_code = result_rx
|
|
703
|
+
.recv_timeout(StdDuration::from_secs(2))
|
|
704
|
+
.expect("callback server should return in time")
|
|
705
|
+
.expect("callback server should return code");
|
|
706
|
+
|
|
707
|
+
assert_eq!(returned_code, "abc123");
|
|
708
|
+
}
|
|
709
|
+
}
|
|
@@ -52,6 +52,12 @@ enum Commands {
|
|
|
52
52
|
Upload {
|
|
53
53
|
/// Option path to JSON report to upload
|
|
54
54
|
report: Option<String>,
|
|
55
|
+
|
|
56
|
+
#[arg(
|
|
57
|
+
long,
|
|
58
|
+
help = "The name of the Corgea project. Defaults to git repository name if found, otherwise to the current directory name."
|
|
59
|
+
)]
|
|
60
|
+
project_name: Option<String>,
|
|
55
61
|
},
|
|
56
62
|
/// Scan the current directory. Supports blast, semgrep and snyk.
|
|
57
63
|
Scan {
|
|
@@ -236,18 +242,18 @@ fn main() {
|
|
|
236
242
|
}
|
|
237
243
|
}
|
|
238
244
|
}
|
|
239
|
-
Some(Commands::Upload { report }) => {
|
|
245
|
+
Some(Commands::Upload { report, project_name }) => {
|
|
240
246
|
verify_token_and_exit_when_fail(&corgea_config);
|
|
241
247
|
match report {
|
|
242
248
|
Some(report) => {
|
|
243
249
|
if report.ends_with(".fpr") {
|
|
244
|
-
fortify_parse(&corgea_config, report);
|
|
250
|
+
fortify_parse(&corgea_config, report, project_name.clone());
|
|
245
251
|
} else {
|
|
246
|
-
scan::read_file_report(&corgea_config, report);
|
|
252
|
+
scan::read_file_report(&corgea_config, report, project_name.clone());
|
|
247
253
|
}
|
|
248
254
|
}
|
|
249
255
|
None => {
|
|
250
|
-
scan::read_stdin_report(&corgea_config);
|
|
256
|
+
scan::read_stdin_report(&corgea_config, project_name.clone());
|
|
251
257
|
}
|
|
252
258
|
}
|
|
253
259
|
}
|
|
@@ -332,8 +338,8 @@ fn main() {
|
|
|
332
338
|
}
|
|
333
339
|
}
|
|
334
340
|
match scanner {
|
|
335
|
-
Scanner::Snyk => scan::run_snyk(&corgea_config),
|
|
336
|
-
Scanner::Semgrep => scan::run_semgrep(&corgea_config),
|
|
341
|
+
Scanner::Snyk => scan::run_snyk(&corgea_config, project_name.clone()),
|
|
342
|
+
Scanner::Semgrep => scan::run_semgrep(&corgea_config, project_name.clone()),
|
|
337
343
|
Scanner::Blast => scanners::blast::run(&corgea_config, fail_on.clone(), fail, only_uncommitted, scan_type.clone(), policy.clone(), out_format.clone(), out_file.clone(), target.clone(), project_name.clone())
|
|
338
344
|
}
|
|
339
345
|
}
|
|
@@ -51,7 +51,7 @@ pub struct ScanUploadResult {
|
|
|
51
51
|
pub project_id: Option<String>,
|
|
52
52
|
}
|
|
53
53
|
|
|
54
|
-
pub fn run_semgrep(config: &Config) {
|
|
54
|
+
pub fn run_semgrep(config: &Config, project_name: Option<String>) {
|
|
55
55
|
println!("Scanning with semgrep...");
|
|
56
56
|
let base_command = "semgrep";
|
|
57
57
|
let mut command = std::process::Command::new(base_command);
|
|
@@ -61,12 +61,12 @@ pub fn run_semgrep(config: &Config) {
|
|
|
61
61
|
|
|
62
62
|
let output = run_command(&base_command.to_string(), command);
|
|
63
63
|
|
|
64
|
-
if let Some(result) = parse_scan(config, output, true) {
|
|
64
|
+
if let Some(result) = parse_scan(config, output, true, project_name) {
|
|
65
65
|
crate::wait::run(config, Some(result.scan_id), result.project_id);
|
|
66
66
|
}
|
|
67
67
|
}
|
|
68
68
|
|
|
69
|
-
pub fn run_snyk(config: &Config) {
|
|
69
|
+
pub fn run_snyk(config: &Config, project_name: Option<String>) {
|
|
70
70
|
println!("Scanning with snyk...");
|
|
71
71
|
let base_command = "snyk";
|
|
72
72
|
let mut command = std::process::Command::new(base_command);
|
|
@@ -76,19 +76,19 @@ pub fn run_snyk(config: &Config) {
|
|
|
76
76
|
|
|
77
77
|
let output = run_command(&base_command.to_string(), command);
|
|
78
78
|
|
|
79
|
-
if let Some(result) = parse_scan(config, output, true) {
|
|
79
|
+
if let Some(result) = parse_scan(config, output, true, project_name) {
|
|
80
80
|
crate::wait::run(config, Some(result.scan_id), result.project_id);
|
|
81
81
|
}
|
|
82
82
|
}
|
|
83
83
|
|
|
84
|
-
pub fn read_stdin_report(config: &Config) {
|
|
84
|
+
pub fn read_stdin_report(config: &Config, project_name: Option<String>) {
|
|
85
85
|
let mut input = String::new();
|
|
86
86
|
let _ = io::stdin().read_to_string(&mut input);
|
|
87
87
|
|
|
88
|
-
let _ = parse_scan(config, input, false);
|
|
88
|
+
let _ = parse_scan(config, input, false, project_name);
|
|
89
89
|
}
|
|
90
90
|
|
|
91
|
-
pub fn read_file_report(config: &Config, file_path: &str) {
|
|
91
|
+
pub fn read_file_report(config: &Config, file_path: &str, project_name: Option<String>) {
|
|
92
92
|
let input = match std::fs::read_to_string(file_path) {
|
|
93
93
|
Ok(input) => input,
|
|
94
94
|
Err(e) => {
|
|
@@ -97,10 +97,10 @@ pub fn read_file_report(config: &Config, file_path: &str) {
|
|
|
97
97
|
}
|
|
98
98
|
};
|
|
99
99
|
|
|
100
|
-
let _ = parse_scan(config, input, false);
|
|
100
|
+
let _ = parse_scan(config, input, false, project_name);
|
|
101
101
|
}
|
|
102
102
|
|
|
103
|
-
pub fn parse_scan(config: &Config, input: String, save_to_file: bool) -> Option<ScanUploadResult> {
|
|
103
|
+
pub fn parse_scan(config: &Config, input: String, save_to_file: bool, project_name: Option<String>) -> Option<ScanUploadResult> {
|
|
104
104
|
debug("Parsing the scan report");
|
|
105
105
|
|
|
106
106
|
// Remove BOM (Byte Order Mark) if present
|
|
@@ -115,7 +115,7 @@ pub fn parse_scan(config: &Config, input: String, save_to_file: bool) -> Option<
|
|
|
115
115
|
std::process::exit(0);
|
|
116
116
|
}
|
|
117
117
|
|
|
118
|
-
return upload_scan(config, parse_result.paths, parse_result.scanner, cleaned_input.to_string(), save_to_file);
|
|
118
|
+
return upload_scan(config, parse_result.paths, parse_result.scanner, cleaned_input.to_string(), save_to_file, project_name);
|
|
119
119
|
}
|
|
120
120
|
|
|
121
121
|
Err(error_message) => {
|
|
@@ -125,7 +125,7 @@ pub fn parse_scan(config: &Config, input: String, save_to_file: bool) -> Option<
|
|
|
125
125
|
}
|
|
126
126
|
}
|
|
127
127
|
|
|
128
|
-
pub fn upload_scan(config: &Config, paths: Vec<String>, scanner: String, input: String, save_to_file: bool) -> Option<ScanUploadResult> {
|
|
128
|
+
pub fn upload_scan(config: &Config, paths: Vec<String>, scanner: String, input: String, save_to_file: bool, project_name: Option<String>) -> Option<ScanUploadResult> {
|
|
129
129
|
let in_ci = running_in_ci();
|
|
130
130
|
let ci_platform = which_ci();
|
|
131
131
|
let github_env_vars = get_github_env_vars();
|
|
@@ -133,7 +133,6 @@ pub fn upload_scan(config: &Config, paths: Vec<String>, scanner: String, input:
|
|
|
133
133
|
let run_id = Uuid::new_v4().to_string();
|
|
134
134
|
let token = config.get_token();
|
|
135
135
|
let base_url = config.get_url();
|
|
136
|
-
let current_dir = std::env::current_dir().expect("Failed to get current directory");
|
|
137
136
|
let project;
|
|
138
137
|
|
|
139
138
|
if in_ci {
|
|
@@ -142,7 +141,7 @@ pub fn upload_scan(config: &Config, paths: Vec<String>, scanner: String, input:
|
|
|
142
141
|
github_env_vars.get("GITHUB_REPOSITORY").expect("Failed to get GITHUB_REPOSITORY").to_string(),
|
|
143
142
|
github_env_vars.get("GITHUB_PR").expect("Failed to get GITHUB_REPOSITORY").to_string())
|
|
144
143
|
} else {
|
|
145
|
-
project =
|
|
144
|
+
project = utils::generic::determine_project_name(project_name.as_deref());
|
|
146
145
|
}
|
|
147
146
|
let repo_data = std::env::var("REPO_DATA").unwrap_or_else(|_| "".to_string()); //encoded data to forward.
|
|
148
147
|
|
|
@@ -9,7 +9,7 @@ use quick_xml::reader::Reader;
|
|
|
9
9
|
use crate::Config;
|
|
10
10
|
use crate::scan::upload_scan;
|
|
11
11
|
|
|
12
|
-
pub fn parse(config: &Config, file_path: &str) {
|
|
12
|
+
pub fn parse(config: &Config, file_path: &str, project_name: Option<String>) {
|
|
13
13
|
let temp_dir = match TempDir::new() {
|
|
14
14
|
Ok(dir) => dir,
|
|
15
15
|
Err(e) => {
|
|
@@ -48,7 +48,7 @@ pub fn parse(config: &Config, file_path: &str) {
|
|
|
48
48
|
}
|
|
49
49
|
|
|
50
50
|
let (scan_data, paths) = extract_file_path(outpath);
|
|
51
|
-
let _scan_id = upload_scan(config, paths, "fortify".to_string(), scan_data, false);
|
|
51
|
+
let _scan_id = upload_scan(config, paths, "fortify".to_string(), scan_data, false, project_name);
|
|
52
52
|
} else {
|
|
53
53
|
println!("File 'audit.fvdl' not found in the archive");
|
|
54
54
|
};
|
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
name: Update Homebrew Formula
|
|
2
|
-
|
|
3
|
-
on:
|
|
4
|
-
release:
|
|
5
|
-
types: [published]
|
|
6
|
-
|
|
7
|
-
jobs:
|
|
8
|
-
update-formula:
|
|
9
|
-
runs-on: ubuntu-latest
|
|
10
|
-
steps:
|
|
11
|
-
- name: Checkout Repository
|
|
12
|
-
uses: actions/checkout@v4
|
|
13
|
-
|
|
14
|
-
- name: Get Latest PyPI Version
|
|
15
|
-
id: get_version
|
|
16
|
-
run: |
|
|
17
|
-
VERSION=$(curl -s https://pypi.org/pypi/corgea-cli/json | jq -r .info.version)
|
|
18
|
-
echo "Latest version: $VERSION"
|
|
19
|
-
echo "version=$VERSION" >> $GITHUB_ENV
|
|
20
|
-
|
|
21
|
-
- name: Get Latest Source Tarball URL
|
|
22
|
-
id: get_tarball
|
|
23
|
-
run: |
|
|
24
|
-
URL=$(curl -s https://pypi.org/pypi/corgea-cli/json | jq -r '.urls[] | select(.packagetype=="sdist") | .url')
|
|
25
|
-
echo "Tarball URL: $URL"
|
|
26
|
-
echo "tarball_url=$URL" >> $GITHUB_ENV
|
|
27
|
-
|
|
28
|
-
- name: Get SHA256 Hash
|
|
29
|
-
id: get_sha
|
|
30
|
-
run: |
|
|
31
|
-
curl -o corgea-cli.tar.gz ${{ env.tarball_url }}
|
|
32
|
-
SHA256=$(shasum -a 256 corgea-cli.tar.gz | awk '{print $1}')
|
|
33
|
-
echo "SHA256: $SHA256"
|
|
34
|
-
echo "sha256=$SHA256" >> $GITHUB_ENV
|
|
35
|
-
|
|
36
|
-
- name: Update Homebrew Formula
|
|
37
|
-
run: |
|
|
38
|
-
brew bump-formula-pr --strict corgea-cli \
|
|
39
|
-
--url=${{ env.tarball_url }} \
|
|
40
|
-
--sha256=${{ env.sha256 }} \
|
|
41
|
-
--no-browse \
|
|
42
|
-
--no-fork \
|
|
43
|
-
--force
|
|
44
|
-
env:
|
|
45
|
-
HOMEBREW_GITHUB_API_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
|
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
|
|
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
|