scanoss 1.39.0__py3-none-any.whl → 1.40.1__py3-none-any.whl

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.
@@ -24,11 +24,11 @@ SPDX-License-Identifier: MIT
24
24
 
25
25
  import json
26
26
  from dataclasses import dataclass
27
- from typing import Any, Dict, List
27
+ from typing import List
28
28
 
29
- from ..policy_check import PolicyStatus
30
- from ..utils.markdown_utils import generate_jira_table, generate_table
31
- from .raw_base import RawBase
29
+ from ...policy_check.policy_check import PolicyCheck, PolicyOutput, PolicyStatus
30
+ from ...utils.markdown_utils import generate_jira_table, generate_table
31
+ from ...utils.scan_result_processor import ScanResultProcessor
32
32
 
33
33
 
34
34
  @dataclass
@@ -44,7 +44,7 @@ class Component:
44
44
  licenses: List[License]
45
45
  status: str
46
46
 
47
- class UndeclaredComponent(RawBase[Component]):
47
+ class UndeclaredComponent(PolicyCheck[Component]):
48
48
  """
49
49
  SCANOSS UndeclaredComponent class
50
50
  Inspects for undeclared components
@@ -59,7 +59,7 @@ class UndeclaredComponent(RawBase[Component]):
59
59
  format_type: str = 'json',
60
60
  status: str = None,
61
61
  output: str = None,
62
- sbom_format: str = 'settings',
62
+ sbom_format: str = 'settings'
63
63
  ):
64
64
  """
65
65
  Initialize the UndeclaredComponent class.
@@ -74,13 +74,14 @@ class UndeclaredComponent(RawBase[Component]):
74
74
  :param sbom_format: Sbom format for status output (default 'settings')
75
75
  """
76
76
  super().__init__(
77
- debug, trace, quiet,format_type, filepath, output, status, name='Undeclared Components Policy'
77
+ debug, trace, quiet, format_type, status, name='Undeclared Components Policy', output=output
78
78
  )
79
79
  self.filepath = filepath
80
- self.format = format
81
80
  self.output = output
82
81
  self.status = status
83
82
  self.sbom_format = sbom_format
83
+ self.results_processor = ScanResultProcessor(self.debug, self.trace, self.quiet, self.filepath)
84
+
84
85
 
85
86
  def _get_undeclared_components(self, components: list[Component]) -> list or None:
86
87
  """
@@ -163,7 +164,7 @@ class UndeclaredComponent(RawBase[Component]):
163
164
 
164
165
  return summary
165
166
 
166
- def _json(self, components: list[Component]) -> Dict[str, Any]:
167
+ def _json(self, components: list[Component]) -> PolicyOutput:
167
168
  """
168
169
  Format the undeclared components as JSON.
169
170
 
@@ -171,16 +172,16 @@ class UndeclaredComponent(RawBase[Component]):
171
172
  :return: Dictionary with formatted JSON details and summary
172
173
  """
173
174
  # Use component grouped by licenses to generate the summary
174
- component_licenses = self._group_components_by_license(components)
175
+ component_licenses = self.results_processor.group_components_by_license(components)
175
176
  details = {}
176
177
  if len(components) > 0:
177
178
  details = {'components': components}
178
- return {
179
- 'details': f'{json.dumps(details, indent=2)}\n',
180
- 'summary': self._get_summary(component_licenses),
181
- }
179
+ return PolicyOutput(
180
+ details=f'{json.dumps(details, indent=2)}\n',
181
+ summary=self._get_summary(component_licenses)
182
+ )
182
183
 
183
- def _markdown(self, components: list[Component]) -> Dict[str, Any]:
184
+ def _markdown(self, components: list[Component]) -> PolicyOutput:
184
185
  """
185
186
  Format the undeclared components as Markdown.
186
187
 
@@ -190,15 +191,15 @@ class UndeclaredComponent(RawBase[Component]):
190
191
  headers = ['Component', 'License']
191
192
  rows = []
192
193
  # TODO look at using SpdxLite license name lookup method
193
- component_licenses = self._group_components_by_license(components)
194
+ component_licenses = self.results_processor.group_components_by_license(components)
194
195
  for component in component_licenses:
195
196
  rows.append([component.get('purl'), component.get('spdxid')])
196
- return {
197
- 'details': f'### Undeclared components\n{generate_table(headers, rows)}\n',
198
- 'summary': self._get_summary(component_licenses),
199
- }
197
+ return PolicyOutput(
198
+ details= f'### Undeclared components\n{generate_table(headers, rows)}\n',
199
+ summary= self._get_summary(component_licenses),
200
+ )
200
201
 
201
- def _jira_markdown(self, components: list) -> Dict[str, Any]:
202
+ def _jira_markdown(self, components: list) -> PolicyOutput:
202
203
  """
