Making an asp.net website multi-lingual is, at first sight, no big deal. But there is quite a gotcha in the tail. I will rush you through the easy part, try to explain the gotcha and hope somebody can help me to find a fix.
I have an asp.net site. Most users are Dutch but an English version should be available as well. By default the pages are presented in Dutch but a visitor whose primary browser language is English should see pages in English. This is a setting in the web.config
<globalization uiCulture="auto:nl" culture="auto:nl" />
The text of the pages are stored in resource files. These are added in the special App_GlobalResources folder. This also applies to a web-application project. In my project I have two resourcefiles TekstStrings.resx contains the default (Dutch) values and TekstStrings.en.resx contains the English version. For a visitor issuing an en browser request the latter resources will be used.
Adding support for another language now boils down to adding another resource file, TekstStrings.fr.resx would add support for French.
The resources are compiled into the app. You can use them by name in markup. For instance as an attribute of a control:
<asp:RequiredFieldValidator ID="RequiredFieldValidator1" runat="server" ControlToValidate="TextBoxNaam" ErrorMessage="<% $ Resources:TekstStrings, LoginUsernameRequired %>"></asp:RequiredFieldValidator></div>
Using the resource content as plain text requires a literal control:
<p><asp:Literal ID="LiteralLoginPrompt" runat="server" Text="<%$ Resources:TekstStrings, LoginPrompt %>"/></p>
You can also use the resources in code.
LabelError.Text = Resources.TekstStrings.LoginUserNameUnknown;
The text on the label now depends on the culture of the browser request.
So far the good news. On the web you will find many variations on the theme, one of my favorite stories is here on MSDN
I had to experience two catches. The first one is IIS and Cassini (the local development server) behaving different. In my case it was tempting to embed the resources in the application. This is the "Build Action" setting on the resource file. This works very well when testing on the local server but does not work at all when the app has to run under IIS.
What was worse, and where I do not have a solution for, is using the resources from code. The example using strongly typed resources only works when the namespace of the application has a flat name. On this page the code snippet works:
namespace ResourcesTester
{
public partial class _Default : System.Web.UI.Page
{
On this one it does not:
namespace HHS.DigiRooster.DigiRoosterSite
{
public partial class Login : System.Web.UI.Page
{
Only because of the namespace. The code will hit an System.Resources.MissingManifestResourceException. A manifest describes the resource-assembly. One way or the other the manifest does not match the namespace which is expected. Googling around tells me it is a bug and that a solution is simple. But I didn't manage to get it right. Any suggestion is very much appreciated.
<Update>
The latter is an artifact resulting from the real catch: You have to watch which custom tool is used to compile your resources. See here for the details.
</update>
Posted
Thu, Feb 15 2007 4:29 AM
by
pvanooijen