Getting null reference exception when NewTransientInstance<T>() is called

May 10, 2013 at 9:21 AM
Hi Guys,
           I am getting this null reference exception whe  I try and create ANY of my objects.
Here is one example. I am calling this in one of my services that is in a separate assembly that is referenceing NakedObjects.Helpers.

Could you help me please?

namespace Lansw.Uwas.Model
{
//[IconName("cellphone.png")]
[IconName("default.png")]
public class Practitioner : BaseDomainObject, IPractitioner
{
    #region Title

    //public override string ToString()
    //{            
    //    var t = new TitleBuilder();
    //    if (NameStyle)
    //    {
    //        t.Append(LastName).Append(FirstName);
    //    }
    //    else
    //    {
    //        t.Append(FirstName).Append(LastName);
    //    }
    //    return t.ToString();
    //}

    #endregion

    #region Injected Services

    // This region should contain properties to hold references to any services required by the
    // object.  Use the 'injs' shortcut to add a new service.
    #region Injected: 


    #endregion

    #endregion

    #region Life Cycle Methods
    // None this object will not be persisted        

    #endregion

    #region ID

    [Key]
    [Hidden]    
    public virtual int PractitionerID { get; set; }

    [Hidden]
    [MemberOrder(15), DefaultValue(false), DisplayName("Reverse name order")]
    public virtual bool NameStyle { get; set; }

    [MemberOrder(1), DisplayName("Last Name")]
    public virtual string LastName { get; set; }
    [MemberOrder(2), DisplayName("FirstName")]
    public virtual string FirstName { get; set; }
    [MemberOrder(3), DisplayName("Preferred Contact Number")]
    public string PreferredContactNumber { get; set; }        

    #endregion              

    #region Row Guid and Modified Date

    #region rowguid

    [Hidden]
    public override Guid rowguid { get; set; }

    #endregion

    #region ModifiedDate

    [MemberOrder(99)]
    [Disabled]
    public override DateTime ModifiedDate { get; set; }

    #endregion

    #endregion

}
}
[NullReferenceException: Object reference not set to an instance of an object.]
NakedObjects.Services.AbstractFactoryAndRepository.NewTransientInstance() +114
Lansw.Uwas.Model.PractitionerRepository.NewPractitioner() in d:\Lansw.Uwas\Lansw.Uwas\Lansw.Uwas.Model\Practitioner\PractitionerRepository.cs:30
UWAS.Services.PractitionerService.GetNextPractitioner() in d:\Lansw.Uwas\Lansw.Uwas\Lansw.Uwas.Services\PractitionerService.cs:47

