fosslight-util 1.4.44__tar.gz → 1.4.46__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.
Files changed (38) hide show
  1. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/PKG-INFO +1 -1
  2. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/setup.py +1 -1
  3. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/correct.py +34 -27
  4. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/download.py +39 -26
  5. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/oss_item.py +2 -2
  6. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/output_format.py +47 -0
  7. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/parsing_yaml.py +2 -1
  8. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/read_excel.py +2 -0
  9. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/write_excel.py +3 -3
  10. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/write_yaml.py +1 -1
  11. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util.egg-info/PKG-INFO +1 -1
  12. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/LICENSE +0 -0
  13. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/MANIFEST.in +0 -0
  14. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/README.md +0 -0
  15. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/requirements.txt +0 -0
  16. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/setup.cfg +0 -0
  17. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/__init__.py +0 -0
  18. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/_get_downloadable_url.py +0 -0
  19. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/compare_yaml.py +0 -0
  20. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/constant.py +0 -0
  21. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/convert_excel_to_yaml.py +0 -0
  22. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/cover.py +0 -0
  23. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/help.py +0 -0
  24. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/resources/frequentLicenselist.json +0 -0
  25. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/resources/frequent_license_nick_list.json +0 -0
  26. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/resources/licenses.json +0 -0
  27. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/set_log.py +0 -0
  28. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/spdx_licenses.py +0 -0
  29. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/timer_thread.py +0 -0
  30. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/write_opossum.py +0 -0
  31. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/write_scancodejson.py +0 -0
  32. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/write_spdx.py +0 -0
  33. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util/write_txt.py +0 -0
  34. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util.egg-info/SOURCES.txt +0 -0
  35. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util.egg-info/dependency_links.txt +0 -0
  36. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util.egg-info/entry_points.txt +0 -0
  37. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util.egg-info/requires.txt +0 -0
  38. {fosslight_util-1.4.44 → fosslight_util-1.4.46}/src/fosslight_util.egg-info/top_level.txt +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: fosslight_util
3
- Version: 1.4.44
3
+ Version: 1.4.46
4
4
  Summary: FOSSLight Util
5
5
  Home-page: https://github.com/fosslight/fosslight_util
6
6
  Author: LG Electronics
@@ -14,7 +14,7 @@ with open('requirements.txt', 'r', 'utf-8') as f:
14
14
  if __name__ == "__main__":
