After my previous post on getting AzureReader2 up and running with ImageResizer – I ran into a problem – I had a page with a foreach on it, where I had a link to each fullsize image. It was all working fine, except for a couple which just wouldn’t work.
<a href="/cloud/blah-1/example.jpg"><img src="/cloud/blah-1/example.jpg?maxwidth=70&maxheight=80" /></a>
<a href="/cloud/blah-2/hello%20world.jpg"><img src="/cloud/blah-2/Hello%20World.jpg?maxwidth=70&maxheight=80" /></a>
Ending up with something like the above…
Notice the ‘hello world’ link is in lower case, FOR SOME REASON.
So the image shows on the page, but when you click on it, you get a 404 error – no image can be found. It’s the case, it needs to match the case in the Azure Blob…
GRRRRRRRRRRRRRRR
So, as part of my on-going project I’ve recently made the decision to shift all my images (uploaded by ME and my USERS) to Azure Blob Storage, instead of the quite frankly ridiculous ‘unique folder system’ ™ that I had been using.
Now, originally I’d been using ImageResizer which was working well, buut, it didn’t work (the way I was using it) with Azure Blobs (at least not in an efficient way).
So.
I do the standard of searching for ‘ImageResizer Azure’ on google, and first on the list: AzureReader plugin, which being me, before I’ve actually clicked on the link I’ve switched to Visual Studio and added the AzureReader nuget package to my site (which is MVC4, using Azure SDK 2 by-the-by). Whilst that installs, I switch back to the browser, and read this: See AzureReader2 if you're using the Azure SDK 2.0. ah.
Uninstall the AzureReader package, install AzureReader2 package.
Bump.
That’s the sound of me hitting a wall. The documentation for both the AzureReader and AzureReader2 plugins are – well – minimalist, sure, they explain about the config settings (and the AzureReader page even explains how to add to azure) but not really on how you would use it. LUCKILY it’s pretty simple, so here goes, this is how to setup AzureReader2 with ImageResizer on an MVC4 Website.
1. Create a new Mvc4 site
(obviously if you have a site already, you can skip this bit) I’m going with an Empty site in my one (with no test project – basically because I’m lazy).

2. Add the nuget packages you need
- Windows Azure Storage (>= 2.0.4.0)
- ImageResizer Web.Config Installation for MVC
- ImageResizer Web.Config Installation
- ImageResizer.Mvc – MVC-friendly utilities
- ImageResizer
- ImageResizer.Plugins.AzureReader2 – Process images from the Azure blobstore
- Image Resizer Fluent Extensions for ASP.NET MVC
- Image Resizer Fluent Extensions
(if you search for and install the ones in blue, you will get the others installed)
3. Start the Storage Emulator
(Yes – I have made a big assumption here that you have the Azure SDK installed – if you don’t – now would be a good time to install it, then come straight back here)
4. Create a container on the development storage
Easiest way to do this (for me) was to use Visual Studio’s Server Explorer:

Give it any name you want, I’ve gone with: imageresizer-example
5. Upload an image to your blob container
Double click on the container, and click on the Upload Blob button:

Then select a biggish image, and whack it in…
So now you should have something like: 
6. Web.Config Edits
They gotta be done, and this is where the meat is, if we go down to the bottom of our Web.Config file, we should see a ‘resizer’ element, which will look something like:
<resizer>
<plugins>
<add name="MvcRoutingShim" />
</plugins>
</resizer>
We need to add our AzureReader2 plugin:
<add name="AzureReader2" connectionString="UseDevelopmentStorage=true" endpoint="http://127.0.0.1:10000/devstoreaccount1/" />
This is the minimum you need to get working.
7. Run
Press CTRL+F5 and ignore any errors you see – there’s no page to display in an empty solution – but that’s of no concern to us. My one started up on port 4598, so replace 4598 with whatever your port is.
In the browser you have open – navigate to: http://localhost:<PORT>/azure/<container>/<file>, so in my case I’m going to: http://localhost:4598/azure/imageresizer-example/example.jpg
Did you get a 404 error? This is because the container we created earlier doesn’t have public permissions. To change this, we’re going to make it public at the blob level, (you can go container if you really want to).
8. Change public access
Right click on the container in the server explorer within visual studio, and go to the ‘Properties’ page. Here, set the PublicAccess property to ‘Blob’:

