summaryrefslogtreecommitdiffstats
path: root/scripts/cve-json-to-text.py
diff options
context:
space:
mode:
authorMarta Rybczynska <rybczynska@gmail.com>2024-08-23 15:10:33 +0200
committerRichard Purdie <richard.purdie@linuxfoundation.org>2024-08-25 15:36:30 +0100
commit38cfb6525eed43304aedcf760afff7aa358645e2 (patch)
treea460688f1420ec2330ad43ec0e4b7e3da509ace3 /scripts/cve-json-to-text.py
parent76cc46211403ad05caa074ee1f8815540c984cc3 (diff)
downloadpoky-38cfb6525eed43304aedcf760afff7aa358645e2.tar.gz
cve-json-to-text: add script
Add a script that converts the cve-check result from the JSON format to the TEXT format. (From OE-Core rev: da4e01dfa538578936e565413871a7496b8752df) Signed-off-by: Marta Rybczynska <marta.rybczynska@ygreky.com> Signed-off-by: Richard Purdie <richard.purdie@linuxfoundation.org>
Diffstat (limited to 'scripts/cve-json-to-text.py')
-rwxr-xr-xscripts/cve-json-to-text.py145
1 files changed, 145 insertions, 0 deletions
diff --git a/scripts/cve-json-to-text.py b/scripts/cve-json-to-text.py
new file mode 100755
index 0000000000..5531ee5eb6
--- /dev/null
+++ b/scripts/cve-json-to-text.py
@@ -0,0 +1,145 @@
1#!/bin/env python3
2# SPDX-FileCopyrightText: OpenEmbedded Contributors
3#
4# SPDX-License-Identifier: MIT
5
6# CVE results conversion script: JSON format to text
7# Derived from cve-report.py from Oniro (MIT, by Huawei Inc)
8
9import sys
10import getopt
11
12infile = "in.json"
13outfile = "out.txt"
14
15
16def show_syntax_and_exit(code):
17 """
18 Show the program syntax and exit with an errror
19 Arguments:
20 code: the error code to return
21 """
22 print("Syntax: %s [-h] [-i inputJSONfile][-o outputfile]" % sys.argv[0])
23 sys.exit(code)
24
25
26def exit_error(code, message):
27 """
28 Show the error message and exit with an errror
29 Arguments:
30 code: the error code to return
31 message: the message to show
32 """
33 print("Error: %s" % message)
34 sys.exit(code)
35
36
37def parse_args(argv):
38 """
39 Parse the program arguments, put options in global variables
40 Arguments:
41 argv: program arguments
42 """
43 global infile, outfile
44 try:
45 opts, args = getopt.getopt(
46 argv, "hi:o:", ["help", "input", "output"]
47 )
48 except getopt.GetoptError:
49 show_syntax_and_exit(1)
50 for opt, arg in opts:
51 if opt in ("-h", "--help"):
52 show_syntax_and_exit(0)
53 elif opt in ("-a", "--all"):
54 show_all = True
55 show_unknown = True
56 elif opt in ("-i", "--input"):
57 infile = arg
58
59def load_json(filename):
60 """
61 Load the JSON file, return the resulting dictionary
62 Arguments:
63 filename: the file to open
64 Returns:
65 Parsed file as a dictionary
66 """
67 import json
68
69 out = {}
70 try:
71 with open(filename, "r") as f:
72 out = json.load(f)
73 except FileNotFoundError:
74 exit_error(1, "Input file (%s) not found" % (filename))
75 except json.decoder.JSONDecodeError as error:
76 exit_error(1, "Malformed JSON file: %s" % str(error))
77 return out
78
79
80def process_data(filename, data):
81 """
82 Write the resulting CSV with one line for each package
83 Arguments:
84 filename: the file to write to
85 data: dictionary from parsing the JSON file
86 Returns:
87 None
88 """
89 if not "version" in data or data["version"] != "1":
90 exit_error(1, "Unrecognized format version number")
91 if not "package" in data:
92 exit_error(1, "Mandatory 'package' key not found")
93
94 lines = ""
95 total_issue_count = 0
96 for package in data["package"]:
97 package_info = ""
98 keys_in_package = {"name", "layer", "version", "issue"}
99 if keys_in_package - package.keys():
100 exit_error(
101 1,
102 "Missing a mandatory key in package: %s"
103 % (keys_in_package - package.keys()),
104 )
105
106 package_info += "LAYER: %s\n" % package["layer"]
107 package_info += "PACKAGE NAME: %s\n" % package["name"]
108 package_info += "PACKAGE VERSION: %s\n" % package["version"]
109
110 for issue in package["issue"]:
111 keys_in_issue = {"id", "status", "detail"}
112 if keys_in_issue - issue.keys():
113 print("Warning: Missing keys %s in 'issue' for the package '%s'"
114 % (keys_in_issue - issue.keys(), package["name"]))
115
116 lines += package_info
117 lines += "CVE: %s\n" % issue["id"]
118 lines += "CVE STATUS: %s\n" % issue["status"]
119 lines += "CVE DETAIL: %s\n" % issue["detail"]
120 if "description" in issue:
121 lines += "CVE DESCRIPTION: %s\n" % issue["description"]
122 if "summary" in issue:
123 lines += "CVE SUMMARY: %s\n" % issue["summary"]
124 if "scorev2" in issue:
125 lines += "CVSS v2 BASE SCORE: %s\n" % issue["scorev2"]
126 if "scorev3" in issue:
127 lines += "CVSS v3 BASE SCORE: %s\n" % issue["scorev3"]
128 if "vector" in issue:
129 lines += "VECTOR: %s\n" % issue["vector"]
130 if "vectorString" in issue:
131 lines += "VECTORSTRING: %s\n" % issue["vectorString"]
132 lines += "MORE INFORMATION: https://nvd.nist.gov/vuln/detail/%s\n" % issue["id"]
133 lines += "\n"
134
135 with open(filename, "w") as f:
136 f.write(lines)
137
138def main(argv):
139 parse_args(argv)
140 data = load_json(infile)
141 process_data(outfile, data)
142
143
144if __name__ == "__main__":
145 main(sys.argv[1:])