Skip to content

Commit 37fb9c5

Browse files
pooknullegegunes
andauthored
K8SPS-392: configure bootstrap readTimeout (#838)
* K8SPS-392: configure bootstrap readTimeout https://perconadev.atlassian.net/browse/K8SPS-392 * `ReadTimeout` => `ReadTimeoutSeconds` --------- Co-authored-by: Ege Güneş <ege.gunes@percona.com>
1 parent 96e369e commit 37fb9c5

File tree

6 files changed

+125
-14
lines changed

6 files changed

+125
-14
lines changed

cmd/bootstrap/async_replication.go

Lines changed: 36 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,18 @@ func bootstrapAsyncReplication(ctx context.Context) error {
7878
return errors.Wrapf(err, "get %s password", apiv1alpha1.UserOperator)
7979
}
8080

81-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserOperator, operatorPass, podIp, mysql.DefaultAdminPort)
81+
params := database.DBParams{
82+
User: apiv1alpha1.UserOperator,
83+
Pass: operatorPass,
84+
Host: podIp,
85+
}
86+
readTimeout, err := getReadTimeout()
87+
if err != nil {
88+
return errors.Wrap(err, "get read timeout")
89+
}
90+
params.ReadTimeoutSeconds = readTimeout
91+
92+
db, err := database.NewDatabase(ctx, params)
8293
if err != nil {
8394
return errors.Wrap(err, "connect to database")
8495
}
@@ -199,7 +210,18 @@ func getTopology(ctx context.Context, fqdn string, peers sets.Set[string]) (stri
199210
}
200211

201212
for _, peer := range sets.List(peers) {
202-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserOperator, operatorPass, peer, mysql.DefaultAdminPort)
213+
params := database.DBParams{
214+
User: apiv1alpha1.UserOperator,
215+
Pass: operatorPass,
216+
Host: peer,
217+
}
218+
readTimeout, err := getReadTimeout()
219+
if err != nil {
220+
return "", nil, errors.Wrap(err, "get read timeout")
221+
}
222+
params.ReadTimeoutSeconds = readTimeout
223+
224+
db, err := database.NewDatabase(ctx, params)
203225
if err != nil {
204226
return "", nil, errors.Wrapf(err, "connect to %s", peer)
205227
}
@@ -254,7 +276,18 @@ func selectDonor(ctx context.Context, fqdn, primary string, replicas []string) (
254276
}
255277

256278
for _, replica := range replicas {
257-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserOperator, operatorPass, replica, mysql.DefaultAdminPort)
279+
params := database.DBParams{
280+
User: apiv1alpha1.UserOperator,
281+
Pass: operatorPass,
282+
Host: replica,
283+
}
284+
readTimeout, err := getReadTimeout()
285+
if err != nil {
286+
return "", errors.Wrap(err, "get read timeout")
287+
}
288+
params.ReadTimeoutSeconds = readTimeout
289+
290+
db, err := database.NewDatabase(ctx, params)
258291
if err != nil {
259292
continue
260293
}

