Saturday, April 19, 2014

Dependency injection with Ninject & Moq

Dependency injection could be a hard concept to grasp for those who haven't used it previously (been there!). I don't profess to be an expert, but I haven't found a good tutorial online that explains how to use Ninject/Moq, so I'll just dabble a bit below in hopes that this helps someone in the future.

If you already happen to be an expert and see any mistakes or have suggestions, I would appreciate feedback.

Download Source if you don't want to read and just want to see the code in action.

Let's take the following code:
public interface IMyObject
{
    string GetValue();
}
public class ImplMyObject : IMyObject
{
    public string GetValue()
    {
        return "ImplMyObject";
    }
}
public class MyObjectHandler
{
    public string GetValueFromMyObject(IMyObject myObj)
    {
        return myObj.GetValue();
    }
}
Very simple, if we want to invoke it, we'll do the following:
static void Main(string[] args)
{
    ImplMyObject myObj = new ImplMyObject();
    MyObjectHandler handler = new MyObjectHandler();
    string myObjValue = handler.GetValueFromMyObject(myObj);
}
Nothing wrong with that, we can pass in any object inheriting from the "IMyObject" interface and get the expected result.

Now, let's say we want to write a test case to test "MyObjectHandler." We could do the following:
public class MockMyObject : IMyObject
{
    public string GetValue()
    {
        return "MockMyObject";
    }
}

[TestMethod]
public void RegularSample()
{
    MockMyObject myObj = new MockMyObject();
    MyObjectHandler handler = new MyObjectHandler();
    Assert.AreEqual("MockMyObject", handler.GetValueFromMyObject(myObj));
}
But now we're cluttering up our code with Mock objects, which really only mean something within a test case and should be maintained with the test case. So why not ignore the object and use Moq?
[TestMethod]
public void MoqObjectSample()
{
    var moqMyObj = new Mock<IMyObject>();
    moqMyObj.Setup(m => m.GetValue()).Returns("MoqObjectSample");

    MyObjectHandler handler = new MyObjectHandler();
    Assert.AreEqual("MoqObjectSample", handler.GetValueFromMyObject(moqMyObj.Object));
}
So far, so good, right? We really don't need to recreate a full object, just Moq it up to return certain results which will test the "MyObjectHandler" code.

Now, let's introduce Ninject into the picture. There may be times when you aren't able to pass interfaces around, or there are too many functions to pass it around if we have deep code and we can't possibly manage passing a DB connection object from our UI layer to our business layer and ultimately to the data access layer. We're still passing interfaces, but we just don't start at the top. So we can't really use Mock objects if we can't pass them in.

Let's look at the following example:
public class MyObjectHandler
{
    public string GetValueFromMyObject()
    {
        IMyObject myObj = new ImplMyObject();
        return myObj.GetValue();
    }
}
Not conducive to much of anything. Let's add a few lines of Ninject code...
internal class NinjectBootstrapper
{
    private static readonly Lazy<IKernel> _kernel = 
        new Lazy<IKernel>(() => new StandardKernel(new Bindings()));

    internal static IKernel Kernel
    {
        get { return _kernel.Value; }
    }
}
public class Bindings : NinjectModule
{
    public override void Load()
    {
        Bind<IMyObject>().To<ImplMyObject>();
    }
}
So above we created the binding for IMyObject to use ImplMyObject and we'll use it as follows:
public string GetValueFromMyObject()
{
    IMyObject myObj = NinjectBootstrapper.Kernel.Get<IMyObject>();
    return myObj.GetValue();
}
Simple and elegant, we can now manage all of our bindings in the Bindings.cs. So why would we want to do this? One reason might be to bind to a mock object in the test code as follows:
[TestMethod]
public void NinjectRebindSample()
{
    NinjectBootstrapper.Kernel.Rebind<IMyObject>().To<MockMyObject>();

    MyObjectHandler handler = new MyObjectHandler();
    Assert.AreEqual("MockMyObject", handler.GetValueFromMyObject());
}
Let's combine the above with a Moq object....
[TestMethod]
public void MoqObjectSample()
{
    var moqMyObj = new Mock<IMyObject>();
    moqMyObj.Setup(m => m.GetValue()).Returns("MoqObjectSample");
    NinjectBootstrapper.Kernel.Rebind<IMyObject>().ToConstant(moqMyObj.Object);

    MyObjectHandler handler = new MyObjectHandler();
    Assert.AreEqual("MoqObjectSample", handler.GetValueFromMyObject());
}
This can get a lot more complex, but a lot more useful. It's just an example to get started. Also keep in mind that there are performance penalties for using Ninject. In most situations this won't matter (and there are techniques to optimize it).

Saturday, November 24, 2012

One down, two to go...

The stability issues I've had previously seemed to have been resolved by changing the power plan settings. I switched Power Options to the "High performance" plan and set the "Turn off display" to Never.



This screenshot was taken yesterday, just before I took down the server to update a few local network settings.

As far as the other two issues.... I haven't had time to play around with RSAT and probably won't any time soon, as RDP works well enough for my needs.


I tried resolving TV stuttering by changing a lot of the NIC configuration settings and was unable to do so. I've also installed HP's Broadcom NIC Windows Server 2012 drivers for the MicroServer, but that didn't help either. However, I did come upon a forum where someone had done this same thing and recommended having a separate NIC dedicated to the VM to solve the stuttering issue. I will try this next and report back.

Currently the WAF is low - the stuttering is annoying.

11/26 Update: I installed a dedicated NIC for the host OS and that didn't resolve the stuttering problem. I did notice that stuttering never happens when watching a live channel, only something recorded, even without a dedicated NIC. The search continues!

Sunday, November 18, 2012

Windows Server 2012 impressions

I've been running Windows Server 2012 in my home "production" environment for a few days now and I'm extremely amazed with the performance and features of the server, however there are a few issues.

First the good:
Windows Server 2012 is extremely easy to administer, very modular and has outstanding performance. When I first installed the system and loaded Windows 7 MC on it, I was a bit skeptical about performance. I thought the Media Center experience would suffer on such an underpowered box as the HP N40L Micro Server, but I was wrong.

To my surprise, after a little tweaking of the host and guest OS it's handled everything without a hiccup. To add to that, since I'm still "playing" with the setup, I haven't disabled the GUI and turned it into a "Core" server to reduce the "attack surface," as Microsoft likes to refer to it.

The VM has absolutely no issues with streaming or recording four HD feeds all at once with power to spare. To add to that, last night I was abusing the disks by having three simultaneous copies of hundreds of gigs between various drives to my Storage Spaces volumes, which were taking up all the CPU. At the time I thought to go and try to watch TV, to determine what the effect of this may be. Although forwarding/rewinding was a little laggy it actually worked quite well. The system seems to prioritize both host and Hyper-V guests very well.

Overall, it feels like Windows 7 Media Center isn't even running in a VM.

Now, the bad:
It's no secret that I love Storage Spaces. It's the biggest reason I've gone through the pain to find a way to use Windows 8 or WS2012, while also having my whole-home Media Center experience. However, administrating Storage Spaces in Windows 8 is a lot easier and more intuitive than in Windows Server 2012. Partially it's because Storage Spaces is more powerful in WS2012 (it supports multiple pools), but also it's because the visual flow of the screen isn't as natural as it is in Windows 8. It takes a little playing to get used to it, and I feel like I "get it" now, but feel like it could have been even better. A small gripe, I know :).

Currently, I administer the server by connecting to the GUI via Remote Desktop. This works really well, but in the future I'd like to get rid of the GUI and run the server as Core (why waste resources?). I've been trying to get the Remote Server Administration tools for Windows 8 (RSAT) to work, but have been having issues. Haven't spent much time on it yet, but it seems like there's a requirement that the machine running RSAT be on the same domain as the server. I've found this great resource: Configuring Remote Management of Hyper-V Server - in a workgroup, and have used a few tips from there, but not quite there yet. When I have more time I may look into this further. The bottom line is that this part isn't as simple as I would imagine it should be.

