refactor: don't use global Config in private func (#1197)
* refactor: cve_client.go * refactor: don't use global Config in private func * remove import alias for config * refactor: dbclient * refactor: resultDir * refactor: resultsDir * refactor * refactor: gost * refactor: db client * refactor: cveDB * refactor: cvedb * refactor: exploitDB * refactor: remove detector/dbclient.go * refactor: writer * refactor: syslog writer * refactor: ips * refactor: ensureResultDir * refactor: proxy * fix(db): call CloseDB * add integration test * feat(report): sort array in json * sort func for json diff * add build-int to makefile * add int-rds-redis to makefile * fix: test case, makefile * fix makefile * show cve count after diff * make diff * diff -c * sort exploits in json for diff * sort metasploit, exploit
This commit is contained in:
		@@ -4,6 +4,7 @@ import (
 | 
			
		||||
	"bytes"
 | 
			
		||||
	"fmt"
 | 
			
		||||
	"reflect"
 | 
			
		||||
	"sort"
 | 
			
		||||
	"strings"
 | 
			
		||||
	"time"
 | 
			
		||||
 | 
			
		||||
@@ -56,7 +57,7 @@ type ScanResult struct {
 | 
			
		||||
	Config            struct {
 | 
			
		||||
		Scan   config.Config `json:"scan"`
 | 
			
		||||
		Report config.Config `json:"report"`
 | 
			
		||||
	} `json:"constant"`
 | 
			
		||||
	} `json:"config"`
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Container has Container information
 | 
			
		||||
@@ -374,6 +375,48 @@ func (r *ScanResult) CheckEOL() {
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func (r *ScanResult) SortForJSONOutput() {
 | 
			
		||||
	for k, v := range r.Packages {
 | 
			
		||||
		sort.SliceStable(v.AffectedProcs, func(i, j int) bool {
 | 
			
		||||
			return v.AffectedProcs[i].PID < v.AffectedProcs[j].PID
 | 
			
		||||
		})
 | 
			
		||||
		sort.SliceStable(v.NeedRestartProcs, func(i, j int) bool {
 | 
			
		||||
			return v.NeedRestartProcs[i].PID < v.NeedRestartProcs[j].PID
 | 
			
		||||
		})
 | 
			
		||||
		r.Packages[k] = v
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	for k, v := range r.ScannedCves {
 | 
			
		||||
		sort.SliceStable(v.AffectedPackages, func(i, j int) bool {
 | 
			
		||||
			return v.AffectedPackages[i].Name < v.AffectedPackages[j].Name
 | 
			
		||||
		})
 | 
			
		||||
		sort.SliceStable(v.DistroAdvisories, func(i, j int) bool {
 | 
			
		||||
			return v.DistroAdvisories[i].AdvisoryID < v.DistroAdvisories[j].AdvisoryID
 | 
			
		||||
		})
 | 
			
		||||
		sort.SliceStable(v.Exploits, func(i, j int) bool {
 | 
			
		||||
			return v.Exploits[i].ID < v.Exploits[j].ID
 | 
			
		||||
		})
 | 
			
		||||
		sort.SliceStable(v.Metasploits, func(i, j int) bool {
 | 
			
		||||
			return v.Metasploits[i].Name < v.Metasploits[j].Name
 | 
			
		||||
		})
 | 
			
		||||
		for kk, vv := range v.CveContents {
 | 
			
		||||
			sort.SliceStable(vv.References, func(i, j int) bool {
 | 
			
		||||
				return vv.References[i].Link < vv.References[j].Link
 | 
			
		||||
			})
 | 
			
		||||
			v.CveContents[kk] = vv
 | 
			
		||||
		}
 | 
			
		||||
 | 
			
		||||
		sort.SliceStable(v.AlertDict.En, func(i, j int) bool {
 | 
			
		||||
			return v.AlertDict.En[i].Title < v.AlertDict.En[j].Title
 | 
			
		||||
		})
 | 
			
		||||
		sort.SliceStable(v.AlertDict.Ja, func(i, j int) bool {
 | 
			
		||||
			return v.AlertDict.Ja[i].Title < v.AlertDict.Ja[j].Title
 | 
			
		||||
		})
 | 
			
		||||
 | 
			
		||||
		r.ScannedCves[k] = v
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// CweDict is a dictionary for CWE
 | 
			
		||||
type CweDict map[string]CweDictEntry
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,7 @@
 | 
			
		||||
package models
 | 
			
		||||
 | 
			
		||||
import (
 | 
			
		||||
	"reflect"
 | 
			
		||||
	"testing"
 | 
			
		||||
 | 
			
		||||
	"github.com/future-architect/vuls/config"
 | 
			
		||||
@@ -92,3 +93,274 @@ func TestIsDisplayUpdatableNum(t *testing.T) {
 | 
			
		||||
		}
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestScanResult_Sort(t *testing.T) {
 | 
			
		||||
	type fields struct {
 | 
			
		||||
		Packages    Packages
 | 
			
		||||
		ScannedCves VulnInfos
 | 
			
		||||
	}
 | 
			
		||||
	tests := []struct {
 | 
			
		||||
		name     string
 | 
			
		||||
		fields   fields
 | 
			
		||||
		expected fields
 | 
			
		||||
	}{
 | 
			
		||||
		{
 | 
			
		||||
			name: "already asc",
 | 
			
		||||
			fields: fields{
 | 
			
		||||
				Packages: map[string]Package{
 | 
			
		||||
					"pkgA": {
 | 
			
		||||
						Name: "pkgA",
 | 
			
		||||
						AffectedProcs: []AffectedProcess{
 | 
			
		||||
							{PID: "1", Name: "procB"},
 | 
			
		||||
							{PID: "2", Name: "procA"},
 | 
			
		||||
						},
 | 
			
		||||
						NeedRestartProcs: []NeedRestartProcess{
 | 
			
		||||
							{PID: "1"},
 | 
			
		||||
							{PID: "2"},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
				ScannedCves: VulnInfos{
 | 
			
		||||
					"CVE-2014-3591": VulnInfo{
 | 
			
		||||
						AffectedPackages: PackageFixStatuses{
 | 
			
		||||
							PackageFixStatus{Name: "pkgA"},
 | 
			
		||||
							PackageFixStatus{Name: "pkgB"},
 | 
			
		||||
						},
 | 
			
		||||
						DistroAdvisories: []DistroAdvisory{
 | 
			
		||||
							{AdvisoryID: "adv-1"},
 | 
			
		||||
							{AdvisoryID: "adv-2"},
 | 
			
		||||
						},
 | 
			
		||||
						Exploits: []Exploit{
 | 
			
		||||
							{ID: "a"},
 | 
			
		||||
							{ID: "b"},
 | 
			
		||||
						},
 | 
			
		||||
						Metasploits: []Metasploit{
 | 
			
		||||
							{Name: "a"},
 | 
			
		||||
							{Name: "b"},
 | 
			
		||||
						},
 | 
			
		||||
						CveContents: CveContents{
 | 
			
		||||
							"nvd": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
							"jvn": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
						AlertDict: AlertDict{
 | 
			
		||||
							En: []Alert{
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
							},
 | 
			
		||||
							Ja: []Alert{
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
			},
 | 
			
		||||
			expected: fields{
 | 
			
		||||
				Packages: map[string]Package{
 | 
			
		||||
					"pkgA": {
 | 
			
		||||
						Name: "pkgA",
 | 
			
		||||
						AffectedProcs: []AffectedProcess{
 | 
			
		||||
							{PID: "1", Name: "procB"},
 | 
			
		||||
							{PID: "2", Name: "procA"},
 | 
			
		||||
						},
 | 
			
		||||
						NeedRestartProcs: []NeedRestartProcess{
 | 
			
		||||
							{PID: "1"},
 | 
			
		||||
							{PID: "2"},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
				ScannedCves: VulnInfos{
 | 
			
		||||
					"CVE-2014-3591": VulnInfo{
 | 
			
		||||
						AffectedPackages: PackageFixStatuses{
 | 
			
		||||
							PackageFixStatus{Name: "pkgA"},
 | 
			
		||||
							PackageFixStatus{Name: "pkgB"},
 | 
			
		||||
						},
 | 
			
		||||
						DistroAdvisories: []DistroAdvisory{
 | 
			
		||||
							{AdvisoryID: "adv-1"},
 | 
			
		||||
							{AdvisoryID: "adv-2"},
 | 
			
		||||
						},
 | 
			
		||||
						Exploits: []Exploit{
 | 
			
		||||
							{ID: "a"},
 | 
			
		||||
							{ID: "b"},
 | 
			
		||||
						},
 | 
			
		||||
						Metasploits: []Metasploit{
 | 
			
		||||
							{Name: "a"},
 | 
			
		||||
							{Name: "b"},
 | 
			
		||||
						},
 | 
			
		||||
						CveContents: CveContents{
 | 
			
		||||
							"nvd": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
							"jvn": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
						AlertDict: AlertDict{
 | 
			
		||||
							En: []Alert{
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
							},
 | 
			
		||||
							Ja: []Alert{
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
			},
 | 
			
		||||
		},
 | 
			
		||||
		{
 | 
			
		||||
			name: "sort",
 | 
			
		||||
			fields: fields{
 | 
			
		||||
				Packages: map[string]Package{
 | 
			
		||||
					"pkgA": {
 | 
			
		||||
						Name: "pkgA",
 | 
			
		||||
						AffectedProcs: []AffectedProcess{
 | 
			
		||||
							{PID: "2", Name: "procA"},
 | 
			
		||||
							{PID: "1", Name: "procB"},
 | 
			
		||||
						},
 | 
			
		||||
						NeedRestartProcs: []NeedRestartProcess{
 | 
			
		||||
							{PID: "91"},
 | 
			
		||||
							{PID: "90"},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
				ScannedCves: VulnInfos{
 | 
			
		||||
					"CVE-2014-3591": VulnInfo{
 | 
			
		||||
						AffectedPackages: PackageFixStatuses{
 | 
			
		||||
							PackageFixStatus{Name: "pkgB"},
 | 
			
		||||
							PackageFixStatus{Name: "pkgA"},
 | 
			
		||||
						},
 | 
			
		||||
						DistroAdvisories: []DistroAdvisory{
 | 
			
		||||
							{AdvisoryID: "adv-2"},
 | 
			
		||||
							{AdvisoryID: "adv-1"},
 | 
			
		||||
						},
 | 
			
		||||
						Exploits: []Exploit{
 | 
			
		||||
							{ID: "b"},
 | 
			
		||||
							{ID: "a"},
 | 
			
		||||
						},
 | 
			
		||||
						Metasploits: []Metasploit{
 | 
			
		||||
							{Name: "b"},
 | 
			
		||||
							{Name: "a"},
 | 
			
		||||
						},
 | 
			
		||||
						CveContents: CveContents{
 | 
			
		||||
							"nvd": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
							"jvn": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
						AlertDict: AlertDict{
 | 
			
		||||
							En: []Alert{
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
							},
 | 
			
		||||
							Ja: []Alert{
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
			},
 | 
			
		||||
			expected: fields{
 | 
			
		||||
				Packages: map[string]Package{
 | 
			
		||||
					"pkgA": {
 | 
			
		||||
						Name: "pkgA",
 | 
			
		||||
						AffectedProcs: []AffectedProcess{
 | 
			
		||||
							{PID: "1", Name: "procB"},
 | 
			
		||||
							{PID: "2", Name: "procA"},
 | 
			
		||||
						},
 | 
			
		||||
						NeedRestartProcs: []NeedRestartProcess{
 | 
			
		||||
							{PID: "90"},
 | 
			
		||||
							{PID: "91"},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
				ScannedCves: VulnInfos{
 | 
			
		||||
					"CVE-2014-3591": VulnInfo{
 | 
			
		||||
						AffectedPackages: PackageFixStatuses{
 | 
			
		||||
							PackageFixStatus{Name: "pkgA"},
 | 
			
		||||
							PackageFixStatus{Name: "pkgB"},
 | 
			
		||||
						},
 | 
			
		||||
						DistroAdvisories: []DistroAdvisory{
 | 
			
		||||
							{AdvisoryID: "adv-1"},
 | 
			
		||||
							{AdvisoryID: "adv-2"},
 | 
			
		||||
						},
 | 
			
		||||
						Exploits: []Exploit{
 | 
			
		||||
							{ID: "a"},
 | 
			
		||||
							{ID: "b"},
 | 
			
		||||
						},
 | 
			
		||||
						Metasploits: []Metasploit{
 | 
			
		||||
							{Name: "a"},
 | 
			
		||||
							{Name: "b"},
 | 
			
		||||
						},
 | 
			
		||||
						CveContents: CveContents{
 | 
			
		||||
							"nvd": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
							"jvn": CveContent{
 | 
			
		||||
								References: References{
 | 
			
		||||
									Reference{Link: "a"},
 | 
			
		||||
									Reference{Link: "b"},
 | 
			
		||||
								},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
						AlertDict: AlertDict{
 | 
			
		||||
							En: []Alert{
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
							},
 | 
			
		||||
							Ja: []Alert{
 | 
			
		||||
								{Title: "a"},
 | 
			
		||||
								{Title: "b"},
 | 
			
		||||
							},
 | 
			
		||||
						},
 | 
			
		||||
					},
 | 
			
		||||
				},
 | 
			
		||||
			},
 | 
			
		||||
		},
 | 
			
		||||
	}
 | 
			
		||||
	for _, tt := range tests {
 | 
			
		||||
		t.Run(tt.name, func(t *testing.T) {
 | 
			
		||||
			r := &ScanResult{
 | 
			
		||||
				Packages:    tt.fields.Packages,
 | 
			
		||||
				ScannedCves: tt.fields.ScannedCves,
 | 
			
		||||
			}
 | 
			
		||||
			r.SortForJSONOutput()
 | 
			
		||||
			if !reflect.DeepEqual(r.Packages, tt.expected.Packages) {
 | 
			
		||||
				t.Errorf("act %+v, want %+v", r.Packages, tt.expected.Packages)
 | 
			
		||||
			}
 | 
			
		||||
 | 
			
		||||
			if !reflect.DeepEqual(r.ScannedCves, tt.expected.ScannedCves) {
 | 
			
		||||
				t.Errorf("act %+v, want %+v", r.ScannedCves, tt.expected.ScannedCves)
 | 
			
		||||
			}
 | 
			
		||||
		})
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -763,14 +763,10 @@ type AlertDict struct {
 | 
			
		||||
 | 
			
		||||
// FormatSource returns which source has this alert
 | 
			
		||||
func (a AlertDict) FormatSource() string {
 | 
			
		||||
	s := []string{}
 | 
			
		||||
	if len(a.En) != 0 {
 | 
			
		||||
		s = append(s, "USCERT")
 | 
			
		||||
	if len(a.En) != 0 || len(a.Ja) != 0 {
 | 
			
		||||
		return "CERT"
 | 
			
		||||
	}
 | 
			
		||||
	if len(a.Ja) != 0 {
 | 
			
		||||
		s = append(s, "JPCERT")
 | 
			
		||||
	}
 | 
			
		||||
	return strings.Join(s, "/")
 | 
			
		||||
	return ""
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Confidences is a list of Confidence
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user