1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33 package net.sf.flatpack;
34
35 import java.io.File;
36 import java.io.FileNotFoundException;
37 import java.io.FileReader;
38 import java.io.IOException;
39 import java.io.InputStream;
40 import java.io.InputStreamReader;
41 import java.io.Reader;
42 import java.util.ArrayList;
43 import java.util.List;
44 import java.util.stream.Stream;
45
46 import net.sf.flatpack.structure.ColumnMetaData;
47 import net.sf.flatpack.util.ParserUtils;
48 import net.sf.flatpack.xml.MetaData;
49
50
51
52
53
54
55 public abstract class AbstractParser implements Parser {
56
57 private boolean handlingShortLines = false;
58
59 private boolean ignoreExtraColumns = false;
60
61 private boolean preserveLeadingWhitespace = true;
62
63 private boolean preserveTrailingWhitespace = false;
64
65 private boolean columnNamesCaseSensitive = false;
66
67 private boolean initialised = false;
68
69 private boolean ignoreParseWarnings = false;
70
71 private boolean nullEmptyStrings = false;
72
73
74 private MetaData pzMetaData = null;
75
76 private String dataDefinition = null;
77
78 private Reader dataSourceReader = null;
79
80 private List<Reader> readersToClose = null;
81
82 private boolean flagEmptyRows;
83
84 private boolean storeRawDataToDataError;
85
86 private boolean storeRawDataToDataSet;
87
88 private String dataFileTable = "DATAFILE";
89
90 private String dataStructureTable = "DATASTRUCTURE";
91
92 private boolean addSuffixToDuplicateColumnNames = false;
93
94 public boolean isAddSuffixToDuplicateColumnNames() {
95 return addSuffixToDuplicateColumnNames;
96 }
97
98 @Override
99 public Parser setAddSuffixToDuplicateColumnNames(final boolean addSuffixToDuplicateColumnNames) {
100 this.addSuffixToDuplicateColumnNames = addSuffixToDuplicateColumnNames;
101 return this;
102 }
103
104 protected AbstractParser(final Reader dataSourceReader) {
105 this.dataSourceReader = dataSourceReader;
106 }
107
108 protected AbstractParser(final Reader dataSourceReader, final String dataDefinition) {
109 this.dataSourceReader = dataSourceReader;
110 this.dataDefinition = dataDefinition;
111 }
112
113 protected void initStreamOrSource(final InputStream dataSourceStream, final File dataSource) throws FileNotFoundException {
114 if (dataSourceStream != null) {
115 final Reader r = new InputStreamReader(dataSourceStream);
116 setDataSourceReader(r);
117 addToCloseReaderList(r);
118 } else if (dataSource != null) {
119 final Reader r = new FileReader(dataSource);
120 setDataSourceReader(r);
121 addToCloseReaderList(r);
122 }
123 }
124
125
126
127
128
129
130 @Override
131 public boolean isHandlingShortLines() {
132 return handlingShortLines;
133 }
134
135
136
137
138
139
140 @Override
141 public Parser setHandlingShortLines(final boolean handleShortLines) {
142 this.handlingShortLines = handleShortLines;
143 return this;
144 }
145
146 @Override
147 public boolean isIgnoreExtraColumns() {
148 return ignoreExtraColumns;
149 }
150
151 @Override
152 public Parser setIgnoreExtraColumns(final boolean ignoreExtraColumns) {
153 this.ignoreExtraColumns = ignoreExtraColumns;
154 return this;
155 }
156
157 @Override
158 public boolean isPreserveLeadingWhitespace() {
159 return preserveLeadingWhitespace;
160 }
161
162 @Override
163 public Parser setPreserveLeadingWhitespace(final boolean preserveLeadingWhitespace) {
164 this.preserveLeadingWhitespace = preserveLeadingWhitespace;
165 return this;
166 }
167
168 @Override
169 public boolean isPreserveTrailingWhitespace() {
170 return preserveTrailingWhitespace;
171 }
172
173 @Override
174 public Parser setPreserveTrailingWhitespace(final boolean preserveTrailingWhitespace) {
175 this.preserveTrailingWhitespace = preserveTrailingWhitespace;
176 return this;
177 }
178
179 @Override
180 public final DataSet parse() {
181 if (!initialised) {
182 init();
183 }
184 return doParse();
185 }
186
187 @Override
188 public final StreamingDataSet parseAsStream() {
189 return new StreamingRecord(parse());
190 }
191
192 @Override
193 public final Stream<Record> stream() {
194 return new StreamingRecord(parse()).stream();
195 }
196
197 protected abstract DataSet doParse();
198
199 protected abstract void init();
200
201 protected void closeReaders() throws IOException {
202 if (readersToClose != null) {
203 for (final Reader r : readersToClose) {
204 r.close();
205 }
206 }
207 }
208
209
210
211 protected void addToCloseReaderList(final Reader r) {
212 if (readersToClose == null) {
213 readersToClose = new ArrayList<>();
214 }
215 readersToClose.add(r);
216 }
217
218 protected void addToMetaData(final List<ColumnMetaData> columns) {
219 if (pzMetaData == null) {
220 pzMetaData = new MetaData(columns, ParserUtils.buidColumnIndexMap(columns, this));
221 } else {
222 pzMetaData.setColumnsNames(columns);
223 pzMetaData.setColumnIndexMap(ParserUtils.buidColumnIndexMap(columns, this));
224 }
225 }
226
227 protected boolean isInitialised() {
228 return initialised;
229 }
230
231 protected void setInitialised(final boolean initialised) {
232 this.initialised = initialised;
233 }
234
235 protected String getDataDefinition() {
236 return dataDefinition;
237 }
238
239 protected void setDataDefinition(final String dataDefinition) {
240 this.dataDefinition = dataDefinition;
241 }
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258 protected void addError(final DefaultDataSet ds, final String errorDesc, final int lineNo, final int errorLevel, final String lineData) {
259 if (errorLevel == 1 && isIgnoreParseWarnings()) {
260
261 return;
262 }
263 ds.addError(new DataError(errorDesc, lineNo, errorLevel, lineData));
264 }
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285 protected void addError(final DefaultDataSet ds, final String errorDesc, final int lineNo, final int errorLevel, final String lineData,
286 final String lastColName, final String lastColValue) {
287 if (errorLevel == 1 && isIgnoreParseWarnings()) {
288
289 return;
290 }
291 ds.addError(new DataError(errorDesc, lineNo, errorLevel, lineData, lastColName, lastColValue));
292 }
293
294
295
296
297 protected Reader getDataSourceReader() {
298 return dataSourceReader;
299 }
300
301
302
303
304
305 protected void setDataSourceReader(final Reader dataSourceReader) {
306 this.dataSourceReader = dataSourceReader;
307 }
308
309 @Override
310 public boolean isColumnNamesCaseSensitive() {
311 return columnNamesCaseSensitive;
312 }
313
314 @Override
315 public Parser setColumnNamesCaseSensitive(final boolean columnNamesCaseSensitive) {
316 this.columnNamesCaseSensitive = columnNamesCaseSensitive;
317 return this;
318 }
319
320 @Override
321 public boolean isIgnoreParseWarnings() {
322 return ignoreParseWarnings;
323 }
324
325 @Override
326 public Parser setIgnoreParseWarnings(final boolean ignoreParseWarnings) {
327 this.ignoreParseWarnings = ignoreParseWarnings;
328 return this;
329 }
330
331 @Override
332 public boolean isNullEmptyStrings() {
333 return nullEmptyStrings;
334 }
335
336 @Override
337 public Parser setNullEmptyStrings(final boolean nullEmptyStrings) {
338 this.nullEmptyStrings = nullEmptyStrings;
339 return this;
340 }
341
342 public MetaData getPzMetaData() {
343 return pzMetaData;
344 }
345
346 public void setPzMetaData(final MetaData pzMap) {
347 this.pzMetaData = pzMap;
348 }
349
350
351
352
353 @Override
354 public boolean isFlagEmptyRows() {
355 return flagEmptyRows;
356 }
357
358
359
360
361
362 @Override
363 public Parser setFlagEmptyRows(final boolean flagEmptyRows) {
364 this.flagEmptyRows = flagEmptyRows;
365 return this;
366 }
367
368
369
370
371 @Override
372 public boolean isStoreRawDataToDataError() {
373 return storeRawDataToDataError;
374 }
375
376
377
378
379
380 @Override
381 public Parser setStoreRawDataToDataError(final boolean storeRawDataToDataError) {
382 this.storeRawDataToDataError = storeRawDataToDataError;
383 return this;
384 }
385
386
387
388
389 @Override
390 public boolean isStoreRawDataToDataSet() {
391 return storeRawDataToDataSet;
392 }
393
394
395
396
397
398 @Override
399 public Parser setStoreRawDataToDataSet(final boolean storeRawDataToDataSet) {
400 this.storeRawDataToDataSet = storeRawDataToDataSet;
401 return this;
402 }
403
404 @Override
405 public String getDataFileTable() {
406 return dataFileTable;
407 }
408
409 @Override
410 public Parser setDataFileTable(final String dataFileTable) {
411 this.dataFileTable = dataFileTable;
412 return this;
413 }
414
415 @Override
416 public String getDataStructureTable() {
417 return dataStructureTable;
418 }
419
420 @Override
421 public Parser setDataStructureTable(final String dataStructureTable) {
422 this.dataStructureTable = dataStructureTable;
423 return this;
424 }
425 }