3 Answers
3

I use layered architecture in all my SharePoint solutions and treat SharePoint generally as the UI layer, keeping it very thin. Any logic goes into the business model and I have DAL wrappers to abstract away the List infrastructure (which also helps with testing).

For a good read on layered architecture in ASP.NET check out this article here. It's ASP.NET and NHibernate, but the principles are the same. There's also a layered architecture sample in .NET here on CodePlex. Again, not SharePoint specific but the principles are the same.

Keep the SharePoint UI thin and resist the temptation to start reading/writing to lists in your web part code. Treat it like a database (because it is!)

Web parts, web controls, application pages etc should only be the UI layer that calls into a layer that is agnostic of the original calling context; calling context could be an event receiver, console application, timer job, workflow, etc. Always ensure that this shared layer you call into does not have a dependency on SPContext.Current since it isn't always there! Accept SPWebs, SPLists, SPLisItems etc as method parameters and constructor parameters. In a web context you can pass these from the SPContext.Current, but in a Console Application you would construct these yourself.

To improve ease of debugging (just press F5) and shorten the developer feedback cycle, I often start off writing a simple Console Application which calls into the layer that will contain the core logic, passing in an SPWeb which I constructed in the Console Application. Once the core logic is finished, I write a thin WebControl or WebPart to replace the Console app, read the SPWeb from the context instead of constructing it, set up event handlers etc.

I'm wondering what type of objects/interfaces you pass between the layers? Do you pass back a SPListItem or do you pass back some kind of interface that represents the SPListItem?

SharePoint is a strange beast because the user actually has the ability to change the data structure via the web interface (they can add/remove/modify columns in a list). If you pass back a object/interface, every time a list is modified by a user, the code would need to be recompiled (and deployed) to accommodate the new column (property). If you pass back the SPListItem, you in effect break the Layer by allowing direct access to the data source (SharePoint).

@Jay: You should ask this as a new question. That way you will get the widest audience and people can upvote the best answer for you. Thanks and welcome to SharePoint Overflow! :-)
–
Alex AngasMar 10 '10 at 11:35