fix(config): Support $$ in config for literal $ (#427)

This commit is contained in:
TwiN 2023-02-11 22:43:13 -05:00 committed by GitHub
parent 542da61215
commit 7d6923730e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 34 additions and 1 deletions

View File

@ -7,6 +7,7 @@ import (
"log" "log"
"os" "os"
"path/filepath" "path/filepath"
"strings"
"time" "time"
"github.com/TwiN/deepmerge" "github.com/TwiN/deepmerge"
@ -214,8 +215,13 @@ func walkConfigDir(path string, fn fs.WalkDirFunc) error {
// parseAndValidateConfigBytes parses a Gatus configuration file into a Config struct and validates its parameters // parseAndValidateConfigBytes parses a Gatus configuration file into a Config struct and validates its parameters
func parseAndValidateConfigBytes(yamlBytes []byte) (config *Config, err error) { func parseAndValidateConfigBytes(yamlBytes []byte) (config *Config, err error) {
// Replace $$ with __GATUS_LITERAL_DOLLAR_SIGN__ to prevent os.ExpandEnv from treating "$$" as if it was an
// environment variable. This allows Gatus to support literal "$" in the configuration file.
yamlBytes = []byte(strings.ReplaceAll(string(yamlBytes), "$$", "__GATUS_LITERAL_DOLLAR_SIGN__"))
// Expand environment variables // Expand environment variables
yamlBytes = []byte(os.ExpandEnv(string(yamlBytes))) yamlBytes = []byte(os.ExpandEnv(string(yamlBytes)))
// Replace __GATUS_LITERAL_DOLLAR_SIGN__ with "$" to restore the literal "$" in the configuration file
yamlBytes = []byte(strings.ReplaceAll(string(yamlBytes), "__GATUS_LITERAL_DOLLAR_SIGN__", "$"))
// Parse configuration file // Parse configuration file
if err = yaml.Unmarshal(yamlBytes, &config); err != nil { if err = yaml.Unmarshal(yamlBytes, &config); err != nil {
return return

View File

@ -1534,7 +1534,34 @@ endpoints:
} }
} }
func TestParseAndValidateConfigBytesWithNoEndpointsOrAutoDiscovery(t *testing.T) { func TestParseAndValidateConfigBytesWithLiteralDollarSign(t *testing.T) {
os.Setenv("GATUS_TestParseAndValidateConfigBytesWithLiteralDollarSign", "whatever")
config, err := parseAndValidateConfigBytes([]byte(`
endpoints:
- name: website
url: https://twin.sh/health
conditions:
- "[BODY] == $$GATUS_TestParseAndValidateConfigBytesWithLiteralDollarSign"
- "[BODY] == $GATUS_TestParseAndValidateConfigBytesWithLiteralDollarSign"
`))
if err != nil {
t.Error("expected no error, got", err.Error())
}
if config == nil {
t.Fatal("Config shouldn't have been nil")
}
if config.Endpoints[0].URL != "https://twin.sh/health" {
t.Errorf("URL should have been %s", "https://twin.sh/health")
}
if config.Endpoints[0].Conditions[0] != "[BODY] == $GATUS_TestParseAndValidateConfigBytesWithLiteralDollarSign" {
t.Errorf("Condition should have been %s", "[BODY] == $GATUS_TestParseAndValidateConfigBytesWithLiteralDollarSign")
}
if config.Endpoints[0].Conditions[1] != "[BODY] == whatever" {
t.Errorf("Condition should have been %s", "[BODY] == whatever")
}
}
func TestParseAndValidateConfigBytesWithNoEndpoints(t *testing.T) {
_, err := parseAndValidateConfigBytes([]byte(``)) _, err := parseAndValidateConfigBytes([]byte(``))
if err != ErrNoEndpointInConfig { if err != ErrNoEndpointInConfig {
t.Error("The error returned should have been of type ErrNoEndpointInConfig") t.Error("The error returned should have been of type ErrNoEndpointInConfig")