Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

run osq runtime tests on windows #1665

Merged
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions pkg/osquery/runtime/osqueryinstance.go
Original file line number Diff line number Diff line change
Expand Up @@ -592,6 +592,13 @@ func (o *OsqueryInstance) StartOsqueryExtensionManagerServer(name string, socket
"err", err,
"extension_name", name,
)
// PR Note, remove after test working
// On windows, during test this always returns error
// "status 1 registering extension: Failed adding registry: SQLITE_CANTOPEN"
// the source of the error is in osquery-go code
// https://github.com/osquery/osquery-go/blob/master/server.go#L217
// coming out of
// https://github.com/osquery/osquery-go/blob/master/gen/osquery/osquery.go#L2225
return fmt.Errorf("running extension server: %w", err)
}
return errors.New("extension manager server exited")
Expand Down
131 changes: 131 additions & 0 deletions pkg/osquery/runtime/runtime_all_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,131 @@
package runtime

import (
"context"
"fmt"
"os"
"path/filepath"
"runtime"
"testing"
"time"

"github.com/apache/thrift/lib/go/thrift"
"github.com/kolide/kit/fsutil"
"github.com/kolide/launcher/ee/agent/storage"
storageci "github.com/kolide/launcher/ee/agent/storage/ci"
typesMocks "github.com/kolide/launcher/ee/agent/types/mocks"
"github.com/kolide/launcher/pkg/backoff"
"github.com/kolide/launcher/pkg/log/multislogger"
"github.com/kolide/launcher/pkg/osquery/runtime/history"
"github.com/kolide/launcher/pkg/packaging"

"github.com/stretchr/testify/mock"
"github.com/stretchr/testify/require"
)

var testOsqueryBinaryDirectory string

// TestMain overrides the default test main function. This allows us to share setup/teardown.
func TestMain(m *testing.M) {
binDirectory, rmBinDirectory, err := osqueryTempDir()
if err != nil {
fmt.Println("Failed to make temp dir for test binaries")
os.Exit(1)
}
defer rmBinDirectory()

s, err := storageci.NewStore(nil, multislogger.NewNopLogger(), storage.OsqueryHistoryInstanceStore.String())
if err != nil {
fmt.Println("Failed to make new store")
os.Exit(1)
}
if err := history.InitHistory(s); err != nil {
fmt.Println("Failed to init history")
os.Exit(1)
}

testOsqueryBinaryDirectory = filepath.Join(binDirectory, "osqueryd")

thrift.ServerConnectivityCheckInterval = 100 * time.Millisecond

if err := downloadOsqueryInBinDir(binDirectory); err != nil {
fmt.Printf("Failed to download osquery: %v\n", err)
os.Exit(1)
}

// Run the tests!
retCode := m.Run()
os.Exit(retCode)
}

// downloadOsqueryInBinDir downloads osqueryd. This allows the test
// suite to run on hosts lacking osqueryd. We could consider moving this into a deps step.
func downloadOsqueryInBinDir(binDirectory string) error {
target := packaging.Target{}
if err := target.PlatformFromString(runtime.GOOS); err != nil {
return fmt.Errorf("Error parsing platform: %s: %w", runtime.GOOS, err)
}

outputFile := filepath.Join(binDirectory, "osqueryd")
if runtime.GOOS == "windows" {
outputFile += ".exe"
}

cacheDir := "/tmp"
if runtime.GOOS == "windows" {
cacheDir = os.Getenv("TEMP")
}

path, err := packaging.FetchBinary(context.TODO(), cacheDir, "osqueryd", target.PlatformBinaryName("osqueryd"), "stable", target)
if err != nil {
return fmt.Errorf("An error occurred fetching the osqueryd binary: %w", err)
}

if err := fsutil.CopyFile(path, outputFile); err != nil {
return fmt.Errorf("Couldn't copy file to %s: %w", outputFile, err)
}

return nil
}

// waitHealthy expects the instance to be healthy within 30 seconds, or else
// fatals the test
func waitHealthy(t *testing.T, runner *Runner) {
require.NoError(t, backoff.WaitFor(func() error {
if runner.Healthy() == nil {
return nil
}
return fmt.Errorf("instance not healthy")
}, 120*time.Second, 5*time.Second))
}

func TestSimplePath(t *testing.T) {
t.Parallel()
rootDirectory, rmRootDirectory, err := osqueryTempDir()
require.NoError(t, err)
defer rmRootDirectory()

k := typesMocks.NewKnapsack(t)
k.On("OsqueryHealthcheckStartupDelay").Return(0 * time.Second).Maybe()
k.On("WatchdogEnabled").Return(false)
k.On("RegisterChangeObserver", mock.Anything, mock.Anything, mock.Anything, mock.Anything, mock.Anything)
k.On("Slogger").Return(multislogger.NewNopLogger())
k.On("PinnedOsquerydVersion").Return("")

runner := New(
k,
WithKnapsack(k),
WithRootDirectory(rootDirectory),
WithOsquerydBinary(testOsqueryBinaryDirectory),
)

go runner.Run()

// never gets health on windows
waitHealthy(t, runner)

require.NotEmpty(t, runner.instance.stats.StartTime, "start time should be added to instance stats on start up")
require.NotEmpty(t, runner.instance.stats.ConnectTime, "connect time should be added to instance stats on start up")

require.NoError(t, runner.Shutdown())
}
106 changes: 0 additions & 106 deletions pkg/osquery/runtime/runtime_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,29 +4,20 @@
package runtime