203
204
  Format the undeclared components as Markdown.
204
205
 
@@ -208,13 +209,13 @@ class UndeclaredComponent(RawBase[Component]):
208
209
  headers = ['Component', 'License']
209
210
  rows = []
210
211
  # TODO look at using SpdxLite license name lookup method
211
- component_licenses = self._group_components_by_license(components)
212
+ component_licenses = self.results_processor.group_components_by_license(components)
212
213
  for component in component_licenses:
213
214
  rows.append([component.get('purl'), component.get('spdxid')])
214
- return {
215
- 'details': f'{generate_jira_table(headers, rows)}',
216
- 'summary': self._get_jira_summary(component_licenses),
217
- }
215
+ return PolicyOutput(
216
+ details= f'{generate_jira_table(headers, rows)}',
217
+ summary= self._get_jira_summary(component_licenses),
218
+ )
218
219
 
219
220
  def _get_unique_components(self, components: list) -> list:
220
221
  """
@@ -272,13 +273,13 @@ class UndeclaredComponent(RawBase[Component]):
272
273
 
273
274
  :return: A list of processed components with their licenses, or `None` if `self.results` is not set.
274
275
  """
275
- if self.results is None:
276
+ if self.results_processor.get_results() is None:
276
277
  return None
277
278
  components: dict = {}
278
279
  # Extract file and snippet components
279
- components = self._get_components_data(self.results, components)
280
+ components = self.results_processor.get_components_data(components)
280
281
  # Convert to list and process licenses
281
- return self._convert_components_to_list(components)
282
+ return self.results_processor.convert_components_to_list(components)
282
283
 
283
284
  def run(self):
284
285
  """
File without changes
@@ -24,11 +24,36 @@ SPDX-License-Identifier: MIT
24
24
  import json
25
25
  from typing import Any
26
26
 
27
- from ..policy_check import T
28
- from .raw_base import RawBase
27
+ from ...scanossbase import ScanossBase
28
+ from ..policy_check.policy_check import T
29
+ from ..utils.scan_result_processor import ScanResultProcessor
30
+
31
+
32
+ class ComponentSummary(ScanossBase):
33
+
34
+ def __init__( # noqa: PLR0913
35
+ self,
36
+ debug: bool = False,
37
+ trace: bool = False,
38
+ quiet: bool = False,
39
+ filepath: str = None,
40
+ format_type: str = 'json',
41
+ output: str = None,
42
+ ):
43
+ """
44
+ Initialize the ComponentSummary class.
29
45
 
46
+ :param debug: Enable debug mode
47
+ :param trace: Enable trace mode
48
+ :param quiet: Enable quiet mode
49
+ :param filepath: Path to the file containing component data
50
+ :param format_type: Output format ('json' or 'md')
51
+ """
52
+ super().__init__(debug, trace, quiet)
53
+ self.filepath = filepath
54
+ self.output = output
55
+ self.results_processor = ScanResultProcessor(debug, trace, quiet, filepath)
30
56
 
31
- class ComponentSummary(RawBase):
32
57
 
33
58
  def _json(self, data: dict[str,Any]) -> dict[str,Any]:
34
59
  """
@@ -77,11 +102,11 @@ class ComponentSummary(RawBase):
77
102
  """
78
103
  Get a component summary from detected components.
79
104
 
80
- :param components: List of all components
105
+ :param scan_components: List of all components
81
106
  :return: Dict with license summary information
82
107
  """
83
108
  # A component is considered unique by its combination of PURL (Package URL) and license
84
- component_licenses = self._group_components_by_license(scan_components)
109
+ component_licenses = self.results_processor.group_components_by_license(scan_components)
85
110
  total_components = len(component_licenses)
