Jean Hibbert's Blog

.NET Framework, SQL Server and other random thoughts.
Training regime - Mon - Friday
I've recently started a new training regime which has been really forcing me back into shape. One week of this regime and I could see a noticeable difference in my physique. Scary stuff.

In addition to my normal diet I am taking in:

I drink 1 protein shake a day.

8 glasses of water a day.

3 cups of rooibos or green tea a day.

2 Tins of Tuna OR 2 steaks OR 2 chicken breasts

This diet is subject to change since I have minimal time to prepare food, and my trainer(Brent) will be revising this diet over the next few weeks.

You can download the training regime here

Posted: Aug 05 2008, 06:45 AM by jean | with no comments
Filed under:
Log4PostSharp : How to set it up

After an hour of banging my head against the wall and much dissapointment at the amount of documentation out there on such a usefull tool as Log4PostSharp I've decided that it would be a good idea to get off my lazy .... and write a short blog post on Log4PostSharp.

Firstly let me give you a quick description of what Log4PostSharp is: 

Log4PostSharp is an Aspect-Oriented tool that allows you to log when a

1) method is entered

2) method is exited

3) when a method throws an exception

Methods that you would like to implement this logging functionality on, only have to be decorated by a Log attribute from the Log4PostSharp namespace.

 
Steps to set up An application to use Log4PostSharp:

1) Download the source code for the Log4Post sharp project from http://postsharp-user-plugins.googlecode.com/svn/trunk/Log4PostSharp/

2) Optionally you can compile the project in VS2008 - There is a \Libraries folder that contains all though if you are still stuck with VS 2005 (like the 95% of the working population :-) )

3) Download and install the PostSharp Aspect Oriented tool from http://www.postsharp.org/.

4) Copy Log4PostSharp.psplugin and Log4PostSharp.Weaver.dll from the Libraries folder in the Log4PostSharp project into the plugins folder created by the PostSharp installation which would normally be at C:\Program Files\PostSharp 1.0\PlugIns

5)  Then in your project: Add references to the following libraries : log4net.dll (from the log4net project) + log4PostSharp.dll (from the log4postsharp project) + PostSharp.Public.dll (from the PostSharp project)

6)  Update your AssemblyInfo.cs file with:

 

[assembly: Log(AttributeTargetTypes = "*", EntryLevel = LogLevel.Debug, ExitLevel = LogLevel.Debug, ExceptionLevel = LogLevel.Error)]

[assembly: log4net.Config.XmlConfigurator(ConfigFile = "Log4PostSharpTest.exe.log4net.config", Watch = true)]

As you can see Log4PostSharpTest.exe.log4net.config is the name of the config file that will hold the log4net configuration settings. 

7) Create a configuration file Log4PostSharpTest.exe.log4net.config and insert the log4net configuration settings: eg

 <?xml version="1.0" encoding="utf-8" ?>

<log4net>

     <appender name="RollingLogFileAppender" type="log4net.Appender.RollingFileAppender">

           <param name="File" value="trace.log" />

           <param name="AppendToFile" value="true" />

           <param name="MaxSizeRollBackups" value="5" />

           <param name="MaximumFileSize" value="100KB" />

           <param name="RollingStyle" value="Size" />

           <param name="StaticLogFileName" value="true" />

           <layout type="log4net.Layout.PatternLayout,log4net">

                <param name="ConversionPattern" value="%d [%t] %-5p %c [%x] - %m%n" />

           </layout>

     </appender>

     <root>

           <level value="DEBUG" />

           <appender-ref ref="RollingLogFileAppender" />

     </root>

</log4net>

 8) Finally decorate the methods in your application that you would like to treack with the logging functionality by using the log attribute as mentioned earlier eg:

 

        [Log(EntryLevel = LogLevel.Debug, EntryText = "Test for '{@i1}', '{@i2}', '{@r1}', '{@r2}'.")]

        [Log(ExitLevel = LogLevel.Fatal, ExitText = "Was called with params: {paramvalues}.")]

        [Log(ExceptionLevel = LogLevel.Fatal, ExceptionText = "Exception occured with parameters : '{@i1}', '{@i2}', '{@r1}', '{@r2}'.")]

