Skip to content

Commit 50e56c6

Browse files
committed
Internal refactoring for escape character
1 parent 98f46ac commit 50e56c6

2 files changed

Lines changed: 30 additions & 11 deletions

File tree

src/main/java/org/apache/commons/csv/CSVFormat.java

Lines changed: 27 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1717,6 +1717,15 @@ public Character getEscapeCharacter() {
17171717
return escapeCharacter;
17181718
}
17191719

1720+
/**
1721+
* Gets the escape character.
1722+
*
1723+
* @return the escape character, may be {@code 0}
1724+
*/
1725+
char getEscapeChar() {
1726+
return escapeCharacter != null ? escapeCharacter.charValue() : 0;
1727+
}
1728+
17201729
/**
17211730
* Gets a copy of the header array.
17221731
*
@@ -2129,26 +2138,28 @@ public synchronized void printRecord(final Appendable appendable, final Object..
21292138
}
21302139

21312140
/*
2132-
* Note: Must only be called if escaping is enabled, otherwise will generate NPE.
2141+
* Note: Must only be called if escaping is enabled, otherwise can throw exceptions.
21332142
*/
21342143
private void printWithEscapes(final CharSequence charSeq, final Appendable appendable) throws IOException {
21352144
int start = 0;
21362145
int pos = 0;
21372146
final int end = charSeq.length();
21382147
final char[] delim = getDelimiterCharArray();
21392148
final int delimLength = delim.length;
2140-
final char escape = getEscapeCharacter().charValue();
2149+
final char escape = getEscapeChar();
21412150
while (pos < end) {
21422151
char c = charSeq.charAt(pos);
21432152
final boolean isDelimiterStart = isDelimiter(c, charSeq, pos, delim, delimLength);
2144-
if (c == CR || c == LF || c == escape || isDelimiterStart) {
2153+
final boolean isCr = c == CR;
2154+
final boolean isLf = c == LF;
2155+
if (isCr || isLf || c == escape || isDelimiterStart) {
21452156
// write out segment up until this char
21462157
if (pos > start) {
21472158
appendable.append(charSeq, start, pos);
21482159
}
2149-
if (c == LF) {
2160+
if (isLf) {
21502161
c = 'n';
2151-
} else if (c == CR) {
2162+
} else if (isCr) {
21522163
c = 'r';
21532164
}
21542165
appendable.append(escape);
@@ -2172,30 +2183,35 @@ private void printWithEscapes(final CharSequence charSeq, final Appendable appen
21722183
}
21732184
}
21742185

2186+
/*
2187+
* Note: Must only be called if escaping is enabled, otherwise can throw exceptions.
2188+
*/
21752189
private void printWithEscapes(final Reader reader, final Appendable appendable) throws IOException {
21762190
int start = 0;
21772191
int pos = 0;
21782192
@SuppressWarnings("resource") // Temp reader on input reader.
21792193
final ExtendedBufferedReader bufferedReader = new ExtendedBufferedReader(reader);
21802194
final char[] delim = getDelimiterCharArray();
21812195
final int delimLength = delim.length;
2182-
final char escape = getEscapeCharacter().charValue();
2196+
final char escape = getEscapeChar();
21832197
final StringBuilder builder = new StringBuilder(IOUtils.DEFAULT_BUFFER_SIZE);
21842198
int c;
21852199
while (EOF != (c = bufferedReader.read())) {
21862200
builder.append((char) c);
21872201
final boolean isDelimiterStart = isDelimiter((char) c, builder.toString() + new String(bufferedReader.lookAhead(delimLength - 1)), pos, delim,
21882202
delimLength);
2189-
if (c == CR || c == LF || c == escape || isDelimiterStart) {
2203+
final boolean isCr = c == CR;
2204+
final boolean isLf = c == LF;
2205+
if (isCr || isLf || c == escape || isDelimiterStart) {
21902206
// write out segment up until this char
21912207
if (pos > start) {
21922208
append(builder.substring(start, pos), appendable);
21932209
builder.setLength(0);
21942210
pos = -1;
21952211
}
2196-
if (c == LF) {
2212+
if (isLf) {
21972213
c = 'n';
2198-
} else if (c == CR) {
2214+
} else if (isCr) {
21992215
c = 'r';
22002216
}
22012217
append(escape, appendable);
@@ -2232,7 +2248,7 @@ private void printWithQuotes(final Object object, final CharSequence charSeq, fi
22322248
// If escape char not specified, default to the quote char
22332249
// This avoids having to keep checking whether there is an escape character
22342250
// at the cost of checking against quote twice
2235-
final char escapeChar = isEscapeCharacterSet() ? getEscapeCharacter().charValue() : quoteChar;
2251+
final char escapeChar = isEscapeCharacterSet() ? getEscapeChar() : quoteChar;
22362252
QuoteMode quoteModePolicy = getQuoteMode();
22372253
if (quoteModePolicy == null) {
22382254
quoteModePolicy = QuoteMode.MINIMAL;
@@ -2436,7 +2452,7 @@ private void validate() throws IllegalArgumentException {
24362452
final boolean emptyDuplicatesAllowed = duplicateHeaderMode == DuplicateHeaderMode.ALLOW_EMPTY;
24372453
for (final String header : headers) {
24382454
final boolean blank = isBlank(header);
2439-
// Sanitise all empty headers to the empty string "" when checking duplicates
2455+
// Sanitize all empty headers to the empty string "" when checking duplicates
24402456
final boolean containsHeader = !dupCheckSet.add(blank ? "" : header);
24412457
if (containsHeader && !(blank && emptyDuplicatesAllowed)) {
24422458
throw new IllegalArgumentException(

src/test/java/org/apache/commons/csv/CSVFormatTest.java

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -393,6 +393,7 @@ public void testEqualsOne() {
393393
final CSVFormat csvFormatTwo = CSVFormat.MYSQL;
394394

395395
assertEquals('\\', (char) csvFormatOne.getEscapeCharacter());
396+
assertEquals('\\', csvFormatOne.getEscapeChar());
396397
assertNull(csvFormatOne.getQuoteMode());
397398

398399
assertTrue(csvFormatOne.getIgnoreEmptyLines());
@@ -426,6 +427,8 @@ public void testEqualsOne() {
426427
assertEquals(QuoteMode.ALL_NON_NULL, csvFormatTwo.getQuoteMode());
427428

428429
assertEquals('\t', csvFormatTwo.getDelimiter());
430+
assertArrayEquals(new char[] { '\t' }, csvFormatTwo.getDelimiterCharArray());
431+
assertEquals("\t", csvFormatTwo.getDelimiterString());
429432
assertEquals("\n", csvFormatTwo.getRecordSeparator());
430433

431434
assertFalse(csvFormatTwo.isQuoteCharacterSet());

0 commit comments

Comments
 (0)