Friday 28 September 2012

Spring Data Neo4j, @MapResult, Cypher, Casing and You!

A quick tip for those of you who are using Cypher with Spring Data Neo4j (SDN):

If you're using the @MapResult way in your Neo4j repositories, be careful of what you use in the corresponding @ResultColumn annotations.

For example, let's say you have the following repository definition (assume that you don't want to use the built-in findAll() method in this case; this example can be extended to other mapping results WLOG):


 
public interface MyRepository extends GraphRepository, RelationshipOperationsRepository {
 @Query("START n=node:__types__(className='com.yourorg.yourproject.entities.MyModel') RETURN COLLECT(n)")
 MyModelData getAllMyModels();
 
 @MapResult
 public interface MyModelData
 {
  @ResultColumn("COLLECT(n)")
  Iterable getMyModels(); 
 }
}

What you'd expect getAllMyModels() to do is to simply return all of those nodes that meet the Cypher criteria (note that the Cypher query above is very similar to what is generated by SDN in its findAll() method; the index referenced is, in fact, created and persisted by SDN).

However, if you call this code, you will get an error similar to the following:

"org.springframework.data.neo4j.support.conversion.NoSuchColumnFoundException: Expexted a column named COLLECT(n) to be in the result set."

You're probably scratching your head and asking yourself at this point, "But I am returning 'COLLECT(n)'!  It's right there in the Cypher query!"

And you're completely right--it is there!

However, try running that same query in the Neo4j web console (wherever your graph database is residing).

Dig through the results, and you'll see that the column returned isn't, in fact, "COLLECT(n)", but, "collect(n)".

Yep, you got it!  It's case sensitive!

So if you change

@ResultColumn("COLLECT(n)")

...to...

@ResultColumn("collect(n)")

...(note that casing of "collect") you'll be good as gold.

Remember that the next time you're diving deep into SDN.

And, as an update, I continue to work on the project I started back in June, and am finally making some headway.  I'm coming across some interesting stuff, and I hope to share more in the coming weeks.

We'll see you on the next post!

Wednesday 27 June 2012

Persisting to Neo4j via Spring Data (or, "Aren't We Persistent?")

Hi gang!

Ok, I'm back with a new post, this time with a post about a couple quirks I ran into while implementing some test cases for Spring Data using Neo4j.  They're not bugs by any stretch; it's just new behaviour to get used to as you venture into the Spring Data world (which I'm loving, by the way).

During my copious amounts of downtime (that should be read while imagining me rolling my eyes so hard that I fall over backwards in my chair), I've been putting together a little playground for me to mess around with and play with Spring Data.

It's definitely evolving and changing as I change things up and try out new ideas, and I fully plan on sharing more about this in future posts.

For now, though, I'm just discussing a couple potential pitfalls newcomers to Spring Data might fall prey to (please pardon the prepositional phrase; I'm sure it won't be the last one).

Background
I've wanted to play with Spring Data a bit more seriously for some time now, so I started a few weeks ago and, I have to say, I'm loving every second of it.  (I'm already a huge Spring fan, and the annotations continue to make my life easier.)

My sandbox goes something like this: After having gone through the docs for Spring Data (especially "Good Relationships"), I thought I'd try out something similar for myself, borrowing the whole "store" concept (as it seems to me to be the best, first choice for implementing a graph database).

Instead of using the whole "movie store" concept, I switched to something a little different to avoid total code reuse (I do borrow some code from the link above but modify it an awful lot).

For any geeks around my age (or older), you will remember a certain computer software retailer called Babbage's.  I have fond memories of begging my parents to go into the store every time we passed one, which wasn't often (at least I don't think it was...).  GameStop Corporation went on to purchase Babbage's (and EB Games, and a bunch of other software retailers), so you're unlikely to see a Babbage's by that name.

With that short trip down memory lane finished (more like memory cul de sac), I decided to model my domain after the concept of a software retailer.  My store will cleverly enough be called Von Neumann's (any CS major and most geeks out there are currently groaning at that joke).

Domain Model
Currently, the domain model consists of the following:



Even looking at the UML diagram above, we can see that it's based on a graph model (can you pick out the entities and/or the relationship(s)?).

Test Cases' Setup
After setting up the relevant project (which I did as a Maven project), I set forth creating some tasks using JUnit.  Before creating the actual test cases, I needed to make sure I had my testing context setup.  I also needed away to ensure that any data being persisted was wiped clean after each run.

Fortunately, instead of having to create such functionality for my project, I learned that Neo4j already has a handy solution!  The ImpermanentGraphDatabase.  This little gem can be found in the Neo4j kernel.  Specifically, I added these lines to my POM (you can see the specific version I'm using, too):


<dependency>
<groupId>org.neo4j</groupId>
<artifactId>neo4j-kernel</artifactId>
<version>1.8.M03</version>
</dependency>


...and then adding the following line to my testing context:

<bean id="graphDBService" class="org.neo4j.test.ImpermanentGraphDatabase" destroy-method="shutdown"/>

And presto!  A suitable testing graph database for my test cases!

(Warning: I am using the latest version that I found worked best for me and is compatible with all my other dependencies.  ImpermanentGraphDatabase as available in earlier versions of Neo4j, as well.)

It should also be noted that I make use of both the Neo4j repositories interfaces AND the Neo4jOperations class for persisting and retrieval.

Another note is that I've made the entire test class @Transactional.

Test Cases Proper
I'll list two of them below and a couple of the quirks I noticed.

Ensuring a Customer Can Make a Purchase
This test case consists of creating a Customer object, a couple Game objects, and making sure that Purchases can be created, persisted and retrieved (along with the associated entities). 


 
 @Test
 public void customerCanMakePurchases()
 {
  // setup our game constants
  final int QTY = 1;
  final String GAME_TITLE = "Space Weasel 3.5";
  final String GAME_TITLE_2 = "The Space Testing Game";
  final String GAME_DESC = "Rodent fun in space!";
  final String GAME_DESC_2 = "Tests in space!";
  final int STOCK_QTY = 10;
  final float PRICE = 59.99f;
  
  // setup our customer constants
  final String FIRST_NAME = "Edgar";
  final String LAST_NAME = "Neubauer";
  
  // create our customer for this test
  Customer customer1 = new Customer();
  
  // set the customer's properties (NOTE: "firstName" is an indexed property in the Customer entity, but "lastName" is not!)
  customer1.setFirstName(FIRST_NAME);
  customer1.setLastName(LAST_NAME);

  // create our games for this test
  Stock game1 = new Game(GAME_TITLE, GAME_DESC, STOCK_QTY, PRICE);
  Stock game2 = new Game(GAME_TITLE_2, GAME_DESC_2, STOCK_QTY + 5, PRICE + 5);

First, do the setup.  (And, for the sake of brevity, I'm leaving out the annotated entities.)

Nothing strange going on here--just creating two games and a single customer.  It is worth noting (for later on) that "firstName" is an indexed property of the Customer entity/node.  This means that it is searchable (also recall that Neo4j's default indexing engine is Lucene).


It had to be done.
The games we've chosen are clearly AAA-title games.  These tests should be interesting.


  // save entities BEFORE saving the relationships!
  template.save(game1);
  template.save(game2);
  template.save(customer1);

  // make those purchases! Support our test economy!
  // (NOTE: "makePurchase" actually uses the "template" parameter to persist the relationship, so no need to do it again)
  Purchase p1 = customer1.makePurchase(template, game1, QTY);  
  Purchase p2 = customer1.makePurchase(template, game2, QTY);

Above, we make sure to persist the 2 games and single customer.  We also do this prior to persisting any relationships.  This is necessary.  In this case, I make use of an instance variable called "template" which is actually an instance of 
Neo4jOperations.  This is one way of accessing the necessary persistence/retrieval functionality we need.

We then create 2 Purchase objects/relationships (Purchase is actually a relationship entity).  It is also worth noting that, instead of using the "template" object to persist the relationships, I've followed the Neo4j tutorial book "Good Relationships" and attempted another way of doing persistence, i.e. by passing the "template" object into the necessary method and having the method (in this case makePurchase) actually do the persisting of the newly-created Purchase.

Again, both "game1" and "game2" need to be persisted prior to persisting any relationships between them.

Still with me?


  // retrieve the customer
  Customer customer1Found = this.customerRepository.findByPropertyValue("firstName", FIRST_NAME);
  
  //
  // Tests
  //
  
  // can we find/retrieve the customer?
  assertNotNull("Unable to find customer.", customer1Found);
  
  // can we find the specific customer for which we are looking?
  assertEquals("Returned customer but not the one searched for.", FIRST_NAME, customer1Found.getFirstName());
  
  // does the retrieved customer have its non-indexed properties returned, as well?
  assertEquals("Returned customer doesn't have non-indexed properties returned.", LAST_NAME, customer1Found.getLastName());

  // retrieve the customer's purchases
  // (NOTE: We case as a Collection just to make checking the number of puchases easier)  
  Iterable purchasesIt = customer1Found.getPurchases();
  Collection purchases = IteratorUtil.asCollection(purchasesIt);
  
  // do we have the correct number of purchases?
  assertEquals("Number of purchases do not match.", 2, purchases.size());

So now we get to some actual testing.

The tests above are all straightforward.  We ensure the following:
  1. We can retrieve a persisted node, specifically via an indexed property.
  2. We can retrieve the correct persisted node for which we are searching.
  3. We can view non-indexed properties from the retrieved node.
  4. We can retrieve the correct number of relationships of the retrieved node.
As noted in Section 9.3 of "Good Relationships", we use Iterable for those node properties that are collections and are to be left as read-only, and Collection or Set for those collections that can be modified.



  // go through the actual purchases...
  Iterator purchIt = purchasesIt.iterator();
  Purchase purchase1 = purchIt.next();
  
  // retrieving objects via Spring Data pulls lazily by default; for eager mapping, use @Fetch (but be forewarned!)
  // ...this means we have to use the fetch() method to finish loading related objects
  Stock s1 = template.fetch(purchase1.getItem());

What if we want to view a node's related nodes' data?


By default, Spring Data loads an entity's relationships lazily, which makes perfect sense (just picture how much memory would be needed if you had a very large, highly connected graph).  Also remember that there are implicit relationships between entities if an entity is contained as a property of another entity.


(Courtesy of Paramount Picture's Forrest Gump)
"Mama said eager loading is like a box of chocolates: You never know what you're gonna get."
Well, at least the chocolates had an easily-determined, finite number in the box...

It is possible to have an eager retrieval by using the @Fetch annotation (be warned, though, that it will currently only work, by default, on node entities and collections of relationships that are based on Collection, Set, or Iterable; Spring Data may expand that in later releases, but I believe you can extend the mappings to work with other classes, if you so desire).

So, with our lazily-loaded relationships, we can use "template"'s fetch method to finish loading in the missing data.  It's as simple as that!  Anyone familiar with ORM will get this immediately.


  // can we retrieve our first purchase successfully w/ its details?
  assertEquals("Purchased item not persisted properly.", GAME_TITLE, s1.getTitle());

  purchase1 = purchIt.next();  
  Stock s2 = template.fetch(purchase1.getItem());
  
  // can we retrieve our second purchase successfully w/ its details?
  assertEquals("Purchased item not persisted properly.", GAME_TITLE_2, s2.getTitle());
  
  // if we're here, then all test ran succesfully.  Hooray!
 }

Above, we run a couple more tests to ensure that we can, in fact, retrieve and view lazily-loaded objects from Neo4j.

Nothing to it!

Making Friends the Easy Way: By Creating Them!
For these tests, we're going to have a look at something a bit more social, i.e. customers befriending other customers (how Utopian!).  I suppose we could make them "rivals" or "enemies", but that's a bit too sinister for this blog (for now...).

Anyway, I have prior to this test method a setup method (annotated with the @Before JUnit annotation) that creates 5 customers (if you're interested, I persist them using a CustomerRespoitory I created by extending the GraphRepository and RelationshipOperationsRepository interfaces).


 @Test
 public void customerFriends()
 {
  // add friends
  c1.addFriend(c2);
  c1.addFriend(c3);
  c1.addFriend(c4);
  c1.addFriend(c5);

  // be careful! setting a "Direction.BOTH" relationship in one node entity will have the ENTIRE relationship saved (*including the adjoining node*) when saving just ONE of the two entities!
  // ...if you save both, Neo4j will remove the duplication (and you'll be left wondering why c1 is a friend of c2, but not vice versa)
  
  // save c1's friends
  customerRepository.save(c1);

In the code above, we have the customer "c1" make friends with the other customers (he's a social butterfly).

Now, perhaps the most important part of this whole blog is shown here (and below).  It has to do with relationships, specifically those that are annotated as being "Direction.BOTH".

As you can see from the comments in the code above, we need to be careful about how we create relationships between nodes and save them.  If we were to create the relationship between, say "c1" and "c2", and then persist each node (and therefore the relationships, which the customer repository will handle), we would notice that the relationships have gone awry, and that the duplicate relationship from "c2" has been removed.

So, what we're going to do is the following (keeping in mind that "c1" and "c2" have already been persisted in the setup method):

  1. Persist "c1" (and thereby its friendship to "c2").
  2. Retrieve "c2".
  3. Add any other friends' relationships to the retrieved "c2" (while not befriending back to "c1").
  4. Persist "c2" (and thereby its friendships to those added in Step 3).

Step 1 is done above.


  // we can't just continue to add friends to this.c2, as once we try to save this.c2, it'll remove the duplicate relationship between c1 and c2.
  // ...so, to get around this, we retrieve the persisted object from the DB
  Customer c2Found = customerRepository.findByPropertyValue("lastName", C2_LNAME);
  c2Found.addFriend(c3);
  c2Found.addFriend(c4);
  c2Found.addFriend(c5);

  // save c2's friends, which will preserve the existing relationship with c1! Old friends can remain friends!
  customerRepository.save(c2Found);

As you can see above, we finish the remaining steps (2 through 4).

Again, note that we DO NOT create a reciprocal relationship from "c2" to "c1".  (One would hope a friendship relationship would be reciprocal; unless you have stalkers or something...)


This would totally help.

All that's left now is to run some tests to ensure that our friends have remained friends throughout all this persisting!


  // retrieve c1 for some tests
  Customer c1Found = customerRepository.findByPropertyValue("lastName", C1_LNAME);
  
  Iterable c1Friends = c1Found.getFriends();
  Collection c1FriendsSet = IteratorUtil.asCollection(c1Friends);
  Iterator custIt = c1Friends.iterator();
  
  int numFriends = 0;
  
  // let's make sure all of c1's friends were retrieved
  assertTrue("Friend not found.", c1FriendsSet.containsAll(IteratorUtil.asCollection(c1.getFriends())));
  
  // let's also make sure that c1 and c2 are still buds specifically (these two are inseparable...you should see them at ComicCon!)
  assertTrue("Friend not found.", c1FriendsSet.contains(c2));
  
  // let's make sure the exact number of friends returned is correct 
  while (custIt.hasNext())
  {   
   custIt.next();
   numFriends++;
  } // while
  
  assertEquals("Number of friends returned incorrect.", 4, numFriends);

  // if we're here, all is well! Huzzah!
}

Above, as in the first test, we make sure that all of the friendships have been properly preserved, both from "c1"'s and "c2"'s perspective.

Conclusion
In this post, we have seen the basics of persisting with Spring Data and a couple of the quirks I ran into.  These are documented within the Spring Data documentation, but it never hurts to bring these little nuances out into the light even further.

We also saw that the ImpermanentGraphDatabase is available to us through the Neo4j kernel which is a wonderful tool for implementing test cases with quick setup and teardown--no needing to write initializers and cleaners for a Neo4j installation!

So there we have it!  A first pass through persisting with Spring Data and implementing some unit tests using Neo4j and JUnit.

If anyone has any questions or I've made a mistake, please feel free to leave feedback.

We'll see you on the next post!

Tuesday 29 May 2012

Supporting an Entrepreneur: Do You Have What It Takes?

When most people think about entering the workforce (or shuffling around a bit in it), they typically think of two types of employment:
  1. "I'm going to work a 9-to-5 job, collect my paycheque every x weeks, do a decent job, work some overtime, earn a promotion or two, keep my work life very detached, and make sure I have plenty of time to do what I want."
  2. "Screw working for other people--I'm going to start up my own company, be my own boss, and make a bunch of money.  Sure, I'll have to sacrifice most/all of my own time and figure out a way to fund my venture, but I know I can make a difference and be guaranteed to do something I love."
In other words, type 1 is the "9-to-5er" while type 2 is the "entrepreneur" (and, depending on circumstances, this can also apply to freelancing).

That would make for a good movie title: "Arnold Schwarzenegger is...The Entrepreneur!"

In this article, we're going to have a look at a third option which I find is largely overlooked (granted, I'm sure there are far more options/goals for employment out there, but in the interest in keeping this simple, I'm sticking to the ones in this article).

This third option is what I refer to as the "entrepreneur supporter".

I had originally planned on writing another series on this matter; however, I'm going to stick to a single article on it and, if interest/time allows, will expand upon the ideas in here in subsequent posts.

Disclaimer
It is important to note, as well, that I am neither advocating nor denouncing one form of employment or the other (or the people who choose them).  What I am doing is writing from my own experience; take it for what it's worth, i.e. caveat emptor).

Decisions, Decisions...
Let's have a look at the first two types of employment and consider what they tend to mean to people.

What we will find is that a lot of the pros and cons are really a matter of perspective, so what one person may find to be a con may be a pro to another.  Keep that in mind as you read through this article.

The 9-to-5er

Pros:
  1. Easier to keep work/life balance and, as The Offspring said, keep them separated.
  2. Fewer concerns about collecting a regular paycheque.
  3. No risks involving your own money.
  4. "Work to live", not "live to work".
Cons:
  1. For the ambitious, limited control/say in how to grow/steer the company.
  2. More likely to be out of the loop as to the status of the company (is it in financial trouble? etc.).
  3. It's easy to lapse into a sense of entitlement (further reading to help combat this within your organization: Ownership Thinking by Brad Hams--highly recommended).
  4. Likely to have your salary/position cap out somewhere not too much higher than where you are now (of course there are exceptions, and for some people, this is less a con than a pro; the lesson: it's important to know what you want).
  5. Working hours are laid out by employer (but seem to be more flexible these days).
For a lot of people, this type of employment is exactly what they want; for others--especially the ambitious--they want something more (or, at least, different).

Let's have a look at the next type.

The Entrepreneur

Pros:
  1. Don't report/answer to anyone but yourself (well, at least until you have a Board and/or shareholders).
  2. Set your own hours/schedule.
  3. You determine exactly what kind of work you want to do (and it's likely something you love--otherwise, why do it?).
  4. You determine what you do with all revenue.
Cons:
  1. Have to fund the venture yourself (or at least raise the funds).
  2. It's your skin in the game: If business is poor/suffering, it's your money on the line.  Not to mention having to cover myriad costs...
  3. All the headaches taken care of by managers, operations, executives, sales, etc. are now your problem.  (Read: Insomnia.)
  4. Frustration.  You'll have to generate new leads/sales all while you're doing the work you set out to do (unless you hire someone else to help with that, but that's yet another cost to bear).
  5. While you set your own schedule, in order to get the business machine going, you're unlikely to have very much free time at all (if any) for the foreseeable future.
  6. Taxes, taxes, taxes.
  7. More taxes.
  8. ...and that's all while you actually do the work you set out to to do!
For those who are ambitious and want this kind of life, it can be extremely rewarding; of course, it's also fraught with risk and peril (kind of like being a knight, but with less chance of being parodied).  The greater the risk, though, the greater the reward.

Like you didn't see this reference coming a mile away.

Surely There Must Be More
So what about those who are looking for something in between those two options?  Something more, where one can affect greater change without needing to commit the shirt off one's back.

There is more, and don't call me Shirley (sorry, couldn't resist).

(From Paramount's Airplane)
Ok, no more Airplane jokes--I promise!

A Bit of Background
Being an "entrepreneur supporter" is an area in which I have considerable experience.

Coming out of school, I had the opportunity to work for various companies as part of my degree's co-operative program.  The companies for which I worked ran the gamut of SME sizes.  I also worked for large, multi-billion dollar corporations (that sounds impressive when I put it like that).

Needless to say, I had a taste of what was involved in working for each size of company.

Without going into gory detail, I had decided that while I wasn't prepared to risk everything, I had more ambition than struggling my way up the corporate ladder for the rest of my natural life, relying on luck and politics as much as hard work and skill in order to get ahead.

There's ambition, and then there's ambition.

As I couldn't really find any direction/advice on what to do in this case (save for some advice which I'll just say was trite), I thought about it, did my own research, and came up with a plan to try out:

I would get a job with a smaller SME in which I could add immediate value, establish myself, invest a good chunk of extra time, learn what I needed to, and work my way to a position of influence as fast as possible.

It worked.

Yes, I had to invest more than a few years' worth of time before I had any kind of measurable influence (including huge swaths of my own), but it worked (by way of my own example, in a company of 40-50 people, I had made VP before I was 28 and currently sit as the CIO of the company).

No one said it would be easy.

Being an Entrepreneur Supporter
At this point, I think it's safe to say that being in such a position is a compromise between being a 9-to-5er and a full-on entrepreneur.

I'm going to share with you, dear reader, some of what I've learned during the course of being an entrepreneur supporter (I like it when section titles line-up so nicely!).

When choosing the company you want to work for, consider the following:
  1. Make sure they do something you are actually interested in.  (Seriously.)
  2. Do your due diligence!  Check out the owner and/or executive (if there is one), what their goals are, and what their short-term, medium-term, and long-term goals (and, if applicable, their exit strategy).
  3. Make sure it's a size you're ok with.  As a general rule, the bigger the company, the more work (and time) you're going to have to put in (more politics, more inertia, etc.).
  4. Make sure you can work with the entrepreneur/executive (let's face it: egos or not, entrepreneurs can be very particular about how they want things done; after all, that's why they started a business instead of working for someone else).
  5. Do your homework on the company!
Strike up a relationship with the owner (and any of his/her executive staff) early on.  If you're going to help steer his/her company, as noted above, you'd best be able to work with that person.  What's more, you'll likely be spending a lot of time with him/her, so getting to know the owner/exec staff early on will go a long way, both in terms of being able to work with the people in question as well as understanding the business in which you're now embroiled.

Keep your ears open and ask questions.  Your MBA might have taught you a lot, or you might be great with technical jobs, but in a small business, chances are very, very good that you will not have learned enough to wear all the different hats you need to (whether you're responsible for those positions or not).  And the odds are good--especially if the business has been around for awhile--that the people currently working there know a thing or three about how to run it well.  Listen to them.  And if you think you know how to do what they do, challenge yourself and find out.  Grow.

Be prepared to be on-call 24/7.  Though most 9-to-5ers are now expected to be reachable for a bit after business hours and deal with occasional emergencies, being on-call in this supporting role is inevitable.  If you want people to listen to you, you have to participate, and that means late-night phone calls, early-morning meetings, last-minute conference calls, and emergencies on long weekends (and being responsive to all of the above).  The idea here is to make the entrepreneur's life easier--not yours.  He/she has enough to worry about.  Let him/her know you can handle the tough situations.  Start small, and the responsibilities will pile up (a mixed blessing to be sure).  It's a small price to pay for having influence without having to worry about your own money in the company.  Take comfort in knowing that you won't have to work 80 hours a week forever.

This will be you, for any number of reasons.  You've been warned.

Don't be the squeaky wheel.  Whatever you negotiate your starting salary/terms to be, make sure you're comfortable with it, because the last thing your boss will want to hear is you justifying why you should get a raise every 6-12 months.  Sure, you might get it every so often, but, that kind of sacrifice (or lack thereof) won't soon be forgotten.  Remember: He/she is sacrificing a lot more than you are; let them know they aren't alone in it and that you're "investing" in your own way.  If you've done your research, your entrepreneurial boss will take care of you (time off, flexible hours, pay raises when possible, etc.).  This actually leads into the next point nicely.

Find a shop where egos are checked at the door--including the entrepreneur's.  This doesn't mean the owner will be cow-towing to you and giving in to your every whim.  What it means is that everyone--including the owner--is prepared to do whatever it takes to make the business work.  You still have to deal with the owner's personality (like any boss), but at least you'll have an added measure of reassurance that you're not going to get taken to the cleaners and/or taken advantage of.

Treat company money like it is your own.  If you're in a position where you make decisions and/or handle company money, treat the money as though it was your own (and I mean that in the best possible way; i.e. don't go spending it all because you can).  Be smart with the money going out.  Be prepared to justify expenditures ("ROI" will become your favourite TLA).  Conversely, be prepared to do whatever it takes to maximize revenue.  Nothing makes you look better than adding serious value to the company's bottom line (an axiom in any-sized business).

Two words: Be flexible.  If you were hired on to be an engineer or developer, be ok with being pushed out of your comfort zone.  Take on tasks that you'll likely make mistakes with (just be careful with how you manage those mistakes--another good lesson).  If your boss wants you to go in his stead somewhere, do it.  If your boss wants you to take out the garbage, heck, do it.  Show that you're reliable.  Wax on, wax off (and all that).  And remember the Golden Rule: "He who has the gold makes the rules." Be prepared to do what the person signing your paycheque wants/needs.  The Golden Rule also speaks to what your boss does with his/her time.  You might not approve/believe it fair/whatever of what your boss does.  Guess what?  It doesn't matter.  It's the same with any job/boss, really, but at least here you can take solace in the fact that it is that person's money paying your wages--that person certainly isn't going to just burn money for the sake of burning money (see above: due diligence).  Get over yourself and focus on your job.  If it really bothers you, then maybe this type of work isn't for you.

Work/life balance.  This one might be a deal-breaker for many.  If you can manage to balance the two the way you like, then all the power to you.  However, be prepared and don't be surprised if those two areas of your life bleed over into each other constantly (and usually much moreso the "work" portion entering into your "personal life" portion).  This "bleed" is happening more and more with many jobs, but it's a fact of life with this type of work.  Entrepreneurs are notorious for having to sacrifice personal relationships for their dreams of their business.  Supporting those entrepreneurs will most definitely require a comparable level of sacrifice; maybe not to the same degree, but make no mistake: Sacrifice will be involved (I really can't overstate that).

Produce!  

No, not THAT kind of produce.

It should go without saying that you should produce results, no matter what tasks you undertake.  You'll likely have to take it a step further, too, and be prepared to do whatever it takes to complete your tasks with a minimum of budget.  Does your solution involve sinking $10 000 in licensing?  Or could you do a bit more work and find a way to cut that cost out with open source or a different solution?  This does not just apply to software, either.

It's still a big risk.  While you might not have skin in the game (unless you really want to go that route), you're certainly not a 9-to-5er.  As time goes on, you'll be exposed to more and more information--both good and bad--and you'll be expected to know what to do with it.  What's more, there's no guarantee that you'll see a big payday/cash out, but you're likely to experience more freedom (with your responsibilities), and with no risk, there's certainly no reward.  Make peace with that as soon as possibly can, and learn from any failures you may encounter.  "Success has many fathers; failure is the bastard son."

Round-up
I'm sure I could go on at greater length, but, what I've disseminated here is at the core of what it takes to successfully support an entrepreneur.

While there certainly is a greater degree of potential reward, as well as freedom and responsibility, it has its share of risks, as well, though not necessarily as severe as if you had started your own business.

I have to say, though, for me, at least, it's been well worth the risk.  Personally, I've invested a lot of my own time into supporting an entrepreneur, and it has taken a lot of sacrifice (it still does), but it can and does pay off.  I enjoy a considerable degree of freedom (along with the Sword of Damacles that often dangles above my head), as well as a long-time friendship with my boss.  It's definitely not for everyone, but for those who do pursue it, it can pay off huge.

I might write more about it at a later date, but in the meantime, questions and constructive feedback are most definitely welcome.

We'll see you on the next post!

Tuesday 22 May 2012

Modern Consulting vs. Classic Consulting: Part 5 (Summary and Conclusion)

Ok, folks, we're down to the summary and conclusion of my series comparing classic consulting and modern consulting by way of our little thought experiment.

In this post, I'll be summarizing what we spent the last three posts examining and bringing things back full circle to the post that started this series (it's kind of like a flashback episode but without the laugh track).

No need for this today!

Let's start off with a little section I like to call...

Recap
Way back in the original post of this series, I'd stated that the company for which I work, BHS Consultants, is an "IT/technology consulting firm"; I'd also stated that this label is a "challenging" one.

By way of comparing and contrasting what I refer to as classic consulting and modern consulting, I set out to define what I meant by the two respective terms with the goal of showing why the label above is a challenging one for my company (which I will finalize in this post).

We compared the two terms by way of a thought experiment, defined as follows:
  1. You are in charge of a large project to implement a new business process that is to be heavily automated.
  2. You have a fixed budget and deadline.
  3. You currently do not have the expertise or staff to undertake and complete the project.
  4. You want to make as big (read: positive) an impression as possible.
We then considered three different options to tackle this project which can be summarized as follows:
  1. Find and take on an internal staff (either full-time or contract) including both SMEs (Subject Matter Experts) and implementors.
  2. Find and contract a knowledgeable consultant to advise on the project and then either field a staff to implement or contract out the work to another firm.
  3. Find and contract a knowledgeable "one-stop shop" that has both the SMEs needed and the manpower to carry out the plan/advice from the SME(s).
Each option is linked below for convenience (I know, I know; I'm just that nice).




Bringing Things Back Full Circle
So now we've seen three different options to address the same situation, all of which have their places.

However, in my experience, when it comes to consulting on technical matters (e.g. as in our thought experiment involving heavy automation)--especially where software and programming is involved--the third option is the one that makes the most sense, both from a time and cost perspective.

Some of you may argue that the above model failed horribly with the outsourcing fiascoes of the 2000s (I'm sure some of you had good experiences, but from my own experience and others I've dealt with, many did not), and that's a topic for another post.  It's difficult to argue with numbers that help your bottom line tremendously ($5/hour for 10 developers? that's tough to beat); however, you get what you pay for, and in many cases, it was either nothing or a product/service of inferior quality.

(Again, I'm not here to bash on every outsourcing venture, but am merely drawing from my own experiences and knowledge.)

But I've also witnessed (and been a part of) many successes with that same model with firms in North America/Europe (some would call it near-sourcing).  When companies see the value we bring with the deliverables we produce, it sinks in with them, and they become hungry for more, which we're only too happy to provide.

So What about That "Challenging Label"?
So why is being called an "IT/technology consulting firm" a challenging label for us?

Because, many times, it sounds like the company is a part of option number two, i.e. in the classic consulting space.  By that definition, BHS Consultants is definitely not a "consulting" firm; however, if you consider option number three, i.e. the modern consulting space, we most certainly do fit the bill.

Explaining those differences and trying to describe the services we can provide is perhaps the most challenging issue we face.  We certainly can't be overly esoteric about what we do, but to list the myriad skills and services we bring to the table would be an invitation to read through a novel!

Can you imagine this as a website?  Yeah, me neither.

Regardless of the challenges, though, we seek to add as much value to our clients as humanly possible.  BHS is extremely passionate about what they do, and I'm no exception. I wouldn't have spent the past decade plus here if I didn't absolutely love what I do.

And while "value" is usually in the form of deliverables (be they tangible or not), we always seek to help educate our clients (and even prospective clients) on the services we provide and the matters in to which they are delving.

Empowering clients to make smart, informed decisions about technology is at the heart of BHS Consulants, and should be at the heart of any IT/technology consulting firm; but being able to help clients actually realize those decisions is where the real value comes in to play.

Conclusion
Ok, there you have it!  We are finally through the entirety of this series!

Thank you for making it this far and reading through (hopefully) all of this series.  I do hope it's been insightful with respect to what I/we do, and with respect to the state of modern consulting.

Please do check us out at bhs-consultants.com (shameless plug, but hey, it's relevant!).

Remember: Both classic consulting and modern consulting have their roles to play in the right situation; but with the ever-expanding role technology plays in day-to-day operations of businesses and the ever-increasing request for plans and advice to be executed and realized, modern consulting will continue to become more and more relevant (and prevalent) by the day.

Thanks once more for your time and patience!

I'll see you on the next post!

Friday 18 May 2012

Modern Consulting vs. Classic Consulting: Part 4

No funny sub-title today; no, sir, it's right down to business!

Recap
The situation we're considering is as follows:
  1. You are in charge of a large project to implement a new business process that is to be heavily automated.
  2. You have a fixed budget and deadline.
  3. You currently do not have the expertise or staff to undertake and complete the project.
  4. You want to make as big (read: positive) an impression as possible.
We are in the middle of examining three different options in order to accomplish this project, as described in the original post in this series.

Again, this series is not meant to be exhaustive by any means; rather, it is an analysis by way of my experience in the consulting business for the past 11+ years.

Last time we looked at option 2 (i.e. what I consider to be a description of a classic consulting scenario).

Option 3 is on deck for this post, so let's get cracking!

Option 3

Find and contract a knowledgeable "one-stop shop" that has both the SMEs needed and the manpower to carry out the plan/advice from the SME(s).

Now we get to the option that combines the role of the consultant and the role of the development team.  What I mean is that instead of sourcing the consultant from one firm and the development from another (or, if you're going internal for development, the development from there), you source all those tasks from a single vendor.


One arrow means one source of responsibility.

We can see in this situation that you only need to deal with one vendor.  Once the vendor is found and contracted, no more time needs to be spent in finding the appropriate staff/contractors to implement your plan once you have it.

What's more, the vendor has a vested interest in coming up with a viable plan that not only can but must be executed, as the same vendor will be providing the development resources.  What good is the plan if the vendor's own resources can't implement it?  Dragging out projects for the sake of additional billing is a serious red flag for any consulting firm.

The vendor is also more likely to be more flexible and accommodating for scope changes (let's face it: they do happen) than having a separate vendor for each purpose (as in option 2).

Project Management and Documentation

(This is a slight aside, but one worth mentioning.)

Often times, the vendor will assign a Project Manager or account liaison to work with you to complete your project.

If there's one piece of advice I can give with respect to having a PM, it's that they are worth paying for.

It's a common occurrence for clients to want to save money by reducing the number of line items and resources as much as possible.  Project management and project documentation are often the first things to go.  Do not give in to this temptation.  A vendor worth its salt will happily walk you through the benefits of having a project manager (as well as having proper documentation, both technical and otherwise).

Vendor Confidence
One argument that is sometimes made is that the client does not want to put all his/her eggs into one basket, so to speak.

I can understand some of the concern in this ("What if the company goes under?" "Will they be transparent enough in their internal interactions?" Etc.).  However, in my professional opinion, in the vast majority of cases, the benefits far outweigh the concerns.

A good way for you to vet the vendor is to investigate any references/testimonials they have (if none are readily available via their website or other means, don't be afraid to ask the vendor for some).  Due diligence is something you should always engage in, regardless.

As a slight aside, look for an honest vendor, and by that I mean one that won't say "yes" to absolutely everything (irrespective of data) and one that won't try to say "it can't be done" whenever you suggest a certain approach.  Consulting is largely about developing a relationship with the client and sharing in the risks and success of the project.

No, not THESE Yes men.

(Again, any such vendor worth its salt will anticipate these concerns and address each one with you.  Your peace of mind should be on the top of their priority list when it comes to dealing with you.)

Rates
It's also possible that the vendor will give a bit of a break on the rate given that you're engaging them not just for consulting/planning work, but for development work, as well.  More hours usually means a greater incentive to keep you, the client, happy.

You might pay a bit more for the lead consultant, but it likely won't be as much as it would have been from a classic consulting firm, and the development resources' rates will likely be less than the lead consultant's.

Also remember that you get what you pay for: Be way of firms that offer development work for $20/hour.  I've never been one for outsourcing, so please don't tell me about sending out your work for $1/hour for a team of 10 developers (I know the likely outcome of those stories).

Who Does the Work?
In most situations, the person performing the consulting should not be the only one doing the development work (this has been known to happen in smaller firms, but outside of smaller projects, this usually doesn't work out so well).  In fact, the consultant should likely not be performing any development in order to remain objective, available, and to "see the forest for the trees".

Pros and Cons
So let's list the pros and cons for option 3:

Pros
  1. Time spent acting as an intermediary between the consultant and the dev team is minimized.  Your time (and your team's time) is important.
  2. Time is saved not needing to find/contract both a consultant and a separate development team.
  3. Greater/enhanced communication between the consultant and the dev team, thereby bypassing/reducing potential miscommunication.
  4. Increased likelihood of successful plan implementation.
  5. Greater flexibility during both planning and execution phases.
  6. Reduced chance of budget and time overrun.
  7. The chance of getting a break on rate is higher (though not guaranteed).
  8. Greater perceived value, in addition to greater actual value (i.e. you're not just getting a document that "passes the weight test".)
Cons
  1. Potential "eggs in one basket" situation.
  2. Can be challenging to find a vendor that has both the domain expertise and development expertise together in one shop if you don't know where to look.
  3. May sacrifice laser-like competency and depth in a particular field for something more akin to a carbide drill or even an entire workshop (think about it).
  4. Increased need for vendor transparency (but this is easily addressed).
Unlike the previous two options, the pros far outnumber the cons.  

This option holds many advantages that address the concerns raised with option 2.

Synopsis
We see here an outline of what I refer to as a modern consulting situation; in other words, the vendor/consulting firm provides a "one-stop shop" for all of your project's needs.  This greatly simplifies matters and streamlines them, especially when you have a technical need such as the one described in this thought experiment.

The value here should be obvious, and while it's not always the right tool for the job, in most technical situations, it is (even in non-technical matters, having the consultant get their hands dirty with plan implementation can be beneficial in a lot of situations).

Yes, consulting is a "noble profession" (as Dr. Weiss puts it), but I believe that the definition of what consultants need to do--especially with respect to the ever-growing need for technical expertise--needs to evolve beyond just writing a plan.

I've come across more than a few consulting firms who do nothing more than produce reams of documentation for a plan that spans hundreds of pages, only to never see the light of day again.  To me, that's not only not adding any value, it's costing a business money and can even become a liability, and that's never acceptable.

Next Time...
...we'll wrap things up with a conclusion to this whole thought experiment and bring it back full circle to where the first post started.

(From Disney's The Lion King)
It's kind of like the circle of life that way <cue Elton John music>.

See you on the next post!