I was listening to coverage of the Beijing Olympics on BBC Radio 5 Live this morning and it was interesting to hear what a spectator had to say about the lack of information that the Beijing organisers provide for spectators. One spectator was at the boxing and apparently there was no information about other events happening or results and, even more impressively, not even a schedule for the boxing either! I would have expected flat screens everywhere with the schedule or, at the least, a printed list.

Surely this is an opportunity for London 2012. With the vast amount of Content Management expertise across the UK, you'd think that we can put together some really great content solutions to give all the right information in the right places to the right people. Just imagine - TV coverage mixed with results screens and schedules... well put together, this could be the big differentiation between Beijing and London. OK, maybe we don't have flashy ceremonies, spectacular fireworks and an immersive cultural experience... but at least we love all sports and we can give a 'sports rich' environment for spectators.

Beijing is out to impress the world, but seems to have missed a trick by not giving spectators the information they need. Let's get this right in London.


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

I recently needed to get the NT user name from VBA code. Not a problem, Microsoft have an advisory note that tells you how to do that and there's a good summary of it on this post:

http://blogs.officezealot.com/charles/archive/2004/12/10/3574.aspx

However, there is a ptentially serious security problem with the other method that Charles suggests on that post - using the environment variable like this:

Environ("USERNAME")

If you are using the username check in VBA for security purposes (for example, matching a username against a list of known users permitted or restricted on some actions) then the method above does not guarantee that the actual username of the logged on user will be returned.

The user can override the default username setting by adding a new environment variable (Control Panel -> System -> Environment Variables) called USERNAME and setting it to whatever they want. Effectively, they are taking the identity of another user as far as the variable is concerned, and anything that looks it up.

It is therefore safer from a security perspective to use the Win32 API call. Note that if you are doing security in VBA you have a bit of a problem anyway though because even if you password protect you code, it's easily crackable.


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

On our blogs, we recently found we were getting this error when trying to edit some posts:

image

The id's given were occasionally different but it was always the same format...

"Could not find category id XX in the Checkbox list which has XX items."

Somehow it seems that SubText has got itself in a twist and allocated invalid category id's to the posts. I suspect that this is actually caused by a funny bug between SubText and Microsoft Live Writer. You see, when you write an article in Live Writer you can allocate the categories for it and post it up to SubText. So far, so good. However, the bug occurs when you have a Post Category and an Article Category with the same name. When the Web Service request hits SubText it might not pull out the correct category id - probably because it checks only by name and grabs the first one. The problem we were having is that some posts were getting added with a category id for an article. Changing the category name for the articles fixed the problem.

You can see if any of your posts have this problem by running the following SQL against the SubText database.

   1: select * from subtext_Content, subtext_Links, subtext_LinkCategories
   2: where subtext_Content.ID = subtext_Links.PostID
   3: and subtext_Links.CategoryID = subtext_LinkCategories.CategoryID
   4: and PostType != CategoryType

If you get rows back, then you need to tweak your data :)

Once you've fixed your data, then the main recommendation I'd make is to use different category names for posts and articles. That way, Live Writer or other Web Service based blog tools won't confuse SubText.


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

I was at a client's office yesterday for the final review meeting of a two-week Use Case exercise. The particular area of the operations that we were pulling out into Use Cases had been the subject of various patchy projects within the organisation over a couple of years. As far as I can tell some of that work had been really good and laid the groundwork for the Use Cases, but it was not organised into any kind of overall picture or process and there was a certain lack of confidence in the previous projects. The concept of the Use Case approach was really quite radical for them, and the timelines we were talking about to draw them out sounded crazy compared to what had gone before.

This is something I come across often with Use Cases when looking at a business area which has been burnt with a 'traditional' approach before. Often good functional requirements and designs do result from these requirements gathering phases but they are just not organised, coherent and in a form that everyone understands and can sign off.

