Sometimes I like to reflect on where I’ve been and where I’m going at work. I’m not talking about any “greater scheme of things”, but rather how my programming is progressing. The book “Code Complete Second Edition“, by Steve McConnell, has me thinking about this again. Rather than let my memory of everywhere I’ve been in my programming at Sharp HealthCare fade away over time, I’ve decided it’s time to put it to words.
What “Code Complete Second Edition” offers is “practical” advice on “software construction”. Whereas one might see “Microsoft” on a book about coding, and think, “It’s a book on C♯ and VB for .Net,” “Code Complete Second Edition” is a code-agnostic look at the process of writing software. I’ve only just started chapter four, before which topics involve pre-coding preparation and design, but I can see where the entire book will be well worth the read.
The work I do doesn’t involve preparation and design. There are no requirements spelled out. There’s no foundation set before the first line of code is written. And I’ve paid for it in rewriting and refactoring code. While part of this was due to a VB6-to-VB.Net upgrade, a lack of planning is the main culprit. So, how did I get here? And where am I going?
When I was hired as Sharp HealthCare in the PFS-ICD, it was unofficially on the promise that my programming ability would improve the EDI process.
Although IS handled building and maintaining the back-end for loading information (payments from government, insurance) into our system, the system has many shortcomings, so a lot of automatically posted information had to be deleted from the system, and then re-keyed correctly. This is where my job started: deleting incorrectly posted items, and re-posting them correctly.
I started out as one would expect: taking ten hours to do an eight hour job (without working overtime to finish it each day). I was working during my breaks and lunch (just don’t tell my supervisor!) to get it all done. I knew this was only temporary, until I really started to get comfortable with the work-flow, and learned tips and tricks to cut down on the take required. Until then, Blue Cross would send double the workload on Tuesdays, but nothing on Wednesdays, meaning I typically had extra papers leftover scattered across my desk on Tuesdays, but Wednesdays were a day where I found myself catching up on work.
PFS-ICD didn’t have a dedicated programmer. There were a few Visual Basic 6 coders, including my manager, but a manager simply doesn’t have the time to be coding everything needed for everyone working under him. This is where the unofficial promise of improving things with my programming came into play.
I started working at Sharp with experience in PHP (which would not be applicable here), Ruby (I managed to get permission to use Ruby, which helped while I learned languages “more fitting” to a Windows-based business environment), and C++ (which I had repeatedly learned and repeatedly forgot prior to working at Sharp).
At Sharp, aside from working in Ruby a bit, I started out with C++ and Visual Basic 6. Even a small C++ program seems to take a lot longer for Visual Studio to compile than it would take to compile a similar-sized program in Linux. Because of this, C++ only saw use for two main programs, while I learned VBScript and Visual Basic 6.
Wait, where did I find time for coding in C++, and learning Visual Basic 6? Wasn’t I taking ten hours to do eight hours of work? I managed to get that eight hour job down to eight hours, then to about six, simply by getting to better know the process. I want from making many mistakes in my first couple of weeks (due to different processes which look similar to a newcomer) to being able to handle the process with relative ease. It didn’t hurt that I was taking a massive number of notes.
The First Months
My first big change was to the Blue Cross process. We receive ERA files in the HIPAA EDI 835 format. (835 is used for incoming payments, and 837, which I don’t deal with, is for outgoing billing.)
The 835 ERA files we received included two kinds of payments: those we were being paid for electronically by ACH, and those which would be later paid for by check by mail.
The transactions paid for by check would be hand-keyed with other checks received on the same day. To our back-end, however, those 835 ERA files included nothing by payments to be posted now. Each ACH and each check in the file would generate a new batch in our system, each batch containing all the transactions (payments) covered by the amount.
My job up to this point had been to go through all those Blue Cross batches. For each of three of our hospital facilities, there would be a single large batch for an ACH, then many smaller batches for check and ACH payments. I had to delete the smaller batches, then by-hand key back in any which were for ACH payments to the large batch. There was also deleting incorrectly posted transactions and re-keying them into the large batch.
Wouldn’t it be nice if the back-end that loads the file and generates batches had some way of knowing which batches to post and which not to post? And wouldn’t it be nice if it could post everything into one batch for me?
That’s where one of my two C++ programs came into play. ACH payments and checks both had a number to represent that payment. For a check, it was the check number. For an ACH, it was essentially a check number, but without a check. ACH payments start with “EG”, followed by a number. Check numbers do not contain a letter in the number. Non-payments have a number starting with a “Z”. Using this information, an 835 ERA file could be loaded, the data could be parsed (rather crudely back then), and anything which should not be posted could be removed from the file (outputting a new file, to preserve the original). At the same time, all of the transactions could be grouped into “one payment”, so our system would post only what should be posted, and into one, single batch.
I had written a C++ program for Medicare 835 ERAs as well, but I don’t recall what went into that. I bet I still have the source code somewhere, but these programs have been replaced, so the source code is no longer needed.
I managed to save so much time thanks to these programs.
Somewhere along the line, I had learned enough about the 835 ERA format to write a Ruby program which can read in an 835 ERA file, parse data from it, and do something with that data. This was used to be able to generate EOB files for Blue Cross payments, since at the time we printed those to paper, but the program we used to generate EOBs was an old DOS program which had to be tricked into being able to print (meaning it could only print from my supervisor’s computer with my supervisor logged in, and only to a certain printer). Also, it would print the entire file, leading to a massive waste in paper if the EOB for a Blue Cross check was lost, and had to be re-printed. By generating these with a Ruby script, I could save them as Word documents (which lead to learning how to create a RTF file by hand), and any given page could be printed out on its own. (It wouldn’t be until later than we’d store EOBs electronically, and stop printing them completely, which further saved time each day, and cut down material costs.)
Another program, written in Visual Basic 6, would control a program called EXTRA! from a company called Attachmate (using a DLL which comes with EXTRA! which allows controlling it), allowed me to write a complex program which would look into each account within an 835 ERA (using a crude method of reading, modifying, and writing the file, which I improved over time into something almost nice) to check each account from the file in our system, and see where on the account the payment should be posted. This effectually eliminated transactions being posted incorrectly (save for minor situations).
I was still fairly new to Visual Basic 6 at the time, but I had learned how to do various things in Visual Basic 6 (as opposed to Visual Basic prior-to-6 methods I had been picking up along the way), and I didn’t know anything about controlling EXTRA!, so when I wrote the program to do this, I actually started by using a program my manager had written to do many different things using EXTRA!. I pulled out the part I need, and improved it for my own use. The best part was always being able to sit back and take a break while that program automated going through our system and gathering information for correctly posting payments. It looked like I was rapidly doing a lot of work, but really I needed only sit there and stare at the screen. Sure, this was also a good time to get other work done, but this early version of the program used up 100% of the computer’s processing power (due to use of an infinite loop to see when EXTRA! had loaded the next screen from our system), so I was limited to sorting, paper-clipping, and stapling any printed papers that needed that done, which was common as printing the EOB typically came right before running a file through this program.
With the elimination of the majority of deleting and re-keying, I was really saving time! But Visual Basic 6 is very limited in some areas, and I was putting a lot of work into working around its limitations. As I was writing more and more Visual Basic 6 applications to automate things, I knew I couldn’t keep using the language. That lead to the request for an upgrade of Visual Studio, so I could use Visual Basic .Net.
Moving to VB.Net
Working with VB.Net after Visual Basic 6 meant I was programming in VB.Net the Visual Basic 6 way, not unlike how my early Visual Basic 6 coding was done in a way used in Visual Basic prior to version 6 (and picked up by me by looking at my manager’s code and by looking things up online). As I wrote new programs in VB.Net, and over time ported my Visual Basic 6 programs (and my C++ programs) to VB.Net, I slowly learned the VB.Net way of doing things. And let me say, there are many nice things about VB.Net, with very little to complain about.
When I worked in Visual Basic 6, I kept a folder called “functions”, and in there I had files where I kept functions that different programs would use. For working in VB.Net, I learned how to write DLLs. Those were fairly loose, and only recently (May of 2009) have I started to develop a “Sharp namespace”, with the functionality of the DLLs sorted into a logical hierarchy, which nicely ties everything together.
Now, here is where “Code Complete Second Edition” comes into play. If I had known about using namespaces in my own code and had properly planned them out (which goes in line with an early chapter in the book about code architecture), I wouldn’t be spending time refactoring my programs to support namespaces for these classes stored in DLLs.
There’s more than that, however. Only recently have I built a logging system which allows any of my programs to log errors to files. When I was the only one using these programs, it was easy enough to have errors as message boxes, and to use the debugger. With a lot of my EDI work now done by a co-worker who uses my programs, as well as my supervisor using my programs, I needed a method to log errors and information about those errors when a program was being used by someone else. This is the kind of planning that simply did not go into any of my existing programs.
These days, most of my programs have been combined into one, single, monolithic “workflow” program. A menu-based system allows for easily navigation from one task to another, and it all really does work well. It took a long time to get to this point, but one thing this workflow program can boast is that it had a fair amount of planning put into its design. Granted, the design has evolved over time, but I planned to write such a program back when I used Visual Basic 6. I had ideas, and worked with those ideas, but never wrote anything due to shortcomings of those ideas. The coding started as a VB.Net application, and the planning allowed me to avoid many potential problems.
Looking to the Future
There are still applications to be written. With Steve McConnell’s “Code Complete Second Edition”, I’m going to be looking at writing those properly from scratch. I also anticipate learning many things about proper design for writing classes, and otherwise improving code structure, which can also be used to improve my existing code. Sure, that’s more refactoring, but when I don’t work with a form for six months, then a new functionality has to be put into it, I want that code to be the cleanest, best written, most well organized, most clearly and understandably commented code it can be.