Good programmer should understand business domain. Really good programmer should understand business needs. Even mediocre Business Analyst must be interested in the technology at least at the same scale as being knowledgeable in business. The guy who handles you a 90-page specification saying: "Here is layout of our buttons - make them work" and disappears until Business Acceptance Testing stage - is just a very wrong person for the job.
Unless your project is a reinvention of a door bell, a lot of analysis is required after spec is done. Writing a specification of what a screen should do is a mere interpreter's job - translate language of business (either from customer's words or from general domain knowledge) to language which developers can comprehend. The real analysis should be applied to understand and predict how things will work when instead of humans (slow, inconsistent) or previous programs (outrageously old and poorly written) our new shiny application will take the load.
I struggled the most with this disconnect between BA's and developers while dealing with transactional data flows - be it database or service calls. A sequence of multiple interconnected actions requires a thorough inventory of all possible outcomes and analysis of subsequent scenarios. In 90% cases these decisions are outsourced to developers and if they don't know any better they make decisions which make sense only from the technical point of view.
The strategy of dealing with the outcome of the transactional process is a business decision, not technical. As a developer I always go for proper rollbacks or configurable re-attempts - but it could very well be what business doesn't need or even doesn't want (it may not even be possible - and you are fighting a half-day brain paralysis). This misunderstanding of business need will result either in an outright wrong logic (which is fixable) or in an over-engineering and significant waste (which will linger around for a long-long time).
So, please, please, Business People - don't roll your eyes when your techies will be asking for your preference between asynchronous callbacks and pub-sub patterns. They feel disturbance in a Force, but just having trouble expressing it in a humane way - be patient (and know your stuff).
Update: Starbucks concurs
*ACID - as from technology, not pharmacology.
Imagining your interviewer naked may be a bad idea sometimes. No, wrong - it is always bad idea. Try this instead:
You know what to do with it, you just can not do
worse.
P.S. Also these would be a great questions to fire in return:
Interview Questions for Potential Employers
RavenDb is great native LINQ no-SQL database which is under active development. It has enormous community support and loads of resources which can help you get started (I wish they had this open course at my time).
Below is the code I ended up with after some time of polishing and tweaking and which finally worked for me. For a quick-start convenience I am providing the instructions in sequential steps.
1. Download and install RavenDB Client nuget package from Hibernating Rhinos.
2. Add "RavenDb" connection string to your web.config file. It is not necessary to use this name but if you'd ever consider AppHarbor hosting with one of the RaveDb add-ons, the deployment script will automatically place correct connection string if it will find "RavenDb" key. And we love automation.
3. The core access class for the Raven API is Document Store. It is expensive to create but it is thread-safe so we can use one singleton instance of it throughout our application life cycle. To achieve that we place the following code in out Global.asax.cs file:
private const string RavenSessionKey = "OpenHouseRaven.Session";
private static DocumentStore documentStore;
public WebApiApplication()
{
BeginRequest += (sender, args) =>
HttpContext.Current.Items[RavenSessionKey] = documentStore.OpenSession();
EndRequest += (sender, args) =>
{
var disposable = HttpContext.Current.Items[RavenSessionKey] as IDisposable;
if (disposable != null) disposable.Dispose();
};
}
protected void InitializaeRavenDbStore()
{
documentStore = new DocumentStore { Url = ConfigurationManager.ConnectionStrings["ravenDb"].ConnectionString };
documentStore.Initialize();
}
public static IDocumentSession CurrentRavenSession
{
get { return (IDocumentSession)HttpContext.Current.Items[RavenSessionKey]; }
}
Add call to InitializaeRavenDbStore() to the end of Application_Start method which should be already there. In this code we initialized DocumentStore class, provided infrastructure to store Raven Document Session and altered WebApiApplication constructor, attaching handlers to BeginRequest and EndRequest events to properly create and dispose the Session object for each request.
4. Next is repository class which will encapsulate all database interaction. Raven is natural with LINQ and generics, so repository can be created to handle specific type.
public class RavenRepository<T>
{
protected IDocumentSession ravenSession;
public RavenRepository(IDocumentSession session)
{
ravenSession = session;
}
public virtual T Find(string id)
{
if (string.IsNullOrEmpty(id)) return default(T);
var item = ravenSession.Load<T>(id);
return item;
}
public virtual IEnumerable<T> FindAll(Func<T, bool> predicate)
{
return predicate == null
? ravenSession.Query<T>()
: ravenSession.Query<T>().Where(predicate);
}
public virtual List<T> InsertOrUpdate(List<T> list)
{
foreach (var entity in list)
{
ravenSession.Store(entity);
}
ravenSession.SaveChanges();
return list;
}
public virtual void Delete(string id)
{
if (string.IsNullOrEmpty(id)) return;
T entity = Find(id);
ravenSession.Delete(entity);
ravenSession.SaveChanges();
}
}
The Raven Document Session object is being injected into the class for better testability. And we love testability.
5. And now the code which all above was preparing us for - the usage:
var repo = new RavenRepository<Person>(WebApiApplication.CurrentRavenSession, null);
var existing = repo.FindAll(p => p.Name == "Smith").FirstOrDefault();
Pretty simple construction with few small tricks - I hope it will save you some start time.
Bookmark it - quite possible the blog can be moved from the Blogger platform.
It's worth it just for the joy of appreciating the humour and craft of the content of the following page (including the URL):
http://warmcrocconf.net/itsover/thankyou.aspx
NB: I just stumbled upon it - I have never heard about it before, I don't understand (yet) what is it about - but it made me very curious. Your experience may vary.
And the prize goes to the Capital One. The image draws a sympathy and instead of some other weirdness it says "We fought bravely and will get up before you count to ten".