9) Run the application and have a look at the magic in the trace.log file output. Since I had my debug setting set to DEBUG, every every event handled by the log4postsharp framework was logged. 

So my output looked like:

2008-07-24 15:49:32,726 [1] DEBUG Log4PostSharpTest.Program [(null)] - Entering method: Void Main(System.String[]).
2008-07-24 15:49:32,757 [1] DEBUG Log4PostSharpTest.Program [(null)] - Entering method: Void MethodWithNoReturnValue().
2008-07-24 15:49:32,757 [1] DEBUG Log4PostSharpTest.Program [(null)] - Exiting method: Void MethodWithNoReturnValue().
2008-07-24 15:49:32,757 [1] FATAL Log4PostSharpTest.Program [(null)] - Calling eebd09aa-c47c-4f2e-a21e-e90d8030ed6a.
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Entering method: Void MethodWithNoReturnValue(System.Guid).
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Exiting method: Void MethodWithNoReturnValue(System.Guid).
2008-07-24 15:49:32,773 [1] FATAL Log4PostSharpTest.Program [(null)] - Return value is: ''.
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Test for '1', 'A', '10', 'X'.
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Entering method: Int32 MultipleArgsMethod(Int32, System.String, Int32 ByRef, System.Object ByRef, System.Guid ByRef, System.String ByRef).
2008-07-24 15:49:32,773 [1] FATAL Log4PostSharpTest.Program [(null)] - Return value is: '51'.
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Exiting method: Int32 MultipleArgsMethod(Int32, System.String, Int32 ByRef, System.Object ByRef, System.Guid ByRef, System.String ByRef).
2008-07-24 15:49:32,773 [1] FATAL Log4PostSharpTest.Program [(null)] - Was called with params: "1", "A", "10", "X", "6fef8a16-9373-490c-bf07-3d47feda5c31", "X".
2008-07-24 15:49:32,773 [1] INFO  Log4PostSharpTest.Program [(null)] - Test message.
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Entering method: System.Guid MethodWithGuidReturnValue().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Exiting method: System.Guid MethodWithGuidReturnValue().
2008-07-24 15:49:32,773 [1] INFO  Log4PostSharpTest.Program [(null)] - Doing stuff.
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Entering method: Int32 MethodWithIntReturnValue().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Exiting method: Int32 MethodWithIntReturnValue().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program+AnotherSubprogram`1[[System.Int32, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] [(null)] - Entering method: Void .cctor().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program+AnotherSubprogram`1[[System.Int32, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] [(null)] - Exiting method: Void .cctor().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program+AnotherSubprogram`1[[System.Int32, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] [(null)] - Entering method: Void .ctor().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program+AnotherSubprogram`1[[System.Int32, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] [(null)] - Exiting method: Void .ctor().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program+AnotherSubprogram`1[[System.Int32, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] [(null)] - Entering method: U Act[U]().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program+AnotherSubprogram`1[[System.Int32, mscorlib, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089]] [(null)] - Exiting method: U Act[U]().
2008-07-24 15:49:32,773 [1] DEBUG Log4PostSharpTest.Program [(null)] - Exiting method: Void Main(System.String[]).
 

Additional information and references:

- http://www.postsharp.org/

- http://postsharp-user-plugins.googlecode.com/svn/wiki/Log4PostSharp.wiki

- http://www.postsharp.org/forum/log4postsharp/

- http://haacked.com/archive/2006/08/08/Log4NetAndExternalConfigurationFileInASP.NET2.0.aspx

- http://code.google.com/p/postsharp-user-plugins/wiki/Log4PostSharp

 
And finally a big thank you to PostSharp for the AOP tool and especially Michal Dabrowski for writing the Log4PostSharp addin. Thanks also to my boss Eden that introduced me to this tool.

I'll be updating this post with more information in the near future. You can either follow the instructions above or you can download my Test application from here.

Happy coding.
Jean

 


 

Posted: Jul 24 2008, 11:59 PM by jean | with no comments
Filed under:
The Matrix - "Temet Nosce"

I've been watching the philosophers take of the Matrix, and one of the realisations I've had about the movie that there are so many different layers of meaning that it's difficult to even comprehend. I'm watching the movie now for the +5 time, and I learn something new every time. I'd say I'm one of those people with an ingrained skeptical view of "societies view of what is write and wrong". My skepticism is also based on the idea that most authority figures are not necessarily basing their decisions on what they truly believe is the greater good for humanity as a whole, but rather how can they be perceived as trying to achieve the greater good.

I think it all boils down to my negative perception of the way human's think. It's as though we don't want to survive anymore we want to conquer and devour everything. Like an obese person thats been locked inside Macdonalds for the night. If you look at how we are destroying the planet, how our greed for material goods consumes us.... How much does a human need to live happily... and the answer is.... not much. Another issue I have with the human race is how blindly we conform to societies "norms". How rarely we actually stand back and ask ourselves whether what we are doing is really necessary, rather than just getting consumed by the rat race, to make as much money as possible and live in a 5 story mansion. The irony of it all is I believe I have more than what I need in this life from a materials perspective but the one thing I don't have is the one thing that I yearn for the most. Maybe it's due to my semi-self destructive personality, or maybe its because until recently I've never felt as though there was a need to settle down, or maybe its because that when I look at life I can't help but seeing it as one seriously ridiculously funny joke considering all the crazy things that happen around me, or maybe it's my rebellious nature that just won't let me conform. That's a lot of maybes. I think I need to understand myself better.

.... which leads me on to one more lesson from the Matrix movie:

the wooden plaque above Neo's head in the kitchen while he is talking to the Oracle says "Know Thyself" in Latin. The stronger your understanding of yourself in terms of your weaknesses and strengths in one dimension (including all other dimensions that would include yourself as a whole) the better control you have over your success, or the more you will be able to achieve, or the closer you will be able to get to true happiness. Then again, what is true happiness?

Keep asking questions.... NEVER stop.



 

Lessons from the Dark Side of Life

This is a way overdue blog post, but one that I will enjoy writing.

I have learned much from my past work and social experiences here in the UK. One thing I don't have(fortunately) are regrets. All my decisions have paid off so far and I now sit in a great position in my life where I have many opportunities available.

Here are some of the basic lessons:

Work

 1. Nothing comes to you without sacrifice. You need to find something that you are passionate about and then it will be easier to make those sacrifices to achieve your goals. There are many people chasing the same goal as you so you need to be ahead of the rest.

 2. Excuses valid or invalid account for nothing. Everybody has an excuse for not achieving any goal they have every tried to achieve. Excuses unfortunately get you nowhere. This is a fact that pertains to you a person's social and work life. I personally don't like people that always have an excuse for why life is so hard on them. You have to learn to take responsibility for your actions. Be hard on yourself, that way you are less likely to make the same mistake twice.

3. Always be honest. Even though you may end up as the "black sheep" at your company your piers will respect you for standing up and speaking your mind. Politics is a disease many companies have and honesty and openness always pays off in the long run. All the great programmers/thinkers I have met have this attribute in the extreme. If you look at architects like Billy Hollis and Alan Cooper, you will notice that when these guys get hired to do a job they cut straight through the company politics like it never existed. One of my favourite Thinkers in this respect is Robert Scoble. (This deserves a blog post of its own!)

4. Know when to shut up. If you are in the company of workers who are more proficient than you are, don't shoot your mouth off with ideas when a problem arises. Listen and learn from those that are better than you are at your job, and give them respect.

5. Stay positive. Even when the chips are down, and the pressure is through the roof. Keep in things in perspective and don't panic. Panic and stress only slow you and those around you down. Also managers should never use fear as a tactic to get their staff to work harder. Fear breeds contempt and does not pay off in the long run.

6. Always stand back and look at the big picture. My father taught me this trick and it saved me countless times. When things don't feel right, and everybody is running around like a headless chicken, stop what you are doing, go make yourself a coffee and look at things from an outsiders perspective. This ALWAYS brings the root problem to the surface.... and the irony of it all is that 99% of the time stress comes from the unknown variables in the problem you are tackling. Cut down the unknowns and you will have a stress free job. (Another blog post will come out of this... ).

Social Life

1. Remain a good person no matter what life deals you. There are so many tainted people out there. Bad experiences can psychologically scare a person, but most of us in our later years are able to put these experiences behind us and move on. It's difficult to move on sometimes when you really loved somebody and they threw it back in your face, but you should never let a break up lower your perception of who you are. People have flaws, and if two people don't suit each other then remain friends and move on.

2. Don't judge other people too quickly. Sometimes somebody that may look as though they don't like you or give you a hard time sometimes have issues that they are trying to deal with and are taking out their problems on the people around them. Always respect nerds (because I am one... ;-)) Nerds can be sometimes be laughed at but intelligent people are normally the survivors in this day and age.

3. Always ensure you reward those who are good to you. This is as basic as just saying 'thank you' sometimes. Greeting your fellow work colleagues in the morning and being courteous is critical to your success. Coming into work in the morning in a mood and taking it out on your work colleagues will only damage your career.

4. Love yourself. You have to believe in yourself to succeed. Give yourself the credit you deserve, and don't be afraid to boast of your achievements. I've meet countless people in my life that are brilliant at what they do but never got anywhere because they didn't believe in themselves. It's scary what we can achieve if we have the right mind set and the confidence required. There are people out there that survive purely off their confidence. Top level managers and directors which require confidence in the extreme. Nothing is wrong with a bit of arrogance either.

Anyway that is all for the moment.

Lots of love to everybody out there.

Jean

Generic type usage-constraints

Since the release of the .Net Framework 2.0 the amount of code I've had to write when building utility functions has diminished greatly. There is only one thing I enjoy more than writing code, and that is deleting code. :) I get to do that a lot nowadays especially when working on legacy .Net Framework 1.0/1.1 projects.

Take a look below and see how I've managed to reduce two functions which are screen specific to one.

    

       // Duplicated in GetFormAInstance

        public static screens.FormB GetFormBInstance(string key, out bool alreadyExists)

        {

 

            screens.FormB form = Controller.GetRegister.Get(key) as screens.FormB;

 

            if (form == null)

            {

                alreadyExists = false;

                form = new screens.FormB();

                Controller.GetRegister.Register(key, form);

            }

            else

            {

                alreadyExists = true;

                form.BringToFront();

            }

 

            return form;

        }

 

        // Duplicated in GetFormBInstance

        public static screens.FormA GetFormAInstance(string key, out bool alreadyExists)

        {

 

            screens.FormA form = Controller.GetRegister.Get(key) as screens.FormA;

 

            if (form == null)

            {

                alreadyExists = false;

                form = new screens.FormA();

                Controller.GetRegister.Register(key, form);

            }

            else

            {

                alreadyExists = true;

                form.BringToFront();

            }

 

            return form;

        }

 

        // Function which uses generics to encapsulate GetFormAInstance and GetFormBInstance

        public static T GetFormInstance<T>(string key, out bool alreadyExists) where T : Form, new()

        {

 

            T form = Controller.GetRegister.Get(key) as T;

 

            if (form == null)

            {

                alreadyExists = false;

                form = new T();

                Controller.GetRegister.Register(key, form);

            }

            else

            {

                alreadyExists = true;

                form.BringToFront();

            }

 

            return form;

        }

 

 

As you can see I am using the ability to define constraints on Type parameters to indicate that the Type returned from GetFormInstance will support the new() constraint and the type will derive from the Form class. If I had not supplied this constraint information the compiler would have have complained about the "form = new T();" line and given me the following error : "Cannot create an instance of the variable type 'T' because it does not have the new() constraint".

Posted: Mar 25 2008, 09:57 PM by jean | with no comments
Filed under:
Pro Active VS Re Active IT project management

Being a programmer, there are a few things that are extremely important to me with regards to the qualities my manager should have.One of the most important characteristics should be the way in which information or instructions are supplied to me.

I like to have:
1) The information I need before I start working on a task. I want to have to ask as few questions as possible during the development process.