With Use Cases, everyone is brought along together. The business, IT, stakeholders - they are all involved right from the start and throughout. And this works because Use Case definition phases work best when they are short, sharp and tightly controlled. For any specific 'group' of business operations typically I like to work on a 2-4 week turnaround of a Use Case set. I also like to focus on User Level Use Cases - IT can worry about subfunction ones later. It's more important to focus on what Use Cases are good at. Don't try and do implementation, don't try and do logic, don't try to design business processes... focus on goals and the steps to get there.

And the end result? At the conclusion of the review meeting yesterday one of the key business representatives announced that they had achieved more in the last two weeks than they had in the last two years. Possibly a little unfair to what had gone before, but does show the degree of confidence that can be instilled by following a good requirements approach.


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

I've been back on the Use Cases recently after a bit of a time away from them doing some fairly deep techie stuff. Every time I work with Use Cases I find myself wondering why people aren't using them more (or similar methods) because they are just such a logical way of doing things. Let's face it - who really wants to bounce around a 100 page requirements document between inboxes ad infinitum with no-one really understanding or owning it? And what IT department wants to get a document like that landing on their desks?

One of the real beauties of Use Cases is how they feed into the Project Plan. Traditionally project plans have been geared around 'modules' of work, but these modules have normally been things like 'homepage' or 'data layer'. That's fine as far as it goes, but if you estimate around that and build your plan on it then how do you work out what each module actually adds to the value of the project, and how much effort within each 'module' is for core functionality and how much is for wishlist items? You often end up manipulating the project plan by having umpteen round-table meetings with project managers and techies to work out what can and can't get pulled in or pushed out and what impact that has on estimates and the plan.

With Use Cases, all that changes. If each Use Case is estimated then you have a statement of what goal is being achieved at what cost. This, to the project plan, is pure gold. It now becomes relatively trivial to work out how things need to be shuffled in and out of the project plan and, crucially, this can now be a business driven exercise rather than requiring techies to get involved. They don't enjoy that shuffling anyway.

In practice there are three key types of project constraint that affect the 'shuffling'; Functionality, Cost and Time.

  • Functionality driven projects: In this type of project, functionality is king. Use Cases help by identifying priorities. All high priority Use Cases need to be put in the plan and this will give a cost and, when resources are factored in too, time. As Use Cases are flagged with changing priorities they can be put in and out of the project plan and the effect is immediately visible.
  • Cost driven projects: All Use Cases have an estimation assigned to them. The beauty of this is that the ROI of each Use Case is much more visible. You pay this, you get this for it. The project plan can be built within a cost including the Use Cases that give the best ROI.
  • Time driven projects: Some projects have a hard deadline. That's fine - with Use Cases you can fit as much in within the timeline and you can easily see what you will or won't get in before the deadline.

If you have good or bad experiences with using Use Cases for project planning do drop me a comment or a mail and let me know. Always interesting to see how theory turns into practice in different scenarios.


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

I've been hanging out on the #epicode IRC channel for the past few months, and over time I've played with several IRC clients such as XChat, Mibbit (for the Web) and HydraIRC. One of the things that you do most often on IRC is /msg people. The server that I use for #epicode is FreeNode. This server requires you to register you nick before doing a /msg. If you try to /msg without registering, you get an error message back from the server. XChat, annoyingly, didn't show me the IRC error and I spent quite some time trying to figure out what was wrong. Mibbit behaves nicely, but you have to enter your credentials every time which is a pain. (tip: on Mibbit,  click the 'Auth' link next to the server dropdown on the main page and you can enter your NickServ password straight in there!) HydraIRC behaves nicely too, but I've been having problems getting it to store my NickServ password so I don't have to enter it every time.

In theory, the password is saved by HydraIRC when you create a favourite, but it doesn't seem to work for channel favourites, only server favourites. No, I've no idea why. If you look in the XML profile file in the HydraIRC installation directory all the information looks correct. Maybe they work for you but they sure are a pain for me. Thankfully, there is an easy workaround. HydraIRC has a bit of a hack called Command Profiles. I wouldn't describe them as a well-documented feature but they do the trick. Essentially a command profile is just a set of IRC commands that can be run automatically when you connect to a particular IRC server. You can find the command profiles by going Options -> Prefs... -> Command Profiles. In there, you create a profile using a special name so that is picked up on logging in to a server. The name, in my case, is FreeNode_OnLoggedIn. Within that I simply put in my NickServ identification.

hydracps

When I go to my #epicode channel favourite now, it automatically runs my identification with NickServ so that I can /msg people without the pesky error message and having to register myself manually with NickServ every time!


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

At the EPiServer Partner Summit I was chatting over dinner to Andy Brodie of Networked Planet. He was remarking that it would be nice within EPiServer to have the capability to show site thumbnails when you hovered over hyperlinks. This intrigued me so when I got back to the UK I did some investigation. There are sites on the internet that do provide a service for this, such as websnapr, but ideally I wanted something that I had full control over.

Time to start coding :)

After some investigation on the web I found a great article about the WebBrowser control and ASP.NET. I tailored it to my needs and got a little thumbnail generator working. I also built a set of JavaScript functions that would show the thumbnails on hyperlinks using DHTML. Next I built a Control Adapter that would pick up EPiServer properties and parse them for hyperlinks. If it found hyperlinks it would insert references to my JavaScript functions. Lastly I wrapped all this in an assembly complete with my Single-Assembly VPP method and using dynamic web resource references.

And so HyperThumbnail was born. Go check it out on EPiCode or see the sample on B&D EPiLabs (hover over the hyperlinks in the content). Deploying to your own site couldn't be easier - simply drag-and-drop the DLL and a .browser file into your website folders.


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

Google have released a lovely little API for their Google Translate service. It uses a RESTful interface and returns a JSON object in the HTTP Response. The usual way to use this would be AJAX-style in client side JavaScript. This might not always be what you want to do though. For example, if you have a server resource in English and you want to show it in the page as Spanish you wouldn't want to render it in English and then have some page load event client side to translate it. You really want to do it server side and render it on the page as Spanish straight away.

Of course, Google know this and so they have provided a couple of snippets on their Google code site for PHP and Java. It should probably be expected, but they decided not to provide a nice .NET snippet. Looking around on the web, I can't find any .NET snippets for it and so I did some digging myself to put together a solution.

Before I throw out the snippet, it's worth explaining briefly what JSON is and what libraries are available. JSON is an object definition 'language' similar conceptually to XML in that it is effectively name tags / value pairs but it has the added advantage that it is part of the JavaScript language definition and can be 'eval'ed in JavaScript to give you a client-side object. This is great for AJAX websites. Whilst you could cook your own JSON handler, there are a few JSON libraries out there for .NET. In fact, Windows Communication Foundation has some JSON support built-in. The only problem is that most of the libraries out there are to do with serializing and deserializing .NET objects as JSON objects. That's fine as far as it goes, but it relies on you already having a well-defined .NET type. With Google Translate, we are getting a JSON object as a string that has no well-known .NET type to deserialize to. It might be possibly in theory to map it to an object or even map it to XML but I explored those options and found them incredibly convoluted.

Thankfully you don't need to write your own little JSON parser though because I did find one library out there to do the job, LitJSON. It has a couple of the usual serializer/deserializer features but in addition it also has a feature to parse JSON into a simple hashtable/array. I tried to do something similar with JSON to XML with WCF but couldn't get it to work. One of my colleagues, Stephen Horsfield, did - and I've included his technique after mine.

And so to the code. The snippet below assumes that you are running this in a web form with the following four web controls:

  • txtSource - textbox for source text
  • txtTranslated - textbox for translated text
  • ddlFrom - drop down list with the 2-letter language values for the source language
  • ddlTo - drop down list with the 2-letter language values for the destination language

