Showing posts with label SOLID. Show all posts
Showing posts with label SOLID. Show all posts

Thursday, April 24, 2014

SharePoint 2013: Require JS + SharePoint Hosted Apps


During my early days I was bit scared writing JavaScript applications since I was so use to C# that I always try to find similar feature or offerings in JavaScript, I must say it took me sometime to really grasp the concepts because there are different ways to do a single task e.g. creating an object. I wanted to apply the basic principles of SOLID and found myself nowhere near to adhering to it.

SOLID:

Single responsibility (SRP)

Open Close (OCP)

Liskov substitution principle (LSP)

Interface segregation principle (ISP)

Dependency inversion principle (DIP)


 

Well I'm too young in JavaScript still to apply all the principles but have at-least I now able to partially apply SRP, DIP up to a certain extent.
Mostly I've seen in SharePoint Hosted apps developers writing a big fat JavaScript file which contains all the business logic and it becomes hard to read and debug (really I mean it).
Modular programming helps a lot here but to achieve one must need to understand modules (class) and how they can be defined in JavaScript, splitting your logic in modules certainly helps you to achieve SRP but that still doesn't solves the root problem as you are still loading the entire module at once which doesn't gives you much benefit in terms of performance. Well loading individual modules can be loaded but you need a solution, and the answer to that is Require.JS, it's an AMD (Asynchronous Module Definition implementation)
Well if you are SharePoint developer then you'll argue that why we need another framework for loading individual module which is already provided by SharePoint via SP.SOD (Script on Demand).
A quick comparison between both approaches
Require JSSOD (Script On Demand)
Highly ConfigurableNo Configurations
Support to External LibrariesNo Exports for External Libraries
Inject, Exports, ShimNo exports or injection support (natively loads the plugin)
Cleaner Dependency construct and resolutionComplex construct to write dependencies within external libraries

 

I won't go in detail of how to setup require.js the documentation is itself self-explanatory trust me It took me a while to get this up but now it's a piece of cake !!!
I'll talk about some important part of the configuration which is required so that a SharePoint developer can leverage functionality and get benefitted from best of both worlds
The key aspect in require.js is configuration which is very powerful important attribute

 



 

Above is my simple configuration for require.js 

Please focus on deps and paths property

#1 Paths : The SharePoint JSOM runtime and main js to be loaded.
#2 Deps : Deps setting causes the runtime and sp.js file to be loaded before any module is loaded, thus making required core and necessary classes available for developer to program.

 

The Module

I've created two module which fetches the current user display name from web and user profile

// Module for Web



 


 

// Module for User Profile

User Profile Code : http://www.vrdmn.com/2013/02/sharepoint-2013-working-with-user.html @vrdmn

 



 


 

The Start-up Module




SP.SOD.loadMultiple(['sp.js', 'userprofile'], ShowUserName);

#1 The responsibility of ensuring that sp.js and sp.userprofile.js has been loaded is delegated to native SharePoint SOD module, the trick is to use SP.SOD.loadMultiple() which loads multiple modules and triggers the final function to be loaded.
Note: Here you can see the difference in the way require.js works and SOD works, require.js injects the dependencies as a parameters and SOD doesn't which gives more clear understanding of what to expect.


I've already published the sample at github: https://github.com/akhileshnirapure/sp_hosted_app_requirejs

Feel free to fork and if you have any question the reach me at Twitter: @AkhileshN
Thanks
Akhilesh Nirapure


Friday, December 13, 2013

Specification Pattern & Client Object Model in SharePoint 2013

 

Hi, well if you guys are really wondering what does this mean and what problem it solves, let checkout the Google’s definition of it what it says

image

 

But still you must be thinking as to where does this fits in our day to day work?

All business problem comes with a detailed specification, but when we have to translate that into code, we often don’t do a good job in crafting them, we tend to ignore a repetitive pattern which can solve handling such specification in much nicer and cleaner way.

Let’s take a simple example,

We have a requirement where we need to verify if a List has following property set Title, Description

At simplest we would write a simple query

 

…..

Context _context = new Context(“Your_SharePoint_Site_Url”)

var result = _context.LoadQuery(_context.Web.Lists.Where(p=>p.Title == “SomeTitle”);

_context.ExecuteQuery();

 

well next day the requirement changes and you’ve been asked to write the similar condition for another module in project, what would u do, go and write a utility class copying over the above code and what !!! job done Smile.

and now you again get a requirement to validate Description property of the List, what would you do, simple copy over the function written in utility class change the where clause and you are done. Smart right? Well yes it really depends on the demand of situation how clean you really want the code.

According to me you are violating following principle from SOLID, like Single responsibility principle, Open Close Principle.

So how can we write the above specification so that we don’t violate SRP and OCP. Well the answer is Specification Pattern

Enough talk let get to code

We define abstract specification class with an abstract method

 public abstract class SpecificationBase<TEntity>
{
public abstract Expression<Func<TEntity, bool>> Predicate { get; }
}




Next we define concrete implementation of specification to which has single responsibility of defining the condition of one business problem.

public class ByListTitle : SpecificationBase<List>
{
private readonly string _title;

public ByListTitle(string title)
{
_title = title;
}

public override Expression<Func<List, bool>> Predicate
{
get
{
return p => p.Title == _title;
}
}
}



Thus now we have a single class which know how to handle a where condition to find title.


Note this is very simple example, think of situation where your business requirement demands to get its data from various sources, so this class can explicitly request that dependencies for the condition to be formulated.


Lets go back and change our initial code to work with the specification pattern.


 

var titleSpecification = new ByListTitle();

var result = _context.LoadQuery(_context.Web.Lists.Where(new ByListTitle("Class").Predicate));

_context.ExecuteQuery();



 


Note the above highlighted lines this is what usually your Where Clause takes a predicate.


 


Cool, well we haven’t done anything fancy here Smile finding a title by explicitly writing additional classes makes no sense, but i just want to remind you this is just a very simplistic example, but the concept can be equally applied with similar codebase to any such business validation component.


 


Let say now we again got requirement to build a complex logic (calling a web-service and some additional regular expression classes) to validate the Description of the List Smile and at the same time we would need to validate the Title. So what’s your take now, will you still say this is easy? i don’t think so, i think you’ll end up cluttering your code with all the logic required to make web-service call and calling the Regx utility.


Indeed, we must strive to stick to SRP and OCP and would not again want to violate such principle. So what would we do, create another specification class Smile this now adheres to SRP and OCP.

public class ByListDescription : SpecificationBase<List>
{
private readonly string _description;

public ByListDescription(string description)
{
_description = description;
}

public override Expression<Func<List, bool>> Predicate
{
get
{
// Code to Call WebService
// Code to call RegX Utility
return p => p.Description == _description;
}
}
}
Now its so easy to add the code logic of calling web-service call and regx utility without cluttering up the code.
But wait we haven’t finished its just one part of requirement covered, we also wanted to combine both the specifications so that 
we can validate both Title and Description at the same time.
Which essentially means we need to supply some kind of “And” logic here. Not to worry you don’t have to write additional code to set it up.
there is already a Predicate Builder present which can simplify and make your life easier Smile
 

So how does our code now look like

var predicates = PredicateBuilder.True<List>();
predicates = predicates.And(new ByListTitle("SomeTitle").Predicate)
.And(new ByListDescription("Some Des").Predicate);

_context.LoadQuery(_context.Web.Lists.Where(predicates));
_context.ExecuteQuery();




Let me take some time to explain the above code using PredicateBuilder


with predicate builder, if you want to build “And” condition then you would need to specify the object, with True extension which in our case “List”. and then wire-up the predicates (i.e. specifications) with “And” extension. which builds a predicate chain.


That’s it, now you have written a clean code adhering to SOLID principle and testable, extensible and maintainable code.


Any new specification can be easily handled just by adding a new class and you are good to go.


 


One more additional helper method if you would like to build such numerous predicates then you can make use of a simple method which can allow you to aggregate all the specifications.

protected bool Validate(params SpecificationBase<T>[] specificationsBase)
{
var pred = PredicateBuilder.True<T>();
pred = specificationsBase.Aggregate(pred, (current, specificationBase) => current.And(specificationBase.Predicate));
var result = _context.LoadQuery(_objectCollection.Where(pred));
_context.ExecuteQuery();
return result != null && result.Count() == 1;
}



Thanks


Akhilesh Nirapure