Beispiel #1
0
        //parse ach header line
        public static ACH ParseHeader(string achHeader, ACH ach, string internalString)
        {
            //if achHeader null or not 94 chars, error message
            string headerRecordTypeCode     = achHeader.Substring(0, 1);
            string priorityCode             = achHeader.Substring(1, 2);
            string immediateDestination     = achHeader.Substring(3, 10);
            string immediateOrigin          = achHeader.Substring(13, 10);
            string fileCreationDate         = achHeader.Substring(23, 6);
            string fileCreationTime         = achHeader.Substring(29, 4);
            string fileIdModifier           = achHeader.Substring(33, 1);
            string recordSize               = achHeader.Substring(34, 3);
            string blockingFactor           = achHeader.Substring(37, 2);
            string formatCode               = achHeader.Substring(39, 1);
            string immediateDestinationName = achHeader.Substring(40, 23);
            string immediateOriginName      = achHeader.Substring(63, 23);
            string referenceCode            = achHeader.Substring(86, 8);

            ach.SetHeader(internalString,
                          headerRecordTypeCode,
                          priorityCode,
                          immediateDestination,
                          immediateOrigin,
                          fileCreationDate,
                          fileCreationTime,
                          fileIdModifier,
                          recordSize,
                          blockingFactor,
                          formatCode,
                          immediateDestinationName,
                          immediateOriginName,
                          referenceCode);
            return(ach);
        }
Beispiel #2
0
 public static string PrintControl(ACH ach)
 {
     return(ach.ControlRecordTypeCode
            + ach.BatchCount
            + ach.BlockCount
            + ach.EntryAddendaCount
            + ach.EntryHash
            + ach.TotalDebit
            + ach.TotalCredit
            + ach.Reserved);
 }
Beispiel #3
0
        public static string PrintBatches(ACH ach)
        {
            string batchStr = "";
            string prepend  = "";

            foreach (Batch batch in ach.Batches)
            {
                batchStr += prepend + BatchPrinter.PrintBatch(batch);
                prepend   = "\n";
            }

            return(batchStr);
        }
Beispiel #4
0
        public static string PrintACH(ACH ach)
        {
            string achString = "";

            if (!string.IsNullOrEmpty(ach.InternalString))
            {
                achString += PrintInternal(ach) + "\n";
            }
            achString += PrintHeader(ach);
            achString += "\n" + PrintBatches(ach);
            achString += "\n" + PrintControl(ach);
            return(achString);
        }
Beispiel #5
0
 public static string PrintHeader(ACH ach)
 {
     return(ach.HeaderRecordTypeCode
            + ach.PriorityCode
            + ach.ImmediateDestination
            + ach.ImmediateOrigin
            + ach.FileCreationDate
            + ach.FileCreationTime
            + ach.FileIdModifier
            + ach.RecordSize
            + ach.BlockingFactor
            + ach.FormatCode
            + ach.ImmediateDestinationName
            + ach.ImmediateOriginName
            + ach.ReferenceCode);
 }
Beispiel #6
0
        static void Main(string[] args)
        {
            //TODO test that create with auto gen of everything also passes all verifies

            //this is what knows about files (as should any user of the NACHO library)
            if (args.Length <= 0)
            {
                //TODO print usage
            }
            else
            {
                System.IO.StreamReader reader = new System.IO.StreamReader(args[0]);
                string messages;
                ACH    ach = ACHParser.ParseStream(reader, out messages);
                //TODO verify ach
                System.Console.WriteLine(messages);
                System.Console.WriteLine("\n" + ACHPrinter.PrintACH(ach));
                System.Console.WriteLine(ach.Verify());

                Entry entry = new Entry(
                    "6",
                    "27",
                    "07640125",
                    "0",
                    "".PadLeft(17),
                    "".PadLeft(10),
                    "".PadLeft(15),
                    "".PadLeft(22),
                    "  ",
                    "0",
                    "".PadLeft(15));

                entry.CheckDigit = Entry.GenerateCheckDigit(entry.ReceivingDFI);


                Entry myEntry = Entry.CreateEntry(Entry.DEBIT_FOR_CHECKING, "012345678", "12345678901234567", "1000", "personid1234", "jon doe", "");
                Batch batch   = Batch.CreateBatch(Batch.SERVICE_CLASS_DEBIT_ONLY, "", "", "", Batch.STANDARD_ENTRY_PPD, "Wlfare Pln", "", "", "", 0);
                batch.AddEntry(myEntry);
                ACH myach = ACH.CreateACH("", " 123456789", "0123456789", "A", "my bank", "my company", "");
                myach.AddBatch(batch);
                myach.SetAutoValues();
                string msg = myach.Verify();
            }
        }
