212ac2f0d5
* Refactor of cameradar library * Old unit tests updated & improved. New unit tests inc * Update documentation & issue template * Update dependencies * Update TravisCI build script to reflect argument change * Remove outdated contributing guide * Update README with more examples and remove part on library * Add second camera to Travis build script & improve error detection * Fix typo in travis script & add missing image to readme * Remember that travis uses bash syntax not fish * Use relative paths for images in the README
322 lines
6.0 KiB
Go
322 lines
6.0 KiB
Go
package cameradar
|
|
|
|
import (
|
|
"errors"
|
|
"io/ioutil"
|
|
"os"
|
|
"testing"
|
|
|
|
"github.com/ullaakut/disgo"
|
|
|
|
"github.com/stretchr/testify/assert"
|
|
"github.com/stretchr/testify/mock"
|
|
"github.com/ullaakut/nmap"
|
|
)
|
|
|
|
type nmapMock struct {
|
|
mock.Mock
|
|
}
|
|
|
|
func (m *nmapMock) Run() (*nmap.Run, error) {
|
|
args := m.Called()
|
|
|
|
if args.Get(0) != nil {
|
|
return args.Get(0).(*nmap.Run), args.Error(1)
|
|
}
|
|
return nil, args.Error(1)
|
|
}
|
|
|
|
var (
|
|
validStream1 = Stream{
|
|
Device: "fakeDevice",
|
|
Address: "fakeAddress",
|
|
Port: 1337,
|
|
}
|
|
|
|
validStream2 = Stream{
|
|
Device: "fakeDevice",
|
|
Address: "differentFakeAddress",
|
|
Port: 1337,
|
|
}
|
|
|
|
invalidStreamNoPort = Stream{
|
|
Device: "invalidDevice",
|
|
Address: "fakeAddress",
|
|
Port: 0,
|
|
}
|
|
|
|
invalidStreamNoAddress = Stream{
|
|
Device: "invalidDevice",
|
|
Address: "",
|
|
Port: 1337,
|
|
}
|
|
)
|
|
|
|
func TestScan(t *testing.T) {
|
|
tests := []struct {
|
|
description string
|
|
|
|
targets []string
|
|
ports []string
|
|
speed int
|
|
removePath bool
|
|
|
|
expectedErr error
|
|
expectedStreams []Stream
|
|
}{
|
|
{
|
|
description: "create new scanner and call scan, no error",
|
|
|
|
targets: []string{"localhost"},
|
|
ports: []string{"80"},
|
|
speed: 5,
|
|
},
|
|
{
|
|
description: "create new scanner with missing nmap installation",
|
|
|
|
removePath: true,
|
|
ports: []string{"80"},
|
|
|
|
expectedErr: errors.New("unable to create network scanner: 'nmap' binary was not found"),
|
|
},
|
|
}
|
|
|
|
for _, test := range tests {
|
|
t.Run(test.description, func(t *testing.T) {
|
|
if test.removePath {
|
|
os.Setenv("PATH", "")
|
|
}
|
|
|
|
scanner := &Scanner{
|
|
term: disgo.NewTerminal(disgo.WithDefaultOutput(ioutil.Discard)),
|
|
targets: test.targets,
|
|
ports: test.ports,
|
|
speed: test.speed,
|
|
}
|
|
|
|
result, err := scanner.Scan()
|
|
|
|
assert.Equal(t, test.expectedErr, err)
|
|
assert.Equal(t, test.expectedStreams, result)
|
|
})
|
|
}
|
|
}
|
|
|
|
func TestInternalScan(t *testing.T) {
|
|
|
|
tests := []struct {
|
|
description string
|
|
|
|
nmapResult *nmap.Run
|
|
nmapError error
|
|
|
|
expectedStreams []Stream
|
|
expectedErr error
|
|
}{
|
|
{
|
|
description: "valid streams",
|
|
|
|
nmapResult: &nmap.Run{
|
|
Hosts: []nmap.Host{
|
|
{
|
|
Addresses: []nmap.Address{
|
|
{
|
|
Addr: validStream1.Address,
|
|
},
|
|
},
|
|
Ports: []nmap.Port{
|
|
{
|
|
State: nmap.State{
|
|
State: "open",
|
|
},
|
|
ID: validStream1.Port,
|
|
Service: nmap.Service{
|
|
Name: "rtsp",
|
|
Product: validStream1.Device,
|
|
},
|
|
},
|
|
},
|
|
},
|
|
{
|
|
Addresses: []nmap.Address{
|
|
{
|
|
Addr: validStream2.Address,
|
|
},
|
|
},
|
|
Ports: []nmap.Port{
|
|
{
|
|
State: nmap.State{
|
|
State: "open",
|
|
},
|
|
ID: validStream2.Port,
|
|
Service: nmap.Service{
|
|
Name: "rtsp-alt",
|
|
Product: validStream2.Device,
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
|
|
expectedStreams: []Stream{validStream1, validStream2},
|
|
},
|
|
{
|
|
description: "two invalid targets, no error",
|
|
|
|
nmapResult: &nmap.Run{
|
|
Hosts: []nmap.Host{
|
|
{
|
|
Addresses: []nmap.Address{
|
|
{
|
|
Addr: invalidStreamNoPort.Address,
|
|
},
|
|
},
|
|
},
|
|
{
|
|
Addresses: []nmap.Address{},
|
|
Ports: []nmap.Port{
|
|
{
|
|
State: nmap.State{
|
|
State: "open",
|
|
},
|
|
ID: validStream2.Port,
|
|
Service: nmap.Service{
|
|
Name: "rtsp-alt",
|
|
Product: invalidStreamNoAddress.Device,
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
|
|
expectedStreams: nil,
|
|
},
|
|
{
|
|
description: "different port states, no error",
|
|
|
|
nmapResult: &nmap.Run{
|
|
Hosts: []nmap.Host{
|
|
{
|
|
Addresses: []nmap.Address{
|
|
{
|
|
Addr: invalidStreamNoPort.Address,
|
|
}},
|
|
Ports: []nmap.Port{
|
|
{
|
|
State: nmap.State{
|
|
State: "closed",
|
|
},
|
|
ID: validStream2.Port,
|
|
Service: nmap.Service{
|
|
Name: "rtsp-alt",
|
|
Product: invalidStreamNoAddress.Device,
|
|
},
|
|
},
|
|
},
|
|
},
|
|
{
|
|
Addresses: []nmap.Address{
|
|
{
|
|
Addr: invalidStreamNoPort.Address,
|
|
}},
|
|
Ports: []nmap.Port{
|
|
{
|
|
State: nmap.State{
|
|
State: "unfiltered",
|
|
},
|
|
ID: validStream2.Port,
|
|
Service: nmap.Service{
|
|
Name: "rtsp-alt",
|
|
Product: invalidStreamNoAddress.Device,
|
|
},
|
|
},
|
|
},
|
|
},
|
|
{
|
|
Addresses: []nmap.Address{
|
|
{
|
|
Addr: invalidStreamNoPort.Address,
|
|
}},
|
|
Ports: []nmap.Port{
|
|
{
|
|
State: nmap.State{
|
|
State: "filtered",
|
|
},
|
|
ID: validStream2.Port,
|
|
Service: nmap.Service{
|
|
Name: "rtsp-alt",
|
|
Product: invalidStreamNoAddress.Device,
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
|
|
expectedStreams: nil,
|
|
},
|
|
{
|
|
description: "not rtsp, no error",
|
|
|
|
nmapResult: &nmap.Run{
|
|
Hosts: []nmap.Host{
|
|
{
|
|
Addresses: []nmap.Address{
|
|
{
|
|
Addr: invalidStreamNoPort.Address,
|
|
}},
|
|
Ports: []nmap.Port{
|
|
{
|
|
State: nmap.State{
|
|
State: "open",
|
|
},
|
|
ID: validStream2.Port,
|
|
Service: nmap.Service{
|
|
Name: "tcp",
|
|
Product: invalidStreamNoAddress.Device,
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
},
|
|
|
|
expectedStreams: nil,
|
|
},
|
|
{
|
|
description: "no hosts found",
|
|
|
|
nmapResult: &nmap.Run{},
|
|
expectedStreams: nil,
|
|
},
|
|
{
|
|
description: "scan failed",
|
|
|
|
nmapError: errors.New("scan failed"),
|
|
expectedErr: errors.New("error while scanning network: scan failed"),
|
|
},
|
|
}
|
|
|
|
for _, test := range tests {
|
|
t.Run(test.description, func(t *testing.T) {
|
|
nmapMock := &nmapMock{}
|
|
|
|
nmapMock.On("Run").Return(test.nmapResult, test.nmapError)
|
|
|
|
scanner := &Scanner{
|
|
term: disgo.NewTerminal(disgo.WithDefaultOutput(ioutil.Discard)),
|
|
}
|
|
|
|
results, err := scanner.scan(nmapMock)
|
|
|
|
assert.Equal(t, test.expectedErr, err)
|
|
assert.Equal(t, test.expectedStreams, results, "wrong streams parsed")
|
|
assert.Equal(t, len(test.expectedStreams), len(results), "wrong streams parsed")
|
|
|
|
nmapMock.AssertExpectations(t)
|
|
})
|
|
}
|
|
}
|