remove QuoteCharacter option

This seems to be one of the most reported issues, as it makes it a lot
harder to safely escape strings.

This option is very much an edge case, and it's causing too much issues
compared to what it provide.
This commit is contained in:
dmathieu 2017-07-13 13:46:35 +02:00
parent a3f95b5c42
commit 2727ac94b0
2 changed files with 5 additions and 58 deletions

View File

@ -52,10 +52,6 @@ type TextFormatter struct {
// QuoteEmptyFields will wrap empty fields in quotes if true
QuoteEmptyFields bool
// QuoteCharacter can be set to the override the default quoting character "
// with something else. For example: ', or `.
QuoteCharacter string
// Whether the logger's out is to a terminal
isTerminal bool
@ -63,9 +59,6 @@ type TextFormatter struct {
}
func (f *TextFormatter) init(entry *Entry) {
if len(f.QuoteCharacter) == 0 {
f.QuoteCharacter = "\""
}
if entry.Logger != nil {
f.isTerminal = IsTerminal(entry.Logger.Out)
}
@ -177,13 +170,6 @@ func (f *TextFormatter) appendValue(b *bytes.Buffer, value interface{}) {
if !f.needsQuoting(stringVal) {
b.WriteString(stringVal)
} else {
b.WriteString(f.quoteString(stringVal))
b.WriteString(fmt.Sprintf("%q", stringVal))
}
}
func (f *TextFormatter) quoteString(v string) string {
escapedQuote := fmt.Sprintf("\\%s", f.QuoteCharacter)
escapedValue := strings.Replace(v, f.QuoteCharacter, escapedQuote, -1)
return fmt.Sprintf("%s%v%s", f.QuoteCharacter, escapedValue, f.QuoteCharacter)
}

View File

@ -3,10 +3,10 @@ package logrus
import (
"bytes"
"errors"
"fmt"
"strings"
"testing"
"time"
"fmt"
)
func TestQuoting(t *testing.T) {
@ -15,7 +15,7 @@ func TestQuoting(t *testing.T) {
checkQuoting := func(q bool, value interface{}) {
b, _ := tf.Format(WithField("test", value))
idx := bytes.Index(b, ([]byte)("test="))
cont := bytes.Contains(b[idx+5:], []byte(tf.QuoteCharacter))
cont := bytes.Contains(b[idx+5:], []byte("\""))
if cont != q {
if q {
t.Errorf("quoting expected for: %#v", value)
@ -41,23 +41,6 @@ func TestQuoting(t *testing.T) {
checkQuoting(false, errors.New("invalid"))
checkQuoting(true, errors.New("invalid argument"))
// Test for custom quote character.
tf.QuoteCharacter = "`"
checkQuoting(false, "")
checkQuoting(false, "abcd")
checkQuoting(false, "/foobar")
checkQuoting(false, "foo_bar")
checkQuoting(false, "foo@bar")
checkQuoting(false, "foobar^")
checkQuoting(true, "foobar$")
checkQuoting(true, "&foobar")
checkQuoting(true, errors.New("invalid argument"))
// Test for multi-character quotes.
tf.QuoteCharacter = "§~±"
checkQuoting(false, "abcd")
checkQuoting(true, errors.New("invalid argument"))
// Test for quoting empty fields.
tf.QuoteEmptyFields = true
checkQuoting(true, "")
@ -65,7 +48,7 @@ func TestQuoting(t *testing.T) {
checkQuoting(true, errors.New("invalid argument"))
}
func TestEscaping_DefaultQuoteCharacter(t *testing.T) {
func TestEscaping(t *testing.T) {
tf := &TextFormatter{DisableColors: true}
testCases := []struct {
@ -105,35 +88,13 @@ func TestEscaping_Interface(t *testing.T) {
}
}
func TestEscaping_CustomQuoteCharacter(t *testing.T) {
tf := &TextFormatter{DisableColors: true}
testCases := []struct {
value string
expected string
quoteChar string
}{
{`ba"r`, `ba"r`, `'`},
{`ba'r`, `ba\'r`, `'`},
{`ba'r`, `ba'r`, `^`},
}
for _, tc := range testCases {
tf.QuoteCharacter = tc.quoteChar
b, _ := tf.Format(WithField("test", tc.value))
if !bytes.Contains(b, []byte(tc.expected)) {
t.Errorf("escaping expected for %q (result was %q instead of %q)", tc.value, string(b), tc.expected)
}
}
}
func TestTimestampFormat(t *testing.T) {
checkTimeStr := func(format string) {
customFormatter := &TextFormatter{DisableColors: true, TimestampFormat: format}
customStr, _ := customFormatter.Format(WithField("test", "test"))
timeStart := bytes.Index(customStr, ([]byte)("time="))
timeEnd := bytes.Index(customStr, ([]byte)("level="))
timeStr := customStr[timeStart+5+len(customFormatter.QuoteCharacter) : timeEnd-1-len(customFormatter.QuoteCharacter)]
timeStr := customStr[timeStart+5+len("\"") : timeEnd-1-len("\"")]
if format == "" {
format = time.RFC3339
}