Beispiel #7
0
        //parse ach footer line
        public static ACH ParseControl(string achControl, ACH ach)
        {
            //TODO if achControl null or not 94 chars then error message
            string controlRecordType        = achControl.Substring(0, 1);
            string controlBatchCount        = achControl.Substring(1, 6);
            string controlBlockCount        = achControl.Substring(7, 6);
            string controlEntryAddendaCount = achControl.Substring(13, 8);
            string controlEntryHash         = achControl.Substring(21, 10);
            string controlTotalDebit        = achControl.Substring(31, 12);
            string controlTotalCredit       = achControl.Substring(43, 12);
            string controlReserved          = achControl.Substring(55, 39);

            ach.SetControl(controlRecordType,
                           controlBatchCount,
                           controlBlockCount,
                           controlEntryAddendaCount,
                           controlEntryHash,
                           controlTotalDebit,
                           controlTotalCredit,
                           controlReserved);
            return(ach);
        }
Beispiel #8
0
 public static string PrintInternal(ACH ach)
 {
     return(ach.InternalString);
 }
Beispiel #9
0
        //parse whole file, calls batch parser, returns new ach
        public static ACH ParseStream(System.IO.StreamReader reader, out string messages)
        {
            //or leave null, return null on (initial, not all) error?
            ACH ach = new ACH();


            string internalString = "";

            uint currentLineNumber = 1;

            messages = "";

            //set to false once we see a valid entry record type code
            //used to determine when we should stop seeing internal lines that
            //should only be at the beginning of the file
            bool didNotRecieveEntry = true;

            bool   recievedAchControlEntry = false;
            int    recordType;
            string internalNewLine = "";

            while ((recordType = reader.Peek()) != -1)
            {
                //if we recieved the ach control entry then add message that another line not expected (except empty line)
                //(but that should be handled by didNotRecieveEntry else case as error)

                //make sure all paths consume at least one line or infinite loop will result

                if (didNotRecieveEntry)
                {
                    //check if first char is a valid record type
                    if (recordType != BATCH_HEADER_RECORD_TYPE_ASCII_VALUE &&
                        recordType != ENTRY_RECORD_TYPE_ASCII_VALUE &&
                        recordType != ADDENDA_RECORD_TYPE_ASCII_VALUE &&
                        recordType != BATCH_CONTROL_RECORD_TYPE_ASCII_VALUE &&
                        recordType != ACH_CONTROL_RECORD_TYPE_ASCII_VALUE)
                    {
                        //this is basically the only valid path, all others should be error that appends message
                        if (recordType != ACH_HEADER_RECORD_TYPE_ASCII_VALUE)
                        {
                            //still an internal message, just append to internal message (with newlines between)
                            internalString += reader.ReadLine();
                            if (internalString != null)//shouldn't get null if recordType peek was successful, but just in case
                            {
                                internalString  = internalNewLine + internalString;
                                internalNewLine = "\n";
                                ++currentLineNumber;
                            }
                            else
                            {
                                //TODO report error it was null
                            }
                        }
                        else
                        {
                            //got the ach header entry, set values, go into batch parse call
                            string achHeader = reader.ReadLine();
                            if (achHeader != null)//shouldn't be null if recordType was successful, but just in case
                            {
                                ParseHeader(achHeader, ach, internalString);

                                //TODO handle if there there's a message from setheader
                                //if setheadermessage not null or ws then say so and add to messages

                                ++currentLineNumber;//update line number after possible use in error message
                            }
                            else
                            {
                                //TODO report unexpected null
                            }

                            //while next char is a new batch header (message if not a batch header or ach control record type, also error if end of stream -1)
                            //for each batch
                            while ((recordType = reader.Peek()) == BATCH_HEADER_RECORD_TYPE_ASCII_VALUE)
                            {
                                string batchMessages;

                                //TODO pass in a new line count int, add to total current line number count
                                uint  linesRead = 0;
                                Batch batch     = BatchParser.ParseStream(reader, out batchMessages, out linesRead, currentLineNumber);
                                messages += batchMessages;

                                if (batch != null)
                                {
                                    ach.Batches.Add(batch);
                                }
                            }
                            //for now test batch parse that just consumes non-ach control entries

                            //when out of batch parse call, reader probably pointing at ach control entry
                            //set more values with that

                            if (recordType != ACH_CONTROL_RECORD_TYPE_ASCII_VALUE)
                            {
                                //TODO consume line and give error message
                            }
                            else
                            {
                                //get ach control data
                                string achControl = reader.ReadLine();
                                if (achControl != null)
                                {
                                    ParseControl(achControl, ach);
                                    recievedAchControlEntry = true;
                                    //TODO if controlmessage is not null/ws then add error to message

                                    //TODO check control values (number of entries, hash, etc) here or in SetControl?  Probably SetControl

                                    ++currentLineNumber;

                                    //TODO error if any non-null/ws lines still in file at this point
                                }
                            }

                            didNotRecieveEntry = false;
                        }
                    }
                    else
                    {
                        messages += "\nReceived what looks like a batch, entry, or ACH control unexpectedly before an ACH header on line " + currentLineNumber.ToString() + ": '" + reader.ReadLine() + "'";
                        ++currentLineNumber;
                    }
                }
                else
                {
                    messages += "\nError on line " + currentLineNumber.ToString() + ": '" + reader.ReadLine() + "'";
                    ++currentLineNumber;
                }
            }

            if (didNotRecieveEntry && !recievedAchControlEntry)
            {
                messages += "\nDid not recieve both an ACH header and control";
            }

            return(ach);
        }