86
111
  # Get undeclared components
87
112
  undeclared_components = len([c for c in component_licenses if c['status'] == 'pending'])
@@ -121,13 +146,13 @@ class ComponentSummary(RawBase):
121
146
 
122
147
  :return: A list of processed components with license data, or `None` if `self.results` is not set.
123
148
  """
124
- if self.results is None:
125
- raise ValueError(f'Error: No results found in ${self.filepath}')
149
+ if self.results_processor.get_results() is None:
150
+ raise ValueError(f'Error: No results found in {self.filepath}')
126
151
 
127
152
  components: dict = {}
128
153
  # Extract component and license data from file and dependency results. Both helpers mutate `components`
129
- self._get_components_data(self.results, components)
130
- return self._convert_components_to_list(components)
154
+ self.results_processor.get_components_data(components)
155
+ return self.results_processor.convert_components_to_list(components)
131
156
 
132
157
  def _format(self, component_summary) -> str:
133
158
  # TODO: Implement formatter to support dynamic outputs
@@ -25,11 +25,12 @@ SPDX-License-Identifier: MIT
25
25
  import json
26
26
  from typing import Any
27
27
 
28
- from ..policy_check import T
29
- from .raw_base import RawBase
28
+ from ...scanossbase import ScanossBase
29
+ from ..policy_check.policy_check import T
30
+ from ..utils.scan_result_processor import ScanResultProcessor
30
31
 
31
32
 
32
- class LicenseSummary(RawBase):
33
+ class LicenseSummary(ScanossBase):
33
34
  """
34
35
  SCANOSS LicenseSummary class
35
36
  Inspects results and generates comprehensive license summaries from detected components.
@@ -38,6 +39,42 @@ class LicenseSummary(RawBase):
38
39
  information, providing detailed summaries including copyleft analysis and license statistics.
39
40
  """
40
41
 
42
+ # Define required license fields as class constants
43
+ REQUIRED_LICENSE_FIELDS = ['spdxid', 'url', 'copyleft', 'source']
44
+
45
+ def __init__( # noqa: PLR0913
46
+ self,
47
+ debug: bool = False,
48
+ trace: bool = False,
49
+ quiet: bool = False,
50
+ filepath: str = None,
51
+ status: str = None,
52
+ output: str = None,
53
+ include: str = None,
54
+ exclude: str = None,
55
+ explicit: str = None,
56
+ ):
57
+ """
58
+ Initialize the LicenseSummary class.
59
+
60
+ :param debug: Enable debug mode
61
+ :param trace: Enable trace mode
62
+ :param quiet: Enable quiet mode
63
+ :param filepath: Path to the file containing component data
64
+ :param output: Path to save detailed output
65
+ :param include: Licenses to include in the analysis
66
+ :param exclude: Licenses to exclude from the analysis
67
+ :param explicit: Explicitly defined licenses
68
+ """
69
+ super().__init__(debug=debug, trace=trace, quiet=quiet)
70
+ self.results_processor = ScanResultProcessor(debug, trace, quiet, filepath, include, exclude, explicit)
71
+ self.filepath = filepath
72
+ self.output = output
73
+ self.status = status
74
+ self.include = include
75
+ self.exclude = exclude
76
+ self.explicit = explicit
77
+
41
78
  def _json(self, data: dict[str,Any]) -> dict[str, Any]:
42
79
  """
43
80
  Format license summary data as JSON.
@@ -78,41 +115,6 @@ class LicenseSummary(RawBase):
78
115
  """
79
116
  pass
80
117
 
81
- # Define required license fields as class constants
82
- REQUIRED_LICENSE_FIELDS = ['spdxid', 'url', 'copyleft', 'source']
83
-
84
- def __init__( # noqa: PLR0913
85
- self,
86
- debug: bool = False,
87
- trace: bool = False,
88
- quiet: bool = False,
89
- filepath: str = None,
90
- status: str = None,
91
- output: str = None,
92
- include: str = None,
93
- exclude: str = None,
94
- explicit: str = None,
95
- ):
96
- """
97
- Initialize the LicenseSummary class.
98
-
99
- :param debug: Enable debug mode
100
- :param trace: Enable trace mode (default True)
101
- :param quiet: Enable quiet mode
102
- :param filepath: Path to the file containing component data
103
- :param output: Path to save detailed output
104
- :param include: Licenses to include in the analysis
105
- :param exclude: Licenses to exclude from the analysis
106
- :param explicit: Explicitly defined licenses
107
- """
108
- super().__init__(debug, trace, quiet, filepath = filepath, output=output)
109
- self.license_util.init(include, exclude, explicit)
110
- self.filepath = filepath
111
- self.output = output
112
- self.status = status
113
- self.include = include
114
- self.exclude = exclude
115
- self.explicit = explicit
116
118
 
117
119
  def _get_licenses_summary_from_components(self, components: list)-> dict:
118
120
  """
@@ -122,7 +124,7 @@ class LicenseSummary(RawBase):
122
124
  :return: Dict with license summary information
123
125
  """
124
126
  # A component is considered unique by its combination of PURL (Package URL) and license
125
- component_licenses = self._group_components_by_license(components)
127
+ component_licenses = self.results_processor.group_components_by_license(components)
126
128
  license_component_count = {}
127
129
  # Count license per component
128
130
  for lic in component_licenses:
@@ -164,14 +166,14 @@ class LicenseSummary(RawBase):
164
166
 
165
167
  :return: A list of processed components with license data, or `None` if `self.results` is not set.
166
168
  """
167
- if self.results is None:
168
- raise ValueError(f'Error: No results found in ${self.filepath}')
169
+ if self.results_processor.get_results() is None:
170
+ raise ValueError(f'Error: No results found in {self.filepath}')
169
171
 
170
172
  components: dict = {}
171
173
  # Extract component and license data from file and dependency results. Both helpers mutate `components`
172
- self._get_components_data(self.results, components)
173
- self._get_dependencies_data(self.results, components)
174
- return self._convert_components_to_list(components)
174
+ self.results_processor.get_components_data(components)
175
+ self.results_processor.get_dependencies_data(components)
176
+ return self.results_processor.convert_components_to_list(components)
175
177
 
176
178
  def _format(self, license_summary) -> str:
177
179
  # TODO: Implement formatter to support dynamic outputs
@@ -94,6 +94,7 @@ class MatchSummary(ScanossBase):
94
94
  self.scanoss_results_path = scanoss_results_path
95
95
  self.line_range_prefix = line_range_prefix
96
96
  self.output = output
97
+ self.print_debug("Initializing MatchSummary class")
97
98
 
98
99
 
99
100
  def _get_match_summary_item(self, file_name: str, result: dict) -> MatchSummaryItem:
@@ -108,11 +109,16 @@ class MatchSummary(ScanossBase):
108
109
  :param result: SCANOSS scan result dictionary containing match details
109
110
  :return: Populated match summary item with all relevant information
110
111
  """
112
+ self.print_trace(f"Creating match summary item for file: {file_name}, id: {result.get('id')}")
113
+
111
114
  if result.get('id') == "snippet":
112
115
  # Snippet match: create URL with line range anchor
113
116
  lines = scanoss_scan_results_utils.get_lines(result.get('lines'))
114
117
  end_line = lines[len(lines) - 1] if len(lines) > 1 else lines[0]
115
118
  file_url = f"{self.line_range_prefix}/{file_name}#L{lines[0]}-L{end_line}"
119
+
120
+ self.print_trace(f"Snippet match: lines {lines[0]}-{end_line}, purl: {result.get('purl')[0]}")
121
+
116
122
  return MatchSummaryItem(
117
123
  file_url=file_url,
118
124
  file=file_name,
@@ -124,6 +130,8 @@ class MatchSummary(ScanossBase):
124
130
  lines=f"{lines[0]}-{lines[len(lines) - 1] if len(lines) > 1 else lines[0]}"
125
131
  )
126
132
  # File match: create URL without line range
133
+ self.print_trace(f"File match: {file_name}, purl: {result.get('purl')[0]}, version: {result.get('version')}")
134
+
127
135
  return MatchSummaryItem(
128
136
  file=file_name,
129
137
  file_url=f"{self.line_range_prefix}/{file_name}",
@@ -176,12 +184,19 @@ class MatchSummary(ScanossBase):
176
184
  required fields and categorizing matches into file matches and snippet matches.
177
185
  Skips invalid or incomplete results with debug messages.
178
186
  """