cmd/bootstrap/utils.go

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import (
66
"net"
77
"os"
88
"path/filepath"
9+
"strconv"
910
"strings"
1011
"time"
1112

@@ -15,6 +16,7 @@ import (
1516
apiv1alpha1 "github.com/percona/percona-server-mysql-operator/api/v1alpha1"
1617
"github.com/percona/percona-server-mysql-operator/pkg/k8s"
1718
"github.com/percona/percona-server-mysql-operator/pkg/mysql"
19+
"github.com/percona/percona-server-mysql-operator/pkg/naming"
1820
)
1921

2022
func getFQDN(svcName string) (string, error) {
@@ -31,6 +33,22 @@ func getFQDN(svcName string) (string, error) {
3133
return fmt.Sprintf("%s.%s.%s", hostname, svcName, namespace), nil
3234
}
3335

36+
func getReadTimeout() (uint32, error) {
37+
s, ok := os.LookupEnv(naming.EnvBootstrapReadTimeout)
38+
if !ok {
39+
return 0, nil
40+
}
41+
readTimeout, err := strconv.Atoi(s)
42+
if err != nil {
43+
return 0, errors.Wrap(err, "failed to parse BOOTSTRAP_READ_TIMEOUT")
44+
}
45+
if readTimeout < 0 {
46+
return 0, errors.New("BOOTSTRAP_READ_TIMEOUT should be a positive value")
47+
}
48+
49+
return uint32(readTimeout), nil
50+
}
51+
3452
func getSecret(username apiv1alpha1.SystemUser) (string, error) {
3553
path := filepath.Join(mysql.CredsMountPath, string(username))
3654
sBytes, err := os.ReadFile(path)

cmd/db/db.go

Lines changed: 32 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010

1111
apiv1alpha1 "github.com/percona/percona-server-mysql-operator/api/v1alpha1"
1212
"github.com/percona/percona-server-mysql-operator/pkg/db"
13+
defs "github.com/percona/percona-server-mysql-operator/pkg/mysql"
1314
)
1415

1516
const defaultChannelName = ""
@@ -22,23 +23,48 @@ type DB struct {
2223
db *sql.DB
2324
}
2425

25-
func NewDatabase(ctx context.Context, user apiv1alpha1.SystemUser, pass, host string, port int32) (*DB, error) {
26+
type DBParams struct {
27+
User apiv1alpha1.SystemUser
28+
Pass string
29+
Host string
30+
Port int32
31+
32+
ReadTimeoutSeconds uint32
33+
}
34+
35+
func (p *DBParams) setDefaults() {
36+
if p.Port == 0 {
37+
p.Port = defs.DefaultAdminPort
38+
}
39+
40+
if p.ReadTimeoutSeconds == 0 {
41+
p.ReadTimeoutSeconds = 10
42+
}
43+
}
44+
45+
func (p *DBParams) DSN() string {
46+
p.setDefaults()
47+
2648
config := mysql.NewConfig()
2749

28-
config.User = string(user)
29-
config.Passwd = pass
50+
config.User = string(p.User)
51+
config.Passwd = p.Pass
3052
config.Net = "tcp"
31-
config.Addr = fmt.Sprintf("%s:%d", host, port)
53+
config.Addr = fmt.Sprintf("%s:%d", p.Host, p.Port)
3254
config.DBName = "performance_schema"
3355
config.Params = map[string]string{
3456
"interpolateParams": "true",
3557
"timeout": "10s",
36-
"readTimeout": "10s",
58+
"readTimeout": fmt.Sprintf("%ds", p.ReadTimeoutSeconds),
3759
"writeTimeout": "10s",
3860
"tls": "preferred",
3961
}
4062

41-
db, err := sql.Open("mysql", config.FormatDSN())
63+
return config.FormatDSN()
64+
}
65+
66+
func NewDatabase(ctx context.Context, params DBParams) (*DB, error) {
67+
db, err := sql.Open("mysql", params.DSN())
4268
if err != nil {
4369
return nil, errors.Wrap(err, "connect to MySQL")
4470
}

cmd/healthcheck/main.go

Lines changed: 31 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import (
1313
"github.com/pkg/errors"
1414

1515
apiv1alpha1 "github.com/percona/percona-server-mysql-operator/api/v1alpha1"
16+
"github.com/percona/percona-server-mysql-operator/cmd/db"
1617
database "github.com/percona/percona-server-mysql-operator/cmd/db"
1718
mysqldb "github.com/percona/percona-server-mysql-operator/pkg/db"
1819
"github.com/percona/percona-server-mysql-operator/pkg/k8s"
@@ -82,7 +83,12 @@ func checkReadinessAsync(ctx context.Context) error {
8283
return errors.Wrapf(err, "get %s password", apiv1alpha1.UserMonitor)
8384
}
8485

85-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserMonitor, monitorPass, podIP, mysql.DefaultAdminPort)
86+
params := db.DBParams{
87+
User: apiv1alpha1.UserMonitor,
88+
Pass: monitorPass,
89+
Host: podIP,
90+
}
91+
db, err := database.NewDatabase(ctx, params)
8692
if err != nil {
8793
return errors.Wrap(err, "connect to db")
8894
}
@@ -117,7 +123,12 @@ func checkReadinessGR(ctx context.Context) error {
117123
return errors.Wrapf(err, "get %s password", apiv1alpha1.UserMonitor)
118124
}
119125

120-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserMonitor, monitorPass, podIP, mysql.DefaultAdminPort)
126+
params := db.DBParams{
127+
User: apiv1alpha1.UserMonitor,
128+
Pass: monitorPass,
129+
Host: podIP,
130+
}
131+
db, err := database.NewDatabase(ctx, params)
121132
if err != nil {
122133
return errors.Wrap(err, "connect to db")
123134
}
@@ -151,7 +162,12 @@ func checkLivenessAsync(ctx context.Context) error {
151162
return errors.Wrapf(err, "get %s password", apiv1alpha1.UserMonitor)
152163
}
153164

154-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserMonitor, monitorPass, podIP, mysql.DefaultAdminPort)
165+
params := db.DBParams{
166+
User: apiv1alpha1.UserMonitor,
167+
Pass: monitorPass,
168+
Host: podIP,
169+
}
170+
db, err := database.NewDatabase(ctx, params)
155171
if err != nil {
156172
return errors.Wrap(err, "connect to db")
157173
}
@@ -171,7 +187,12 @@ func checkLivenessGR(ctx context.Context) error {
171187
return errors.Wrapf(err, "get %s password", apiv1alpha1.UserMonitor)
172188
}
173189

174-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserMonitor, monitorPass, podIP, mysql.DefaultAdminPort)
190+
params := db.DBParams{
191+
User: apiv1alpha1.UserMonitor,
192+
Pass: monitorPass,
193+
Host: podIP,
194+
}
195+
db, err := database.NewDatabase(ctx, params)
175196
if err != nil {
176197
return errors.Wrap(err, "connect to db")
177198
}
@@ -202,7 +223,12 @@ func checkReplication(ctx context.Context) error {
202223
return errors.Wrapf(err, "get %s password", apiv1alpha1.UserMonitor)
203224
}
204225

205-
db, err := database.NewDatabase(ctx, apiv1alpha1.UserMonitor, monitorPass, podIP, mysql.DefaultAdminPort)
226+
params := db.DBParams{
227+
User: apiv1alpha1.UserMonitor,
228+
Pass: monitorPass,
229+
Host: podIP,
230+
}
231+
db, err := database.NewDatabase(ctx, params)
206232
if err != nil {
207233
return errors.Wrap(err, "connect to db")
208234
}

deploy/cr.yaml

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,9 @@ spec:
4545

4646
size: 3
4747

48+
# env:
49+
# - name: BOOTSTRAP_READ_TIMEOUT
50+
# value: "600"
4851
resources:
4952
requests:
5053
memory: 1G

pkg/naming/env.go

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
package naming
2+
3+
const (
4+
EnvBootstrapReadTimeout = "BOOTSTRAP_READ_TIMEOUT"
5+
)

0 commit comments

Comments
 (0)