Skip to content
This repository was archived by the owner on Jan 22, 2019. It is now read-only.

Commit a234143

Browse files
committed
Start working on #32
1 parent ca27718 commit a234143

File tree

4 files changed

+77
-24
lines changed

4 files changed

+77
-24
lines changed

src/main/java/com/fasterxml/jackson/dataformat/csv/CsvSchema.java

Lines changed: 25 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -60,8 +60,6 @@
6060
* read column names from the document itself.
6161
* </li>
6262
*</ul>
63-
*
64-
* @since 1.9
6563
*/
6664
public class CsvSchema
6765
implements FormatSchema,
@@ -185,7 +183,8 @@ public static class Builder
185183

186184
protected char _columnSeparator = DEFAULT_COLUMN_SEPARATOR;
187185

188-
protected char _quoteChar = DEFAULT_QUOTE_CHAR;
186+
// note: need to use int to allow -1 for 'none'
187+
protected int _quoteChar = DEFAULT_QUOTE_CHAR;
189188

190189
// note: need to use int to allow -1 for 'none'
191190
protected int _escapeChar = DEFAULT_QUOTE_CHAR;
@@ -284,6 +283,14 @@ public Builder setQuoteChar(char c) {
284283
return this;
285284
}
286285

286+
/**
287+
* @since 2.4
288+
*/
289+
public Builder disableQuoteChar() {
290+
_quoteChar = -1;
291+
return this;
292+
}
293+
287294
/**
288295
* Method for specifying character used for optional escaping
289296
* of characters in quoted String values.
@@ -348,15 +355,15 @@ protected void _checkIndex(int index) {
348355

349356
protected final char _columnSeparator;
350357

351-
protected final char _quoteChar;
358+
protected final int _quoteChar;
352359

353360
protected final int _escapeChar;
354361

355362
protected final char[] _lineSeparator;
356363

357364
public CsvSchema(Column[] columns,
358365
boolean useHeader, boolean skipFirstDataRow,
359-
char columnSeparator, char quoteChar, int escapeChar,
366+
char columnSeparator, int quoteChar, int escapeChar,
360367
char[] lineSeparator)
361368
{
362369
if (columns == null) {
@@ -387,7 +394,7 @@ public CsvSchema(Column[] columns,
387394
*/
388395
protected CsvSchema(Column[] columns,
389396
boolean useHeader, boolean skipFirstDataRow,
390-
char columnSeparator, char quoteChar, int escapeChar,
397+
char columnSeparator, int quoteChar, int escapeChar,
391398
char[] lineSeparator,
392399
Map<String,Column> columnsByName)
393400
{
@@ -476,7 +483,13 @@ public CsvSchema withQuoteChar(char c) {
476483
new CsvSchema(_columns, _useHeader, _skipFirstDataRow,
477484
_columnSeparator, c, _escapeChar, _lineSeparator, _columnsByName);
478485
}
479-
486+
487+
public CsvSchema withoutQuoteChar() {
488+
return (_quoteChar == -1) ? this :
489+
new CsvSchema(_columns, _useHeader, _skipFirstDataRow,
490+
_columnSeparator, -1, _escapeChar, _lineSeparator, _columnsByName);
491+
}
492+
480493
public CsvSchema withEscapeChar(char c) {
481494
return (_escapeChar == c) ? this
482495
: new CsvSchema(_columns, _useHeader, _skipFirstDataRow,
@@ -498,7 +511,7 @@ public CsvSchema withoutColumns() {
498511
return new CsvSchema(NO_COLUMNS, _useHeader, _skipFirstDataRow,
499512
_columnSeparator, _quoteChar, _escapeChar, _lineSeparator, _columnsByName);
500513
}
501-
514+
502515
/*
503516
/**********************************************************************
504517
/* Public API, FormatSchema
@@ -519,9 +532,12 @@ public String getSchemaType() {
519532
public boolean useHeader() { return _useHeader; }
520533
public boolean skipFirstDataRow() { return _skipFirstDataRow; }
521534
public char getColumnSeparator() { return _columnSeparator; }
522-
public char getQuoteChar() { return _quoteChar; }
535+
public int getQuoteChar() { return _quoteChar; }
523536
public int getEscapeChar() { return _escapeChar; }
524537
public char[] getLineSeparator() { return _lineSeparator; }
538+
539+
public boolean usesQuoteChar() { return _quoteChar >= 0; }
540+
public boolean usesEscapeChar() { return _escapeChar >= 0; }
525541

526542
/*
527543
/**********************************************************************

src/main/java/com/fasterxml/jackson/dataformat/csv/impl/CsvWriter.java

Lines changed: 14 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ public final class CsvWriter
4444

4545
final protected char _cfgColumnSeparator;
4646

47-
final protected char _cfgQuoteCharacter;
47+
final protected int _cfgQuoteCharacter;
4848

4949
final protected char[] _cfgLineSeparator;
5050

@@ -155,6 +155,7 @@ public CsvWriter(CsvWriter base, CsvSchema newSchema)
155155

156156
private final int _calcSafeChar()
157157
{
158+
// note: quote char may be -1 to signify "no quoting":
158159
int min = Math.max(_cfgColumnSeparator, _cfgQuoteCharacter);
159160
for (int i = 0; i < _cfgLineSeparatorLength; ++i) {
160161
min = Math.max(min, _cfgLineSeparator[i]);
@@ -403,7 +404,8 @@ public void _writeQuoted(String text) throws IOException
403404
if (_outputTail >= _outputEnd) {
404405
_flushBuffer();
405406
}
406-
final char q = _cfgQuoteCharacter;
407+
// NOTE: caller should guarantee quote char is valid (not -1) at this point:
408+
final char q = (char) _cfgQuoteCharacter;
407409
_outputBuffer[_outputTail++] = q;
408410
// simple case: if we have enough room, no need for boundary checks
409411
final int len = text.length();
@@ -414,7 +416,7 @@ public void _writeQuoted(String text) throws IOException
414416
for (int i = 0; i < len; ++i) {
415417
char c = text.charAt(i);
416418
if (c == q) { // double up
417-
_outputBuffer[_outputTail++] = _cfgQuoteCharacter;
419+
_outputBuffer[_outputTail++] = q;
418420
if (_outputTail >= _outputEnd) {
419421
_flushBuffer();
420422
}
@@ -427,13 +429,15 @@ public void _writeQuoted(String text) throws IOException
427429
private final void _writeLongQuoted(String text) throws IOException
428430
{
429431
final int len = text.length();
432+
// NOTE: caller should guarantee quote char is valid (not -1) at this point:
433+
final char q = (char) _cfgQuoteCharacter;
430434
for (int i = 0; i < len; ++i) {
431435
if (_outputTail >= _outputEnd) {
432436
_flushBuffer();
433437
}
434438
char c = text.charAt(i);
435-
if (c == _cfgQuoteCharacter) { // double up
436-
_outputBuffer[_outputTail++] = _cfgQuoteCharacter;
439+
if (c == q) { // double up
440+
_outputBuffer[_outputTail++] = q;
437441
if (_outputTail >= _outputEnd) {
438442
_flushBuffer();
439443
}
@@ -443,7 +447,7 @@ private final void _writeLongQuoted(String text) throws IOException
443447
if (_outputTail >= _outputEnd) {
444448
_flushBuffer();
445449
}
446-
_outputBuffer[_outputTail++] = _cfgQuoteCharacter;
450+
_outputBuffer[_outputTail++] = q;
447451
}
448452

449453
public void writeRaw(String text) throws IOException
@@ -571,6 +575,10 @@ public void close(boolean autoClose) throws IOException
571575
*/
572576
protected final boolean _mayNeedQuotes(String value, int length)
573577
{
578+
// 21-Mar-2014, tatu: If quoting disabled, don't quote
579+
if (_cfgQuoteCharacter < 0) {
580+
return false;
581+
}
574582
// let's not bother checking long Strings, just quote already:
575583
if (length > MAX_QUOTE_CHECK) {
576584
return true;

src/test/java/com/fasterxml/jackson/dataformat/csv/TestParserQuotes.java

Lines changed: 33 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -6,16 +6,16 @@
66

77
public class TestParserQuotes extends ModuleTestBase
88
{
9-
/*
10-
/**********************************************************************
11-
/* Helper types
12-
/**********************************************************************
13-
*/
14-
159
@JsonPropertyOrder({"age, name"})
1610
protected static class AgeName {
1711
public int age;
1812
public String name;
13+
14+
public AgeName() { }
15+
public AgeName(int age, String name) {
16+
this.age = age;
17+
this.name = name;
18+
}
1919
}
2020

2121
@JsonPropertyOrder({"s1", "s2", "s3"})
@@ -56,4 +56,31 @@ public void testSimpleMultiLine() throws Exception
5656
assertFalse(it.hasNext());
5757
it.close();
5858
}
59+
60+
// [Issue#32]
61+
public void testDisablingQuotes() throws Exception
62+
{
63+
CsvMapper mapper = mapperForCsv();
64+
mapper.disable(CsvParser.Feature.WRAP_AS_ARRAY);
65+
CsvSchema schema = mapper.schemaFor(AgeName.class)
66+
.withoutQuoteChar()
67+
;
68+
69+
// First, read something and expect quotes to be retained
70+
71+
// final String RAW_NAME = "\"UNKNOWN\"";
72+
final String RAW_NAME = "\"UNKNOWN";
73+
74+
MappingIterator<AgeName> it = mapper.reader(schema).withType(AgeName.class).readValues(
75+
"38,"+RAW_NAME+"\n");
76+
assertTrue(it.hasNext());
77+
AgeName user = it.nextValue();
78+
assertEquals(38, user.age);
79+
assertEquals(RAW_NAME, user.name);
80+
assertFalse(it.hasNext());
81+
it.close();
82+
83+
String csv = mapper.writer(schema).writeValueAsString(user).trim();
84+
assertEquals("38,"+RAW_NAME, csv);
85+
}
5986
}

src/test/java/com/fasterxml/jackson/dataformat/csv/failing/TestWriter.java

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -4,13 +4,15 @@
44
import com.fasterxml.jackson.databind.ObjectWriter;
55
import com.fasterxml.jackson.dataformat.csv.CsvMapper;
66
import com.fasterxml.jackson.dataformat.csv.CsvSchema;
7+
import com.fasterxml.jackson.dataformat.csv.ModuleTestBase;
78
import com.google.common.collect.ImmutableMap;
89
import org.junit.Test;
910

10-
import java.lang.String;import static org.junit.Assert.assertEquals;
11-
12-
public class TestWriter {
11+
import java.lang.String;
1312

13+
// [Issue#33]
14+
public class TestWriter extends ModuleTestBase
15+
{
1416
@Test
1517
public void testWrite_NoNulls() throws JsonProcessingException {
1618
final CsvSchema.Builder csvSchemaBuilder = new CsvSchema.Builder();

0 commit comments

Comments
 (0)