187
+ self.print_debug(f"Loading scan results from: {self.scanoss_results_path}")
188
+
179
189
  # Load scan results from JSON file
180
190
  scan_results = load_json_file(self.scanoss_results_path)
181
191
  gitlab_matches_summary = ComponentMatchSummary(files=[], snippet=[])
182
192
 
193
+ self.print_debug(f"Processing {len(scan_results)} files from scan results")
194
+ self.print_trace(f"Line range prefix set to: {self.line_range_prefix}")
195
+
183
196
  # Process each file and its results
184
197
  for file_name, results in scan_results.items():
198
+ self.print_trace(f"Processing file: {file_name} with {len(results)} results")
199
+
185
200
  for result in results:
186
201
  # Skip non-matches
187
202
  if result.get('id') == "none":
@@ -196,8 +211,15 @@ class MatchSummary(ScanossBase):
196
211
  summary_item = self._get_match_summary_item(file_name, result)
197
212
  if result.get('id') == "snippet":
198
213
  gitlab_matches_summary.snippet.append(summary_item)
214
+ self.print_trace(f"Added snippet match for {file_name}")
199
215
  else:
200
216
  gitlab_matches_summary.files.append(summary_item)
217
+ self.print_trace(f"Added file match for {file_name}")
218
+
219
+ self.print_debug(
220
+ f"Match summary complete: {len(gitlab_matches_summary.files)} file matches, "
221
+ f"{len(gitlab_matches_summary.snippet)} snippet matches"
222
+ )
201
223
 
202
224
  return gitlab_matches_summary
203
225
 
@@ -212,14 +234,23 @@ class MatchSummary(ScanossBase):
212
234
  :param gitlab_matches_summary: Container with categorized file and snippet matches to format
213
235
  :return: Complete Markdown document with formatted match tables
214
236
  """
237
+ self.print_debug("Generating Markdown from match summaries")
215
238
 
216
239
  if len(gitlab_matches_summary.files) == 0 and len(gitlab_matches_summary.snippet) == 0:
240
+ self.print_debug("No matches to format - returning empty string")
217
241
  return ""
218
242
 
243
+ self.print_trace(
244
+ f"Formatting {len(gitlab_matches_summary.files)} file matches and "
245
+ f"{len(gitlab_matches_summary.snippet)} snippet matches"
246
+ )
247
+
219
248
  # Define table headers
220
249
  file_match_headers = ['File', 'License', 'Similarity', 'PURL', 'Version']
221
250
  snippet_match_headers = ['File', 'License', 'Similarity', 'PURL', 'Version', 'Lines']
251
+
222
252
  # Build file matches table
253
+ self.print_trace("Building file matches table")
223
254
  file_match_rows = []
224
255
  for file_match in gitlab_matches_summary.files:
225
256
  row = [
@@ -233,6 +264,7 @@ class MatchSummary(ScanossBase):
233
264
  file_match_table = generate_table(file_match_headers, file_match_rows)
234
265
 
235
266
  # Build snippet matches table
267
+ self.print_trace("Building snippet matches table")
236
268
  snippet_match_rows = []
237
269
  for snippet_match in gitlab_matches_summary.snippet:
238
270
  row = [
@@ -262,6 +294,8 @@ class MatchSummary(ScanossBase):
262
294
  markdown += snippet_match_table
263
295
  markdown += "\n</details>\n"
264
296
 
297
+ self.print_trace(f"Markdown generation complete (length: {len(markdown)} characters)")
298
+ self.print_debug("Match summary Markdown generation complete")
265
299
  return markdown
266
300
 
267
301
  def run(self):
@@ -275,16 +309,33 @@ class MatchSummary(ScanossBase):
275
309
  3. Generates Markdown report
276
310
  4. Outputs to file or stdout
277
311
  """
312
+ self.print_debug("Starting match summary generation process")
313
+ self.print_trace(
314
+ f"Configuration - Results path: {self.scanoss_results_path}, Output: {self.output}, "
315
+ f"Line range prefix: {self.line_range_prefix}"
316
+ )
317
+
278
318
  # Load and process scan results into categorized matches