15
15
  setup(
16
16
  name='fosslight_util',
17
- version='1.4.44',
17
+ version='1.4.46',
18
18
  package_dir={"": "src"},
19
19
  packages=find_packages(where='src'),
20
20
  description='FOSSLight Util',
@@ -49,6 +49,7 @@ def correct_with_yaml(correct_filepath, path_to_scan, scanner_oss_list):
49
49
  continue
50
50
  correct_contents = copy.deepcopy(sheet_contents)
51
51
  scanner_name = constant.supported_sheet_and_scanner[sheet_name]
52
+ matched_source_path_with_sbom = []
52
53
  for idx, oss_raw_item in enumerate(sheet_contents):
53
54
  if len(oss_raw_item) < 9:
54
55
  logger.warning(f"sheet list is too short ({len(oss_raw_item)}): {oss_raw_item}")
@@ -57,33 +58,39 @@ def correct_with_yaml(correct_filepath, path_to_scan, scanner_oss_list):
57
58
  oss_item.set_sheet_item(oss_raw_item, scanner_name)
58
59
 
59
60
  matched_yi = []
60
- oss_rel_path = os.path.normpath(os.path.join(rel_path, oss_item.source_name_or_path[0]))
61
- for y_idx, yi in enumerate(yaml_oss_list):
62
- if not yi.source_name_or_path:
63
- continue
64
- for ys_idx, yi_path in enumerate(yi.source_name_or_path):
65
- yi_item = copy.deepcopy(yi)
66
- if ((os.path.normpath(yi_path) == os.path.normpath(oss_rel_path))
67
- or ((os.path.normpath(oss_rel_path).startswith(os.path.normpath(yi_path.rstrip('*')))))):
68
- find_match = True
69
- yi_item.source_name_or_path = []
70
- yi_item.source_name_or_path = oss_item.source_name_or_path[0]
71
- matched_yi.append(yi_item)
72
- matched_yaml[y_idx][ys_idx] = 1
73
- if len(matched_yi) > 0:
74
- for matched_yi_item in matched_yi:
75
- matched_oss_item = copy.deepcopy(matched_yi_item)
76
- if matched_oss_item.comment:
77
- matched_oss_item.comment += '/'
78
- matched_oss_item.comment += 'Loaded from sbom-info.yaml'
79
-
80
- if sheet_name == 'BIN_FL_Binary':
81
- matched_oss_item.bin_vulnerability = oss_item.bin_vulnerability
82
- matched_oss_item.bin_tlsh = oss_item.bin_tlsh
83
- matched_oss_item.bin_sha1 = oss_item.bin_sha1
84
-
85
- matched_oss_array = matched_oss_item.get_print_array(scanner_name)[0]
86
- correct_contents.append(matched_oss_array)
61
+ if not oss_item.source_name_or_path[0] in matched_source_path_with_sbom:
62
+ oss_rel_path = os.path.normpath(os.path.join(rel_path, oss_item.source_name_or_path[0]))
63
+ for y_idx, yi in enumerate(yaml_oss_list):
64
+ if not yi.source_name_or_path:
65
+ continue
66
+ for ys_idx, yi_path in enumerate(yi.source_name_or_path):
67
+ yi_item = copy.deepcopy(yi)
68
+ if ((os.path.normpath(yi_path) == os.path.normpath(oss_rel_path)) or
69
+ ((os.path.normpath(oss_rel_path).startswith(os.path.normpath(yi_path.rstrip('*')))))):
70
+ find_match = True
71
+ yi_item.source_name_or_path = []
72
+ yi_item.source_name_or_path = oss_item.source_name_or_path[0]
73
+ matched_source_path_with_sbom.append(oss_item.source_name_or_path[0])
74
+ matched_yi.append(yi_item)
75
+ matched_yaml[y_idx][ys_idx] = 1
76
+ if len(matched_yi) > 0:
77
+ for matched_yi_item in matched_yi:
78
+ matched_oss_item = copy.deepcopy(matched_yi_item)
79
+ if matched_oss_item.comment:
80
+ matched_oss_item.comment += '/'
81
+ matched_oss_item.comment += 'Loaded from sbom-info.yaml'
82
+ if sheet_name == 'BIN_FL_Binary':
83
+ matched_oss_item.bin_vulnerability = oss_item.bin_vulnerability
84
+ matched_oss_item.bin_tlsh = oss_item.bin_tlsh
85
+ matched_oss_item.bin_sha1 = oss_item.bin_sha1
86
+ matched_oss_array = matched_oss_item.get_print_array(scanner_name)[0]
87
+ correct_contents.append(matched_oss_array)
88
+ oss_item.exclude = True
89
+ if oss_item.comment:
90
+ oss_item.comment += '/'
91
+ oss_item.comment += 'Excluded by sbom-info.yaml'
92
+ correct_contents[idx] = oss_item.get_print_array(scanner_name)[0]
93
+ else:
87
94
  oss_item.exclude = True
88
95
  if oss_item.comment:
89
96
  oss_item.comment += '/'
@@ -46,12 +46,14 @@ class Alarm(threading.Thread):
46
46
 
47
47
 
48
48
  class TimeOutException(Exception):
49
- pass
49
+ def __init__(self, message, error_code):
50
+ super().__init__(message)
51
+ self.error_code = error_code
50
52
 
51
53
 
52
54
  def alarm_handler(signum, frame):
53
55
  logger.warning("download timeout! (%d sec)", SIGNAL_TIMEOUT)
54
- raise TimeOutException()
56
+ raise TimeOutException(f'Timeout ({SIGNAL_TIMEOUT} sec)', 1)
55
57
 
56
58
 
57
59
  def change_src_link_to_https(src_link):
@@ -127,6 +129,7 @@ def cli_download_and_extract(link: str, target_dir: str, log_dir: str, checkout_
127
129
 
128
130
  success = True
129
131
  msg = ""
132
+ msg_wget = ""
130
133
  oss_name = ""
131
134
  oss_version = ""
132
135
  log_file_name = "fosslight_download_" + \
@@ -156,16 +159,20 @@ def cli_download_and_extract(link: str, target_dir: str, log_dir: str, checkout_
156
159
 
157
160
  success, downloaded_file, msg_wget, oss_name, oss_version = download_wget(link, target_dir, compressed_only)
158
161
  if success:
159
- success = extract_compressed_file(downloaded_file, target_dir, True)
162
+ success = extract_compressed_file(downloaded_file, target_dir, True, compressed_only)
160
163
  # Download from rubygems.org
161
164
  elif is_rubygems and shutil.which("gem"):
162
165
  success = gem_download(link, target_dir, checkout_to)
163
166
  if msg:
164
167
  msg = f'git fail: {msg}'
165
- if msg_wget:
166
- msg = f'{msg}, wget fail: {msg_wget}'
168
+ if is_rubygems:
169
+ msg = f'gem download: {success}'
167
170
  else:
168
- msg = f'{msg}, wget success'
171
+ if msg_wget:
172
+ msg = f'{msg}, wget fail: {msg_wget}'
173
+ else:
174
+ msg = f'{msg}, wget success'
175
+
169
176
  except Exception as error:
170
177
  success = False
171
178
  msg = str(error)
@@ -232,13 +239,14 @@ def download_git_clone(git_url, target_dir, checkout_to="", tag="", branch=""):
232
239
  if github_token != "":
233
240
  callbacks = git.RemoteCallbacks(credentials=git.UserPass("foo", github_token)) # username is not used, so set to dummy
234
241
 
235
- if platform.system() != "Windows":
236
- signal.signal(signal.SIGALRM, alarm_handler)
237
- signal.alarm(SIGNAL_TIMEOUT)
238
- else:
239
- alarm = Alarm(SIGNAL_TIMEOUT)
240
- alarm.start()
241
242
  try:
243
+ if platform.system() != "Windows":
244
+ signal.signal(signal.SIGALRM, alarm_handler)
245
+ signal.alarm(SIGNAL_TIMEOUT)
246
+ else:
247
+ alarm = Alarm(SIGNAL_TIMEOUT)
248
+ alarm.start()
249
+
242
250
  Path(target_dir).mkdir(parents=True, exist_ok=True)
243
251
  repo = git.clone_repository(git_url, target_dir,
244
252
  bare=False, repository=None,
@@ -273,13 +281,15 @@ def download_wget(link, target_dir, compressed_only):
273
281
  oss_name = ""
274
282
  oss_version = ""
275
283
  downloaded_file = ""
276
- if platform.system() != "Windows":
277
- signal.signal(signal.SIGALRM, alarm_handler)
278
- signal.alarm(SIGNAL_TIMEOUT)
279
- else:
280
- alarm = Alarm(SIGNAL_TIMEOUT)
281
- alarm.start()
284
+
282
285
  try:
286
+ if platform.system() != "Windows":
287
+ signal.signal(signal.SIGALRM, alarm_handler)
288
+ signal.alarm(SIGNAL_TIMEOUT)
289
+ else:
290
+ alarm = Alarm(SIGNAL_TIMEOUT)
291
+ alarm.start()
292
+
283
293
  Path(target_dir).mkdir(parents=True, exist_ok=True)
284
294
 
285
295
  ret, new_link, oss_name, oss_version = get_downloadable_url(link)
@@ -320,14 +330,14 @@ def extract_compressed_dir(src_dir, target_dir, remove_after_extract=True):
320
330
  try:
321
331
  files_path = [os.path.join(src_dir, x) for x in os.listdir(src_dir)]
322
332
  for fname in files_path:
323
- extract_compressed_file(fname, target_dir, remove_after_extract)
333
+ extract_compressed_file(fname, target_dir, remove_after_extract, True)
324
334
  except Exception as error:
325
335
  logger.debug(f"Extract files in dir - failed: {error}")
326
336
  return False
327
337
  return True
328
338
 
329
339
 
330
- def extract_compressed_file(fname, extract_path, remove_after_extract=True):
340
+ def extract_compressed_file(fname, extract_path, remove_after_extract=True, compressed_only=True):
331
341
  success = True
332
342
  try:
333
343
  is_compressed_file = True
@@ -349,7 +359,8 @@ def extract_compressed_file(fname, extract_path, remove_after_extract=True):
349
359
  decompress_bz2(fname, extract_path)
350
360
  else:
351
361
  is_compressed_file = False
352
- success = False
362
+ if compressed_only:
363
+ success = False
353
364
  logger.warning(f"Unsupported file extension: {fname}")
354
365
 
355
366
  if remove_after_extract and is_compressed_file:
@@ -419,11 +430,13 @@ def gem_download(link, target_dir, checkout_to):
419
430
  fetch_result = subprocess.check_output(fetch_cmd, universal_newlines=True)
420
431
  fetch_result = fetch_result.replace('\n', '').split(' ')[-1]
421
432
  downloaded_gem = f"{fetch_result}.gem"
422
-
423
- # gem unpack
424
- subprocess.check_output(['gem', 'unpack', downloaded_gem], universal_newlines=True)
425
- # move unpacked file to target directory
426
- shutil.move(fetch_result, target_dir)
433
+ if not os.path.isfile(downloaded_gem):
434
+ success = False
435
+ else:
436
+ # gem unpack
437
+ subprocess.check_output(['gem', 'unpack', downloaded_gem], universal_newlines=True)
438
+ # move unpacked file to target directory
439
+ shutil.move(fetch_result, target_dir)
427
440
  except Exception as error:
428
441
  success = False
429
442
  logger.warning(f"gem download - failed: {error}")
@@ -201,7 +201,7 @@ class OssItem:
201
201
 
202
202
  json_item["version"] = self.version
203
203
  if len(self.source_name_or_path) > 0:
204
- json_item["source name or path"] = self.source_name_or_path
204
+ json_item["source path"] = self.source_name_or_path
205
205
  if len(self.license) > 0:
206
206
  json_item["license"] = self.license
207
207
  if self.download_location != "":
@@ -217,7 +217,7 @@ class OssItem:
217
217
  if len(self.depends_on) > 0:
218
218
  json_item["depends on"] = self.depends_on
219
219
  if self.purl != "":
220
- json_item["purl"] = self.purl
220
+ json_item["package url"] = self.purl
221
221
 
222
222
  return json_item
223
223
 
@@ -56,6 +56,53 @@ def check_output_format(output='', format='', customized_format={}):
56
56
  return success, msg, output_path, output_file, output_extension
57
57
 
58
58
 
59
+ def check_output_formats(output='', formats=[], customized_format={}):
60
+ success = True
61
+ msg = ''
62
+ output_path = ''
63
+ output_files = []
64
+ output_extensions = []
65
+
66
+ if customized_format:
67
+ support_format = customized_format
68
+ else:
69
+ support_format = SUPPORT_FORMAT
70
+
71
+ if formats:
72
+ # If -f option exist
73
+ formats = [format.lower() for format in formats]
74
+ for format in formats:
75
+ if format not in list(support_format.keys()):
76
+ success = False
77
+ msg = 'Enter the supported format with -f option: ' + ', '.join(list(support_format.keys()))
78
+ else:
79
+ output_extensions.append(support_format[format])
80
+
81
+ if success:
82
+ if output != '':
83
+ basename_extension = ''
84
+ if not os.path.isdir(output):
85
+ output_path = os.path.dirname(output)
86
+
87
+ basename = os.path.basename(output)
88
+ basename_file, basename_extension = os.path.splitext(basename)
89
+ if basename_extension:
90
+ if formats:
91
+ if basename_extension not in output_extensions:
92
+ success = False
93
+ msg = f"The format of output file(-o:'{output}') should be in the format list(-f:'{formats}')."
94
+ else:
95
+ if basename_extension not in support_format.values():
96
+ success = False
97
+ msg = 'Enter the supported file extension: ' + ', '.join(list(support_format.values()))
98
+ output_extensions.append(basename_extension)
99
+ output_files = [basename_file for _ in range(len(output_extensions))]
100
+ else:
101
+ output_path = output
102
+
103
+ return success, msg, output_path, output_files, output_extensions
104
+
105
+
59
106
  def write_output_file(output_file_without_ext, file_extension, sheet_list, extended_header={}, hide_header={}, cover=""):
60
107
  success = True
61
108
  msg = ''
@@ -101,7 +101,8 @@ def set_value_switch(oss, key, value, yaml_file=""):
101
101
  oss.download_location = value
102
102
  elif key in ['license', 'license text']:
103
103
  oss.license = value
104
- elif key in ['file name or path', 'source name or path', 'file', 'binary name']:
104
+ elif key in ['file name or path', 'source name or path', 'source path',
105
+ 'file', 'binary name', 'binary path']:
105
106
  oss.source_name_or_path = value
106
107
  elif key in ['copyright text', 'copyright']:
107
108
  oss.copyright = value
@@ -66,7 +66,9 @@ def read_oss_report(excel_file: str, sheet_names: str = "") -> List[OssItem]:
66
66
  _item_idx = {
67
67
  "ID": IDX_CANNOT_FOUND,
68
68
  "Source Name or Path": IDX_CANNOT_FOUND,
69
+ "Source Path": IDX_CANNOT_FOUND,
69
70
  "Binary Name": IDX_CANNOT_FOUND,
71
+ "Binary Path": IDX_CANNOT_FOUND,
70
72
  "OSS Name": IDX_CANNOT_FOUND,
71
73
  "OSS Version": IDX_CANNOT_FOUND,
72
74
  "License": IDX_CANNOT_FOUND,
@@ -15,15 +15,15 @@ import fosslight_util.constant as constant
15
15
  from jsonmerge import merge
16
16
  from fosslight_util.cover import CoverItem
17
17
 
18
- _HEADER = {'BIN (': ['ID', 'Binary Name', 'Source Code Path',
18
+ _HEADER = {'BIN (': ['ID', 'Binary Path', 'Source Code Path',
19
19
  'NOTICE.html', 'OSS Name', 'OSS Version',
20
20
  'License', 'Download Location', 'Homepage',
21
21
  'Copyright Text', 'Exclude', 'Comment'],
22
- 'SRC': ['ID', 'Source Name or Path', 'OSS Name',
22
+ 'SRC': ['ID', 'Source Path', 'OSS Name',
23
23
  'OSS Version', 'License', 'Download Location',
24
24
  'Homepage', 'Copyright Text', 'Exclude',
25
25
  'Comment'],
26
- 'BIN': ['ID', 'Binary Name', 'OSS Name', 'OSS Version',
26
+ 'BIN': ['ID', 'Binary Path', 'OSS Name', 'OSS Version',
27
27
  'License', 'Download Location', 'Homepage',
28
28
  'Copyright Text', 'Exclude', 'Comment']}
29
29
  _OUTPUT_FILE_PREFIX = "FOSSLight-Report_"
@@ -93,7 +93,7 @@ def create_yaml_with_ossitem(item, yaml_dict):
93
93
  oss_info.get('homepage', '') == item.homepage and \
94
94
  oss_info.get('download location', '') == item.download_location and \
95
95
  oss_info.get('exclude', False) == item.exclude:
96
- oss_info.get('source name or path', []).extend(item.source_name_or_path)
96
+ oss_info.get('source path', []).extend(item.source_name_or_path)
97
97
  oss_info.pop('comment', None)
98
98
  merged = True
99
99
  break
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.1
2
2
  Name: fosslight-util
3
- Version: 1.4.44
3
+ Version: 1.4.46
4
4
  Summary: FOSSLight Util
5
5
  Home-page: https://github.com/fosslight/fosslight_util
6
6
  Author: LG Electronics
File without changes