Oren Eini

CEO of RavenDB

a NoSQL Open Source Document Database

Get in touch with me:

oren@ravendb.net +972 52-548-6969

Posts: 7,567
|
Comments: 51,185
Privacy Policy · Terms
filter by tags archive
time to read 3 min | 415 words

The part that I hate the most about a project of a type that I never done before is the start. The issue is that I produce a design that mostly works, but when new stuff need to be implemented, I often need to explore several approaches before I know what will work for this project, my last post in an example of the approaches I thought about for persisting object graphs.

The thing that really bothers me is that changing those approaches can lead to major changes in the code. This means that there are extended periods of time that I can't even build the code successfully (30 minutes to an hour, at times). This makes me very nervous, but I don't see how I can avoid doing this as I study the various ways to implement this functionality. In this case, the changes involved changing an interface that was common to many classes in the project, so that caused quite a bit of pain until I settle on the correct approach.

I was at the Israel User Group meeting today and talked with Justin who termed this as a "Design Bug". I like this term. The only encouraging part is that after the initial pain I get a stable base to work from. The bad part is that the changes are big enough that I can't really test drive them beyond very big tests (save the object graph and then load it, for example). Those type of tests are more integration oriented than developer oriented. They help me define the big goal, but not how I get there.

I guess that this is why XP has Spiking for unknown functionality. I'm pretty sure that I'm commiting horrendous crime for doing this with code that will go to production, but in this case, I don't have much implemented yet (only some interesting graph output functionality), so I feel that it is safe to do this.

One thing that I noticed happening is that I lose abstraction along the way. For instnace, when I tried XML Serialization, it couldn't handle interfaces, so I changed several interfaces to abstract classes. When I realized that XML Serialization would probably not work, I revert the changes. For now, I'm seeing this as removing premature abstraction on my part, and if I need this functionality later, it wouldn't be a problem.

time to read 2 min | 395 words

Hammet has posted a comment from his article about Castle. The comment basically talks about reuse in NVelocity, one of the MonoRail's View Engines.

NVelocity is not a full fledge programming language, and that means that you can't do some things that you can do with a full langauge (at least not easily). The end result is that you really don't want to write TheUberGrid in NVelocity, so you may end up writing a one-off, per scenario template, instead of a general control that can accept anything you throws at it and is infinitely more configurable.

Surprisingly enough, or maybe not, the one-off effort usually pays better dividends in terms of the amount of effort involved to get what you need. There is quite a bit to say about specialized solutions to those problems. I had an UberGrid myself, and in order to add a new datatype, I need to edit a dictionary of type > parsing delegate. Sure, it can handle everything from enum localization to showing descriptive text of every object in the system. But I dread the day that I'll have to display the same object in two different forms, since that is not supported, and will require major re-writing.

We're using this UberGrid quite a bit, and it's... nice. But it doesn't really gives us anything. I still code the template per page, setting all the parameters, ordering, etc. It would be just as much work to do it in place, and there wouldn't be any duplication of effort or code. More and more, I'm leaning toward simpler solutions, rather than complex ones.

On the surface, the simple solution may not have all the quantities to do interplanetary navigation (which I don't relish doing in NVelocity), but I find that more often than not, I don't need to do this kind of stuff in those scenario. Good design will keep duplication away, but it shouldn't, and mustn't be at the cost of additional complexity or abstraction.

One off solutions, to one off scenarios are not to be discouraged. When you get the second duplicate scenario, then it is time to start worrying about reusing staff. And because you already got a working implementation, it will be much easier.

time to read 8 min | 1483 words

It's about time I'll post about my trouble making rules again. I've been doing some DATT* work on them, and I got to the point where I can write a rule in an hour or so (including tests, of course), instead of a day.

Partly it is because I'm now using Fitnesse to write the tests, which allows for a very nice way to declare rules and various states and then test them. I'm not sure if the problem is with what I'm doing or the way I'm doing it, but when I wrote the tests in C# I got a lot of tedious initialization code, one method call, and a lot of verfication code. Using Fitnesse I'm able to express that in a natural syntax:

create rules
create employee ayende
add employee rule coffee breaks every 3 hours

coffe break
employee coffee break time
ayende 13:00
ayende 14:00
ayende 17:00
ayende 20:00


validate employee ayende
can't take a coffee break on 14:00, take another on 16:00
what are you doing working on 20:00, go home!

It takes about ten minutes to write that, including the code that makes it run, and it's very malleble to change, so I can very easily create new test cases, or modify existing one. Fitnesse is usually used for acceptance tests, and I can certainly see why. The problem in testing rules is that almost by defination, they are first and foremost business concerns, and they usually need something to run on, which mean a lot of state to setup.

There are some patterns about dealing with that, but I found that Fitnesse is easy and add a lot to the fun. This week the FitLibrary for .Net should be out, which will make it even better.

* Design All The Time

time to read 1 min | 95 words

Well, it's been a while since the daily release cycles, but I've another release out, 2.4.1

This one adds the ability to mock abstract classes. It's strange, but until today I recieved no requests about it.

This release also comes with a custom version of Dynamic Proxy. Usually you won't have to worry about that, unless you intend to hack Rhino Mocks, and so far it doesn't seems like it would be neccecary.

Oh, the download is in the usual place.

time to read 2 min | 366 words

For me, the hardest part about software project is not quite the beginning, but what follows after. In the beginning, you need to work how to start the project, what is the environment you're going to work with, what is the data access strategy is going to be, etc. 

If you're an Agile practitioner, you're going to start out not knowing where you'll go. It may lead you to and fro as you discover the architecture of your system. I really don't like this part, since you're working hard, producing a lot of things that you'll need later, but you are still too early to get something meaningful going.

In my current project I started out by just mapping out my data acess strategy and implementing CRUD functionality for the basic building blocks. From there, you can start implementing most of the features of the system. But you can't do its heart yet.

Some software systems are all about CRUD, takes Blogs for example. But most applications, while using CRUD heavily, need an extra spark to be useful. A payroll system is mostly about CRUD. You add a worker, add a salary, and that is about it (yes, gross over simplification, I know). The interesting part usually happen behind the scene, and has little to do with CRUD per se. I'm at this point right now, I'm mostly over the routine database access stuff, although there are some pitfalls that I still need to thread carefully by.

What I've to do now is to give the system its heart. That extra something that you can't do in an Excel sheet, if you please :-). And that is the most frustrating part of the work as far as I'm concerned. I'm building blocks that will be useful at a later stage, but too many blocks are missing to get any real functionality. It's a problem because you can't really see what your efforts have given you. I find it maddening, and it's going to be another week at least before I've enough functionality to start combining it in interesting ways.

time to read 7 min | 1370 words

This post really hit a chord. I'm a firm believer in the values of tests. They're essenstial to have heathly software. But I often find myself in situations where a new functionality is just isn't testable. It's not testable because I've no idea how it is going to look until I write it.

Let's take a recent scenario, I wanted to add a rule that checks some variables within a spesific range. So I create a test that looks like this:

[TestMethod]
public void AtLeast5OccurancesInMonth()
{
   Calendar calendar= //.. create calender ...
   Rule rule = NumberOfOccurances.Min(5, Period.Month, Severity.Error);
   List<RuleResult> results = new List<RuleResult>();

   rule.Apply(calendar, results);

   Assert.AreEqual(3, results.Count);
}

When I get to the point where I write the rule, I find that I don't have any way to implement this rule because I've no way to get a month from a calendar. So to write this test I needed to have a way to get months from a calendar.

I supposed that I could've written a set of tests for getting months from calendars. But I would've lost the state that I was in, so I just added the ability to get  a collection of months from a calendar (which does require some logic) and wrote the code to implement the test. Later on, I went ahead and wrote the tests for the months property, of course.

A TDD Purist would note that I probably needed to just stub the Apply method to just return 3 RuleResults, and advance from there. In my opinion, such baby steps are dementing. Your milage might vary.

As an aside, as I was writing this post I got an email on the TDD Mailing List on just this subject. I'm going to repreduce my answer here in full:

I can tell you that I had /several/ cases where I knew that I wanted to add new functionality to my code and I wrote a test, run it, and it worked!

I was absolutely astounded, and started a debug fest that lasted thirty minutes to discover that yes; the code already does what I want.

I just had a moment like that two days ago, when I expected a result of 1 and got 28, and I realized that the code was doing the expected thing, but that my understanding of the system was flawed. You can check out the post about it the first surprise I got here.

In any complex system, you're going to get into situations where you can't really understand all the interactions in the systems. Maybe you want to get X when A, B & C are in a certain state. Unless you've a really good memory, you probably can't recall of the top of your head all the code paths that a test may exercise. Add in inheritance, polymorphism and a host of other GoF patterns, and you can very easily have functionality in the software that you don't realize that you have.

I often get to the point where I'm 90% done, and I need to add the final 40%, and I write a test in order to debug it to see what is going on. At a minimum, you can see how and why your test fails.

Of course, after saying all of that, I must confess that I sometimes writes code first, and tests later. But I really believe that once you're beyond the 50% point, you should precede each step with a test. Before that, it depends on the level of complexity in the system.

Well, what is my stance in this subject. The answer is that it depends :-)

When I'm just starting to write a system, I often write a little code, and then write the tests for it. I may experiment with a lot of different implementations until I decide that this or that is the currect way to go. Because of the very fluidity (is that a word? Apperantly it is, hard English langauge) of the project in the opening stages, I don't invest any time in writing tests that I'll end up throwing away after a couple of days. I just write the code to have something to start working on. When I'm starting to write the actual production code, I write enough until I get too nervous to continue. This usually start the moment I write code that relies on code that I haven't tested yet.

My algorithm for it very simple:

while(true)
{
   WriteCode();
   while ( IsNervousAboutCode() )
   {
        WriteTests();
    }
}

Not very sophisticated, but it works for me right now. When I start to get into the point where I'm building functionality on top of functionality, I revert to the good ole test-first pattern. Especially since then I can get a real value from designing the way the code will look and act when I'm writing the tests.

I find that in the beginning of a project writing the tests first is a problem for me since I actually don't know what I'll do next. I've a list of features, and I've 0 lines of code. What do I do then? I start writing the domain objects that I can see right now and write a test at the interaction points.

Something that I found very useful is write the stupid tests. The stupid tests are tests that test functionality that you know are going to work. Creating an object and asserting that the properties are currect, for instance. I keep catching stupid mistakes there that pass the compiler. This is one of the most common mistakes I make:

public Employee(string name)
{
   this._name = Name;
}

Can you spot the bug? The tests will catch it and make sure that I won't ever break it.

It seems that I'm making judgement calls based on gut feeling. So it may not be very helpful for the readers :-)

time to read 2 min | 333 words

Most of the interesting applications today talk to a database at one point or another. Unless you're writing a document centric client side application (think Word, Excel), you need to deal with databases.

And that is a problem. It's a problem because beyond this point, all your trusty tools leave you to forage forward on you on. A simple thing like a change of a field in the database may require a tremendous amount of effort to fix if you're not careful.

One danger that may occur if you subscribe to the school of thought of Continous Refactoring is that your domain model and the database model will grow apart. I recently had to change the name of a concept in my model. (Say, from Location to Position.)

It's very easy to do it on the code, and just as easy to leave the database in its current state (it's working, isn't it?). The problem is that while it's okay to map blog_author to Author, it's probably not okay to map user_location to Position. The cocepts has a slightly different meaning, and it's not very clear what the relationship is between the database and the model unless you look at the mapping.

I had some problems with getting a script from my databse (now solved ;-) ), so this was a real issue to me. I kept changing the database schema using VS 2005, but I had no way to get the scripts out. (Which would've allowed the use of the advance technique known as Search & Replace).

Anyway, the point of this post is that you need to pay attention to the database when you refactor the model. It's hard, especially if you've data in the database and not an empty structure. But letting the databse out of sync with the model is a sure way to get confustion along the road.

time to read 2 min | 238 words

I was in the Agile Israel meeting earilier this earlier week, and I overheard a couple of guys* talking about mocking objects. The talk went something like this:

Guy #1: Most developers don't understand mock objects.
Guy #2: But then you explain it to them and when they get it, they become the local gurus.
Guy #1: Yes, but then they try to use mocks everywhere and make a mess of things.

Do you have similar experiances? I'm the author of a mocking framework, and I find that I don't use mocking all that often. Then again, my recent projects were mainly in compiler internals and the like, not much you can mock there.

I'm currently building a business application, so I expect to make heavy use of mocking the moment I move away from the data access layer, which is my curent focus.

* This was my first meeting, so I don't know any of the names, I did meet Justin, though.

time to read 2 min | 391 words

I've often spoke of how much I want an easy-to-use bug tracking software, but I never did much about it since no free package was able to satisfy everything that I needed. Specifically, free, open source and working with MySQL. A big plus would've been if it would've been written in C# or Boo.

Now, bug tracking is certainly not a hard problem, is mostly direct work against database, some reports and a lot of thinking about work flow. Beyond that, it's mostly grunt work of adding features that are neccecary, but quite boring. (Prove me wrong, show me a feature of a bug tracking system that excites you.) Create a way to search bugs with enough flexibility is a must, for example, but it isn't really interesting.

I've now found a package that I'm glad to be able to use: FlySpray is a free (LGPL) bug tracking software that has quite a bit of features that I consider neccecary, has a good UI (unlike some other systems) and seems to be capable. It has one big minus as far as I'm concerned, which is that it's written in PHP. I don't have anything against PHP*, but it does bring back the bad old days of ASP and the mess that can happen there.

Unline the usual, the longest part was not cutomizing the UI to integrate with the rest of the site (although it took quite some time). The long part was integrating with the bug tracking system (and vice versa). It had to do with writing shell scripts on a remote system which I only have shell access to. I'm not a unix guy, and shell scripts require some deep knowledge in the ability of the system in order to get them to work as expected. I couldn't even get the script to execute properly and in the end I just used FlySpray' script as is. In addition: command line editing seems to require far too much knowledge.

Anyway, you can see the latest addition to my sites here: http://bugs.ayende.com

* I was able to understand enough that I could dig in the code and fix some problems without ever writing a single line of PHP code.

time to read 2 min | 223 words

I've released Rhino Mocks 2.0 to the wild, beware of rapid productivity increases that may result :-)

Anyway, it took so long because I wrote detailed documentation for the project. For such a small library, it sure has a lot of way to use it. You can read the documentation here. And download the binaries and code from here. I wrote this version after seeing how cool NMock2 was, to take advantage of many of the ideas there. The resulting product is very good, IMHO :-D

Drop me a line if you like it. 

On other news, Roy has a great 3 minutes speech about Mock Objects.

I should also mention that I posted the documentation as an article for Code Project. Hopefully this will generate some interest in the library. I'm going to put it on TestDriven.Com as well, last time I got to be mentioned on the Daily Grind.

"Modem: How a Southerner asks for seconds..." -- Tech Support Slogan
"If your attack is going well, you have walked into an ambush." -- Army Sergant
"IBM: It's Beyond Monolithic" -- Tech Support Slogan

FUTURE POSTS

No future posts left, oh my!

RECENT SERIES

  1. Production Postmortem (52):
    07 Apr 2025 - The race condition in the interlock
  2. RavenDB (13):
    02 Apr 2025 - .NET Aspire integration
  3. RavenDB 7.1 (6):
    18 Mar 2025 - One IO Ring to rule them all
  4. RavenDB 7.0 Released (4):
    07 Mar 2025 - Moving to NLog
  5. Challenge (77):
    03 Feb 2025 - Giving file system developer ulcer
View all series

RECENT COMMENTS

Syndication

Main feed Feed Stats
Comments feed   Comments Feed Stats
}