319
+ self.print_trace("Loading and processing scan results")
279
320
  matches = self._get_matches_summary()
280
321
 
281
322
  # Format matches as GitLab-compatible Markdown
323
+ self.print_trace("Generating Markdown output")
282
324
  matches_md = self._markdown(matches)
283
325
  if matches_md == "":
326
+ self.print_debug("No matches found - exiting")
284
327
  self.print_stdout("No matches found.")
285
328
  return
329
+
286
330
  # Output to file or stdout
331
+ self.print_trace("Writing output")
332
+ if self.output:
333
+ self.print_debug(f"Writing match summary to file: {self.output}")
334
+ else:
335
+ self.print_debug("Writing match summary to 'stdout'")
336
+
287
337
  self.print_to_file_or_stdout(matches_md, self.output)
338
+ self.print_debug("Match summary generation complete")
288
339
 
289
340
 
290
341
 
@@ -22,11 +22,10 @@ SPDX-License-Identifier: MIT
22
22
  THE SOFTWARE.
23
23
  """
24
24
 
25
- from abc import abstractmethod
26
25
  from enum import Enum
27
26
  from typing import Any, Dict, TypeVar
28
27
 
29
- from ..policy_check import PolicyCheck
28
+ from ...scanossbase import ScanossBase
30
29
  from ..utils.file_utils import load_json_file
31
30
  from ..utils.license_utils import LicenseUtil
32
31
 
@@ -51,12 +50,13 @@ class ComponentID(Enum):
51
50
  #
52
51
 
53
52
  T = TypeVar('T')
54
- class RawBase(PolicyCheck[T]):
53
+ class ScanResultProcessor(ScanossBase):
55
54
  """
56
- A base class to perform inspections over scan results.
55
+ A utility class for processing and transforming scan results.
57
56
 
58
- This class provides a basic for scan results inspection, including methods for
59
- processing scan results components and licenses.
57
+ This class provides functionality for processing scan results, including methods for
58
+ loading, parsing, extracting, and aggregating component and license data from scan results.
59
+ It serves as a shared data processing layer used by both policy checks and summary generators.
60
60
 
61
61
  Inherits from:
62
62
  ScanossBase: A base class providing common functionality for SCANOSS-related operations.
@@ -67,40 +67,19 @@ class RawBase(PolicyCheck[T]):
67
67
  debug: bool = False,
68
68
  trace: bool = False,
69
69
  quiet: bool = False,
70
- format_type: str = None,
71
- filepath: str = None,
72
- output: str = None,
73
- status: str = None,
74
- name: str = None,
70
+ result_file_path: str = None,
71
+ include: str = None,
72
+ exclude: str = None,
73
+ explicit: str = None,
75
74
  ):
76
- super().__init__(debug, trace, quiet, format_type,status, name, output)
75
+ super().__init__(debug, trace, quiet)
76
+ self.result_file_path = result_file_path
77
77
  self.license_util = LicenseUtil()
78
- self.filepath = filepath
79
- self.output = output
78
+ self.license_util.init(include, exclude, explicit)
80
79
  self.results = self._load_input_file()
81
80
 
82
- @abstractmethod
83
- def _get_components(self):
84
- """
85
- Retrieve and process components from the preloaded results.
86
-
87
- This method performs the following steps:
88
- 1. Checks if the results have been previously loaded (self.results).
89
- 2. Extracts and processes components from the loaded results.
90
-
91
- :return: A list of processed components, or None if an error occurred during any step.
92
-
93
- Possible reasons for returning None include:
94
- - Results not loaded (self.results is None)
95
- - Failure to extract components from the results
96
-
97
- Note:
98
- - This method assumes that the results have been previously loaded and stored in self.results.
99
- - Implementations must extract components (e.g. via `_get_components_data`,
100
- `_get_dependencies_data`, or other helpers).
101
- - If `self.results` is `None`, simply return `None`.
102
- """
103
- pass
81
+ def get_results(self) -> Dict[str, Any]:
82
+ return self.results
104
83
 
105
84
  def _append_component(self, components: Dict[str, Any], new_component: Dict[str, Any]) -> Dict[str, Any]:
106
85
  """
@@ -213,7 +192,7 @@ class RawBase(PolicyCheck[T]):
213
192
  else:
214
193
  component['undeclared'] += 1
215
194
 
216
- def _get_components_data(self, results: Dict[str, Any], components: Dict[str, Any]) -> Dict[str, Any]:
195
+ def get_components_data(self, components: Dict[str, Any]) -> Dict[str, Any]:
217
196
  """
218
197
  Extract and process file and snippet components from results.
219
198
 
@@ -230,11 +209,11 @@ class RawBase(PolicyCheck[T]):
230
209
  which tracks the number of occurrences of each license
231
210
 
232
211
  Args:
233
- results: A dictionary containing the raw results of a component scan
212
+ components: A dictionary containing the raw results of a component scan
234
213
  Returns:
235
214
  Updated components dictionary with file and snippet data
236
215
  """
237
- for component in results.values():
216
+ for component in self.results.values():
238
217
  for c in component:
239
218
  component_id = c.get('id')
240
219
  if not component_id:
@@ -266,15 +245,13 @@ class RawBase(PolicyCheck[T]):
266
245
  # End components loop
267
246
  return components
268
247
 
269
- def _get_dependencies_data(self, results: Dict[str, Any], components: Dict[str, Any]) -> Dict[str, Any]:
248
+ def get_dependencies_data(self,components: Dict[str, Any]) -> Dict[str, Any]:
270
249
  """
271
250
  Extract and process dependency components from results.
272
-
273
- :param results: A dictionary containing the raw results of a component scan
274
251
  :param components: Existing components dictionary to update
275
252
  :return: Updated components dictionary with dependency data
276
253
  """
277
- for component in results.values():
254
+ for component in self.results.values():
278
255
  for c in component:
279
256
  component_id = c.get('id')
280
257
  if not component_id:
@@ -313,12 +290,12 @@ class RawBase(PolicyCheck[T]):
313
290
  Dict[str, Any]: The parsed JSON data
314
291
  """
315
292
  try:
316
- return load_json_file(self.filepath)
293
+ return load_json_file(self.result_file_path)
317
294
  except Exception as e:
318
295
  self.print_stderr(f'ERROR: Problem parsing input JSON: {e}')
319
296
  return None
320
297
 
321
- def _convert_components_to_list(self, components: dict):
298
+ def convert_components_to_list(self, components: dict):
322
299
  if components is None:
323
300
  self.print_debug(f'WARNING: Components is empty {self.results}')
324
301
  return None
@@ -372,7 +349,7 @@ class RawBase(PolicyCheck[T]):
372
349
  self.print_debug("No priority sources found, returning all licenses as list")
373
350
  return licenses_data
374
351
 
375
- def _group_components_by_license(self,components):
352
+ def group_components_by_license(self,components):
376
353
  """
377
354
  Groups components by their unique component-license pairs.
378
355
 
@@ -425,5 +402,5 @@ class RawBase(PolicyCheck[T]):
425
402
 
426
403
 
427
404
  #
428
- # End of PolicyCheck Class
429
- #
405
+ # End of ScanResultProcessor Class
406
+ #
@@ -63,6 +63,7 @@ class ScannerHFH:
63
63
  depth: int = DEFAULT_HFH_DEPTH,
64
64
  recursive_threshold: float = DEFAULT_HFH_RECURSIVE_THRESHOLD,
65
65
  min_accepted_score: float = DEFAULT_HFH_MIN_ACCEPTED_SCORE,
66
+ use_grpc: bool = False,
66
67
  ):
67
68
  """
68
69
  Initialize the ScannerHFH.
@@ -107,6 +108,7 @@ class ScannerHFH:
107
108
  self.rank_threshold = rank_threshold
108
109
  self.recursive_threshold = recursive_threshold
109
110
  self.min_accepted_score = min_accepted_score
111
+ self.use_grpc = use_grpc
110
112
 
111
113
  def scan(self) -> Optional[Dict]:
112
114
  """
@@ -134,7 +136,7 @@ class ScannerHFH:
134
136
  spinner_thread.start()
135
137
 
136
138
  try:
137
- response = self.client.folder_hash_scan(hfh_request)
139
+ response = self.client.folder_hash_scan(hfh_request, self.use_grpc)
138
140
  if response:
139
141
  self.scan_results = response
140
142
  finally: