Files
trivy/pkg/utils/utils_test.go
Teppei Fukuda 74717b888e feat: support client/server mode (#295)
* chore(app): change dir

* feat(rpc): add a proto file and auto-generated files

* chore(dep): add dependencies

* fix(app): fix import path

* fix(integration): fix import path

* fix(protoc): use enum for severity

* chore(Makefile): add fmt andd protoc

* chore(clang): add .clang-format

* refactor: split functions for client/server (#296)

* refactor(db): split db.Download

* refactor(standalone): create a different package

* refactor(vulnerability): split FillAndFilter

* fix(protoc): use enum for severity

* chore(Makefile): add fmt andd protoc

* chore(clang): add .clang-format

* fix(db): remove an unused variable

* fix(db): expose the github client as an argument of constructor

* refactor(vulnerability): add the detail message

* feat(rpc): add rpc client (#302)

* fix(protoc): use enum for severity

* chore(Makefile): add fmt andd protoc

* chore(clang): add .clang-format

* feat(rpc): convert types

* feat(rpc): add rpc client

* token: Refactor to handle bad headers being set

Signed-off-by: Simarpreet Singh <simar@linux.com>

* feat(rpc): add rpc server (#303)

* feat(rpc): add rpc server

* feat(utils): add CopyFile

* feat(server/config): add config struct

* feat(detector): add detector

* feat(scanner): delegate procedures to detector

* fix(scanner): fix the interface

* test(mock): add mocks

* test(rpc/server): add tests

* test(rpc/ospkg/server): add tests

* tets(os/detector): add tests

* refactor(library): move directories

* chore(dependency): add google/wire

* refactor(library): introduce google/wire

* refactor(ospkg/detector): move directory

* feat(rpc): add eosl

* refactor(ospkg): introduce google/wire

* refactor(wire): bind an interface

* refactor(client): use wire.Struct

* chore(Makefile): fix wire

* test(server): add AssertExpectations

* test(server): add AssertExpectations

* refactor(server): remove debug log

* refactor(error): add more context messages

* test(server): fix error message

* refactor(test): create a constructor of mock

* refactor(config): remove an unused variable

* test(config): add an assertion to test the config struct

* feat(client/server): add sub commands (#304)

* feat(rpc): add rpc server

* feat(utils): add CopyFile

* feat(server/config): add config struct

* feat(detector): add detector

* feat(scanner): delegate procedures to detector

* fix(scanner): fix the interface

* feat(client/server): add sub commands

* merge(server3)

* test(scan): remove an unused mock

* refactor(client): generate the constructor by wire

* fix(cli): change the default port

* fix(server): use auto-generated constructor

* feat(ospkg): return eosl

* test(integration): add integration tests for client/server (#306)

* fix(server): remove unnecessary options

* test(integration): add integration tests for client/server

* fix(server): wrap an error

* fix(server): change the update interval

* fix(server): display the error detail

* test(config): add an assertion to test the config struct

* fix(client): returns an error when failing to initizlie a logger

* test(ospkg/server): add eosl

* Squashed commit of the following:

* test(server): refactor and add tests (#307)

* test(github): create a mock

* test(db): create a mock

* test(server): add tests for DB hot update

* chore(db): add a log message

* refactor(db): introduce google/wire

* refactor(rpc): move directory

* refactor(injector): fix import name

* refactor(import): remove new lines

* fix(server): display the error detail

* fix(server): change the update interval

* fix(server): wrap an error

* test(integration): add integration tests for client/server

* fix(server): remove unnecessary options

* refactor(server): return an error when failing to initialize a logger

* refactor(server): remove unused error

* fix(client/server): fix default port

* chore(README): add client/server

* chore(README): update
2019-12-13 15:00:11 +02:00

196 lines
3.9 KiB
Go

package utils
import (
"io"
"io/ioutil"
"os"
"path/filepath"
"reflect"
"strings"
"testing"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
"github.com/aquasecurity/trivy/pkg/log"
"github.com/kylelemons/godebug/pretty"
)
func touch(t *testing.T, name string) {
f, err := os.Create(name)
if err != nil {
t.Fatal(err)
}
if err := f.Close(); err != nil {
t.Fatal(err)
}
}
func write(t *testing.T, name string, content string) {
err := ioutil.WriteFile(name, []byte(content), 0666)
if err != nil {
t.Fatal(err)
}
}
func TestFileWalk(t *testing.T) {
if err := log.InitLogger(false, false); err != nil {
t.Fatal(err)
}
td, err := ioutil.TempDir("", "walktest")
if err != nil {
t.Fatal(err)
}
defer os.RemoveAll(td)
if err := os.MkdirAll(filepath.Join(td, "dir"), 0755); err != nil {
t.Fatal(err)
}
touch(t, filepath.Join(td, "dir/foo1"))
touch(t, filepath.Join(td, "dir/foo2"))
write(t, filepath.Join(td, "dir/foo3"), "foo3")
write(t, filepath.Join(td, "dir/foo4"), "foo4")
sawDir := false
sawFoo1 := false
sawFoo2 := false
sawFoo4 := false
var contentFoo3 []byte
walker := func(r io.Reader, path string) error {
if strings.HasSuffix(path, "dir") {
sawDir = true
}
if strings.HasSuffix(path, "foo1") {
sawFoo1 = true
}
if strings.HasSuffix(path, "foo2") {
sawFoo2 = true
}
if strings.HasSuffix(path, "foo3") {
contentFoo3, err = ioutil.ReadAll(r)
if err != nil {
t.Fatal(err)
}
}
if strings.HasSuffix(path, "foo4") {
sawFoo4 = true
}
return nil
}
targetFiles := map[string]struct{}{
"dir/foo2": {},
"dir/foo3": {},
}
err = FileWalk(td, targetFiles, walker)
if err != nil {
t.Fatal(err)
}
if sawDir {
t.Error("directories must not be passed to walkFn")
}
if sawFoo1 || sawFoo4 {
t.Error("a file not included in targetFiles must not be passed to walkFn")
}
if sawFoo2 {
t.Error("an empty file must not be passed to walkFn")
}
if string(contentFoo3) != "foo3" {
t.Error("The file content is wrong")
}
}
func TestFilterTargets(t *testing.T) {
vectors := map[string]struct {
prefix string
targets map[string]struct{} // Target files
expected map[string]struct{}
err error // Expected error to occur
}{
"normal": {
prefix: "dir",
targets: map[string]struct{}{
"dir/file1": {},
"dir/file2": {},
"foo/bar": {},
},
expected: map[string]struct{}{
"file1": {},
"file2": {},
},
err: nil,
},
"other directory with the same prefix": {
prefix: "dir",
targets: map[string]struct{}{
"dir/file1": {},
"dir2/file2": {},
},
expected: map[string]struct{}{
"file1": {},
},
err: nil,
},
}
for testName, v := range vectors {
t.Run(testName, func(t *testing.T) {
actual, err := FilterTargets(v.prefix, v.targets)
if err != nil {
t.Errorf("err: got %v, want %v", v.err, err)
}
if !reflect.DeepEqual(actual, v.expected) {
t.Errorf("[%s]\n%s", testName, pretty.Compare(v.expected, actual))
}
})
}
}
func TestCopyFile(t *testing.T) {
type args struct {
src string
dst string
}
tests := []struct {
name string
args args
content []byte
want string
wantErr string
}{
{
name: "happy path",
content: []byte("this is a content"),
args: args{},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
src := tt.args.src
if tt.args.src == "" {
s, err := ioutil.TempFile("", "src")
require.NoError(t, err, tt.name)
_, err = s.Write(tt.content)
require.NoError(t, err, tt.name)
src = s.Name()
}
dst := tt.args.dst
if tt.args.dst == "" {
d, err := ioutil.TempFile("", "dst")
require.NoError(t, err, tt.name)
dst = d.Name()
require.NoError(t, d.Close(), tt.name)
}
_, err := CopyFile(src, dst)
if tt.wantErr != "" {
require.NotNil(t, err, tt.name)
assert.Equal(t, err.Error(), tt.wantErr, tt.name)
} else {
assert.NoError(t, err, tt.name)
}
})
}
}