Go back to your browser and refresh the page
One thing to note is that the URL despite what you typed in, now points to the Azure Blob url directly:

This is because we’re not doing any modifications to the picture, so ImageResizer has just forwarded us directly to the blob, which is nice. But lets get ImageResizer doing a resize:
9. Resizing
Very VERY simple. Just add ?width=200 to the end of your url (obviously if the picture you are pulling isn’t at least 200 pixels wide this will have no effect). So:
http://localhost:<PORT>/azure/<container>/<file>?width=200,

Aceness!
Now – yes – I’m using Azure (now), but personally I’d rather hide that fact so if I decide to go S3, I don’t have to update all my URLs, luckily – this is all in the config, so last thing:
10. Web.Config changes (again)
Let’s edit our plugin line and add the ‘prefix’ attribute.
<add name="AzureReader2" prefix="~/cloud/" connectionString="UseDevelopmentStorage=true" endpoint="http://127.0.0.1:10000/devstoreaccount1/" />
now all the links will look like:
http://localhost:<PORT>/cloud/<container>/<file>?width=200
which is pretty cool.
Conclusions
ImageResizer is – well, Awesome. I’m personally going to be getting a license soon (I’ve not used this in production yet), but I can’t see any reason why I wouldn’t.
If you need ImageResizing I have yet to find a better alternative – and it’s really not that expensive (by the by – full disclosure – I have not received anything to influence me. This is all from personal research)
I’ve put my files here: http://sdrv.ms/V4DSnV but you’ll still need to create the azure container yourself. 7Zip appears to do a weird unzip and doesn’t create the empty folders as folders, so if it doesn’t load with a ‘missing app_data’ folder error – that’s why.
Addendum
I believe – if you are looking for a connection config element for a production system you want something like this:
<add name="AzureReader2" connectionString="DefaultEndpointsProtocol=https;AccountName=NAME;AccountKey=KEY" endpoint="http://NAME.blob.core.windows.net/" />
Though – this is speculation – I can’t confirm the results as I’m not running this against a production server at the moment. I’ll let you know if it’s NOT that.
Just getting this off the bat, I presume this will also work for Blend 5, but I can’t confirm it…
Anyhews, I imagine you’re here because you want to know how to create an addin for Blend, so let’s jump right in there!
First, and foremost, we’re going to need to ensure our development environment has the right setup, so the checklist:
- Visual Studio 2012
- Blend for Visual Studio 2012
OK, let’s create a new project (class library, .NET 4.5):
Hello.Extension
The ‘.Extension’ bit is very very important. The addin will not work unless it is named in this way. You can put whatever you want at the front, but it has to have the extension bit.
OK, so now we have a solution with one project. To this project we need to add references to the following things:
- Microsoft.Expression.Extensibility (from c:\program files\Microsoft Visual Studio 11.0\Blend\ -- x86 folder if you are on an x64 windows install)
- Microsoft.Expression.Framework (same location as above)
- PresentationCore
- PresentationFramework
- WindowsBase
- System.ComponentModel.Composition
Got them? ACE.
Let’s now add a project to contain our control, so, create a new WPF Application project, cunningly named something like ‘Hello.Control’… (I’m creating a WPF application here, because I’m too lazy to dig up the correct references, and this will add all the ones I need
)
Once that is created, delete the App.xaml and MainWindow.xaml files, we won’t be needing them. You will also need to change the properties of the project itself, so it is only a class library.
Once that is done, let’s add a new UserControl, which will be this:
<UserControl x:Class="Hello.Control.HelloControl"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<Grid>
<TextBlock Text="HELLO!!!"/>
</Grid>
</UserControl>
Impressive eh?
Now, let’s reference the WPF project from the Extension library. All that’s left now is to code up our extension…
So, add a class to the Extension project (name wise doesn’t matter), and make it implement the IPackage interface from the Microsoft.Expression.Extensibility library:
public class HelloExtension : IPackage { /**/ }
We’ll implement the two methods we need to:
public class HelloExtension : IPackage
{
public void Load(IServices services) { }
public void Unload() { }
}
We’re only really concerned about the Load method in this case, as let’s face it, the extension we have doesn’t need to do a lot to bog off. The interesting thing about the Load method is that it receives an IServices instance. This allows us to get access to all the services that Expression provides, in this case we’re interested in one in particular, the ‘IWindowService’
So, let’s get that bad boy…
private IWindowService _windowService;
public void Load(IServices services)
{
_windowService = services.GetService<IWindowService>();
}
Nailed it… But why? The WindowService allows us to register our UserControl with Blend, which in turn allows people to activate and see it, which is a big plus point. So, let’s do that…
We’ll create an ‘Initialize’ method to create our new control, and add it to the WindowService:
private HelloControl _helloControl;
public void Initialize()
{
_helloControl = new HelloControl();
if (_windowService.PaletteRegistry["HelloPanel"] == null)
_windowService.RegisterPalette("HelloPanel", _helloControl, "Hello Window");
}
First we check that we’re not already registered, and if we’re not we register, the first argument is the identifier used by the service to, well, identify your extension. The second argument is the actual control, the third argument is the name that people will see in the ‘Windows’ menu of Blend itself (so important note here – don’t put anything embarrassing or (need I say it?) sweary…)
There are only two things to do now -
- Call ‘Initialize()’ from our Load method, and
- Export the class
- This is easy money – add [Export(typeof(IPackage))] to the top of our class…
The full code will (should) look like this:
[Export(typeof (IPackage))]
public class HelloExtension : IPackage
{
private HelloControl _helloControl;
private IWindowService _windowService;
public void Load(IServices services)
{
_windowService = services.GetService<IWindowService>();
Initialize();
}
public void Unload()
{
}
public void Initialize()
{
_helloControl = new HelloControl();
if (_windowService.PaletteRegistry["HelloControl"] == null)
_windowService.RegisterPalette("HelloControl", _helloControl, "Hello Window");
}
}
If you build this and copy it to your ‘Extensions’ folder in Blend (c:\program files\microsoft visual studio 11.0\blend\) and start Blend, you should see ‘Hello Window’ listed in the Window menu:

That as they say is it!
Now, I know that this has been written about, but both of the main places (http://www.richard-banks.org/2011/02/running-neo4j-on-azure.html and http://blog.neo4j.org/2011/02/announcing-neo4j-on-windows-azure.html) utilise VS2010, and well, I’m on VS2012 and Windows 8. Not that I think Win 8 had anything to do with it really, anyhews!
I’m going to begin from the beginning, this is my first foray into running something on Azure, so it’s been a bit of a learning curve. But luckily the Neo4J guys have got us started, so let’s download the VS2010 solution: http://neo4j.org/get?file=Neo4j.Azure.Server.zip
OK, the other thing we’ll need is the VS2012 Azure SDK, so let’s get that as well: http://www.windowsazure.com/en-us/develop/downloads/ (I just did the full install).
Now, unzip the VS2010 solution and let’s open it in VS2012:
<your location>\Neo4j.Azure.Server\Neo4j.Azure.Server.sln
One-way-upgrade? Yer! Ignore the migration report – we don’t care!
Let’s build that sucker… Ahhh 14 errors…
WindowsAzure does not exist in the namespace ‘Microsoft’
Not a problem right? We’ve installed the SDK, just need to update the references:
We can ignore the Test projects, they don’t use Azure, we’re interested in the other projects, so what we’ll do is remove the broken references, and add the correct ones, so expand the references bit of each project:

hunt out those yellow exclamation marks, and delete them! You’ll need to add the right ones back in (listed below), when you go to the ‘Add Reference’ dialog

make sure you have ‘Assemblies’ and ‘Framework’ selected before you seach (and search for ‘microsoft.win’ to narrow it down)

So the references you need for each project are:
- CollectDiagnosticsData
- Microsoft.WindowsAzure.Diagnostics
- Microsoft.WindowsAzure.StorageClient
- Diversify.WindowsAzure.ServiceRuntime
- Microsoft.WindowsAzure.CloudDrive
- Microsoft.WindowsAzure.ServiceRuntime
- Microsoft.WindowsAzure.StorageClient
Right, so let’s build again… Sweet! No errors.
Now we need to setup our Blobs, I’m assuming you are using the most up-to-date Java you happened to have downloaded :) in my case that’s JRE7, and that is located in:
C:\Program Files (x86)\Java\jre7
So, zip up that folder into whatever you want to call it, I went with jre7.zip, and stuck it in a temp folder for now. In that same temp folder I also copied the neo4j zip I was using: neo4j-community-1.7.2-windows.zip
OK, now, we need to get these into our Blob storage, this is where a lot of stuff becomes unstuck - I didn’t find any applications that helped me use the blob storage, one would crash (because my internet speed is so slow) and the other just didn’t work – sure it looked like it had worked, but when push came to shove it didn’t.
So this is how I got my files into Blob (local first):
1. Run the ‘Storage Emulator’ (just search for that in the start menu)
2. That takes a little while to start up so fire up another instance of Visual Studio in the mean time, and create a new Console Application.
3. Manage Nuget Packages for that solution and add ‘Windows Azure Storage’