[InvokeException: Object reference not set to an instance of an object.]
NakedObjects.Reflector.DotNet.Reflect.Util.InvokeUtils.InvocationException(String error, Exception e) +252
NakedObjects.Reflector.DotNet.Reflect.Util.InvokeUtils.Invoke(MethodInfo method, Object obj, Object[] parameters) +122
NakedObjects.Reflector.DotNet.Reflect.Util.InvokeUtils.Invoke(MethodInfo method, INakedObject nakedObject, INakedObject[] parameters) +337
NakedObjects.Reflector.DotNet.Facets.Actions.Invoke.ActionInvocationFacetViaMethod.Invoke(INakedObject inObject, INakedObject[] parameters) +322
NakedObjects.Reflector.Transaction.Facets.Actions.Invoke.<>c__DisplayClass1.<Invoke>b__0() +85
NakedObjects.Reflector.Transaction.Facets.Actions.Invoke.ActionInvocationFacetWrapTransaction.InvokeInTransaction(Func1 action) +264
NakedObjects.Reflector.Transaction.Facets.Actions.Invoke.ActionInvocationFacetWrapTransaction.Invoke(INakedObject target, INakedObject[] parameters) +165
NakedObjects.Reflector.Spec.NakedObjectActionImpl.Execute(INakedObject nakedObject, INakedObject[] parameterSet) +267
NakedObjects.Web.Mvc.Controllers.GenericControllerImpl.Execute(INakedObjectAction action, INakedObject target, INakedObject[] parameterSet) +77
NakedObjects.Web.Mvc.Controllers.GenericControllerImpl.ActionAsFind(ObjectAndControlData controlData, FormCollection form) +773
NakedObjects.Web.Mvc.Controllers.GenericControllerImpl.Edit(ObjectAndControlData controlData, FormCollection form) +303
Lansw.Uwas.RunMVC.Intranet.Controllers.GenericController.Edit(ObjectAndControlData controlData, FormCollection form) in d:\Lansw.Uwas\Lansw.Uwas\Lansw.Uwas.RunMVC.Intranet\Controllers\GenericController.cs:42
lambda_method(Closure , ControllerBase , Object[] ) +246
System.Web.Mvc.ActionMethodDispatcher.Execute(ControllerBase controller, Object[] parameters) +59
System.Web.Mvc.ReflectedActionDescriptor.Execute(ControllerContext controllerContext, IDictionary
2 parameters) +435
System.Web.Mvc.ControllerActionInvoker.InvokeActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor, IDictionary2 parameters) +60
System.Web.Mvc.Async.AsyncControllerActionInvoker.InvokeSynchronousActionMethod(ControllerContext controllerContext, ActionDescriptor actionDescriptor, IDictionary
2 parameters) +50
System.Web.Mvc.Async.<>c__DisplayClass42.<BeginInvokeSynchronousActionMethod>b__41() +75
System.Web.Mvc.Async.<>c__DisplayClass81.<BeginSynchronous>b__7(IAsyncResult _) +44
System.Web.Mvc.Async.WrappedAsyncResult
1.End() +139
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +102
System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeActionMethod(IAsyncResult asyncResult) +49
System.Web.Mvc.Async.<>c__DisplayClass39.<BeginInvokeActionMethodWithFilters>b__33() +126
System.Web.Mvc.Async.<>c__DisplayClass4f.<InvokeActionMethodFilterAsynchronously>b__49() +323
System.Web.Mvc.Async.<>c__DisplayClass37.<BeginInvokeActionMethodWithFilters>b__36(IAsyncResult asyncResult) +44
System.Web.Mvc.Async.WrappedAsyncResult1.End() +139
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +102
System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeActionMethodWithFilters(IAsyncResult asyncResult) +50
System.Web.Mvc.Async.<>c__DisplayClass2a.<BeginInvokeAction>b__20() +68
System.Web.Mvc.Async.<>c__DisplayClass25.<BeginInvokeAction>b__22(IAsyncResult asyncResult) +184
System.Web.Mvc.Async.WrappedAsyncResult
1.End() +136
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +56
System.Web.Mvc.Async.AsyncControllerActionInvoker.EndInvokeAction(IAsyncResult asyncResult) +40
System.Web.Mvc.<>c__DisplayClass1d.<BeginExecuteCore>b__18(IAsyncResult asyncResult) +40
System.Web.Mvc.Async.<>c__DisplayClass4.<MakeVoidDelegate>b__3(IAsyncResult ar) +47
System.Web.Mvc.Async.WrappedAsyncResult1.End() +151
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +59
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +40
System.Web.Mvc.Controller.EndExecuteCore(IAsyncResult asyncResult) +44
System.Web.Mvc.Async.<>c__DisplayClass4.<MakeVoidDelegate>b__3(IAsyncResult ar) +47
System.Web.Mvc.Async.WrappedAsyncResult
1.End() +151
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +59
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +40
System.Web.Mvc.Controller.EndExecute(IAsyncResult asyncResult) +39
System.Web.Mvc.Controller.System.Web.Mvc.Async.IAsyncController.EndExecute(IAsyncResult asyncResult) +39
System.Web.Mvc.<>c__DisplayClass8.<BeginProcessRequest>b__3(IAsyncResult asyncResult) +45
System.Web.Mvc.Async.<>c__DisplayClass4.<MakeVoidDelegate>b__3(IAsyncResult ar) +47
System.Web.Mvc.Async.WrappedAsyncResult`1.End() +151
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +59
System.Web.Mvc.Async.AsyncResultWrapper.End(IAsyncResult asyncResult, Object tag) +40
System.Web.Mvc.MvcHandler.EndProcessRequest(IAsyncResult asyncResult) +40
System.Web.Mvc.MvcHandler.System.Web.IHttpAsyncHandler.EndProcessRequest(IAsyncResult result) +38
System.Web.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute() +9629708
System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously) +155
Coordinator
May 10, 2013 at 9:36 AM
The error suggests that the null reference is the Container, which should be automatically injected into AbstractFactoryAndRepository.

My guess is that you have added an injected container into your own class PractitionerRepository (which I see inherits from AbstractFactoryAndRepository). The effect of this is to shadow the injected container in AbstractFactoryAndRepository - so only one of the properties will get injected. If you have done this, remove the injected container from PractitionerRepository - because you can just reference the one in the superclass.

N.B. This unintentional shadowing should have generated a Warning in Visual Studio. Pay attention to all warnings. In fact I strongly recommend that you set VS to turn all Warnings into Errors - that way you can't overlook them. (If you're not familiar how to to do that, look it up on Stack Overflow or Microsoft forums).
May 13, 2013 at 2:52 AM
Thanks guys but no I had not shadowed the Container in the PractitionerRepository .
However as I said I have my service in a separate assembly and this has caused the problem.
As this service will be a separate service that will access a separate WCF service to get the data for this service I thought I would put it in a separate assembly.
I added the service and the respository that it needs to the contributed actions.
However the the PractitionerRepository that is contained in the service has a null value for the Container when the ervice object is used.
So inorder to get this working for now, I just moved the service code into the repository class and just the contributed actions just uses this repository.
So I have got rid of the service for now.
I had a reference to my service assembly in the main RunMVC project.

Regards,
             Alistair
Editor
May 13, 2013 at 6:20 AM
Strange, because we have services defined in different assemblies, and it all works fine.

So the problem - whatever it is - is a little more subtle

Dan
Coordinator
May 13, 2013 at 8:24 AM
As Dan says, there is no problem with having your domain model (including services) split across multiple assemblies - we do this a lot.

If the ProductRepository did not have a container injected into it (and you had not shadowed the container property) then this suggests to me that the Naked Objects framework had no knowledged of that instance of the ProductRepository. You say that both 'the service' (I'll call that ServiceA) and the ProductRepository were registered in the Run class (it doesn't matter whether that's as MenuServices, ContributedActions, or SystemServices) - in which case the container should be injected into them when they are instantiated there.

Which makes me wonder if, say, within ServiceA (or anywhere else in the domain code) you are instantiating the service separately - in which case NOF has no knowledge of it. To clarify - NOF only knows about the instances of those services instantiated within the service registrations. You make use of those services (which will have had a container and any other services they depend upon) injected into them - by means of dependency injection.
May 13, 2013 at 9:38 AM
Thanks heaps guys I added the PractitionerRepository into the SystemServices as well (which I should not have to do) but the Container in the PractionerResposity is still nulll.
I am able to create newtransistent objects from a domain object.

Here is my RunWeb class

using Lansw.Uwas.Model;
using NakedObjects;
using NakedObjects.Boot;
using NakedObjects.Core.Context;
using NakedObjects.Core.NakedObjectsSystem;
using NakedObjects.EntityObjectStore;
using NakedObjects.Web.Mvc;
using NakedObjects.Web.Mvc.Helpers;
//using UWAS.Services;

namespace Lansw.Uwas.RunMVC.Intranet.App_Start {
public class RunWeb : RunMvc {
    protected override NakedObjectsContext Context {
        get { return HttpContextContext.CreateInstance(); }
    }

    protected override IServicesInstaller MenuServices {
        get {
            return new ServicesInstaller(
                                            new WorkOfferRepository()                                                
                                        );
        }
    }

    protected override IServicesInstaller ContributedActions {
        get { return new ServicesInstaller(
                                            new PractitionerRepository()
                                            //new PractitionerService()
                                          ); 
        }
    }

    protected override IServicesInstaller SystemServices {
        get { return new ServicesInstaller(
                                                new SimpleEncryptDecrypt(),
                                                new PractitionerRepository()
                                          ); 
        }
    }


    // example functions that gets types for AssociateTypes below  
    //private static Type[] AdventureWorksTypes() {
    //    var allTypes =  AppDomain.CurrentDomain.GetAssemblies().Single(a => a.GetName().Name == "AdventureWorksModel").GetTypes();
    //    return allTypes.Where(t => t.BaseType == typeof(AWDomainObject) && !t.IsAbstract).ToArray();
    //}
    //
    //private static Type[] CodeFirstTypes() {
    //    return new[] {typeof(Class1), typeof(Class2)};
    //}

    protected override IObjectPersistorInstaller Persistor
    {
        get
        {
            // Database.DefaultConnectionFactory = new SqlCeConnectionFactory("System.Data.SqlServerCe.4.0"); //For in-memory database
            // Database.SetInitializer(new DropCreateDatabaseIfModelChanges<MyDbContext>()); //Optional behaviour for CodeFirst
            var installer = new EntityPersistorInstaller();

            installer.UsingCodeFirstContext(() => new UWASDbContext());

            // installer.UsingEdmxContext("Model").AssociateTypes(AdventureWorksTypes); // for Model/Database First
            // installer.UsingCodeFirstContext(() => new MyDbContext()).AssociateTypes(CodeFirstTypes);  //For Code First

            return installer;
        }
    }

    public static void Run() {
        new RunWeb().Start();
    }
}
}

And here is my Repository class

// Copyright © Naked Objects Group Ltd ( http://www.nakedobjects.net).
// All Rights Reserved. This code released under the terms of the
// Microsoft Public License (MS-PL) ( http://opensource.org/licenses/ms-pl.html)
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using NakedObjects;
using NakedObjects.Services;
using Lansw.Uwas.Interfaces;

namespace Lansw.Uwas.Model
{
[DisplayName("Practitioners")]
public class PractitionerRepository : AbstractFactoryAndRepository
{
    #region Injected Services

    //#region Injected: XXXRepository

    //public XXXRepository XXXRepository { set; protected get; }


    //#endregion

    #endregion

    #region NewPractitioner

    public Practitioner NewPractitioner()
    {
        //var practitioner = Container.NewTransientInstance<Practitioner>();
        var practitioner = Container.NewTransientInstance<Practitioner>(); // Container is null ???

        return (practitioner);
    }

    //[MemberOrder(2)]
    //public List<IPractitioner> AllPractitioners()
    //{
    //    var practitioners = this.Instances<IPractitioner>();

    //    return (practitioners.ToList());
    //}

    public List<Practitioner> GetAllActivePractitioners()
    {
        List<Practitioner> practitioners = new List<Practitioner>();

        var practitioner = NewPractitioner();

        practitioner.PractitionerID = 1;
        practitioner.FirstName = "Fred";
        practitioner.LastName = "Boil";
        practitioner.CourtVenue = "a";
        practitioner.PreferredContactNumber = "0293656318";

        practitioners.Add(practitioner);

        var practitioner2 = NewPractitioner();

        practitioner2.PractitionerID = 2;
        practitioner2.FirstName = "Wilbur";
        practitioner2.LastName = "Wild";
        practitioner2.CourtVenue = "a";
        practitioner2.PreferredContactNumber = "0293656319";

        practitioners.Add(practitioner2);
        //return (practitioners.ToList<IPractitioner>());
        return (practitioners);
    }

    private void AddTitleString(List<string> practionersAsTitleStrings, Practitioner practitioner)
    {
        practionersAsTitleStrings.Add(practitioner.ToString());
    }

    public List<string> GetAllActivePractitionersAsTitleStrings()
    {            
        List<string> practionersAsTitleStrings = new List<string>();

        this.GetAllActivePractitioners().ForEach(x => AddTitleString(practionersAsTitleStrings, x));

        return (practionersAsTitleStrings);
    }

    public Practitioner GetNextPractitioner()
    {
        var practitionerRepository = new PractitionerRepository();

        //var x = new WorkOfferRepository();

        var practitioner = practitionerRepository.NewPractitioner();

        practitioner.PractitionerID = 1;
        practitioner.FirstName = "Next";
        practitioner.LastName = "Practitioner";
        practitioner.CourtVenue = "a";
        practitioner.PreferredContactNumber = "0293656785";

        return (practitioner);
    }

    #endregion


    public List<Practitioner> GetAllActivePractitionersByCourt(string CourtVenue)
    {
        string court = CourtVenue.ToLowerInvariant();
        return (this.GetAllActivePractitioners().Where(x => x.CourtVenue.ToLowerInvariant() == court).ToList());
    }
}
}
Editor
May 13, 2013 at 9:44 AM
There's definitely something remiss here.. in GetNextPractitioner() you are instantiating a new PractitionerRepository. Why would you do that? Perhaps this - in some very roundabout way - is the cause of the issue?


    public Practitioner GetNextPractitioner()
    {
        var practitionerRepository = new PractitionerRepository();

        //var x = new WorkOfferRepository();

        var practitioner = practitionerRepository.NewPractitioner();

        practitioner.PractitionerID = 1;
        practitioner.FirstName = "Next";
        practitioner.LastName = "Practitioner";
        practitioner.CourtVenue = "a";
        practitioner.PreferredContactNumber = "0293656785";

        return (practitioner);
    }
May 13, 2013 at 11:09 PM
THANKS HEAPS GUYS THAT WAS IT, this was just some dead code that I had that I didn't check!
SO this new Repository would not be registered with the services so thats why NO could not find it. I just needed to do the following code below..
So repositories are registered as singletons in the container. Can you make them transient? Not that I need to do that now.

public Practitioner GetNextPractitioner()
    {
        var practitioner = this.NewPractitioner();

        practitioner.PractitionerID = 1;
        practitioner.FirstName = "Next";
        practitioner.LastName = "Practitioner";
        practitioner.CourtVenue = "a";
        practitioner.PreferredContactNumber = "0293656785";

        return (practitioner);
    }
Best Regards,
               Alistair
Editor
May 14, 2013 at 5:43 AM