I've experienced several crashes (BSOD's). A few of which I can recreate and a few of which I can't. The ones I can recreate have to do with the Hyper-V guest (Window 7) copying files from a local virtual drive to a share located on the host. I've since dedicated a spare 750Gb drive to the Windows 7 guest via pass-through in the VM, so copying, for my purposes, is no longer necessary. The crashes which I can't recreate were happening every 16-24 hours or so. I don't know what they were a result of, but I suspected power settings (since the HP N40L doesn't support S3 sleep). I've since changed the power settings to "High performance" and disabled turning off the display (which had been disconnected). So far this seems to have cured the problem. I'm cautiously optimistic and will continue monitoring the server.

Last, but not least, although there are no performance problems with the Windows 7 Hyper-V guest OS, when watching TV, at times I will see a stutter on the screen. For a couple of seconds, every once in a while, the image and audio freeze. When I rewind the recording it plays through the same section just fine, so I know it's not an issue with the recording. I suspect it may have something to do with the network configuration, but don't know the root cause just yet.

Conclusion:

All in all, despite the few glitches, I'm very happy with the entire setup. Windows Server 2012 feels like a solid product, but I would certainly wait for a few more patches before running it in a business production environment. My stability issues may be due to the type of setup I'm running - no question it's not conventional - so I'll give Microsoft the benefit of a doubt, but would caution that anyone planning on running this new server software at least test it properly for their needs.

Tuesday, November 13, 2012

Windows Server 2012/Windows 8 Pro + Windows 7 Ultimate Media Center

After an exhaustive exercise of playing with multiple operating systems, I have finally come up with, what I believe, is the best Windows Media Center (WMC) setup for my needs.

The ideal WMC configuration in many people's mind is having Windows Home Server 2011 with Media Center. Since Media Center isn't supported in a server OS, the next option would be to run Windows 7 in a VM. I wasn't happy with this setup for two reasons:
1. Windows Home Server 2011 doesn't have great native support for dealing well with storage; many loathe Microsoft the removal of Drive Extender (DE), without providing similar or better functionality.
2. Windows Home Server 2011 doesn't have Hyper-V role, which would relegate me to running a less optimized desktop VM.

The aforementioned issues are easily cured by installing Windows Server 2012 or Windows 8 Pro. Both include Hyper-V role and both come with Storage Spaces. Additionally, both have features one would look for in Windows Home Server, such as the ability to back up desktops on the local network. This write-up will be geared towards Windows Server 2012, however rest assured that almost everything I'm writing about I've also tested in Windows 8 Pro. I just prefer running a Windows Server because it includes ReFS, has a slimmer profile for the HP N40L (especially without the GUI interface) and is easier to administer (with more server features).

 To get everything working fist install Windows Server 2012 or Windows 8 Pro and enable the Hyper-V role as well as the .NET Framework 3.5 feature.

Windows 8:

Windows Server 2012:



Next, install the latest Ceton InfiniTV Windows 7 Beta drivers on the host OS. The reason I went for the beta drivers is to be able to upgrade the InfiniTV's Hardware firmware due to the minimum requirements needed to setup the host to share the Ceton InfiniTV to other machines on the network.

Next, in Hyper-V manager, click on "Virtual Switch Manager..." and add a new External Network.



 Now that that's done, we need to configure Ceton InfiniTV to have a different IP which makes it visible to the local subnet. I used these Missing Remote instructions. The only change I made was bridging to the virtual ethernet, since that's already bridged to the physical.


If everything was done properly, you should now be able to see Ceton InfiniTV as a media device in Network Connections
The next steps are easy: install a Windows 7 client to be the Media Center server, install the Ceton drivers on that server and the rest will be auto-detected during setup. One caveat is that you'll need to override Digital Cable Advisor (DCA) to get everything set up, otherwise (at least on my HP N40L Micro Server) there won't be enough horsepower to pass the test natively.


As of this writing, channel switching is slightly more sluggish than I'm used to, however not terrible. I've made absolutely no optimizations to Windows Server 2012 Standard host nor the Windows 7 Ultimate client. Additionally at present both are running on an HDD as I'm running this as a "beta" setup. As soon as I get the chance, I'll move everything to an SSD drive, which in my experience runs VM's indistinguishably fast from bare-metal.

The screenshot of the Task Manager below was taken from the host machine while the Media Center client was streaming two HD broadcasts to two of my TV's.


Overall I'm very satisfied with this setup at present and will tweak it going forward. There are a lot of benefits to running Windows Server 2012 or Windows 8 Pro as the host OS and I'll be writing about those in the future.

Saturday, November 3, 2012

Windows Server 2012 Installation: Error Code 0xc0000005

I was installing Windows Server 2012 on the HP N40L Micro Server and kept receiving the following error when creating a new installation partition:

"Windows installation encountered an unexpected error. Verify that the installation sources are accessible and restart the installation.

Error code 0xC0000005"

After swapping drives, SATA ports and running Memtest86+ I thought to unplug the SSD drive. The drive was connected and showed up in the BIOS, but mysteriously didn't show up as a possible target during the Windows Server 2012 installation. Unplugging the drive cleared up the issue.

Thought I'd throw this out there for those Googling around trying to solve a similar problem.

Wednesday, October 31, 2012

Power outages and energy efficiency...


Just like many folks on the east coast, we lost power due to Hurricane Sandy. Thankfully, we were prepared this time, due to the Halloween storm last year. When there's no electricity the priorities are having the necessities working: refrigeration and heat. This is all we had turned on aside from a few chargers (batteries, laptops and phones), given that my Honda EU2000i generator only provides 2,000 watts of power.

One of the selling points of the HP N40L Micro Server, to me, was the energy efficiency. This difference shows up in the monthly bill and it's not the only product I own with such a selling point. My whole house, in fact, is powered by very energy efficient ("Energy Star") appliances and most of the house is lit with CFL bulbs.

Last night I decided to hook up a Kill-A-Watt to the main line going from the generator into the house to see how much power we're using, since my wife wanted to have the lights in the bathroom to bathe our son. To my surprise, our usage was really minimal, well under 100-watts. Sure, that's fine while the oil boiler and the fridge aren't running, but when those kick on they'll use lots of power, right? Well, according to what I've seen not quite. For example, the LG fridge only seems to use 150watts while running and shoots up to 450 watts on start-up.Much better than I expected.

So the next thought was: let's start flipping breakers on to see how much more the generator can support. All I can say is, the generator has been running in ECO mode for the past 42-plus-hours, sipping only ~3-4 gallons of fuel while my whole house is lit up like a Christmas tree.

It would be easier to list the few appliances we can't use than those we can, but I'd like to list them out to make a point. We currently have the following running (and 95% of it is in ECO mode):
  • Refridgirator
  • Oil boiler for heat/hot water
  • Portable induction stove to heat up food/water/etc.
  • Two laptops
  • HP N40L MicroServer (still recording TV)
  • Cable modem, wireless router and gigabit switch
  • All lights and outlets are powered up
  • Phone/battery chargers
  • 63" Samsung plasma TV w/Yamaha receiver, wireless headset and Samsung Media Live MCE
  • Keurig coffee maker (this one is the worst @ 1200watts when boiling water)
  • Bathroom exhaust vents
  • and many more...

The generator will leave ECO mode when the fridge kicks in (couple of seconds every 30-60minutes), when the boiler turns on (30-60 seconds about twice per day), when Keurig is boiling water (couple minutes once per day) or when we're cooking with the induction stove.

Bottom line is that I'm really surprised that we have everything we need and even a many things we don't all functioning with so little power. Additionally, unless we're cooking, there's plenty of headroom to have all of the above running all at the same time.


In the past, my goal has been to possibly purchase a second Honda EU2000i Companion to link them and provide up to 4,000 watts of power (in addition to redundancy); but I've just never been able to justify the price tag of another unit given how rarely we lose power. Well, after doing a bit of testing with the Kill-A-Watt meter I'm very comfortable sticking with a single unit.

One caveat must be mentioned: because I'm running my generator in ECO mode most of the time when a huge surge goes on from an appliance asking for power there's a slight drop in power which can be seen as lights dimming. The power supply in a computer, TV and other major electronics have no problems dealing with that. They just keep on humming. However, the power supplies in small electronics such as routers and switches may force a reboot of the device. This hasn't been a problem in my case because I've moved all of those devices to get power from APC Back-UPS 550. Normally this serves to power the cable modem, wireless router and the HP N40L server to allow it to gracefully shut down, but I ran an extension cord from it to my office, which has the gigabit switch for the whole-home-Media-Center and it's been perfect.

Friday, October 26, 2012

Windows 8 Pro Media Center

Updated (see below)

Windows 8 finally became Generally Available (GA) today which means one thing: Windows Media Center (WMC) feature add-on is finally available!

If you try to add this feature through Windows 8, you'll notice there's a $9.99 price tag. Well, good news: until January 31, 2013 it's available for free! To get a free code, go to: http://windows.microsoft.com/en-US/windows-8/feature-packs and input your email address. The code will show up in your Inbox within a few minutes.

I installed WMC loosely using the following instructions: http://cetoncorp.com/blog/infinitv-on-windows-8-consumer-preview/

In order, I did the following:

  • Go to Search -> Settings. Type "Features" and launch "Turn Windows features on or off"
    • Install .NET Framework 3.5
  • Install the latest Ceton InfiniTV Windows 7 drivers. Yes, these will work in Windows 8
  • Go to Search -> Settings. Type "features" and launch "Add features to Windows 8"
    • Insert the free code you've received to download Windows Media Center feature and install the feature (this will take a few minutes and may take a few restarts)
  •  Run Windows Media Center and set it up as usual for your purposes. Keep in mind that to run Digital Cable Advisor (DCA) you must be physically connected to a monitor, not remoted into the server

That's it!

Update:
Unfortunately, it seems that my current Media Center Extenders do not work with Windows 8 Pro WMC. They connect to the server and then all of the sudden there's a black screen and that's it. Nothing. I've tried with a Samsung Media Live and a Linksys DMA2100.

Very disappointing... I had just ordered several upgrades for the server, specifically for Windows 8. If anyone has gotten this to work, please let me know!