Now you’re set up to add the code:
public static void Main()
{
CloudStorageAccount cloudStorageAccount = CloudStorageAccount.DevelopmentStorageAccount;
CloudBlobClient client = cloudStorageAccount.CreateCloudBlobClient();
client.Timeout = TimeSpan.FromMinutes(30);
CloudBlobContainer container = client.GetContainerReference("neo4j"); //This will create it as well
UploadBlob(container, "jre7.zip", "c:\\temp\\jre7.zip");
UploadBlob(container, "neo4j-community-1.7.2-windows.zip", "c:\\temp\\neo4j-community-1.7.2-windows.zip");
}
private static void UploadBlob(CloudBlobContainer container, string blobName, string filename)
{
CloudBlob blob = container.GetBlobReference(blobName);
using (FileStream fileStream = File.OpenRead(filename))
blob.UploadFromStream(fileStream);
}
This will upload the files to your local storage account (to switch to an Azure one, you’ll need to create a storage account, and use those credentials when you make your CloudStorageAccount above)
To test you’ve got them uploaded correctly, go to:
http://localhost:10000/devstoreaccount1/neo4j/jre7.zip
and you will hopefully download the zip file you just uploaded.
Now that those files are there, we are ready for some final configuration…
Right click on the Neo4jServerHost role in the Neo4j.Azure.Server cloud project:

Click on the ‘Settings’ tab and we’ll need to do some changes – by default, the 1.7.2 edition of neo4J unzips to:
neo4j-community-1.7.2
So, we need to update all the ‘neo4j-1.3.M02’ directories to be ‘neo4j-community-1.7.2’, we also need to update the Java runtime location, so we start with this:

and end with this:

Now, I also changed the Endpoints settings, to be HTTP (from TCP) and to have a port of 7410 (mainly because that’s straight down on the numpad)

The last ‘gotcha’ is some hard coded consts, which had me looking for ages, they are in the ‘ConfigSettings’ class of the ‘Neo4jServerHost’ project, and the ones we’re interested in are:
- Neo4jFileName
- JavaZipFileName
Change those both to what that should be.
OK
Nearly there (I promise)!
Run the ‘Compute Emulator’ (same deal with the Start menu), in your system tray you should have an Azure icon, when the compute emulator is up and running, right click on the icon and select ‘Show Compute Emulator UI’

The last steps!
Make sure the ‘Neo4j.Azure.Server’ cloud project is set up as the start project and let’s hit
F5
tension mounts, the build takes place (you need to accept the UAC warning) and VS does it’s stuff. If you look at the Compute Emulator UI you’ll see some log stuff (which you’ll need if this goes awry – but it won’t don’t worry!)

In a bit, the console and a Java window will pop up:

Then the console will bog off, leaving just the Java one, and if we switch back to the Compute Emulator UI and scroll up we should be able to see a line telling us the port number we’ve been assigned (in my case 7411):

