Monday, 20 May 2013

Listening to traffic

While developing a web app, it's easy to inspect the traffic in the browser (chrome, IE and firefox have all the ability to show traffic related to the page you are debugging). I recently refactored a lib to remove a library and use a raw webrequest. This was a move to remove dependencies. In my tests I added machine name instead of localhost and got the traffic in Fiddler. An easy way to remove the abstraction and start accessing the real json api.

Thursday, 13 December 2012

Test your update scripts

This is a lesson I should have learned. It comes back to bite me and my coworkers ever so often. Running a script to update data without test is always quick and dirty. SSIS is a wonderful tool, but there are fundamental flaws to this tool as it's really hard to test SSIS packages. The beauty of using ruby or some other language (powershell, python, et.c.) is that you can write tests for the code. So, when you're doing yourself the favor of using ruby, write tests!

Tuesday, 4 December 2012

Writers and readers

Reading source code is hard. One way of dealing with this is rewriting what is not understood. This can help focus on some parts of the code, but can be detrimental since it's easy to overlook functionality in files that are not touched or files that look too complex (throwing away functionality). One way of doing this is to create a fork to rewrite one, in order to be able to throw away the changes made essentially to read the code. 

It's usually harder to read code than to write it. Trying to read a 700 line method can be to hard, thus it may need some therapeutic refactoring in reduce the components to pieces that can be understood.

Among several programmers, one reason why there is a tug o war between them can be because of non orthogonal and different best practices: They keep rewriting each others code because they have different ideas on what tradeoffs to prefer.

Thursday, 22 November 2012

Type matching in c#

I was thinking about how nice you have it in some languages where you can do a case statement for types. Thing is, we have a lot of compiler goodness in C# already.

By being explicit about the type and using type inference we can have a generic Case statement of a maximum length (depends on how many if else you think are ok to add).

I find it pretty sweet to write code like this:

TypeMatch.Case(exception,
  (GnarlyType e) => { HandleGnarly(e); },
  (FuncyType e1) => { HandleFunky(e1); },
  () => { Explode(); });

Instead of:
var e = exception as GnarlyType;
if (e!=null){ HandleGnarly(e); }
else {
  var e1 = exception as FunkyType;
  if (e1!=null){
    HandleFunky(e1);
  }else{
    Explode();
  }
}

Wednesday, 14 November 2012

IEnumerator love

Some times you encounter a class that implements IEnumerator without any IEnumerable implementation. To preserve the spirit of the enumerator (basically a cursor) we can just add an extension method that yields the elements.

But most of the time it's simply to add a ".Cast()" if it is IEnumerable without the extra type information.

Saturday, 10 November 2012

Debugging fuzzy coding

As a programmer it is easy to adopt a view of the world in light of our experience. The workings of the world starts to look as something out of the matrix. This has some funny consequences:
While listening to a person reasoning about the complicated events today from the point of view of famous thinkers; You can get the feeling of hearing a formalized thought pattern executed by a very complex machine. This sort of meta thinking naturally can be attributed to the formalization of execution that you work with, i.e. it is a view of programmable minds from the view of a mind programmed by thinking about programming.

This kind of thinking is useless unless it can be applied.

In the terms of a programmer: We are looking into how to debug the domain. The most important aspect of getting to know a domain is learning the language of that domain. The meaning of words inside that discussion context.

How do we reduce the task to something manageable? Simply learning all the language and statements associated with a given domain a huge undertaking. What is it that we want to learn? One of the interesting aspect of the domain is the grammar and the macro expansion of that domain. If we apply this to the world of programming, what kind of form of statements and what kind macros are we thinking in?

Most programmers work with the following concepts (I'm trying to simplify it):
methods, classes (and instances of the classes), variables
The most important execution constructs are:
if, for

Naming methods, classes and variables turns the execution into a meaningful flow. Mostly we are working with details surrounding execution of our concepts. A programmer is working a lot with detail management (much like a weaver of a tapestry have to manage the the threads in order to get a working picture). A very serious problem is that it's hard to find the right level of detail and abstraction to work with. The concepts above can be used to create detail at arbitrary levels. Kind of like lego versus duplo.

For the most part, many tend to prefer immutable constructs: Specified classes that do not change their behavior after initialization. This greatly simplifies reasoning.

Since programmers are working so much with abstractions, we tend to overdo abstraction.

What kind of conclusion can I draw from this? I'm not sure. It reads like the exact opposite of statistics. Mostly we program in predictable ways that get unpredictable due to the complexity rather than randomness of the input. Do we expect people to behave in this manner? Well, they sometimes behave similarly at a cursory glance. The big question would be what kind of programming we would write for people?

Wednesday, 7 November 2012

The code I wrote is a mess

Many times when you return to code that you have written you will swear and be annoyed with your lack of foresight.

We have been using a library since a while back. There is a definite strength to having a simple way of exposing actions from a console application. The code for the library and runner Isop is a mess. A mess designed to avoid having to code a messy console application in order to do quick interactions with your code (.net code to be specific). The focus of the lib has always been to cater to the needs of business applications. I've not spent time cleaning up the code since it satisfies the criteria: If it works, why fix it?

It annoys me that I don't have the time and energy to write beautiful code. This instinct is both healthy and dangerous. It helps you create maintainable applications, but it can also get you mired down into polishing. Ultimately it goes down to the fact that different structure caters to different intent and intent often changes (thus the unpleasant hindsight). Sometimes it's that you had something simple to begin with, but as you fill in the gaps it becomes complicated.

What I'm trying to say is that it's really hard to avoid the problem of complicated code or code that does not fit your intent. What you need is to refactor. This is the skill to use.