Types of questions I would like to avoid are:
1) What is the project code for this project so I can book time to it?
2) How would you like me to implement the functionality requested in the UI?
UI development is always a pain if the specification is unclear or non-existent because everybody has there own opinion on the best way to implement the look/feel of a set of features which will satisfy the business requirements. Normally there are many roads through a forest (i.e. choices to make) in software development, but within the UI sphere the no. of choices increase dramatically.

The key here is to minimize the no. of assumptions the developer is forced to make. The less assumptions the developer has to make, the less the developer has to worry whether he has made the right choice and the less risk there is that the way in which the software is satisfying the functionality requirement will be incorrect.

Guide to managing your habits:
1) The manager is not interested in how the business requirements are implemented as long as the time constraints allocated to satisfying them are met.
 - This sort of attitude inevitable leads to developers creating hacks if the time constraints are to severe.
2) Management asking you questions that are not relevant to the current problem domain. This is always due to poor communication between the programmer and manager. A developer should always touch base with his manager at least once a day. Your manager pays your salary, so at least give him the respect of updating him on the project's progress once a day.
3) Always be 100% honest and thorough. Keep your manager informed of what your impediments are, no matter how much the manager doesn't want to hear. Management will only respect the developer for being honest and raising any project impediments early in the software development life cycle.

