Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for empty segments (no data elements) #11

Merged
merged 1 commit into from
Apr 29, 2020
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -495,9 +495,15 @@ public EDIStreamWriter writeElementData(CharSequence text) throws EDIStreamExcep
ensureLevelAtLeast(LEVEL_ELEMENT);
for (int i = 0, m = text.length(); i < m; i++) {
char curr = text.charAt(i);

if (characters.isDelimiter(curr)) {
throw new IllegalArgumentException("Value contains separator");
if (releaseIndicator > 0) {
write(releaseIndicator);
} else {
throw new IllegalArgumentException("Value contains separator: " + curr);
}
}

write(curr);
elementBuffer.put(curr);
}
Expand Down
18 changes: 14 additions & 4 deletions src/main/java/io/xlate/edi/internal/stream/tokenization/Lexer.java
Original file line number Diff line number Diff line change
Expand Up @@ -232,6 +232,10 @@ public void parse() throws IOException, EDIException {
closeSegment();
eventsReady = nextEvent();
break;
case SEGMENT_EMPTY:
emptySegment();
eventsReady = nextEvent();
break;
case COMPONENT_END:
handleComponent();
eventsReady = nextEvent();
Expand Down Expand Up @@ -265,12 +269,12 @@ public void parse() throws IOException, EDIException {
}

void handleStateHeaderTag(int input) {
buffer.put((char) input);
buffer.put((char) input);
dialect.appendHeader(characters, (char) input);
}

void handleStateElementDataBinary() {
/*
/*
* Not all of the binary data has been consumed. I.e. #next was
* called before completion.
*/
Expand All @@ -280,7 +284,7 @@ void handleStateElementDataBinary() {
}

void handleStateInterchangeCandidate(int input) throws EDIException {
stream.mark(500);
stream.mark(500);
buffer.put((char) input);
final char[] header = buffer.array();
final int length = buffer.position();
Expand All @@ -293,7 +297,7 @@ void handleStateInterchangeCandidate(int input) throws EDIException {
}

void handleStateHeaderData(int input) throws EDIException {
dialect.appendHeader(characters, (char) input);
dialect.appendHeader(characters, (char) input);

if (characters.isDelimiter(input)) {
if (characters.getDelimiter(CharacterClass.SEGMENT_DELIMITER) == input) {
Expand Down Expand Up @@ -441,6 +445,12 @@ private void closeSegment() throws EDIException {
enqueue(sen, 0);
}

private void emptySegment() throws EDIException {
openSegment();
popMode(Mode.SEGMENT);
enqueue(sen, 0);
}

private void handleElement() throws EDIException {
if (previous != State.ELEMENT_END_BINARY) {
addElementEvent();
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ public enum State {
ELEMENT_END_BINARY(17),

SEGMENT_END(10),
SEGMENT_EMPTY(10),

TRAILER_TAG_I(18),
TRAILER_TAG_E(19),
Expand Down Expand Up @@ -111,6 +112,7 @@ public enum State {
private static final State ER = State.ELEMENT_REPEAT;
private static final State EE = State.ELEMENT_END;
private static final State SE = State.SEGMENT_END;
private static final State SY = State.SEGMENT_EMPTY;

private static final State ZI = State.TRAILER_TAG_I;
private static final State ZE = State.TRAILER_TAG_E;
Expand Down Expand Up @@ -157,8 +159,8 @@ public enum State {

/* SE+TS Tag Search */{ TS, T1, T1, T1, ZI, T1, T1, ZU, T1, T1, __, __, __, __, __, TS, __, __, __ },
/* T1 Tag Char 1 * */{ __, T2, T2, T2, T2, T2, T2, T2, T2, T2, __, __, __, __, __, __, __, __, __ },
/* T2 Tag Char 2 * */{ __, T3, T3, T3, T3, T3, T3, T3, T3, T3, __, SB, __, __, __, __, __, __, __ },
/* T3 Tag Char 3 * */{ __, __, __, __, __, __, __, __, __, __, __, SB, __, __, __, __, __, __, __ },
/* T2 Tag Char 2 * */{ __, T3, T3, T3, T3, T3, T3, T3, T3, T3, SY, SB, __, __, __, __, __, __, __ },
/* T3 Tag Char 3 * */{ __, __, __, __, __, __, __, __, __, __, SY, SB, __, __, __, __, __, __, __ },

/* Element Process */{ ED, ED, ED, ED, ED, ED, ED, ED, ED, ED, SE, EE, CE, ER, DR, EI, EI, ED, EI },
/* Data Release */{ ED, ED, ED, ED, ED, ED, ED, ED, ED, ED, ED, ED, ED, ED, ED, EI, EI, ED, EI },
Expand Down
101 changes: 101 additions & 0 deletions src/test/java/io/xlate/edi/internal/stream/StaEDIStreamWriterTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -631,6 +631,107 @@ public int read() throws IOException {
assertEquals(expected.toString().trim(), result.toString().trim());
}

@Test
public void testInputEquivalenceEDIFACT_IATA_PNRGOV() throws Exception {
EDIInputFactory inputFactory = EDIInputFactory.newFactory();
final ByteArrayOutputStream expected = new ByteArrayOutputStream(16384);

InputStream source = new InputStream() {
final InputStream delegate;
{
delegate = getClass().getResourceAsStream("/EDIFACT/pnrgov.edi");
}

@Override
public int read() throws IOException {
int value = delegate.read();

if (value != -1) {
expected.write(value);
return value;
}

return -1;
}
};
EDIStreamReader reader = inputFactory.createEDIStreamReader(source);

EDIOutputFactory outputFactory = EDIOutputFactory.newFactory();
outputFactory.setProperty(EDIOutputFactory.PRETTY_PRINT, true);
ByteArrayOutputStream result = new ByteArrayOutputStream(16384);
EDIStreamWriter writer = null;

EDIStreamEvent event;
String tag = null;
boolean composite = false;

try {
while (reader.hasNext()) {
event = reader.next();

switch (event) {
case START_INTERCHANGE:
for (Map.Entry<String, Character> delim : reader.getDelimiters().entrySet()) {
outputFactory.setProperty(delim.getKey(), delim.getValue());
}
writer = outputFactory.createEDIStreamWriter(result);
writer.startInterchange();
break;
case END_INTERCHANGE:
writer.endInterchange();
break;
case START_SEGMENT:
tag = reader.getText();
writer.writeStartSegment(tag);
break;
case END_SEGMENT:
writer.writeEndSegment();
break;
case START_COMPOSITE:
writer.writeStartElement();
composite = true;
break;
case END_COMPOSITE:
writer.endElement();
composite = false;
break;
case ELEMENT_DATA:
String text = reader.getText();

if ("UNA".equals(tag)) {
continue;
}

if (composite) {
writer.startComponent();
writer.writeElementData(text);
writer.endComponent();
} else {
if (reader.getLocation().getElementOccurrence() > 1) {
writer.writeRepeatElement();
} else {
writer.writeStartElement();
}
writer.writeElementData(text);
writer.endElement();
}
break;
case ELEMENT_DATA_BINARY:
writer.writeStartElementBinary();
writer.writeBinaryData(reader.getBinaryData());
writer.endElement();
break;
default:
break;
}
}
} finally {
reader.close();
}

assertEquals(expected.toString().trim(), result.toString().trim());
}

@Test
public void testInputEquivalenceEDIFACTB() throws Exception {
EDIInputFactory inputFactory = EDIInputFactory.newFactory();
Expand Down
88 changes: 88 additions & 0 deletions src/test/resources/EDIFACT/pnrgov.edi
Original file line number Diff line number Diff line change
@@ -0,0 +1,88 @@
UNA:+.\*'
UNB+IATA:1+1A+KRC+130527:0649+0003'
UNH+1+PNRGOV:11:1:IA+270513/0649/SQ/602'
MSG+:22'
ORG+1A:MUC'
TVL+270513:1430:270513:2205+SIN+ICN+SQ+602'
EQN+1'
SRC'
RCI+1A:3PGZOV::190313:1354'
DAT+700:270513:0559'
ORG+1A:MUC+32393340:SINSQ08AA+NCE+SQ:NCE+A+SG+ELPD+CFDE59+9C'
TIF+BELT:I+ISABELLE MRS:A:2:1'
FTI+SQ:8794285757'
IFT+4:63::SQ'
REF+:001C451486DFF0CC'
SSR+DOCS:HK:1:SQ:::::/P/GBR/512731999/GBR/20SEP12/FI/25OCT17/BELT/SOP HY OLIVIA/'
SSR+DOCS:HK:1:SQ:::::/P/GBR/509229987/GBR/01JUL78/F/12NOV22/BELT/ISAB ELLE RUTH/'
TIF+BELT:I+SOPHY:IN:3'
IFT+4:63::SQ'
SSR+DOCS:HK:1:SQ:::::/P/GBR/512731999/GBR/20SEP12/FI/25OCT17/BELT/SOP HY OLIVIA/'
TVL+270513:1430:270513:2205+SIN+ICN+SQ+602:D'
RPI+1+HK'
APD+333'
SSR+INFT:HK:1:SQ:::SIN:ICN:BELT/SOPHY 20SEP12+::2'
SSR+DOCS:HK:1:SQ:::SIN:ICN:/P/GBR/509229987/GBR/01JUL78/F/12NOV22/BEL T/ISABELLE RUTH/+::2'
RCI+1A:3PGZOV::190313:1354'
DAT'
ORG+SQ++++A'
TRI++SIN-168:::2'
TIF+BELT:I+ISABELLE MRS:A:2'
SSD+011D++++J'
TBD++3:33:700++HP:SIN- 168+618:0123456789:2:ICN+618:0123456788:3:ICN+618:0123456787:722356:ICN'
DAT'
ORG+SQ++++A'
TRI++SIN-169:::3'
TIF+BELT:I+SOPHY:IN:3'
SSD+011D++++J'
LTS+0/O/NM/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+0/O/SS/SQ 602 D 27MAY 1 SINICN LK1 1430 2205/NN \*1A/E\* /SQ/SG/C/I/CAB J//1///// /Y 1625/B 153//AY 1838/EY 1685/SINICN/D'
LTS+0/O/SR/SSR INFTSQNN1 BELT/SOPHY 20SEP12/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+0/O/SR/SSR FQTVSQHK/ SQ8794285757 S/KFES/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+0/O/SR/SSR FQTSSQHK1 SQ8794285757 S/KFES/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+0/O/SR/SSR DOCSSQHK1 P/GB/509229987/GB/01JUL78/F/12NOV22/BELT/ISABELLE//H/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+0/Z/AMADEUS E RETAIL CR-SINSQ08AA 32393340 SU 0001AA/DS- 9CCFDE59 19MAR1354Z'
LTS+0/1/R/SR/SSR INFTSQKK1 BELT/SOPHY 20SEP12/HN/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+1/Z/1AINV RM SQ 191354 CR-1AINV RM SQ 0000 19MAR1354Z'
LTS+2/P/QE/SINSQ0100/1C15D4'
LTS+2/Z/1AINV RM SQ 191354 CR-1AI NV R 19MAR1354Z'
LTS+3/Z/ -SQ/WSSQSAA CR-SINSQ08AA 32393340 GS 9999WS/RO-9C404C04 SAAW330SQ 00000000 19MAR1354Z'
LTS+4/Z/1AINV RM SQ 191354 CR-1AINV RM SQ
LTS+0/5/C/5/AP AMADEUS-H'
LTS+0/5/C/27/TKXL 20MAR/0004/SINSQ08AA'
LTS+5/A/27/TKOK 19MAR/SINSQ08AA'
LTS+5/6/R/27/TKOK 19MAR/SINSQ08AA'
LTS+6/Z/AA CR-SINSQ08AA 32393340 SU 0001AA/DS-9CCFDF66 19MAR1359Z'
LTS+7/Z//DCS-SYNCUS CR-SINSQ00CO 00000000 PD 6160MC/DS-9CBABA44 23MAY1240Z'
LTS+0/8/C/SR/SSR FQTVSQHK/ SQ8794285757 S/KFES/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+0/8/C/SR/SSR FQTSSQHK1 SQ8794285757 S/KFES/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+8/A/SR/SSR FQTVSQHK/ SQ8794285757 G/QPPS/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+8/A/SR/SSR FQTSSQHK1 SQ8794285757 G/QPPS/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+8/Z/CSXAPU CR-NCE1A0SQ0 SU 0001AA 24MAY2009Z'
LTS+9/Z/1AINV RM SQ 242009 CR-1AINV RM SQ 0000 24MAY2009Z'
LTS+1/10/R/SR/SSR INFTSQHK1 BELT/SOPHY 20SEP12/KK/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+4/10/R/SR/SSR BSCTSQHK1/KK/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+10/Z/ETK-ISSBOE CR-SINSQ01W0 32391122 GS 1916VV/RO-9CB39093 MUCPI2SQ1 00000000 25MAY0309Z'
LTS+11/A/SK/SK LKPX SQ HK1 Z8OWIE-P1/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+11/Z/ISSBOE CR-SINSQ01W0 32391122 GS 1916VV/RO-9CB39093 MUCPI2SQ1 00000000 25MAY0313Z'
LTS+12/Z/MRS BELT CR-SINSQ01W0 32391122 GS 1916VV/RO-9CB39093 MUCPI2SQ1 00000000 25MAY0315Z'
LTS+13/Z/1AINV RM SQ 250315 CR-1AINV RM SQ 0000 25MAY0315Z'
LTS+14/A/7/RX \*\*\*\*\*\*\*\* ATTN SINKKXH SINKDXH SINKNXH PLS ASSIST PAX WITH TKT 618-2402058077 AND 618-2402241436 TO BE SEATED TOGETHER FLT'
LTS+14/A/7/RX SQ602 D SIN - ICN 27MAY13 14\:30 ON BSCT SEAT X MANY THANKS SINRRRSQ'
LTS+14/A/7/RX MS BELT CALLED TO UPDATE SEAT RQST X ADDED SEAT / MEAL X TELEX SENT X NIL SEATS AND MEALS X MOBILE CONTACT NUMBER UPDATED'
LTS+14/A/7/RX X VIAN / 8\:48 IST 25/5/2013'
LTS+14/Z/MRS BELT CR-SINSQ01W0 32391122 GS 1916VV/RO-9CB39093 MUCPI2SQ1 00000000 25MAY0320Z'
LTS+15/A/SR/SSR DOCSSQHK1 P/GBR/512731999/GBR/20SEP12/FI/25OCT17/BELT/SOPHY OLIVIA//BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+15/A/SR/SSR DOCSSQHK1 P/GBR/512731999/GBR/20SEP12/FI/25OCT17/BELT/SOPHY OLIVIA//SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+15/Z//DCS-IREQ CR-SINSQ00VW 00000000 GS 9743EC/DS-9CBCCB00 27MAY0422Z'
LTS+0/16/C/SR/SSR DOCSSQHK1 P/GB/509229987/GB/01JUL78/F/12NOV22/BELT/ISABELLE//H/SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+16/A/SR/SSR DOCSSQHK1 P/GBR/509229987/GBR/01JUL78/F/12NOV22/BELT/ISABELLE RUTH//SQ 602 D 27MAY SINICN/BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+16/Z//DCS-IREQ CR-SINSQ00VW 00000000 GS 9743EC/DS-9CBAB9B5 27MAY0423Z'
LTS+17/A/SR/SSR DOCSSQHK1 P/GBR/509229987/GBR/01JUL78/F/12NOV22/BELT/ISABELLE RUTH//BELT/ISABELLE MRS(ADT)(INF/SOPHY/20SEP12)'
LTS+17/Z//DCS-IREQ CR-SINSQ00VW 00000000 GS 9743EC/DS-9CBAB9D5 27MAY0423Z'
LTS+18/Z//DCS-SYNCUS CR-SINSQ00VW 00000000 GS 9743EC/DS-9CBABA1D 27MAY0423Z'
LTS+19/Z//DCS-SYNCUS CR-SINSQ00VW 00000000 GS 9743EC/DS-9CBCCB14 27MAY0423Z'
LTS+20/Z//DCS-SYNCUS CR-SINSQ00CO 00000000 PD 2092EL/DS-9CBAB94B 27MAY0559Z'
LTS+21/Z//DCS-SYNCUS CR-SINSQ00CO 00000000 PD 2092EL/DS-9CBABA1A 27MAY0559Z'
UNT+85+1'
UNZ+1+0003'