2021-09-10 19:26:39 +00:00
|
|
|
package main
|
|
|
|
|
|
|
|
import (
|
2021-09-14 12:11:07 +00:00
|
|
|
"context"
|
Add read replica testing helpers and fix non-sso login bug (#4908)
not set on the INSERT.
- OUT: Only sets the ID on the passed session and returns it. (`CreatedAt`, `AccessedAt`, are not set.)
New version:
```go
func (ds *Datastore) NewSession(ctx context.Context, userID uint, sessionKey string) (*fleet.Session, error) {
sqlStatement := `
INSERT INTO sessions (
user_id,
` + "`key`" + `
)
VALUES(?,?)
`
result, err := ds.writer.ExecContext(ctx, sqlStatement, userID, sessionKey)
if err != nil {
return nil, ctxerr.Wrap(ctx, err, "inserting session")
}
id, _ := result.LastInsertId() // cannot fail with the mysql driver
return ds.sessionByID(ctx, ds.writer, uint(id))
}
```
- IN: Define arguments that are truly used when creating a session.
- OUT: Load and return the fleet.Session struct with all values set (using the `ds.writer` to support read replicas correctly).
PS: The new `NewSession` version mimics what we already do with other entities, like policies (`Datastore.NewGlobalPolicy`).
2022-04-04 23:52:05 +00:00
|
|
|
"os"
|
2021-09-10 19:26:39 +00:00
|
|
|
"testing"
|
|
|
|
"time"
|
|
|
|
|
|
|
|
"github.com/fleetdm/fleet/v4/server/fleet"
|
|
|
|
"github.com/fleetdm/fleet/v4/server/live_query"
|
|
|
|
"github.com/fleetdm/fleet/v4/server/pubsub"
|
|
|
|
"github.com/fleetdm/fleet/v4/server/service"
|
Add read replica testing helpers and fix non-sso login bug (#4908)
not set on the INSERT.
- OUT: Only sets the ID on the passed session and returns it. (`CreatedAt`, `AccessedAt`, are not set.)
New version:
```go
func (ds *Datastore) NewSession(ctx context.Context, userID uint, sessionKey string) (*fleet.Session, error) {
sqlStatement := `
INSERT INTO sessions (
user_id,
` + "`key`" + `
)
VALUES(?,?)
`
result, err := ds.writer.ExecContext(ctx, sqlStatement, userID, sessionKey)
if err != nil {
return nil, ctxerr.Wrap(ctx, err, "inserting session")
}
id, _ := result.LastInsertId() // cannot fail with the mysql driver
return ds.sessionByID(ctx, ds.writer, uint(id))
}
```
- IN: Define arguments that are truly used when creating a session.
- OUT: Load and return the fleet.Session struct with all values set (using the `ds.writer` to support read replicas correctly).
PS: The new `NewSession` version mimics what we already do with other entities, like policies (`Datastore.NewGlobalPolicy`).
2022-04-04 23:52:05 +00:00
|
|
|
kitlog "github.com/go-kit/kit/log"
|
|
|
|
"github.com/go-kit/kit/log/level"
|
2021-09-10 19:26:39 +00:00
|
|
|
"github.com/stretchr/testify/assert"
|
|
|
|
"github.com/stretchr/testify/require"
|
|
|
|
)
|
|
|
|
|
|
|
|
func TestLiveQuery(t *testing.T) {
|
|
|
|
rs := pubsub.NewInmemQueryResults()
|
|
|
|
lq := new(live_query.MockLiveQuery)
|
Add read replica testing helpers and fix non-sso login bug (#4908)
not set on the INSERT.
- OUT: Only sets the ID on the passed session and returns it. (`CreatedAt`, `AccessedAt`, are not set.)
New version:
```go
func (ds *Datastore) NewSession(ctx context.Context, userID uint, sessionKey string) (*fleet.Session, error) {
sqlStatement := `
INSERT INTO sessions (
user_id,
` + "`key`" + `
)
VALUES(?,?)
`
result, err := ds.writer.ExecContext(ctx, sqlStatement, userID, sessionKey)
if err != nil {
return nil, ctxerr.Wrap(ctx, err, "inserting session")
}
id, _ := result.LastInsertId() // cannot fail with the mysql driver
return ds.sessionByID(ctx, ds.writer, uint(id))
}
```
- IN: Define arguments that are truly used when creating a session.
- OUT: Load and return the fleet.Session struct with all values set (using the `ds.writer` to support read replicas correctly).
PS: The new `NewSession` version mimics what we already do with other entities, like policies (`Datastore.NewGlobalPolicy`).
2022-04-04 23:52:05 +00:00
|
|
|
|
|
|
|
logger := kitlog.NewJSONLogger(os.Stdout)
|
|
|
|
logger = level.NewFilter(logger, level.AllowDebug())
|
|
|
|
|
2022-05-10 15:29:17 +00:00
|
|
|
_, ds := runServerWithMockedDS(t, &service.TestServerOpts{
|
Add read replica testing helpers and fix non-sso login bug (#4908)
not set on the INSERT.
- OUT: Only sets the ID on the passed session and returns it. (`CreatedAt`, `AccessedAt`, are not set.)
New version:
```go
func (ds *Datastore) NewSession(ctx context.Context, userID uint, sessionKey string) (*fleet.Session, error) {
sqlStatement := `
INSERT INTO sessions (
user_id,
` + "`key`" + `
)
VALUES(?,?)
`
result, err := ds.writer.ExecContext(ctx, sqlStatement, userID, sessionKey)
if err != nil {
return nil, ctxerr.Wrap(ctx, err, "inserting session")
}
id, _ := result.LastInsertId() // cannot fail with the mysql driver
return ds.sessionByID(ctx, ds.writer, uint(id))
}
```
- IN: Define arguments that are truly used when creating a session.
- OUT: Load and return the fleet.Session struct with all values set (using the `ds.writer` to support read replicas correctly).
PS: The new `NewSession` version mimics what we already do with other entities, like policies (`Datastore.NewGlobalPolicy`).
2022-04-04 23:52:05 +00:00
|
|
|
Rs: rs,
|
|
|
|
Lq: lq,
|
|
|
|
Logger: logger,
|
|
|
|
})
|
|
|
|
|
|
|
|
users, err := ds.ListUsersFunc(context.Background(), fleet.UserListOptions{})
|
|
|
|
require.NoError(t, err)
|
|
|
|
var admin *fleet.User
|
|
|
|
for _, user := range users {
|
|
|
|
if user.GlobalRole != nil && *user.GlobalRole == fleet.RoleAdmin {
|
|
|
|
admin = user
|
|
|
|
}
|
|
|
|
}
|
2021-09-10 19:26:39 +00:00
|
|
|
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.HostIDsByNameFunc = func(ctx context.Context, filter fleet.TeamFilter, hostnames []string) ([]uint, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return []uint{1234}, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.LabelIDsByNameFunc = func(ctx context.Context, labels []string) ([]uint, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return nil, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.AppConfigFunc = func(ctx context.Context) (*fleet.AppConfig, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return &fleet.AppConfig{}, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.NewQueryFunc = func(ctx context.Context, query *fleet.Query, opts ...fleet.OptionalArg) (*fleet.Query, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
query.ID = 42
|
|
|
|
return query, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.NewDistributedQueryCampaignFunc = func(ctx context.Context, camp *fleet.DistributedQueryCampaign) (*fleet.DistributedQueryCampaign, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
camp.ID = 321
|
|
|
|
return camp, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.NewDistributedQueryCampaignTargetFunc = func(ctx context.Context, target *fleet.DistributedQueryCampaignTarget) (*fleet.DistributedQueryCampaignTarget, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return target, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.HostIDsInTargetsFunc = func(ctx context.Context, filter fleet.TeamFilter, targets fleet.HostTargets) ([]uint, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return []uint{1}, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.CountHostsInTargetsFunc = func(ctx context.Context, filter fleet.TeamFilter, targets fleet.HostTargets, now time.Time) (fleet.TargetMetrics, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return fleet.TargetMetrics{TotalHosts: 1, OnlineHosts: 1}, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.NewActivityFunc = func(ctx context.Context, user *fleet.User, activityType string, details *map[string]interface{}) error {
|
2021-09-10 19:26:39 +00:00
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
lq.On("QueriesForHost", uint(1)).Return(
|
|
|
|
map[string]string{
|
|
|
|
"42": "select 42, * from time",
|
|
|
|
},
|
|
|
|
nil,
|
|
|
|
)
|
|
|
|
lq.On("QueryCompletedByHost", "42", 99).Return(nil)
|
|
|
|
lq.On("RunQuery", "321", "select 42, * from time", []uint{1}).Return(nil)
|
|
|
|
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.DistributedQueryCampaignTargetIDsFunc = func(ctx context.Context, id uint) (targets *fleet.HostTargets, err error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return &fleet.HostTargets{HostIDs: []uint{99}}, nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.DistributedQueryCampaignFunc = func(ctx context.Context, id uint) (*fleet.DistributedQueryCampaign, error) {
|
Add read replica testing helpers and fix non-sso login bug (#4908)
not set on the INSERT.
- OUT: Only sets the ID on the passed session and returns it. (`CreatedAt`, `AccessedAt`, are not set.)
New version:
```go
func (ds *Datastore) NewSession(ctx context.Context, userID uint, sessionKey string) (*fleet.Session, error) {
sqlStatement := `
INSERT INTO sessions (
user_id,
` + "`key`" + `
)
VALUES(?,?)
`
result, err := ds.writer.ExecContext(ctx, sqlStatement, userID, sessionKey)
if err != nil {
return nil, ctxerr.Wrap(ctx, err, "inserting session")
}
id, _ := result.LastInsertId() // cannot fail with the mysql driver
return ds.sessionByID(ctx, ds.writer, uint(id))
}
```
- IN: Define arguments that are truly used when creating a session.
- OUT: Load and return the fleet.Session struct with all values set (using the `ds.writer` to support read replicas correctly).
PS: The new `NewSession` version mimics what we already do with other entities, like policies (`Datastore.NewGlobalPolicy`).
2022-04-04 23:52:05 +00:00
|
|
|
return &fleet.DistributedQueryCampaign{
|
|
|
|
ID: 321,
|
|
|
|
UserID: admin.ID,
|
|
|
|
}, nil
|
2021-09-10 19:26:39 +00:00
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.SaveDistributedQueryCampaignFunc = func(ctx context.Context, camp *fleet.DistributedQueryCampaign) error {
|
2021-09-10 19:26:39 +00:00
|
|
|
return nil
|
|
|
|
}
|
2021-09-14 12:11:07 +00:00
|
|
|
ds.QueryFunc = func(ctx context.Context, id uint) (*fleet.Query, error) {
|
2021-09-10 19:26:39 +00:00
|
|
|
return &fleet.Query{}, nil
|
|
|
|
}
|
|
|
|
|
|
|
|
go func() {
|
|
|
|
time.Sleep(2 * time.Second)
|
|
|
|
require.NoError(t, rs.WriteResult(
|
|
|
|
fleet.DistributedQueryResult{
|
|
|
|
DistributedQueryCampaignID: 321,
|
|
|
|
Rows: []map[string]string{{"bing": "fds"}},
|
|
|
|
Host: fleet.Host{
|
|
|
|
ID: 99,
|
|
|
|
UpdateCreateTimestamps: fleet.UpdateCreateTimestamps{
|
|
|
|
UpdateTimestamp: fleet.UpdateTimestamp{
|
|
|
|
UpdatedAt: time.Now().UTC(),
|
|
|
|
},
|
|
|
|
},
|
|
|
|
DetailUpdatedAt: time.Now().UTC(),
|
|
|
|
Hostname: "somehostname",
|
|
|
|
},
|
|
|
|
},
|
|
|
|
))
|
|
|
|
}()
|
|
|
|
|
|
|
|
expected := `{"host":"somehostname","rows":[{"bing":"fds","host_hostname":"somehostname"}]}
|
|
|
|
`
|
|
|
|
assert.Equal(t, expected, runAppForTest(t, []string{"query", "--hosts", "1234", "--query", "select 42, * from time"}))
|
|
|
|
}
|