Skip to content

Commit

Permalink
Refactoring Redis (#1271)
Browse files Browse the repository at this point in the history
* RedisConfig -> Redis

* moved redis config to seperate file

* bugfix in config test during parallel processing

* implement config.Configurable in Redis config

* use Context in GetRedisCache

* use Context in New

* caching resolver test fix

* use Context in PublishEnabled

* use Context in getResponse

* remove ctx field

* bugfix in api interface test

* propperly close channels

* set ruler for go files from 80 to 111

* line break because function length is to long

* only execute redis.New if it is enabled in config

* stabilized flaky tests

* Update config/redis.go

Co-authored-by: ThinkChaos <ThinkChaos@users.noreply.github.com>

* Update config/redis_test.go

Co-authored-by: ThinkChaos <ThinkChaos@users.noreply.github.com>

* Update config/redis_test.go

Co-authored-by: ThinkChaos <ThinkChaos@users.noreply.github.com>

* Update config/redis_test.go

Co-authored-by: ThinkChaos <ThinkChaos@users.noreply.github.com>

* Update config/redis.go

Co-authored-by: ThinkChaos <ThinkChaos@users.noreply.github.com>

* Update config/redis_test.go

Co-authored-by: ThinkChaos <ThinkChaos@users.noreply.github.com>

* fix ruler

* redis test refactoring

* vscode setting cleanup

* removed else if chain

* Update redis_test.go

* context race fix

* test fail on missing seintinel servers

* cleanup context usage

* cleanup2

* context fixes

* added context util

* disabled nil context rule for tests

* copy paste error ctxSend -> CtxSend

* use util.CtxSend

* fixed comment

* fixed flaky test

* failsafe and tests

---------

Co-authored-by: ThinkChaos <ThinkChaos@users.noreply.github.com>
  • Loading branch information
kwitsch and ThinkChaos committed Nov 27, 2023
1 parent 15bd383 commit fda2dbe
Show file tree
Hide file tree
Showing 20 changed files with 571 additions and 194 deletions.
23 changes: 13 additions & 10 deletions .devcontainer/devcontainer.json
Expand Up @@ -31,19 +31,13 @@
"GitHub.vscode-github-actions"
],
"settings": {
"go.lintFlags": ["--config=${containerWorkspaceFolder}/.golangci.yml"],
"go.lintFlags": [
"--config=${containerWorkspaceFolder}/.golangci.yml",
"--fast"
],
"go.alternateTools": {
"go-langserver": "gopls"
},
"[go]": {
"editor.defaultFormatter": "golang.go"
},
"[json][jsonc][github-actions-workflow]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[markdown]": {
"editor.defaultFormatter": "yzhang.markdown-all-in-one"
},
"markiscodecoverage.searchCriteria": "**/*.lcov",
"runItOn": {
"commands": [
Expand All @@ -52,6 +46,15 @@
"cmd": "${workspaceRoot}/.devcontainer/scripts/runItOnGo.sh ${fileDirname} ${workspaceRoot}"
}
]
},
"[go]": {
"editor.defaultFormatter": "golang.go"
},
"[json][jsonc][github-actions-workflow]": {
"editor.defaultFormatter": "esbenp.prettier-vscode"
},
"[markdown]": {
"editor.defaultFormatter": "yzhang.markdown-all-in-one"
}
}
}
Expand Down
4 changes: 4 additions & 0 deletions .golangci.yml
Expand Up @@ -98,3 +98,7 @@ issues:
- gochecknoinits
- gochecknoglobals
- gosec
- path: _test\.go
linters:
- staticcheck
text: "SA1012:"
1 change: 1 addition & 0 deletions .vscode/settings.json
Expand Up @@ -8,6 +8,7 @@
"source.organizeImports": true,
"source.fixAll": true
},
"editor.rulers": [120],
"go.showWelcome": false,
"go.survey.prompt": false,
"go.useLanguageServer": true,
Expand Down
12 changes: 6 additions & 6 deletions api/api_interface_impl.go
Expand Up @@ -29,8 +29,8 @@ type BlockingStatus struct {

// BlockingControl interface to control the blocking status
type BlockingControl interface {
EnableBlocking()
DisableBlocking(duration time.Duration, disableGroups []string) error
EnableBlocking(ctx context.Context)
DisableBlocking(ctx context.Context, duration time.Duration, disableGroups []string) error
BlockingStatus() BlockingStatus
}

Expand Down Expand Up @@ -71,7 +71,7 @@ func NewOpenAPIInterfaceImpl(control BlockingControl,
}
}

