diff --git a/crates/forge_analyzer/src/definitions.rs b/crates/forge_analyzer/src/definitions.rs index e9b7bd2..d55f98f 100644 --- a/crates/forge_analyzer/src/definitions.rs +++ b/crates/forge_analyzer/src/definitions.rs @@ -996,7 +996,7 @@ impl FunctionAnalyzer<'_> { [PropPath::Def(def), ref authn @ .., PropPath::Static(ref last)] if (*last == *"requestJira" || *last == *"requestConfluence" - || *last == *"requestBitbucket") + || *last == *"requestBitbucket") // TODO: so here JSM (and likely JS) is bundled inside Jira && Some(&ImportKind::Default) == self.res.is_imported_from(def, "@forge/api") => { diff --git a/crates/forge_analyzer/src/interp.rs b/crates/forge_analyzer/src/interp.rs index b443a92..f4649a7 100644 --- a/crates/forge_analyzer/src/interp.rs +++ b/crates/forge_analyzer/src/interp.rs @@ -394,7 +394,6 @@ pub struct Interp<'cx, C: Runner<'cx>> { pub jira_service_management_permission_resolver: &'cx PermissionHashMap, pub jira_permission_resolver: &'cx PermissionHashMap, pub confluence_permission_resolver: &'cx PermissionHashMap, - pub jira_service_management_regex_map: &'cx HashMap, pub bitbucket_permission_resolver: &'cx PermissionHashMap, pub jira_software_regex_map: &'cx HashMap, pub jira_service_management_regex_map: &'cx HashMap, @@ -553,7 +552,6 @@ impl<'cx, C: Runner<'cx>> Interp<'cx, C> { jira_service_management_permission_resolver, jira_permission_resolver, confluence_permission_resolver, - jira_service_management_regex_map, bitbucket_permission_resolver, jira_software_regex_map, jira_service_management_regex_map, diff --git a/crates/forge_permission_resolver/src/permissions_resolver.rs b/crates/forge_permission_resolver/src/permissions_resolver.rs index b157635..573b7ab 100644 --- a/crates/forge_permission_resolver/src/permissions_resolver.rs +++ b/crates/forge_permission_resolver/src/permissions_resolver.rs @@ -35,6 +35,10 @@ struct RequestDetails { default )] permission: Vec, + + // For parsing Jira Software as that swagger doesn't follow "x-atlassian-oauth2-scopes" scope style + #[serde(default)] + security: Vec, } #[derive(Default, Debug, Clone, PartialEq, Eq, Deserialize)] @@ -44,6 +48,12 @@ struct PermissionData { scopes: Vec, } +#[derive(Default, Debug, Clone, PartialEq, Eq, Deserialize)] +struct SecurityData { + #[serde(default, rename = "OAuth2")] + oauth2: Vec, +} + #[derive(Clone, Copy, Hash, PartialEq, Eq, Debug)] pub enum RequestType { Get, @@ -204,12 +214,25 @@ fn get_request_type( } fn get_scopes(endpoint_data: &RequestDetails) -> Vec { - endpoint_data + let mut scopes = endpoint_data .permission .iter() .flat_map(|data| &*data.scopes) .cloned() - .collect() + .collect::>(); + + if scopes.is_empty() { + // For Jira Software if the initial scopes are empty, try the scopes from the security field + scopes.extend( + endpoint_data + .security + .iter() + .flat_map(|sec| &sec.oauth2) + .cloned(), + ); + } + + scopes } #[cfg(test)] @@ -369,9 +392,9 @@ mod test { } #[test] - fn test_get_organization() { - let (permission_map, regex_map) = get_permission_resolver_jira_service_management(); - let url = "/rest/servicedeskapi/organization"; + fn test_get_issues_for_epic() { + let (permission_map, regex_map) = get_permission_resolver_jira_software(); + let url = "/rest/agile/1.0/sprint/23"; let request_type = RequestType::Get; let result = check_url_for_permissions(&permission_map, ®ex_map, request_type, url); @@ -380,30 +403,28 @@ mod test { assert!(!result.is_empty(), "Should have parsed permissions"); assert!( - result.contains(&String::from("manage:servicedesk-customer")), - "Should require manage:servicedesk-customer permission" + result.contains(&String::from("read:sprint:jira-software")), + "Should require read:sprint:jira-software permission" ); } - // TODO: this fails right now as the Jira Software swagger does not have the "x-atlassian-oauth2-scopes" in it that we parse for with serde - // #[test] - // fn test_get_issues_for_epic() { - // let (permission_map, regex_map) = get_permission_resolver_jira_software(); - // let url = "/rest/agile/1.0/sprint/23"; - // let request_type = RequestType::Get; - // let result = check_url_for_permissions(&permission_map, ®ex_map, request_type, url); + #[test] + fn test_get_all_boards() { + let (permission_map, regex_map) = get_permission_resolver_jira_software(); + let url = "/rest/agile/1.0/board"; + let request_type = RequestType::Get; + let result = check_url_for_permissions(&permission_map, ®ex_map, request_type, url); - // println!("Permission Map: {:?}", permission_map); // TODO: this does not give back any scopes? - // println!("Regex Map: {:?}", regex_map); + println!("Permission Map: {:?}", permission_map); + println!("Regex Map: {:?}", regex_map); - // assert!(!result.is_empty(), "Should have parsed permissions"); + assert!(!result.is_empty(), "Should have parsed permissions"); - // // let expected_permission: Vec = vec![ - // // String::from("read:epic:jira-software"), - // // String::from("read:issue-details:jira"), - // // String::from("read:jql:jira"), - // // ]; + let expected_permission: Vec = vec![ + String::from("read:board-scope:jira-software"), + String::from("read:project:jira"), + ]; - // // assert_eq!(result, expected_permission); - // } + assert_eq!(result, expected_permission); + } } diff --git a/crates/fsrt/src/main.rs b/crates/fsrt/src/main.rs index 5693115..ffbb8d1 100644 --- a/crates/fsrt/src/main.rs +++ b/crates/fsrt/src/main.rs @@ -7,8 +7,8 @@ mod test; use clap::{Parser, ValueHint}; use forge_permission_resolver::permissions_resolver::{ get_permission_resolver_bitbucket, get_permission_resolver_confluence, - get_permission_resolver_jira, - get_permission_resolver_jira_service_management, get_permission_resolver_jira_software, + get_permission_resolver_jira, get_permission_resolver_jira_service_management, + get_permission_resolver_jira_software, }; use std::{