Skip to content

Commit b52ebc5

Browse files
authored
Merge pull request #251 from manni83/script_fixes
Batch update vulnerability enhancements and fixes
2 parents 180ff1c + 32f922c commit b52ebc5

File tree

3 files changed

+19
-14
lines changed

3 files changed

+19
-14
lines changed

blackduck/Vulnerabilities.py

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ def get_vulnerable_bom_components(self, version_obj, limit=9999):
2828
param_string = self._get_parameter_string({'limit': limit})
2929
url = "{}{}".format(url, param_string)
3030
response = self.execute_get(url, custom_headers=custom_headers)
31+
response.raise_for_status()
3132
return response.json()
3233

3334
# TODO: Remove or refactor this

examples/client/get_project_vulnerabilites_as_csv.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@
2727
)
2828

2929
def strip_newline(str):
30-
return str.replace('\r', '').replace('\n', ' ')
30+
return str.replace('\r', '').replace('\n', '\\n')
3131

3232
def match_component(selected_components, component):
3333
if (len(selected_components) == 0):

examples/vuln_batch_remediation.py

Lines changed: 17 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,9 @@
8484

8585
def load_remediation_input(remediation_file):
8686
with open(remediation_file, mode='r', encoding="utf-8") as infile:
87-
reader = csv.reader(infile)
87+
dialect = csv.Sniffer().sniff(infile.read(), delimiters=';,')
88+
infile.seek(0)
89+
reader = csv.reader(infile, dialect)
8890
#return {rows[0]:[rows[1],rows[2]] for rows in reader}
8991
return {rows[0]:rows[1:] for rows in reader}
9092

@@ -95,7 +97,7 @@ def remediation_is_valid(vuln, remediation_data):
9597

9698
if vulnerability_name in remediation_data.keys():
9799
remediation = remediation_data[vulnerability_name]
98-
if (remediation_status == remediation[0] and remediation_comment == remediation[1]):
100+
if (remediation_status == remediation[0] and remediation_comment == remediation[1].replace('\\n','\n')):
99101
return None
100102
return remediation_data[vulnerability_name]
101103
else:
@@ -127,11 +129,11 @@ def set_vulnerablity_remediation(hub, vuln, remediation_status, remediation_comm
127129
url = vuln['_meta']['href']
128130
update={}
129131
update['remediationStatus'] = remediation_status
130-
update['comment'] = remediation_comment
132+
update['comment'] = remediation_comment.replace('\\n','\n')
131133
response = hub.execute_put(url, data=update)
132134
return response
133135

134-
def process_vulnerabilities(hub, vulnerable_components, remediation_data=None, exclusion_data=None, dry_run=False):
136+
def process_vulnerabilities(hub, vulnerable_components, remediation_data=None, exclusion_data=None, dry_run=False, overwrite_existing=False):
135137

136138
if (dry_run):
137139
print(f"Opening dry run output file: {dry_run}")
@@ -142,8 +144,8 @@ def process_vulnerabilities(hub, vulnerable_components, remediation_data=None, e
142144
print('"Component Name","Component Version","CVE","Reason","Remeidation Status","HTTP response code"')
143145

144146
for vuln in vulnerable_components['items']:
145-
if vuln['vulnerabilityWithRemediation']['remediationStatus'] == "NEW":
146-
remediation_action = None
147+
if overwrite_existing or vuln['vulnerabilityWithRemediation']['remediationStatus'] == "NEW":
148+
remediation_action = None
147149
exclusion_action = None
148150

149151
if (remediation_data):
@@ -164,8 +166,7 @@ def process_vulnerabilities(hub, vulnerable_components, remediation_data=None, e
164166

165167
if (remediation_action):
166168
if (dry_run):
167-
remediation_action.insert(0, vuln['vulnerabilityWithRemediation']['vulnerabilityName'])
168-
csv_writer.writerow(remediation_action)
169+
csv_writer.writerow([vuln['vulnerabilityWithRemediation']['vulnerabilityName']] + remediation_action)
169170
else:
170171
resp = set_vulnerablity_remediation(hub, vuln, remediation_action[0],remediation_action[1])
171172
count += 1
@@ -218,6 +219,7 @@ def main(argv=None): # IGNORE:C0111
218219
parser.add_argument("--cve-remediation-list-custom-field-label", default='CVE Remediation List', help='Label of Custom Field on Black Duck that contains remeidation list file name')
219220
parser.add_argument("--origin-exclusion-list-custom-field-label", default='Origin Exclusion List', help='Label of Custom Field on Black Duck that containts origin exclusion list file name')
220221
parser.add_argument('-V', '--version', action='version', version=program_version_message)
222+
parser.add_argument("--overwrite-existing", dest='overwrite_existing', action="store_true", help='By default only NEW vulnerabilities are remediated. Enabling this flag will update all vulnerabilities.')
221223

222224
# Process arguments
223225
args = parser.parse_args()
@@ -231,6 +233,7 @@ def main(argv=None): # IGNORE:C0111
231233
#dry_run = args.dry_run
232234
#dry_run_output = args.dry_run_output
233235
dry_run = args.dry_run
236+
overwrite_existing = args.overwrite_existing
234237
print(args.dry_run)
235238

236239
message = f"{program_version_message}\n\n Project: {projectname}\n Version: {projectversion}\n Process origin exclusion list: {process_origin_exclulsion}\n Process CVE remediation list: {process_cve_remediation}"
@@ -271,16 +274,17 @@ def main(argv=None): # IGNORE:C0111
271274
exclusion_data = None
272275

273276

274-
# Retrieve the vulnerabiltites for the project version
275-
vulnerable_components = hub.get_vulnerable_bom_components(version)
276277

277-
process_vulnerabilities(hub, vulnerable_components, remediation_data, exclusion_data, dry_run)
278-
278+
# Retrieve the vulnerabiltites for the project version. Newer API versions only allow 1000 items at most.
279+
vulnerable_components = hub.get_vulnerable_bom_components(version, 1000)
280+
281+
process_vulnerabilities(hub, vulnerable_components, remediation_data, exclusion_data, dry_run, overwrite_existing)
282+
279283
return 0
280284
except Exception:
281285
### handle keyboard interrupt ###
282286
traceback.print_exc()
283287
return 0
284288

285289
if __name__ == "__main__":
286-
sys.exit(main())
290+
sys.exit(main())

0 commit comments

Comments
 (0)