import (
"context"
"errors"
"fmt"
"log/slog"
"os"
"os/exec"
"path/filepath"
"runtime"
"strings"
"syscall"
"testing"
"time"

"github.com/apache/thrift/lib/go/thrift"
"github.com/kolide/kit/fsutil"
"github.com/kolide/kit/testutil"
"github.com/kolide/launcher/ee/agent/flags/keys"
"github.com/kolide/launcher/ee/agent/storage"
storageci "github.com/kolide/launcher/ee/agent/storage/ci"
typesMocks "github.com/kolide/launcher/ee/agent/types/mocks"
"github.com/kolide/launcher/pkg/log/multislogger"
"github.com/kolide/launcher/pkg/osquery/runtime/history"
"github.com/kolide/launcher/pkg/packaging"
"github.com/kolide/launcher/pkg/threadsafebuffer"
osquery "github.com/osquery/osquery-go"

Expand All @@ -35,41 +26,6 @@ import (
"github.com/stretchr/testify/require"
)

var testOsqueryBinaryDirectory string

// TestMain overrides the default test main function. This allows us to share setup/teardown.
func TestMain(m *testing.M) {
binDirectory, rmBinDirectory, err := osqueryTempDir()
if err != nil {
fmt.Println("Failed to make temp dir for test binaries")
os.Exit(1)
}
defer rmBinDirectory()

s, err := storageci.NewStore(nil, multislogger.NewNopLogger(), storage.OsqueryHistoryInstanceStore.String())
if err != nil {
fmt.Println("Failed to make new store")
os.Exit(1)
}
if err := history.InitHistory(s); err != nil {
fmt.Println("Failed to init history")
os.Exit(1)
}

testOsqueryBinaryDirectory = filepath.Join(binDirectory, "osqueryd")

thrift.ServerConnectivityCheckInterval = 100 * time.Millisecond

if err := downloadOsqueryInBinDir(binDirectory); err != nil {
fmt.Printf("Failed to download osquery: %v\n", err)
os.Exit(1)
}

// Run the tests!
retCode := m.Run()
os.Exit(retCode)
}

// getBinDir finds the directory of the currently running binary (where we will
// look for the osquery extension)
func getBinDir() (string, error) {
Expand Down Expand Up @@ -266,29 +222,6 @@ func TestCreateOsqueryCommand_SetsDisabledWatchdogSettingsAppropriately(t *testi
k.AssertExpectations(t)
}

// downloadOsqueryInBinDir downloads osqueryd. This allows the test
// suite to run on hosts lacking osqueryd. We could consider moving this into a deps step.
func downloadOsqueryInBinDir(binDirectory string) error {
target := packaging.Target{}
if err := target.PlatformFromString(runtime.GOOS); err != nil {
return fmt.Errorf("Error parsing platform: %s: %w", runtime.GOOS, err)
}

outputFile := filepath.Join(binDirectory, "osqueryd")
cacheDir := "/tmp"

path, err := packaging.FetchBinary(context.TODO(), cacheDir, "osqueryd", target.PlatformBinaryName("osqueryd"), "stable", target)
if err != nil {
return fmt.Errorf("An error occurred fetching the osqueryd binary: %w", err)
}

if err := fsutil.CopyFile(path, outputFile); err != nil {
return fmt.Errorf("Couldn't copy file to %s: %w", outputFile, err)
}

return nil
}

func TestBadBinaryPath(t *testing.T) {
t.Parallel()
rootDirectory, rmRootDirectory, err := osqueryTempDir()
Expand Down Expand Up @@ -429,45 +362,6 @@ func TestFlagsChanged(t *testing.T) {
runner.Interrupt(errors.New("test error"))
}

// waitHealthy expects the instance to be healthy within 30 seconds, or else
// fatals the test
func waitHealthy(t *testing.T, runner *Runner) {
testutil.FatalAfterFunc(t, 30*time.Second, func() {
for runner.Healthy() != nil {
time.Sleep(500 * time.Millisecond)
}
})
}

func TestSimplePath(t *testing.T) {
t.Parallel()
rootDirectory, rmRootDirectory, err := osqueryTempDir()
require.NoError(t, err)
defer rmRootDirectory()

k := typesMocks.NewKnapsack(t)
k.On("OsqueryHealthcheckStartupDelay").Return(0 * time.Second).Maybe()
k.On("WatchdogEnabled").Return(false)
k.On("RegisterChangeObserver", mock.Anything, mock.Anything, mock.Anything, mock.Anything, mock.Anything)
k.On("Slogger").Return(multislogger.NewNopLogger())
k.On("PinnedOsquerydVersion").Return("")

runner := New(
k,
WithKnapsack(k),
WithRootDirectory(rootDirectory),
WithOsquerydBinary(testOsqueryBinaryDirectory),
)
go runner.Run()

waitHealthy(t, runner)

require.NotEmpty(t, runner.instance.stats.StartTime, "start time should be added to instance stats on start up")
require.NotEmpty(t, runner.instance.stats.ConnectTime, "connect time should be added to instance stats on start up")

require.NoError(t, runner.Shutdown())
}

func TestMultipleShutdowns(t *testing.T) {
t.Parallel()
rootDirectory, rmRootDirectory, err := osqueryTempDir()
Expand Down
Loading