Skip to content

Instantly share code, notes, and snippets.

@joncloud
Created August 19, 2016 21:55
Show Gist options
  • Save joncloud/08b498e50591bbaa926c20f22ddd598c to your computer and use it in GitHub Desktop.
Save joncloud/08b498e50591bbaa926c20f22ddd598c to your computer and use it in GitHub Desktop.
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace ConsoleApplication17
{
class Program
{
static void Main(string[] args)
{
string text = "0T011.35000000OKAPPROVEDCVI406000000025701601100000000099901122201TEST/BLUEFIN03120160801150802CARDBIN=412493#";
using (StringReader reader = new StringReader(text))
using (CommandReader commandReader = new CommandReader(reader))
{
commandReader.Read();
var t01 = commandReader.Command.ToT01();
Console.WriteLine(new { t01.Amount });
}
}
}
class T01Command
{
public decimal Amount { get; set; }
}
static class CommandExtensions
{
public static T01Command ToT01(this Command command)
{
T01Command t01 = new T01Command();
// Ignore type.
command.Fields.Dequeue();
var field = command.Fields.Dequeue();
t01.Amount = decimal.Parse(field.Value);
return t01;
}
}
class Command
{
public Command(int status)
{
Fields = new Queue<Field>();
Status = status;
}
public Queue<Field> Fields { get; }
public int Status { get; }
}
class Field
{
public Field(string value)
{
Units = new Queue<string>();
Value = value;
}
public Queue<string> Units { get; }
public string Value { get; }
public override string ToString() => Value;
}
class CommandReader : IDisposable
{
TextReader reader;
CommandReaderState state;
public CommandReader(TextReader reader)
{
this.reader = reader;
}
public Command Command { get; private set; }
public void Read()
{
int position = 0;
char[] buffer = new char[80];
int read;
const char stx = '\x02';
const char fs = '\x1c';
const char us = '\x1f';
StringBuilder field = new StringBuilder();
StringBuilder unit = new StringBuilder();
int statusStart = -1;
while ((read = reader.ReadBlock(buffer, position, buffer.Length)) > 0)
{
for (int i = 0; i < buffer.Length;)
{
char c = buffer[i];
switch (state)
{
case CommandReaderState.None:
if (c == stx) { state = CommandReaderState.Status; }
if (c == fs) { state = CommandReaderState.BeginField; }
i++;
break;
case CommandReaderState.Status:
if (statusStart == -1) { statusStart = i; }
if (c == fs)
{
int status = int.Parse(new string(buffer, statusStart, i - statusStart));
Command = new Command(status);
state = CommandReaderState.BeginField;
}
i++;
break;
case CommandReaderState.BeginField:
if (unit.Length > 0)
{
Command.Fields.Peek().Units.Enqueue(unit.ToString());
}
unit.Clear();
if (field.Length > 0)
{
Command.Fields.Enqueue(new Field(field.ToString()));
}
field.Clear();
state = CommandReaderState.Field;
break;
case CommandReaderState.Field:
if (c == fs) { state = CommandReaderState.BeginField; }
else if (c == us) { state = CommandReaderState.BeginUnit; }
else { field.Append(c); }
i++;
break;
case CommandReaderState.BeginUnit:
if (unit.Length > 0)
{
Command.Fields.Peek().Units.Enqueue(unit.ToString());
}
unit.Clear();
state = CommandReaderState.Unit;
break;
case CommandReaderState.Unit:
if (c == fs) { state = CommandReaderState.BeginField; }
else if (c == us) { state = CommandReaderState.BeginUnit; }
else { unit.Append(c); }
i++;
break;
}
}
}
}
public void Dispose()
{
((IDisposable)reader).Dispose();
}
enum CommandReaderState
{
None,
Status,
BeginField,
Field,
BeginUnit,
Unit
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment