From 9ccf78fe6871035117560e46eb47ad6763114f18 Mon Sep 17 00:00:00 2001 From: Julien Date: Sun, 15 Mar 2015 20:37:59 +0000 Subject: [PATCH 1/2] Validation: Calculate the FIX messages body length and compare it to the one given in FIX field BodyLength(9) Also put correct values in the examples --- scripts/app/FixParser.js | 43 ++++++++++++++++++++++++++++++++++++++++ scripts/app/main.js | 8 ++++---- styles/styles.css | 10 ++++++++++ 3 files changed, 57 insertions(+), 4 deletions(-) diff --git a/scripts/app/FixParser.js b/scripts/app/FixParser.js index 5bcc984..a517bdf 100644 --- a/scripts/app/FixParser.js +++ b/scripts/app/FixParser.js @@ -6,6 +6,7 @@ define( { var FIELD_CHECKSUM = 10, BEGIN_STRING = 8, + BODY_LENGTH = 9, MSG_TYPE = 35, SENDER_COMP_ID = 49, TARGET_COMP_ID = 56; @@ -57,6 +58,7 @@ define( fieldId: fieldId, value: value, field: field, + raw: fieldId + "=" + value + "\01", decodedValue: decodedValue, classes: classes.join(' ') }); @@ -117,6 +119,47 @@ define( } ); + // BodyLength(9) verification + _.each( + messages, + function(message) + { + var field_bodylength = undefined; + length = 0; + + _.each( + message.fields, + function(field) + { + if ( field.fieldId == BODY_LENGTH ) { + field_bodylength = field; + return; + } + + // Some fields are not part of the FIX message body, skip them + if ( field.fieldId == BEGIN_STRING || field.fieldId == FIELD_CHECKSUM ) { + return; + } + + length += field.raw.length; + } + ); + + if ( ! field_bodylength ) { + return; + } + + if ( field_bodylength.value == length ) { + field_bodylength.classes += ' valid'; + field_bodylength.decodedValue = 'Valid'; + } + else { + field_bodylength.classes += ' invalid'; + field_bodylength.decodedValue = '/!\\ Invalid (expected ' + length + ')'; + } + } + ); + return messages; }; diff --git a/scripts/app/main.js b/scripts/app/main.js index 32c2355..82aa667 100644 --- a/scripts/app/main.js +++ b/scripts/app/main.js @@ -137,10 +137,10 @@ define( $('#clear').click(function() { input.val(''); return false; }); var sampleMessages = [ - 'outgoing: 8=FIX.4.2|9=179|35=AE|56=LSEHub|49=BROKERX|128=LSETR|34=2175|52=20120126-15:15:54|918=GBP|31=89.0000000|64=20120126|828=1|60=20120126-13:32:49|32=6|22=4|571=124|43=N|570=N|150=0|48=GB0007188757|10=017|\n' + - 'incoming: 8=FIX.4.2|9=113|35=AR|49=LSEHub|56=BROKERX|115=LSETR|34=2006|52=20120126-15:15:54|370=20120126-15:15:54.822|571=124|150=0|939=0|10=126|', - 'outgoing: 8=FIX.4.2|9=127|35=AE|49=LSEHub|56=LSETR|115=BROKERX|34=2287|43=N|52=20120330-12:14:09|370=20120330-12:14:09.816|571=00008661533TRLO1-1-1-0|150=H|10=113|\n' + - 'incoming: 8=FIX.4.2|9=106|35=AR|34=2486|49=LSETR|52=20120330-12:14:10.379|56=LSEHub|128=BROKERX|150=H|571=00008661533TRLO1-1-1-0|939=0|10=103', + 'outgoing: 8=FIX.4.2|9=178|35=AE|56=LSEHub|49=BROKERX|128=LSETR|34=2175|52=20120126-15:15:54|918=GBP|31=89.0000000|64=20120126|828=1|60=20120126-13:32:49|32=6|22=4|571=124|43=N|570=N|150=0|48=GB0007188757|10=017|\n' + + 'incoming: 8=FIX.4.2|9=112|35=AR|49=LSEHub|56=BROKERX|115=LSETR|34=2006|52=20120126-15:15:54|370=20120126-15:15:54.822|571=124|150=0|939=0|10=126|', + 'outgoing: 8=FIX.4.2|9=130|35=AE|49=LSEHub|56=LSETR|115=BROKERX|34=2287|43=N|52=20120330-12:14:09|370=20120330-12:14:09.816|571=00008661533TRLO1-1-1-0|150=H|10=113|\n' + + 'incoming: 8=FIX.4.2|9=109|35=AR|34=2486|49=LSETR|52=20120330-12:14:10.379|56=LSEHub|128=BROKERX|150=H|571=00008661533TRLO1-1-1-0|939=0|10=103|', 'outgoing: 8=FIX.4.2|9=175|35=AE|49=BROKERX|56=LSEHub|34=17|52=20120202-16:04:44|128=LSETR|918=EUR|31=89.0000000|64=20120202|828=1007|60=20120202-16:04:44|32=6|22=4|571=1698|570=N|150=0|48=AT0000785555|10=087|\n' + 'incoming: 8=FIX.4.2|9=111|35=AR|49=LSEHub|56=BROKERX|115=LSETR|34=16|52=20120202-16:04:44|370=20120202-16:04:45.257|571=1698|150=0|939=0|10=026|' ]; diff --git a/styles/styles.css b/styles/styles.css index 82cb07e..e1ba22a 100644 --- a/styles/styles.css +++ b/styles/styles.css @@ -120,6 +120,16 @@ tr.system-field color: #aaa; } +tr.header-field.valid .field-value +{ + color: #0c0; +} + +tr.header-field.invalid .field-value +{ + color: #f00; +} + tr.deprecated-field td.field-name { text-decoration: line-through; From d0797843534363cf3c07e083f8b820fc9b6f9b3c Mon Sep 17 00:00:00 2001 From: Julien Date: Sun, 15 Mar 2015 20:50:25 +0000 Subject: [PATCH 2/2] Validation: Calculate the checksum and compare it to the one given in the FIX message Also put correct checksums in the examples --- scripts/app/FixParser.js | 41 ++++++++++++++++++++++++++++++++++++++++ scripts/app/main.js | 12 ++++++------ styles/styles.css | 2 ++ 3 files changed, 49 insertions(+), 6 deletions(-) diff --git a/scripts/app/FixParser.js b/scripts/app/FixParser.js index a517bdf..4f95df4 100644 --- a/scripts/app/FixParser.js +++ b/scripts/app/FixParser.js @@ -160,6 +160,47 @@ define( } ); + // Checksum(10) verification + _.each( + messages, + function(message) + { + var field_checksum = undefined; + sum = 0; + + _.each( + message.fields, + function(field) + { + if ( field.fieldId == FIELD_CHECKSUM ) { + field_checksum = field; + return; + } + + for ( var i = 0 ; i < field.raw.length ; i++ ) { + sum += field.raw.charCodeAt(i); + } + } + ); + + // Modulo 256 + pad up to 3 characters with zero + sum = ("00" + (sum % 256)).slice(-3); + + if ( ! field_checksum ) { + return; + } + + if ( field_checksum.value == sum ) { + field_checksum.classes += ' valid'; + field_checksum.decodedValue = 'Valid'; + } + else { + field_checksum.classes += ' invalid'; + field_checksum.decodedValue = '/!\\ Invalid (expected ' + sum + ')'; + } + } + ); + return messages; }; diff --git a/scripts/app/main.js b/scripts/app/main.js index 82aa667..e9fea6b 100644 --- a/scripts/app/main.js +++ b/scripts/app/main.js @@ -137,12 +137,12 @@ define( $('#clear').click(function() { input.val(''); return false; }); var sampleMessages = [ - 'outgoing: 8=FIX.4.2|9=178|35=AE|56=LSEHub|49=BROKERX|128=LSETR|34=2175|52=20120126-15:15:54|918=GBP|31=89.0000000|64=20120126|828=1|60=20120126-13:32:49|32=6|22=4|571=124|43=N|570=N|150=0|48=GB0007188757|10=017|\n' + - 'incoming: 8=FIX.4.2|9=112|35=AR|49=LSEHub|56=BROKERX|115=LSETR|34=2006|52=20120126-15:15:54|370=20120126-15:15:54.822|571=124|150=0|939=0|10=126|', - 'outgoing: 8=FIX.4.2|9=130|35=AE|49=LSEHub|56=LSETR|115=BROKERX|34=2287|43=N|52=20120330-12:14:09|370=20120330-12:14:09.816|571=00008661533TRLO1-1-1-0|150=H|10=113|\n' + - 'incoming: 8=FIX.4.2|9=109|35=AR|34=2486|49=LSETR|52=20120330-12:14:10.379|56=LSEHub|128=BROKERX|150=H|571=00008661533TRLO1-1-1-0|939=0|10=103|', - 'outgoing: 8=FIX.4.2|9=175|35=AE|49=BROKERX|56=LSEHub|34=17|52=20120202-16:04:44|128=LSETR|918=EUR|31=89.0000000|64=20120202|828=1007|60=20120202-16:04:44|32=6|22=4|571=1698|570=N|150=0|48=AT0000785555|10=087|\n' + - 'incoming: 8=FIX.4.2|9=111|35=AR|49=LSEHub|56=BROKERX|115=LSETR|34=16|52=20120202-16:04:44|370=20120202-16:04:45.257|571=1698|150=0|939=0|10=026|' + 'outgoing: 8=FIX.4.2|9=178|35=AE|56=LSEHub|49=BROKERX|128=LSETR|34=2175|52=20120126-15:15:54|918=GBP|31=89.0000000|64=20120126|828=1|60=20120126-13:32:49|32=6|22=4|571=124|43=N|570=N|150=0|48=GB0007188757|10=206|\n' + + 'incoming: 8=FIX.4.2|9=112|35=AR|49=LSEHub|56=BROKERX|115=LSETR|34=2006|52=20120126-15:15:54|370=20120126-15:15:54.822|571=124|150=0|939=0|10=059|', + 'outgoing: 8=FIX.4.2|9=130|35=AE|49=LSEHub|56=LSETR|115=BROKERX|34=2287|43=N|52=20120330-12:14:09|370=20120330-12:14:09.816|571=00008661533TRLO1-1-1-0|150=H|10=074|\n' + + 'incoming: 8=FIX.4.2|9=109|35=AR|34=2486|49=LSETR|52=20120330-12:14:10.379|56=LSEHub|128=BROKERX|150=H|571=00008661533TRLO1-1-1-0|939=0|10=073|', + 'outgoing: 8=FIX.4.2|9=175|35=AE|49=BROKERX|56=LSEHub|34=17|52=20120202-16:04:44|128=LSETR|918=EUR|31=89.0000000|64=20120202|828=1007|60=20120202-16:04:44|32=6|22=4|571=1698|570=N|150=0|48=AT0000785555|10=076|\n' + + 'incoming: 8=FIX.4.2|9=111|35=AR|49=LSEHub|56=BROKERX|115=LSETR|34=16|52=20120202-16:04:44|370=20120202-16:04:45.257|571=1698|150=0|939=0|10=015|' ]; $('a.sample-message-link').click(function() diff --git a/styles/styles.css b/styles/styles.css index e1ba22a..761732e 100644 --- a/styles/styles.css +++ b/styles/styles.css @@ -120,11 +120,13 @@ tr.system-field color: #aaa; } +tr.system-field.valid .field-value, tr.header-field.valid .field-value { color: #0c0; } +tr.system-field.invalid .field-value, tr.header-field.invalid .field-value { color: #f00;