xref: /aosp_15_r20/external/spdx-tools/reporter/reporter.go (revision ba677afa8f67bb56cbc794f4d0e378e0da058e16)
1*ba677afaSXin Li// Package reporter contains functions to generate a basic license count
2*ba677afaSXin Li// report from an in-memory SPDX Package section whose Files have been
3*ba677afaSXin Li// analyzed.
4*ba677afaSXin Li// SPDX-License-Identifier: Apache-2.0 OR GPL-2.0-or-later
5*ba677afaSXin Lipackage reporter
6*ba677afaSXin Li
7*ba677afaSXin Liimport (
8*ba677afaSXin Li	"fmt"
9*ba677afaSXin Li	"io"
10*ba677afaSXin Li	"sort"
11*ba677afaSXin Li	"text/tabwriter"
12*ba677afaSXin Li
13*ba677afaSXin Li	"github.com/spdx/tools-golang/spdx/v2_1"
14*ba677afaSXin Li	"github.com/spdx/tools-golang/spdx/v2_2"
15*ba677afaSXin Li	"github.com/spdx/tools-golang/spdx/v2_3"
16*ba677afaSXin Li)
17*ba677afaSXin Li
18*ba677afaSXin Li// ===== 2.1 Reporter functions =====
19*ba677afaSXin Li
20*ba677afaSXin Li// Generate2_1 takes a Package whose Files have been analyzed and an
21*ba677afaSXin Li// io.Writer, and outputs to the io.Writer a tabulated count of
22*ba677afaSXin Li// the number of Files for each unique LicenseConcluded in the set.
23*ba677afaSXin Lifunc Generate2_1(pkg *v2_1.Package, w io.Writer) error {
24*ba677afaSXin Li	if pkg.FilesAnalyzed == false {
25*ba677afaSXin Li		return fmt.Errorf("Package FilesAnalyzed is false")
26*ba677afaSXin Li	}
27*ba677afaSXin Li	totalFound, totalNotFound, foundCounts := countLicenses2_1(pkg)
28*ba677afaSXin Li
29*ba677afaSXin Li	wr := tabwriter.NewWriter(w, 0, 0, 2, ' ', tabwriter.AlignRight)
30*ba677afaSXin Li
31*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  License found\n", totalFound)
32*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  License not found\n", totalNotFound)
33*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  TOTAL\n", totalFound+totalNotFound)
34*ba677afaSXin Li	fmt.Fprintf(wr, "\n")
35*ba677afaSXin Li
36*ba677afaSXin Li	counts := []struct {
37*ba677afaSXin Li		lic   string
38*ba677afaSXin Li		count int
39*ba677afaSXin Li	}{}
40*ba677afaSXin Li	for k, v := range foundCounts {
41*ba677afaSXin Li		var entry struct {
42*ba677afaSXin Li			lic   string
43*ba677afaSXin Li			count int
44*ba677afaSXin Li		}
45*ba677afaSXin Li		entry.lic = k
46*ba677afaSXin Li		entry.count = v
47*ba677afaSXin Li		counts = append(counts, entry)
48*ba677afaSXin Li	}
49*ba677afaSXin Li
50*ba677afaSXin Li	sort.Slice(counts, func(i, j int) bool { return counts[i].count > counts[j].count })
51*ba677afaSXin Li
52*ba677afaSXin Li	for _, c := range counts {
53*ba677afaSXin Li		fmt.Fprintf(wr, "%d\t  %s\n", c.count, c.lic)
54*ba677afaSXin Li	}
55*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  TOTAL FOUND\n", totalFound)
56*ba677afaSXin Li
57*ba677afaSXin Li	wr.Flush()
58*ba677afaSXin Li	return nil
59*ba677afaSXin Li}
60*ba677afaSXin Li
61*ba677afaSXin Lifunc countLicenses2_1(pkg *v2_1.Package) (int, int, map[string]int) {
62*ba677afaSXin Li	if pkg == nil || pkg.Files == nil {
63*ba677afaSXin Li		return 0, 0, nil
64*ba677afaSXin Li	}
65*ba677afaSXin Li
66*ba677afaSXin Li	totalFound := 0
67*ba677afaSXin Li	totalNotFound := 0
68*ba677afaSXin Li	foundCounts := map[string]int{}
69*ba677afaSXin Li	for _, f := range pkg.Files {
70*ba677afaSXin Li		if f.LicenseConcluded == "" || f.LicenseConcluded == "NOASSERTION" {
71*ba677afaSXin Li			totalNotFound++
72*ba677afaSXin Li		} else {
73*ba677afaSXin Li			totalFound++
74*ba677afaSXin Li			foundCounts[f.LicenseConcluded]++
75*ba677afaSXin Li		}
76*ba677afaSXin Li	}
77*ba677afaSXin Li
78*ba677afaSXin Li	return totalFound, totalNotFound, foundCounts
79*ba677afaSXin Li}
80*ba677afaSXin Li
81*ba677afaSXin Li// ===== 2.2 Reporter functions =====
82*ba677afaSXin Li
83*ba677afaSXin Li// Generate2_2 takes a Package whose Files have been analyzed and an
84*ba677afaSXin Li// io.Writer, and outputs to the io.Writer a tabulated count of
85*ba677afaSXin Li// the number of Files for each unique LicenseConcluded in the set.
86*ba677afaSXin Lifunc Generate2_2(pkg *v2_2.Package, w io.Writer) error {
87*ba677afaSXin Li	if pkg.FilesAnalyzed == false {
88*ba677afaSXin Li		return fmt.Errorf("Package FilesAnalyzed is false")
89*ba677afaSXin Li	}
90*ba677afaSXin Li	totalFound, totalNotFound, foundCounts := countLicenses2_2(pkg)
91*ba677afaSXin Li
92*ba677afaSXin Li	wr := tabwriter.NewWriter(w, 0, 0, 2, ' ', tabwriter.AlignRight)
93*ba677afaSXin Li
94*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  License found\n", totalFound)
95*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  License not found\n", totalNotFound)
96*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  TOTAL\n", totalFound+totalNotFound)
97*ba677afaSXin Li	fmt.Fprintf(wr, "\n")
98*ba677afaSXin Li
99*ba677afaSXin Li	counts := []struct {
100*ba677afaSXin Li		lic   string
101*ba677afaSXin Li		count int
102*ba677afaSXin Li	}{}
103*ba677afaSXin Li	for k, v := range foundCounts {
104*ba677afaSXin Li		var entry struct {
105*ba677afaSXin Li			lic   string
106*ba677afaSXin Li			count int
107*ba677afaSXin Li		}
108*ba677afaSXin Li		entry.lic = k
109*ba677afaSXin Li		entry.count = v
110*ba677afaSXin Li		counts = append(counts, entry)
111*ba677afaSXin Li	}
112*ba677afaSXin Li
113*ba677afaSXin Li	sort.Slice(counts, func(i, j int) bool { return counts[i].count > counts[j].count })
114*ba677afaSXin Li
115*ba677afaSXin Li	for _, c := range counts {
116*ba677afaSXin Li		fmt.Fprintf(wr, "%d\t  %s\n", c.count, c.lic)
117*ba677afaSXin Li	}
118*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  TOTAL FOUND\n", totalFound)
119*ba677afaSXin Li
120*ba677afaSXin Li	wr.Flush()
121*ba677afaSXin Li	return nil
122*ba677afaSXin Li}
123*ba677afaSXin Li
124*ba677afaSXin Lifunc countLicenses2_2(pkg *v2_2.Package) (int, int, map[string]int) {
125*ba677afaSXin Li	if pkg == nil || pkg.Files == nil {
126*ba677afaSXin Li		return 0, 0, nil
127*ba677afaSXin Li	}
128*ba677afaSXin Li
129*ba677afaSXin Li	totalFound := 0
130*ba677afaSXin Li	totalNotFound := 0
131*ba677afaSXin Li	foundCounts := map[string]int{}
132*ba677afaSXin Li	for _, f := range pkg.Files {
133*ba677afaSXin Li		if f.LicenseConcluded == "" || f.LicenseConcluded == "NOASSERTION" {
134*ba677afaSXin Li			totalNotFound++
135*ba677afaSXin Li		} else {
136*ba677afaSXin Li			totalFound++
137*ba677afaSXin Li			foundCounts[f.LicenseConcluded]++
138*ba677afaSXin Li		}
139*ba677afaSXin Li	}
140*ba677afaSXin Li
141*ba677afaSXin Li	return totalFound, totalNotFound, foundCounts
142*ba677afaSXin Li}
143*ba677afaSXin Li
144*ba677afaSXin Li// ===== 2.3 Reporter functions =====
145*ba677afaSXin Li
146*ba677afaSXin Li// Generate2_3 takes a Package whose Files have been analyzed and an
147*ba677afaSXin Li// io.Writer, and outputs to the io.Writer a tabulated count of
148*ba677afaSXin Li// the number of Files for each unique LicenseConcluded in the set.
149*ba677afaSXin Lifunc Generate2_3(pkg *v2_3.Package, w io.Writer) error {
150*ba677afaSXin Li	if pkg.FilesAnalyzed == false {
151*ba677afaSXin Li		return fmt.Errorf("Package FilesAnalyzed is false")
152*ba677afaSXin Li	}
153*ba677afaSXin Li	totalFound, totalNotFound, foundCounts := countLicenses2_3(pkg)
154*ba677afaSXin Li
155*ba677afaSXin Li	wr := tabwriter.NewWriter(w, 0, 0, 2, ' ', tabwriter.AlignRight)
156*ba677afaSXin Li
157*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  License found\n", totalFound)
158*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  License not found\n", totalNotFound)
159*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  TOTAL\n", totalFound+totalNotFound)
160*ba677afaSXin Li	fmt.Fprintf(wr, "\n")
161*ba677afaSXin Li
162*ba677afaSXin Li	counts := []struct {
163*ba677afaSXin Li		lic   string
164*ba677afaSXin Li		count int
165*ba677afaSXin Li	}{}
166*ba677afaSXin Li	for k, v := range foundCounts {
167*ba677afaSXin Li		var entry struct {
168*ba677afaSXin Li			lic   string
169*ba677afaSXin Li			count int
170*ba677afaSXin Li		}
171*ba677afaSXin Li		entry.lic = k
172*ba677afaSXin Li		entry.count = v
173*ba677afaSXin Li		counts = append(counts, entry)
174*ba677afaSXin Li	}
175*ba677afaSXin Li
176*ba677afaSXin Li	sort.Slice(counts, func(i, j int) bool { return counts[i].count > counts[j].count })
177*ba677afaSXin Li
178*ba677afaSXin Li	for _, c := range counts {
179*ba677afaSXin Li		fmt.Fprintf(wr, "%d\t  %s\n", c.count, c.lic)
180*ba677afaSXin Li	}
181*ba677afaSXin Li	fmt.Fprintf(wr, "%d\t  TOTAL FOUND\n", totalFound)
182*ba677afaSXin Li
183*ba677afaSXin Li	wr.Flush()
184*ba677afaSXin Li	return nil
185*ba677afaSXin Li}
186*ba677afaSXin Li
187*ba677afaSXin Lifunc countLicenses2_3(pkg *v2_3.Package) (int, int, map[string]int) {
188*ba677afaSXin Li	if pkg == nil || pkg.Files == nil {
189*ba677afaSXin Li		return 0, 0, nil
190*ba677afaSXin Li	}
191*ba677afaSXin Li
192*ba677afaSXin Li	totalFound := 0
193*ba677afaSXin Li	totalNotFound := 0
194*ba677afaSXin Li	foundCounts := map[string]int{}
195*ba677afaSXin Li	for _, f := range pkg.Files {
196*ba677afaSXin Li		if f.LicenseConcluded == "" || f.LicenseConcluded == "NOASSERTION" {
197*ba677afaSXin Li			totalNotFound++
198*ba677afaSXin Li		} else {
199*ba677afaSXin Li			totalFound++
200*ba677afaSXin Li			foundCounts[f.LicenseConcluded]++
201*ba677afaSXin Li		}
202*ba677afaSXin Li	}
203*ba677afaSXin Li
204*ba677afaSXin Li	return totalFound, totalNotFound, foundCounts
205*ba677afaSXin Li}
206