Of course you could easily swap these with command line args or whatever you like. I have put the snippet in C# and the .NET 2.0 framework, but of course you could rework it for VB.NET or even for .NET 1.0.

   1: // do a check to make sure that we aren't making Google unhappy
   2: if (txtSource.Text.Length > 500)
   3: {
   4:     throw new Exception("Google Translation license forbids more than 500 characters to be translated at once!");
   5: }
   6:  
   7: // create the web request to the Google Translate REST interface
   8: WebRequest oRequest = WebRequest.Create("http://ajax.googleapis.com/ajax/services/language/translate?v=1.0&q=" + HttpUtility.UrlEncode(txtSource.Text) + "&langpair=" + ddlFrom.SelectedValue + "%7C" + ddlTo.SelectedValue);
   9:  
  10: // make the web call
  11: WebResponse oResponse = oRequest.GetResponse();
  12:  
  13: // grab the response stream
  14: StreamReader oReader = new StreamReader(oResponse.GetResponseStream());
  15:  
  16: // put the whole response in a string
  17: string sContent = oReader.ReadToEnd();
  18:  
  19: // parse the string into the litJSON simple object model
  20: JsonData oData = JsonMapper.ToObject(sContent);
  21:  
  22: // write out the translated text
  23: txtTranslated.Text = oData["responseData"]["translatedText"].ToString();

You could enhance this by using the Google Translate API call to auto-detect the source language, but for simplicity I haven't bothered with that extra step.

So lets see what it would look like with WCF. You'll need to include a using statement for System.IO, System.Xml and System.Runtime.Serialization.Json (and reference the appropriate DLLs):

   1: XmlDocument doc = new XmlDocument();
   2: XmlDictionaryReader xr = JsonReaderWriterFactory.CreateJsonReader(s,
   3: XmlDictionaryReaderQuotas.Max);
   4: doc.Load(xr);
   5: xr.Close();
   6: s.Close();

For more details see the complete post on Steve's blog.

And that is how easy it is to call Google Translate from .NET! I'm currently thinking of some funky ways that I could integrate it with the EPiServer Edit mode. There are all sorts of possibilities. Suggestions on a postcard of how you might want it to look. Maybe a right-click option on the navigation tree? Maybe an extra button in the editor? Maybe something that catches the event when a language for a page is created?

Lastly, a tip on the 2-letter languages. I used the System.Globalization feature of .NET to create the drop down lists with their names. Snippet below:

   1: CultureInfo [] aCultures = CultureInfo.GetCultures(CultureTypes.NeutralCultures);
   2:  
   3: foreach (CultureInfo oCulture in aCultures)
   4: {
   5:     if (ConfigurationManager.AppSettings["SupportedLanguages"].IndexOf(oCulture.TwoLetterISOLanguageName) >= 0)
   6:     {
   7:         ListItem oItem = new ListItem(oCulture.EnglishName, oCulture.TwoLetterISOLanguageName);
   8:  
   9:         ddlFrom.Items.Add(oItem);
  10:         ddlTo.Items.Add(oItem);
  11:     }
  12: }

All that is needed after that is a line in the web.config like so:

   1: <appSettings>
   2:   <add key="SupportedLanguages" value="ar,bg,zh,hr,cs,da,nl,en,fi,fr,de,el,hi,it,ja,ko,no,pl,pt,ro,ru,es,sv"/>
   3: </appSettings>

Hope this is useful to someone. There's a whole load more that could be done such as error checking and catching but that is for a later post once I work out how far I can take this.


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

As part of the launch of Interakting, the pan-european web agency brand of Business & Decision, the E-Business blogs have been reskinned. The blog engine we use is built on SubText, a great little .NET blog engine. Not the easiest to skin, but manageable.

Have a browse around. It's the same guys blogging the same great stuff - just a little less blue/grey and a bit more pink :)

 


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist

The company I work for, Business & Decision, is launching a new brand for their global digital agency function; "Interakting". Apparently "Business & Decision" works better as a brand in their other areas (Business Intelligence, Customer Intelligence and Management Consulting) than it does in E-Business. No shock there then :)

It's not officially launched in the UK yet, but you can get a sneak peek of our branding at our shiny new Interakting UK website.

The site was built in our Interakting office here in Oxford, and is running on EPiServer 5. Any feedback let me know and I'll get them through to the team. You may also recognise the tag cloud - it's CloudCuckoo - and we've put it in a little wrapper to make tagging only available to site editors!


Bookmark with :
Digg It! DZone StumbleUpon Technorati Reddit Del.icio.us Newsvine Furl Blinklist