-
Notifications
You must be signed in to change notification settings - Fork 63
/
test_server.go
96 lines (77 loc) · 3.72 KB
/
test_server.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
package test
import (
"context"
"database/sql"
"testing"
"allaboutapps.dev/aw/go-starter/internal/api"
"allaboutapps.dev/aw/go-starter/internal/api/router"
"allaboutapps.dev/aw/go-starter/internal/config"
)
// WithTestServer returns a fully configured server (using the default server config).
func WithTestServer(t *testing.T, closure func(s *api.Server)) {
t.Helper()
defaultConfig := config.DefaultServiceConfigFromEnv()
WithTestServerConfigurable(t, defaultConfig, closure)
}
// WithTestServerFromDump returns a fully configured server (using the default server config) and allows for a database dump to be injected.
func WithTestServerFromDump(t *testing.T, dumpConfig DatabaseDumpConfig, closure func(s *api.Server)) {
t.Helper()
defaultConfig := config.DefaultServiceConfigFromEnv()
WithTestServerConfigurableFromDump(t, defaultConfig, dumpConfig, closure)
}
// WithTestServerConfigurable returns a fully configured server, allowing for configuration using the provided server config.
func WithTestServerConfigurable(t *testing.T, config config.Server, closure func(s *api.Server)) {
t.Helper()
ctx := context.Background()
WithTestServerConfigurableContext(ctx, t, config, closure)
}
// WithTestServerConfigurableContext returns a fully configured server, allowing for configuration using the provided server config.
// The provided context will be used during setup (instead of the default background context).
func WithTestServerConfigurableContext(ctx context.Context, t *testing.T, config config.Server, closure func(s *api.Server)) {
t.Helper()
WithTestDatabaseContext(ctx, t, func(db *sql.DB) {
t.Helper()
execClosureNewTestServer(ctx, t, config, db, closure)
})
}
// WithTestServerConfigurableFromDump returns a fully configured server, allowing for configuration using the provided server config and a database dump to be injected.
func WithTestServerConfigurableFromDump(t *testing.T, config config.Server, dumpConfig DatabaseDumpConfig, closure func(s *api.Server)) {
t.Helper()
ctx := context.Background()
WithTestServerConfigurableFromDumpContext(ctx, t, config, dumpConfig, closure)
}
// WithTestServerConfigurableFromDumpContext returns a fully configured server, allowing for configuration using the provided server config and a database dump to be injected.
// The provided context will be used during setup (instead of the default background context).
func WithTestServerConfigurableFromDumpContext(ctx context.Context, t *testing.T, config config.Server, dumpConfig DatabaseDumpConfig, closure func(s *api.Server)) {
t.Helper()
WithTestDatabaseFromDump(t, dumpConfig, func(db *sql.DB) {
t.Helper()
execClosureNewTestServer(ctx, t, config, db, closure)
})
}
// Executes closure on a new test server with a pre-provided database
func execClosureNewTestServer(ctx context.Context, t *testing.T, config config.Server, db *sql.DB, closure func(s *api.Server)) {
t.Helper()
// https://stackoverflow.com/questions/43424787/how-to-use-next-available-port-in-http-listenandserve
// You may use port 0 to indicate you're not specifying an exact port but you want a free, available port selected by the system
config.Echo.ListenAddress = ":0"
s := api.NewServer(config)
// attach the already initialized db
s.DB = db
if err := s.InitMailer(); err != nil {
t.Fatalf("Failed to init mailer: %v", err)
}
// attach any other mocks
s.Push = NewTestPusher(t, db)
if err := s.InitI18n(); err != nil {
t.Fatalf("Failed to init i18n service: %v", err)
}
router.Init(s)
closure(s)
// echo is managed and should close automatically after running the test
if err := s.Echo.Shutdown(ctx); err != nil {
t.Fatalf("failed to shutdown server: %v", err)
}
// disallow any further refs to managed object after running the test
s = nil
}