Skip to content

Commit d7cc0ff

Browse files
committed
Update sql
1 parent c3786a5 commit d7cc0ff

File tree

11 files changed

+124
-37
lines changed

11 files changed

+124
-37
lines changed

cli/server.go

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -165,9 +165,10 @@ func Server(dflags *codersdk.DeploymentFlags, newAPI func(context.Context, *code
165165
}
166166
defer listener.Close()
167167

168+
var tlsConfig *tls.Config
168169
if dflags.TLSEnable.Value {
169-
listener, err = configureServerTLS(
170-
listener, dflags.TLSMinVersion.Value,
170+
tlsConfig, err = configureTLS(
171+
dflags.TLSMinVersion.Value,
171172
dflags.TLSClientAuth.Value,
172173
dflags.TLSCertFiles.Value,
173174
dflags.TLSKeyFiles.Value,
@@ -176,6 +177,7 @@ func Server(dflags *codersdk.DeploymentFlags, newAPI func(context.Context, *code
176177
if err != nil {
177178
return xerrors.Errorf("configure tls: %w", err)
178179
}
180+
listener = tls.NewListener(listener, tlsConfig)
179181
}
180182

181183
tcpAddr, valid := listener.Addr().(*net.TCPAddr)
@@ -888,7 +890,7 @@ func loadCertificates(tlsCertFiles, tlsKeyFiles []string) ([]tls.Certificate, er
888890
return certs, nil
889891
}
890892

891-
func configureServerTLS(listener net.Listener, tlsMinVersion, tlsClientAuth string, tlsCertFiles, tlsKeyFiles []string, tlsClientCAFile string) (net.Listener, error) {
893+
func configureTLS(tlsMinVersion, tlsClientAuth string, tlsCertFiles, tlsKeyFiles []string, tlsClientCAFile string) (*tls.Config, error) {
892894
tlsConfig := &tls.Config{
893895
MinVersion: tls.VersionTLS12,
894896
}
@@ -958,7 +960,7 @@ func configureServerTLS(listener net.Listener, tlsMinVersion, tlsClientAuth stri
958960
tlsConfig.ClientCAs = caPool
959961
}
960962

961-
return tls.NewListener(listener, tlsConfig), nil
963+
return tlsConfig, nil
962964
}
963965

964966
func configureGithubOAuth2(accessURL *url.URL, clientID, clientSecret string, allowSignups bool, allowOrgs []string, rawTeams []string, enterpriseBaseURL string) (*coderd.GithubOAuth2Config, error) {

codersdk/features.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@ type Feature struct {
4444
type Entitlements struct {
4545
Features map[string]Feature `json:"features"`
4646
Warnings []string `json:"warnings"`
47+
Errors []string `json:"errors"`
4748
HasLicense bool `json:"has_license"`
4849
Experimental bool `json:"experimental"`
4950
Trial bool `json:"trial"`

enterprise/coderd/coderd.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -137,7 +137,7 @@ func New(ctx context.Context, options *Options) (*API, error) {
137137
if err != nil {
138138
return nil, xerrors.Errorf("initialize replica: %w", err)
139139
}
140-
api.derpMesh = derpmesh.New(options.Logger.Named("derpmesh"), api.DERPServer)
140+
api.derpMesh = derpmesh.New(options.Logger.Named("derpmesh"), api.DERPServer, nil)
141141

142142
err = api.updateEntitlements(ctx)
143143
if err != nil {

enterprise/coderd/license/license.go

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@ func Entitlements(
3030
entitlements := codersdk.Entitlements{
3131
Features: map[string]codersdk.Feature{},
3232
Warnings: []string{},
33+
Errors: []string{},
3334
}
3435
for _, featureName := range codersdk.FeatureNames {
3536
entitlements.Features[featureName] = codersdk.Feature{
@@ -172,15 +173,15 @@ func Entitlements(
172173
switch feature.Entitlement {
173174
case codersdk.EntitlementNotEntitled:
174175
if entitlements.HasLicense {
175-
entitlements.Warnings = append(entitlements.Warnings,
176-
"You have multiple replicas but your license is not entitled to high availability.")
176+
entitlements.Errors = append(entitlements.Warnings,
177+
"You have multiple replicas but your license is not entitled to high availability. You will be unable to connect to workspaces.")
177178
} else {
178-
entitlements.Warnings = append(entitlements.Warnings,
179-
"You have multiple replicas but high availability is an Enterprise feature.")
179+
entitlements.Errors = append(entitlements.Warnings,
180+
"You have multiple replicas but high availability is an Enterprise feature. You will be unable to connect to workspaces.")
180181
}
181182
case codersdk.EntitlementGracePeriod:
182183
entitlements.Warnings = append(entitlements.Warnings,
183-
"You have multiple replicas but your license for high availability is expired.")
184+
"You have multiple replicas but your license for high availability is expired. Reduce to one replica or workspace connections will stop working.")
184185
}
185186
}
186187

enterprise/coderd/license/license_test.go

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -227,8 +227,8 @@ func TestEntitlements(t *testing.T) {
227227
entitlements, err := license.Entitlements(context.Background(), db, slog.Logger{}, 2, coderdenttest.Keys, all)
228228
require.NoError(t, err)
229229
require.False(t, entitlements.HasLicense)
230-
require.Len(t, entitlements.Warnings, 1)
231-
require.Equal(t, "You have multiple replicas but high availability is an Enterprise feature.", entitlements.Warnings[0])
230+
require.Len(t, entitlements.Errors, 1)
231+
require.Equal(t, "You have multiple replicas but high availability is an Enterprise feature. You will be unable to connect to workspaces.", entitlements.Errors[0])
232232
})
233233

234234
t.Run("MultipleReplicasNotEntitled", func(t *testing.T) {
@@ -245,8 +245,8 @@ func TestEntitlements(t *testing.T) {
245245
})
246246
require.NoError(t, err)
247247
require.True(t, entitlements.HasLicense)
248-
require.Len(t, entitlements.Warnings, 1)
249-
require.Equal(t, "You have multiple replicas but your license is not entitled to high availability.", entitlements.Warnings[0])
248+
require.Len(t, entitlements.Errors, 1)
249+
require.Equal(t, "You have multiple replicas but your license is not entitled to high availability. You will be unable to connect to workspaces.", entitlements.Errors[0])
250250
})
251251

252252
t.Run("MultipleReplicasGrace", func(t *testing.T) {
@@ -266,6 +266,6 @@ func TestEntitlements(t *testing.T) {
266266
require.NoError(t, err)
267267
require.True(t, entitlements.HasLicense)
268268
require.Len(t, entitlements.Warnings, 1)
269-
require.Equal(t, "You have multiple replicas but your license for high availability is expired.", entitlements.Warnings[0])
269+
require.Equal(t, "You have multiple replicas but your license for high availability is expired. Reduce to one replica or workspace connections will stop working.", entitlements.Warnings[0])
270270
})
271271
}

enterprise/derpmesh/derpmesh.go

Lines changed: 13 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@ package derpmesh
22

33
import (
44
"context"
5+
"crypto/tls"
56
"net"
67
"net/url"
78
"sync"
@@ -17,20 +18,22 @@ import (
1718
)
1819

1920
// New constructs a new mesh for DERP servers.
20-
func New(logger slog.Logger, server *derp.Server) *Mesh {
21+
func New(logger slog.Logger, server *derp.Server, tlsConfig *tls.Config) *Mesh {
2122
return &Mesh{
22-
logger: logger,
23-
server: server,
24-
ctx: context.Background(),
25-
closed: make(chan struct{}),
26-
active: make(map[string]context.CancelFunc),
23+
logger: logger,
24+
server: server,
25+
tlsConfig: tlsConfig,
26+
ctx: context.Background(),
27+
closed: make(chan struct{}),
28+
active: make(map[string]context.CancelFunc),
2729
}
2830
}
2931

3032
type Mesh struct {
31-
logger slog.Logger
32-
server *derp.Server
33-
ctx context.Context
33+
logger slog.Logger
34+
server *derp.Server
35+
ctx context.Context
36+
tlsConfig *tls.Config
3437

3538
mutex sync.Mutex
3639
closed chan struct{}
@@ -93,6 +96,7 @@ func (m *Mesh) addAddress(address string) (bool, error) {
9396
if err != nil {
9497
return false, xerrors.Errorf("create derp client: %w", err)
9598
}
99+
client.TLSConfig = m.tlsConfig
96100
client.MeshKey = m.server.MeshKey()
97101
client.SetURLDialer(func(ctx context.Context, network, addr string) (net.Conn, error) {
98102
var dialer net.Dialer

enterprise/derpmesh/derpmesh_test.go

Lines changed: 89 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,22 @@
11
package derpmesh_test
22

33
import (
4+
"bytes"
45
"context"
6+
"crypto/ecdsa"
7+
"crypto/elliptic"
8+
"crypto/rand"
9+
"crypto/tls"
10+
"crypto/x509"
11+
"crypto/x509/pkix"
12+
"encoding/pem"
513
"errors"
614
"io"
15+
"math/big"
16+
"net"
717
"net/http/httptest"
818
"testing"
19+
"time"
920

1021
"github.com/stretchr/testify/assert"
1122
"github.com/stretchr/testify/require"
@@ -29,12 +40,41 @@ func TestDERPMesh(t *testing.T) {
2940
t.Run("ExchangeMessages", func(t *testing.T) {
3041
// This tests messages passing through multiple DERP servers.
3142
t.Parallel()
32-
firstServer, firstServerURL := startDERP(t)
43+
firstServer, firstServerURL, firstTLSName := startDERP(t)
3344
defer firstServer.Close()
34-
secondServer, secondServerURL := startDERP(t)
35-
firstMesh := derpmesh.New(slogtest.Make(t, nil).Named("first").Leveled(slog.LevelDebug), firstServer)
45+
secondServer, secondServerURL, secondTLSName := startDERP(t)
46+
firstMesh := derpmesh.New(slogtest.Make(t, nil).Named("first").Leveled(slog.LevelDebug), firstServer, firstTLSName)
3647
firstMesh.SetAddresses([]string{secondServerURL})
37-
secondMesh := derpmesh.New(slogtest.Make(t, nil).Named("second").Leveled(slog.LevelDebug), secondServer)
48+
secondMesh := derpmesh.New(slogtest.Make(t, nil).Named("second").Leveled(slog.LevelDebug), secondServer, secondTLSName)
49+
secondMesh.SetAddresses([]string{firstServerURL})
50+
defer firstMesh.Close()
51+
defer secondMesh.Close()
52+
53+
first := key.NewNode()
54+
second := key.NewNode()
55+
firstClient, err := derphttp.NewClient(first, secondServerURL, tailnet.Logger(slogtest.Make(t, nil)))
56+
require.NoError(t, err)
57+
secondClient, err := derphttp.NewClient(second, firstServerURL, tailnet.Logger(slogtest.Make(t, nil)))
58+
require.NoError(t, err)
59+
err = secondClient.Connect(context.Background())
60+
require.NoError(t, err)
61+
62+
sent := []byte("hello world")
63+
err = firstClient.Send(second.Public(), sent)
64+
require.NoError(t, err)
65+
66+
got := recvData(t, secondClient)
67+
require.Equal(t, sent, got)
68+
})
69+
t.Run("ExchangeMessages", func(t *testing.T) {
70+
// This tests messages passing through multiple DERP servers.
71+
t.Parallel()
72+
firstServer, firstServerURL, firstTLSName := startDERP(t)
73+
defer firstServer.Close()
74+
secondServer, secondServerURL, secondTLSName := startDERP(t)
75+
firstMesh := derpmesh.New(slogtest.Make(t, nil).Named("first").Leveled(slog.LevelDebug), firstServer, firstTLSName)
76+
firstMesh.SetAddresses([]string{secondServerURL})
77+
secondMesh := derpmesh.New(slogtest.Make(t, nil).Named("second").Leveled(slog.LevelDebug), secondServer, secondTLSName)
3878
secondMesh.SetAddresses([]string{firstServerURL})
3979
defer firstMesh.Close()
4080
defer secondMesh.Close()
@@ -58,8 +98,8 @@ func TestDERPMesh(t *testing.T) {
5898
t.Run("RemoveAddress", func(t *testing.T) {
5999
// This tests messages passing through multiple DERP servers.
60100
t.Parallel()
61-
server, serverURL := startDERP(t)
62-
mesh := derpmesh.New(slogtest.Make(t, nil).Named("first").Leveled(slog.LevelDebug), server)
101+
server, serverURL, tlsName := startDERP(t)
102+
mesh := derpmesh.New(slogtest.Make(t, nil).Named("first").Leveled(slog.LevelDebug), server, tlsName)
63103
mesh.SetAddresses([]string{"http://fake.com"})
64104
// This should trigger a removal...
65105
mesh.SetAddresses([]string{})
@@ -84,8 +124,8 @@ func TestDERPMesh(t *testing.T) {
84124
meshes := make([]*derpmesh.Mesh, 0, 20)
85125
serverURLs := make([]string, 0, 20)
86126
for i := 0; i < 20; i++ {
87-
server, url := startDERP(t)
88-
mesh := derpmesh.New(slogtest.Make(t, nil).Named("mesh").Leveled(slog.LevelDebug), server)
127+
server, url, tlsName := startDERP(t)
128+
mesh := derpmesh.New(slogtest.Make(t, nil).Named("mesh").Leveled(slog.LevelDebug), server, tlsName)
89129
t.Cleanup(func() {
90130
_ = server.Close()
91131
_ = mesh.Close()
@@ -132,15 +172,54 @@ func recvData(t *testing.T, client *derphttp.Client) []byte {
132172
}
133173
}
134174

135-
func startDERP(t *testing.T) (*derp.Server, string) {
175+
func startDERP(t *testing.T) (*derp.Server, string, *tls.Config) {
136176
logf := tailnet.Logger(slogtest.Make(t, nil))
137177
d := derp.NewServer(key.NewNode(), logf)
138178
d.SetMeshKey("some-key")
139179
server := httptest.NewUnstartedServer(derphttp.Handler(d))
180+
commonName := "something.org"
181+
server.TLS = &tls.Config{
182+
Certificates: []tls.Certificate{generateTLSCertificate(t, commonName)},
183+
}
140184
server.Start()
141185
t.Cleanup(func() {
142186
_ = d.Close()
143187
})
144188
t.Cleanup(server.Close)
145-
return d, server.URL
189+
return d, server.URL, server.TLS
190+
}
191+
192+
func generateTLSCertificate(t testing.TB, commonName string) tls.Certificate {
193+
privateKey, err := ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
194+
require.NoError(t, err)
195+
template := x509.Certificate{
196+
SerialNumber: big.NewInt(1),
197+
Subject: pkix.Name{
198+
Organization: []string{"Acme Co"},
199+
CommonName: commonName,
200+
},
201+
DNSNames: []string{commonName},
202+
NotBefore: time.Now(),
203+
NotAfter: time.Now().Add(time.Hour * 24 * 180),
204+
205+
KeyUsage: x509.KeyUsageKeyEncipherment | x509.KeyUsageDigitalSignature,
206+
ExtKeyUsage: []x509.ExtKeyUsage{x509.ExtKeyUsageServerAuth},
207+
BasicConstraintsValid: true,
208+
IPAddresses: []net.IP{net.ParseIP("127.0.0.1")},
209+
}
210+
211+
derBytes, err := x509.CreateCertificate(rand.Reader, &template, &template, &privateKey.PublicKey, privateKey)
212+
require.NoError(t, err)
213+
var certFile bytes.Buffer
214+
require.NoError(t, err)
215+
_, err = certFile.Write(pem.EncodeToMemory(&pem.Block{Type: "CERTIFICATE", Bytes: derBytes}))
216+
require.NoError(t, err)
217+
privateKeyBytes, err := x509.MarshalPKCS8PrivateKey(privateKey)
218+
require.NoError(t, err)
219+
var keyFile bytes.Buffer
220+
err = pem.Encode(&keyFile, &pem.Block{Type: "PRIVATE KEY", Bytes: privateKeyBytes})
221+
require.NoError(t, err)
222+
cert, err := tls.X509KeyPair(certFile.Bytes(), keyFile.Bytes())
223+
require.NoError(t, err)
224+
return cert
146225
}

go.mod

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ replace github.com/tcnksm/go-httpstat => github.com/kylecarbs/go-httpstat v0.0.0
4040

4141
// There are a few minor changes we make to Tailscale that we're slowly upstreaming. Compare here:
4242
// https://github.com/tailscale/tailscale/compare/main...coder:tailscale:main
43-
replace tailscale.com => github.com/coder/tailscale v1.1.1-0.20220926024748-50f068456c6c
43+
replace tailscale.com => github.com/coder/tailscale v1.1.1-0.20221014173742-9f1da7795630
4444

4545
// Switch to our fork that imports fixes from http://github.com/tailscale/ssh.
4646
// See: https://github.com/coder/coder/issues/3371

go.sum

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -351,8 +351,8 @@ github.com/coder/retry v1.3.0 h1:5lAAwt/2Cm6lVmnfBY7sOMXcBOwcwJhmV5QGSELIVWY=
351351
github.com/coder/retry v1.3.0/go.mod h1:tXuRgZgWjUnU5LZPT4lJh4ew2elUhexhlnXzrJWdyFY=
352352
github.com/coder/ssh v0.0.0-20220811105153-fcea99919338 h1:tN5GKFT68YLVzJoA8AHuiMNJ0qlhoD3pGN3JY9gxSko=
353353
github.com/coder/ssh v0.0.0-20220811105153-fcea99919338/go.mod h1:ZSS+CUoKHDrqVakTfTWUlKSr9MtMFkC4UvtQKD7O914=
354-
github.com/coder/tailscale v1.1.1-0.20220926024748-50f068456c6c h1:xa6lr5Pj87Is26tgpzwBsEGKL7aVz7/fRGgY9QIbf3E=
355-
github.com/coder/tailscale v1.1.1-0.20220926024748-50f068456c6c/go.mod h1:5amxy08qijEa8bcTW2SeIy4MIqcmd7LMsuOxqOlj2Ak=
354+
github.com/coder/tailscale v1.1.1-0.20221014173742-9f1da7795630 h1:FgWWdu0fnFEpUNjW0vOaCuOxOZ/GQzn6oo7p5IMlSA0=
355+
github.com/coder/tailscale v1.1.1-0.20221014173742-9f1da7795630/go.mod h1:5amxy08qijEa8bcTW2SeIy4MIqcmd7LMsuOxqOlj2Ak=
356356
github.com/containerd/aufs v0.0.0-20200908144142-dab0cbea06f4/go.mod h1:nukgQABAEopAHvB6j7cnP5zJ+/3aVcE7hCYqvIwAHyE=
357357
github.com/containerd/aufs v0.0.0-20201003224125-76a6863f2989/go.mod h1:AkGGQs9NM2vtYHaUen+NljV0/baGCAPELGm2q9ZXpWU=
358358
github.com/containerd/aufs v0.0.0-20210316121734-20793ff83c97/go.mod h1:kL5kd6KM5TzQjR79jljyi4olc1Vrx6XBlcyj3gNv2PU=

0 commit comments

Comments
 (0)