The message I am trying to put across here is always be pro-active in terms of providing information. Whether you are a manager or developer make sure your work colleagues have the information before the need it. This prevents them from having to come to you to ask for it and disturb your work rhythm. Developers of today are really required to be jack of all trades. And one of the most important trades include managing their managers.

Jean Hibbert

Windows Work Flow (WWF) / .Net Framework

I have to say I have been working with WWF for the past few days and I am impressed with this technology. Not only is the designer able to visually build the work flow but the designer is able to execute the work flow also.

By customising the Activities Designer objects, the developer can also manipulate the design time behaviour of the composite and simple activities within the designer. The CompositeActivityDesigner and the ActivityDesigner are base classes that can be used with to provide overridable methods to manipulate the design time features
of thier custom activities.

if (t == null)

throw new NullReferenceException("Cannot display a null transaction");

WorkflowDesignerLoader loader = GetService(typeof(WorkflowDesignerLoader)) as WorkflowDesignerLoader;

if (loader == null)

throw new NullReferenceException("Could not load workflow designer loader");

IDesignerHost designerHost = this.designSurface.GetService(typeof(IDesignerHost)) as IDesignerHost;

CompositeActivity rootActivity = designerHost.RootComponent as CompositeActivity;

.......

loader.AddActivityToDesigner(rootActivity);

The above code loads a set of custom activities into the designer.

Posted: Feb 19 2008, 07:18 PM by jean | with no comments
Filed under:
Poor leadership in South Africa

I'd like to dedicate this blog post to Thabo Mbeki. I've never met the man, but I can say he has never failed to dissapoint me. He's never made any difference to South Africa, or voiced any speech that could inspire since he has come to office. A luke warm failure of note.

Jacob Zuma is a different story. The future president of South Africa loves to sing a song which has the lyrics "bring me my machine gun". It seems as though Africa as a continent does not work well when it comes to the implementation of Democratic policies. This is because the majority of the population are ignorant (not stupid) and cannot descern a good leader from a poor one. Maybe we need a new type of democracy, or political outlook when it gets to developing countries.

A system that will:

a) Only allow educated members to vote. i.e members which have a matric or above.

b) Give more power to the police force to execute punishment on the spot.

Nelson Mandela was a great leader because he was willing to put the past behind him and look into the future.

 

Posted: Feb 13 2008, 07:42 PM by jean | with no comments
Filed under:
Daily thoughts...

Ok, its time to start using my blog. For much of 2007 and all of 2008 this poor blog has been deserted and left to wallow in it's misery. I actually feel sorry for my blog, I mean... not only does it only display meaningless blog posts that are incomplete and obviously written in a rush (between the hours of 11h40 and 12h00 just  before my lunch break is supposed to start) but if you were looking for a blog that will change your life.... look elsewhere is all i can say. Ok.

So I watched a movie directed by George Clooney a while back... starring Sam Rockwell. It's about a guy who didn't really know what life was about and didn't really care. He just knew what he wanted out of life, and what he wanted was pretty simple. The problem is he just really doesn't see the point to anything at all. We work, we die, people cry. We watch mind numbing game shows and have parties where we flirt with one another and perform insane mating dances. Anyway, this guy in this movie goes through a difficult experience and at the end of it he realises life it more superficial than he initially expected. In fact most people see life this way and are only willing to give when they know they will receive. What I want to say is that you have to live for yourself in the 21st century, but you have to hold onto your own dignity. You must always be willing to give without have the notion of always receiving something in return. We should all at least try to make this world a better place. If there is a god, that is what he will judge you on. NOT the number of times you went to church.

There is so much philosophising and analysing to do. Its better to just sometimes do your best to enjoy your life. Keep a balance. And that will always mean making a sacrifice to stay healthy and sane.

 

Posted: Feb 12 2008, 07:22 AM by jean | with no comments
Filed under:
Quotes by Friends

There are those time when friends come up with the most classic quotes:

 Here are some:

"The truth never lies"

 "We have to go out this weekend because it only comes around once a year"

Tony the foursies man.

"marriage is the only adventure that is open to the truly cowardly."

Mike the spike.

 More to come...

Posted: Dec 29 2007, 06:02 AM by jean | with no comments
Filed under:
Defining the service layer dependency tree using UML Sequence diagrams and the Dependency Injection pattern

UML sequence diagrams can be used to identify interfaces for an application's

Service layers which in turn can be used to generate a service layer dependency tree.

 

When designing an OO application there are three different object types to consider, in accordance with UML standards and robustness analysis. They are the entity, boundary and controller objects which map to the MVC paradigm respectively.

 

The Model within the MVC pattern contains the core business logic of the application, and two types of objects exist within it:

 

Entity (database) objects

 

These objects are easily identified in our use cases from the nouns.

 

Entity objects map to the tables in the database and define the data entities that the application will manipulate. These objects are persisted to the database when changes occur. These objects normally include implement their persistence functionality through interfaces as depicted in the "domain object persistence pattern". These objects are also generally easily defined and identified by understanding what data needs to be persisted by the application. A tree like object structure can normally be generated along with the related persistence code using code generators.

 

Business objects

 

The business objects along with the entity objects belong to the Model in the MVC pattern. The Business objects define a particular set of services required by the application.

 

Defining the interfaces for the different service layer objects and understanding their dependency on one another is integral to leveraging the re-usability and “plug and play” type architecture that OO systems allow for.

 

The business objects are the primary objects that manipulate the application’s entity objects, communicate with the controller objects and define the "service layers" of an application, otherwise known as an application's business service layers.

 

The key lies in the application of UML sequence diagrams. Once the use cases have been developed the use cases can be used to assist in identifying what general services which are required in the system by looking at the actions that take place during a particular use case.

 

As an example I will use a simplified notification system to explain what I mean.

 Use case:

1. User subscribes with the system.

2. The user provides search criteria information that defines the user’s profile.

 

3. The system checks the newly added system data on a daily basis against the user’s profile to determine whether the user should receive notifications.

3. Notifications are not sent if a user’s subscription is no longer valid.

 Data entities defined from nouns:

User

Notification

Subscription

Profile

 

You will notice that although the data entities have been identified, they say nothing about the actions (business logic) required to fulfil the system’s purpose.

 

Processes that can be identified from the Actions/Verbs within the use case can be used to derive the business services required by the application.

 Service entities (business objects) that can be identified from the use case:

Service

Responsibility

Subscription service

Managing user subscriptions. Checking whether subscriptions are still valid.

Data service

Updating and inserting data into the database.

Search service

Building the search criteria from the user profile to search the database and retrieve notifications that must be sent out.

Notification service

Send out the notifications to users who have a search profile with criteria matching the recently added data.

 

We could derive a scheduler service also from the above use case but for the purpose of this article and to keep things simple, the notification service will assume this responsibility. In certain instances it’s beneficial to break up service components as soon as they start taking on responsibilities that don’t neatly fit into their category of service.

 

“Subscribing” implies that there is some kind of "data service layer" that the system required to load and store data in the relevant data store.

 

You will notice that nowhere in this article do I refer to a particular type of technology in terms of data store or data packets (eg.ado.net datasets, xml) retrieved from the data store. The use cases and sequence diagrams ONLY depict objects within the UML modelling language. The technology used to develop the system or the data store used to store the data is up to the developer.

  

   

Derived Interfaces from sequence diagram

  

  

Identifying the Service Layer Dependency Tree

 

You will notice that subscription service layer relies on the data service layer to insert profiles and subscriptions. The subscription service also relies on the search and notification service. The search service relies on the data service to return notification data.

 

The resulting class diagram will thus look as follows:

  

     

Windows forms VS. ASP.NET applications

 

A common design error made by developer's that have done a lot of windows programming is the abuse of the object entity tree within web applications. Loading the entire object tree into memory gives a developer an enormous advantage when developing windows applications in that they have instant access to any data entity in the database and their persistence functionality.

 

What you have to bear in mind is the short lived life cycle of the entity object within web applications versus the long lived life cycle within windows applications. This means that within web applications it should only be useful to load the necessary data entity objects into memory that you are interested in displaying within the requested web page.

  

Conclusion

 

I generally find that using inheritance tree structures within an application ties one down to a particularly rigid set of inheritance rules within your objects and doesn’t allow for the type of polymorphic flexibility that interfaces provide.

Interfaces also promote a plug and play type architecture within the different service layers of the application (i.e. layers of the application can be removed and substituted with other objects as long as they implement the substituted layer's interface(e.g. the data service layer)).

 

Dependency injection also forces the layers to be created in the correct order and allows these layers to be easily identified within the sequence diagram as depicted earlier.

Posted: Dec 18 2007, 07:01 PM by jean | with no comments
Filed under:
UK Naturalisation ,the process, the papers and other requirements.

As a South African, I've recently applied for my UK naturalisation on the basis that I have had indefinite leave to remain now for 3 years and have been living in the UK for 8 years altogether:

- The full process of getting all the paper together took 3 full months. Hopefully this blog entry will assist anybody that is intersted in becomming a UK citizen.

Requirements included:

1) Filling out the forms which can be found at: http://www.ind.homeoffice.gov.uk/applying/nationality/formsandguidance/

2) You will require 2 referees (close friends) that you have known for over 3 years to sign the forms, one of them must be of a professional standing(eg an accountant) and the other must be a British citizen.

3) You must also complete a UK knowledge test. You can book the test at your local library through a no that can be found in the information guide. http://www.ind.homeoffice.gov.uk/6353/11406/anguidance1.pdf The information guide also explains how to fill in the forms (http://www.ind.homeoffice.gov.uk/6353/11406/anapplicationform.pdf). You will have to supply the certificate as proof that you passed the test with your forms.

4) You will need to supply 1 passport photo.

5) You will need to supply all your letters of employment since you started working in the UK.