func (i *OpenAPIInterfaceImpl) DisableBlocking(_ context.Context,
func (i *OpenAPIInterfaceImpl) DisableBlocking(ctx context.Context,
request DisableBlockingRequestObject,
) (DisableBlockingResponseObject, error) {
var (
Expand All @@ -91,7 +91,7 @@ func (i *OpenAPIInterfaceImpl) DisableBlocking(_ context.Context,
groups = strings.Split(*request.Params.Groups, ",")
}

err = i.control.DisableBlocking(duration, groups)
err = i.control.DisableBlocking(ctx, duration, groups)

if err != nil {
return DisableBlocking400TextResponse(log.EscapeInput(err.Error())), nil
Expand All @@ -100,9 +100,9 @@ func (i *OpenAPIInterfaceImpl) DisableBlocking(_ context.Context,
return DisableBlocking200Response{}, nil
}

func (i *OpenAPIInterfaceImpl) EnableBlocking(_ context.Context, _ EnableBlockingRequestObject,
func (i *OpenAPIInterfaceImpl) EnableBlocking(ctx context.Context, _ EnableBlockingRequestObject,
) (EnableBlockingResponseObject, error) {
i.control.EnableBlocking()
i.control.EnableBlocking(ctx)

return EnableBlocking200Response{}, nil
}
Expand Down
4 changes: 2 additions & 2 deletions api/api_interface_impl_test.go
Expand Up @@ -37,11 +37,11 @@ func (m *ListRefreshMock) RefreshLists() error {
return args.Error(0)
}

func (m *BlockingControlMock) EnableBlocking() {
func (m *BlockingControlMock) EnableBlocking(_ context.Context) {
_ = m.Called()
}

func (m *BlockingControlMock) DisableBlocking(t time.Duration, g []string) error {
func (m *BlockingControlMock) DisableBlocking(_ context.Context, t time.Duration, g []string) error {
args := m.Called(t, g)

return args.Error(0)
Expand Down
16 changes: 1 addition & 15 deletions config/config.go
Expand Up @@ -219,7 +219,7 @@ type Config struct {
Caching CachingConfig `yaml:"caching"`
QueryLog QueryLogConfig `yaml:"queryLog"`
Prometheus MetricsConfig `yaml:"prometheus"`
Redis RedisConfig `yaml:"redis"`
Redis Redis `yaml:"redis"`
Log log.Config `yaml:"log"`
Ports PortsConfig `yaml:"ports"`
MinTLSServeVer TLSVersion `yaml:"minTlsServeVersion" default:"1.2"`
Expand Down Expand Up @@ -280,20 +280,6 @@ type (
}
)

// RedisConfig configuration for the redis connection
type RedisConfig struct {
Address string `yaml:"address"`
Username string `yaml:"username" default:""`
Password string `yaml:"password" default:""`
Database int `yaml:"database" default:"0"`
Required bool `yaml:"required" default:"false"`
ConnectionAttempts int `yaml:"connectionAttempts" default:"3"`
ConnectionCooldown Duration `yaml:"connectionCooldown" default:"1s"`
SentinelUsername string `yaml:"sentinelUsername" default:""`
SentinelPassword string `yaml:"sentinelPassword" default:""`
SentinelAddresses []string `yaml:"sentinelAddresses"`
}

type (
FQDNOnly = toEnable
EDE = toEnable
Expand Down
2 changes: 1 addition & 1 deletion config/config_test.go
Expand Up @@ -169,7 +169,7 @@ var _ = Describe("Config", func() {
err = writeConfigDir(tmpDir)
Expect(err).Should(Succeed())

_, err := LoadConfig(tmpDir.Path, true)
c, err = LoadConfig(tmpDir.Path, true)
Expect(err).Should(Succeed())

defaultTestFileConfig(c)
Expand Down
57 changes: 57 additions & 0 deletions config/redis.go
@@ -0,0 +1,57 @@
package config

import (
"strings"

"github.com/sirupsen/logrus"
)

// Redis configuration for the redis connection
type Redis struct {
Address string `yaml:"address"`
Username string `yaml:"username" default:""`
Password string `yaml:"password" default:""`
Database int `yaml:"database" default:"0"`
Required bool `yaml:"required" default:"false"`
ConnectionAttempts int `yaml:"connectionAttempts" default:"3"`
ConnectionCooldown Duration `yaml:"connectionCooldown" default:"1s"`
SentinelUsername string `yaml:"sentinelUsername" default:""`
SentinelPassword string `yaml:"sentinelPassword" default:""`
SentinelAddresses []string `yaml:"sentinelAddresses"`
}

// IsEnabled implements `config.Configurable`
func (c *Redis) IsEnabled() bool {
return c.Address != ""
}

// LogConfig implements `config.Configurable`
func (c *Redis) LogConfig(logger *logrus.Entry) {
if len(c.SentinelAddresses) == 0 {
logger.Info("address: ", c.Address)
}

logger.Info("username: ", c.Username)
logger.Info("password: ", obfuscatePassword(c.Password))
logger.Info("database: ", c.Database)
logger.Info("required: ", c.Required)
logger.Info("connectionAttempts: ", c.ConnectionAttempts)
logger.Info("connectionCooldown: ", c.ConnectionCooldown)

if len(c.SentinelAddresses) > 0 {
logger.Info("sentinel:")
logger.Info(" master: ", c.Address)
logger.Info(" username: ", c.SentinelUsername)
logger.Info(" password: ", obfuscatePassword(c.SentinelPassword))
logger.Info(" addresses:")

for _, addr := range c.SentinelAddresses {
logger.Info(" - ", addr)
}
}
}

// obfuscatePassword replaces all characters of a password except the first and last with *
func obfuscatePassword(pass string) string {
return strings.Repeat("*", len(pass))
}
104 changes: 104 additions & 0 deletions config/redis_test.go
@@ -0,0 +1,104 @@
package config

import (
"github.com/0xERR0R/blocky/log"
"github.com/creasty/defaults"
. "github.com/onsi/ginkgo/v2"
. "github.com/onsi/gomega"
)

var _ = Describe("Redis", func() {
var (
c Redis
err error
)

suiteBeforeEach()

BeforeEach(func() {
err = defaults.Set(&c)
Expect(err).Should(Succeed())
})

Describe("IsEnabled", func() {
When("all fields are default", func() {
It("should be disabled", func() {
Expect(c.IsEnabled()).Should(BeFalse())
})
})

When("Address is set", func() {
BeforeEach(func() {
c.Address = "localhost:6379"
})

It("should be enabled", func() {
Expect(c.IsEnabled()).Should(BeTrue())
})
})
})

Describe("LogConfig", func() {
BeforeEach(func() {
logger, hook = log.NewMockEntry()
})

When("all fields are default", func() {
It("should log default values", func() {
c.LogConfig(logger)

Expect(hook.Messages).Should(
SatisfyAll(ContainElement(ContainSubstring("address: ")),
ContainElement(ContainSubstring("username: ")),
ContainElement(ContainSubstring("password: ")),
ContainElement(ContainSubstring("database: ")),
ContainElement(ContainSubstring("required: ")),
ContainElement(ContainSubstring("connectionAttempts: ")),
ContainElement(ContainSubstring("connectionCooldown: "))))
})
})

When("Address is set", func() {
BeforeEach(func() {
c.Address = "localhost:6379"
})

It("should log address", func() {
c.LogConfig(logger)

Expect(hook.Messages).Should(ContainElement(ContainSubstring("address: localhost:6379")))
})
})

When("SentinelAddresses is set", func() {
BeforeEach(func() {
c.SentinelAddresses = []string{"localhost:26379", "localhost:26380"}
})

It("should log sentinel addresses", func() {
c.LogConfig(logger)

Expect(hook.Messages).Should(
SatisfyAll(
ContainElement(ContainSubstring("sentinel:")),
ContainElement(ContainSubstring(" addresses:")),
ContainElement(ContainSubstring(" - localhost:26379")),
ContainElement(ContainSubstring(" - localhost:26380"))))
})
})
})

Describe("obfuscatePassword", func() {
When("password is empty", func() {
It("should return empty string", func() {
Expect(obfuscatePassword("")).Should(Equal(""))
})
})

When("password is not empty", func() {
It("should return obfuscated password", func() {
Expect(obfuscatePassword("test123")).Should(Equal("*******"))
})
})
})
})

0 comments on commit fda2dbe

Please sign in to comment.