(If you can’t see it, don’t worry.. press CTRL+A on the emulator, then CTRL+C, copy all the text and paste it into something like Notepad, then just do a Find for ‘port’ you’ll soon see it)
Go to your favourite browser, and head to: http://localhost:YOURPORT/
and you should see the WebAdmin!
See you on the cloud side hopefully!
Chris
PS Other gotchas!
OK, I’ve been caught out a couple of times:
- I had an instance of Neo4J running as a service on my machine, the Azure instance wanted to run the https version of the server on the same port as the Service was running on, and so Java would complain that the port was already in use..
- The first time I converted the project, it didn’t update the version of the Azure library to load, in the App.Config of the Neo4jServerHost project, and VS would throw an exception saying it couldn’t find the Azure dll version 1.0.0.0.
In this we get neo4j to install as a service!
I have to do some mocking of an ITable to be able to test some of my code, as you may imagine this is the point where we’re crossing the data boundary… Now, ITable is a total bugger to mock, I’ve tried on (at least) 3 separate occasions to get it mocked, and have only now, finally achieved an 80% solution.
(Nothing is ever 100%)
I’m not using any mock framework, they just take too long to setup (in this case) and instead have a concrete class that implements ITable and uses an IList as it’s base.
Without further ado:
using System;
using System.Collections;
using System.Collections.Generic;
using System.Data.Linq;
using System.Linq;
using System.Linq.Expressions;
public class MockTable<T> : ITable<T> where T : class
{
private readonly IList<T> _entities;
public MockTable(IList<T> entities)
{
_entities = entities;
}
#region ITable<T> Members
public IEnumerator<T> GetEnumerator()
{
return _entities.GetEnumerator();
}
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
public Expression Expression
{
get
{
return _entities.AsQueryable().Expression;
}
}
public Type ElementType
{
get
{
return _entities.AsQueryable().ElementType;
}
}
public IQueryProvider Provider
{
get
{
return _entities.AsQueryable().Provider;
}
}
public void InsertOnSubmit(T entity)
{
throw new NotImplementedException();
}
public void Attach(T entity)
{
throw new NotImplementedException();
}
public void DeleteOnSubmit(T entity)
{
throw new NotImplementedException();
}
#endregion ITable<T> Members
}
To use, in your test, let’s say you have an IDataContext (and why not) looking like this:
public interface IDataContext
{
ITable<Person> People { get; set; }
}
You can then mock this interface like so:
[TestMethod]
public void Something_DoesSomething_WhenSomething()
{
//Create seed list
var people = new List<Person>{ new Person{Name = "Chris Skardon"} };
//Create new Mock
var dataContextMock = new Mock<IDataContext>();
//Setup the People ITable property
dataContextMock
.Setup(dc => dc.People)
.Returns(new MockTable<Person>(people));
/* Asserts etc */
}
It’s obviously not perfect, I haven’t bothered with several methods, but I’ll get to them later…
Chris
I’ve been battling this now for an hour or so, and as all the reponses I’ve seen online haven’t really helped, I thought I’d whack this up..
The error I got was:
The code generator 'Microsoft.ServiceModel.DomainServices.Tools.CSharpCodeDomClientCodeGenerator' encountered a fatal exception and could not generate code for project 'TheProject.csproj':
Exception has been thrown by the target of an invocation.
Now, searching online comes up with loads of things, but the most important one I found was on Microsoft Connect. It’s actually a comment from ArielBH, which says:
From my exprience it is connected to the DataAnnotions attributes when it is looking for types in the resx.
When I tried to manipulate the Buisness Applocation template and move Ria Services link and files to other assembly I had the same issue. When I removed all references to those resx files this issue disappered.
I indeed have a class using DataAnnotations linking to a resx file… So, I removed all the attributes linking to the resx files, (i.e. removing all the validation…) and did another compile…
At this point RIA decides to actually give the correct error, that a method was missing…
So, point of note is that the DataAnnotations will mask the actual error, but once you’ve fixed the error, putting the DataAnnotations back will be fine…
Grrrr
Chris
The old skool way of passing InitParams in aspx is well documented, adding a:
<param name="initParams" value="<%=InitParams%>" />
which is accessing the public ‘InitParams’ member in the code-behind file, which is inevitably set up via the ‘Page_Init’ handler.
All well and good, but not practical in MVC, so… how to do this?
(NB. This is just how I’ve done it, it’s not the only solution)
There are a few things to change:
1. The Model
I’ve created a SilverlightHostModel, it only has one property in it (at the moment), to hold the InitParams:
namespace Webby.Models
{
public class SilverlightHostModel
{
public string InitParams { get; set; }
}
}
2. The Controller
The controller is going to create the model and pass it to the view..
public ViewResult Ria()
{
SilverlightHostModel host = new SilverlightHostModel();
host.InitParams = "IpAddress=" + System.Web.HttpContext.Current.Request.ServerVariables["REMOTE_ADDR"];
return View(host);
}
3. The View
The view needs to be strongly-typed to the Model, so we add this to the top of the new view:
@model Webby.Models.SilverlightHostModel
and where we’re hosting the Silverlight control itself, we change the param to read:
<param name="initParams" value="@Model.InitParams"/>
4. The App.xaml.cs Application_Startup
You (I presume) already have this done, but you would get your new parameter like so
private void Application_Startup(object sender, StartupEvents e)
{
//Get the ip address from InitParams
string ip = e.InitParams["IpAddress"];
this.RootVisual = new MainPage();
}
Done!
Chris
Today is the big day, the day I attempt to use Ajax in the app…
I’ve never done this (well, tell a lie, I’ve done it in a ‘tutorial’ site, but that was a while ago now), so it’s going to be interesting..
OK, basics first, let’s start with the @Ajax.ActionLink
Right, first stab:
@Ajax.ActionLink("Click to get latest",
"LatestEntry",
new AjaxOptions
{
UpdateTargetId = "ajaxEntrant",
InsertionMode = InsertionMode.Replace,
HttpMethod = "GET"
})
As far as I’m aware, I’m asking to get the ‘LatestEntry’ from the current controller, and in doing so, I will replace the #ajaxEntrant DOM bit with the result. So. I guess I’d better get the result working…
To the controller!
public PartialResult LatestEntry()
{
var entrant =_db.Entrants.OrderByDescending(e => e.Id).Single();
return PartialView("_Entrant", entrant);
}
Pretty simple, just returns the last entry in a PartialView… but! I have yet to make my partial view, so onto that!
@model Webby.Entrant
<div class="entrant">
<h4>@Model.Name</h4>
</div>
Again, super simple, (I’m really just testing at this point)…
All the code is now there (as far as I know), so F5 and in…
And once again, in the traditionally disappointing way of the norm, it doesn’t work, sure… it opens the right view, but it doesn’t replace the #ajaxEntry DOM element, rather it replaces the whole page… The source code (again, as far as I know) looks ok:
<a data-ajax="true" data-ajax-method="GET" data-ajax-mode="replace" data-ajax-update="#ajaxEntrants" href="/Entrants/LatestEntrant">Click to get latest</a>
Changing the InsertionMode to any of the other modes has the same effect..
It’s not the DOM name either, changing that has the same effect.. i.e. none.
It’s not the partial view either, just making that a <p> has (again) no effect…
Ahhhhh --- what a schoolboy error… I had neglected (ahem) to actually put the script bit into the calling page (another save from stackoverflow):
<script src="@Url.Content("~/Scripts/jquery.unobtrusive-ajax.js")" type="text/javascript"></script>
I’ve now stuck that into the _Layout.cshtml view temporarily to aid the development process… :)
Onwards and upwards!
Chris
So, last night I realised that I’d made some bad decisions with the database, structure and naming, so… I’ve now refactored it all, and I’m feeling… hmmm… meh about it. I suspect I will redo it all later, but for now it will do….
I’ve also come to the conclusion that I was maybe trying too much for the initial release, so as a consequence I have removed one part of the project… (which, by-the-by, I intend to have published in a month or so – and yes Andy, that is one month longer than I mentioned to you in that email :))
@Html.DisplayFor()
I find myself using DisplayFor a lot at the moment, is this correct? I mean – it works, but is that really only for forms? Do I need to use it? Should I use it?