6) You will need to download the payment slip http://www.ind.homeoffice.gov.uk/6353/11464/fee_notes_paymentslip.pdf The cost of applying for naturalisation is a whopping £655 at the moment.

The above is a summary of what is required. Hope this helps!

Writing an effective search stored procedure with paging functionality

Writing a search engine can be a nightmare. There are so many permutations of possible search criteria that can be handed down to the DBM system that one is tempted to steer towards writing code that generates dynamic SQL on on the client side. This can become become very difficult to maintain especially since the dynamic SQL generation code will always compile, even if the database structure changes. We do not want our search engine to break down in front of the client. No thank you.

 A technique that I have developed is would use a stored procedure to filter out all the ID's of the records that do not satisfy the search critiria and populate a temp table that can be once again filtered for the relevant page that the client is searching for:

The count(*) at the botton of the stored procedure just returns that total no of records so that the caller can determine which page is bieng displayed. Notice how the proc_FetchFilteredID's inserts the filtered IDs into temp table #filtered_ids.

/* fetch the filtered id's */

CREATE TABLE #filtered_ids (clientid INT)

INSERT INTO #filtered_ids

EXEC proc_FetchFilteredIDs @startdate, @enddate, @searchtext, @status

SELECT id, [name], guid, startTime, finishTime, Status

FROM

(

SELECT ROW_NUMBER() OVER (ORDER BY t.pk_id DESC) AS Row,

t.pk_id as id,

e.[name],

t.guid as guid,

t.startTime as startTime,

t.finishTime as finishTime,

t.fk_statusid as Status,

FROM tClient t WHERE t.pk_id IN (SELECT jobid FROM #filtered_ids)

)

AS Entries

WHERE Row >= @startRowIndex AND Row <= (@startRowIndex + @maximumRows)

/* Get the total number of rows */

SELECT @totalrowcount = COUNT(*)

from tClient t,

WHERE t.pk_id IN (SELECT clientid FROM #filtered_ids)

DROP TABLE #filtered_ids

If there are any better ways of writing search stored procedures please shout.

Jean 

 

 

Posted: Oct 30 2007, 07:32 PM by jean | with no comments
Filed under:
Citrix IE frame Freezes due to Office 2003 language toolbar.

I've just assisted recently in hunting down the reason for the IE frame presented by the Citrix presentation server for freezing when the word document is opened inside the Citrix frame.

What the Citrix software does is it supplies a secure HTTP link to a Citrix presentation server which allows the user to select an application (windows or web) to open and use via the Citrix IE window.

Resourses which have assisted me in resolving this issue include:

http://support.citrix.com/article/CTX104445&searchID=-1 http://support.microsoft.com/kb/282599 More to come on this issue... Jean
The relevance of relativity

Hey .... not that anybody reads my blog... but who cares...
 
I thought I would mention that there has been something bothering me for a while now. People tend to hand pick reasons in a biased fashion from their basket of reasoning to facilitate their personal causes during a debate.
 
Being able to stand back and provide totally neutral advice or feedback is one of those gifts that only truly great thinkers amongst us are able to do. Being able to accept and more importantly REALIZE ones mistakes is an even greater gift, and is a true sign of intelligence.
 
EXAMPLE
The age old debate of stored procs against inline SQL. I prefer stored procs because they extract the SQL from application and provide an abstracted type of database interface along with integrated security. You will get some programmers that will give you the reason that they use stored procs because they can be compiled on the DB level to improve performance. Although this is true the amount of performance gained by a well designed SQL statement RELATIVE to the performance gained by the compilation of the stored proc is not EVEN RELEVANT. i.e. the time the SQL takes to execute against the DB outweighs compilation of the execution plan by 10 to 1 time in 99% of all cases.
 
As you can see from the above analogy there are always reasons to do the wrong thing but they are outweighed heavily against the reasons to do the right thing. It just takes common sense to weigh then up  properly, and make the right decisions.

Posted: Aug 11 2007, 02:02 AM by jean | with no comments
Filed under:
More Posts Next page »