We store resources for multilingual sites in a database. We have created several tools that simplify their creation and access to them. There's a custom ExpressionBuilder that allows us to use this syntax:
<asp:linkbutton runat='server' text='<%$ LanguageStrings:ClickMe%>' />
And a custom shortcut containing the default text, and adds a row to the database, if it does not already exist.
<r:languagelabel runat="server" name="AboutUs">About Us</r:languagelabel>
A table containing rows contains one column for each language. This simplifies the creation of the site in English (or regardless of the default language), and then sends the table (which fills itself) to the translator. It is also very easy to see in which languages ββyou need to translate the material. With resources every time you need to add a new line, you need to stop what you are doing, and then go to the resource file for each language and add the resource.
Here is the code for the language label:
''' <summary> ''' Retrieves a language-specific string. ''' </summary> Public Class LanguageLabel Inherits Label Private _Name As String Public Property Name() As String Get Return _Name End Get Set(ByVal value As String) _Name = value End Set End Property Private Sub Populate() If Len(Me.Name) > 0 Then Dim LanguageString As String = GetLanguageString(Me.Name, Me.Text) If Len(LanguageString) > 0 Then Me.Text = LanguageString End If End Sub Private Sub LanguageLabel_PreRender(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.PreRender Populate() End Sub Protected Overrides Sub Render(ByVal writer As System.Web.UI.HtmlTextWriter) ' By default a label wraps the text in a <span>, which we don't want in some situations writer.Write(Me.Text) End Sub End Class
and utility function:
Public Function GetLanguageString(ByVal Name As String, Optional ByVal DefaultText As String = "") As String Dim DefaultLanguage As Language = Languages.GetById(1) Name = StripPunctuation(Name).Trim.Replace(" ", "") ' Remove punctuation, spaces from name Dim SelectSql As String = String.Format("Select {0},{1} from LanguageStrings where Name=@Name ", Languages.CurrentLanguage.Code, DefaultLanguage.Code) Dim LanguageStringTable As DataTable = ExecuteDataset(cs, CommandType.Text, SelectSql, New SqlParameter("@Name", Name)).Tables(0) If LanguageStringTable IsNot Nothing AndAlso LanguageStringTable.Rows.Count > 0 Then Dim LanguageText As String = LanguageStringTable.Rows(0)(Languages.CurrentLanguage.Code).ToString Dim DefaultLanguageText As String = LanguageStringTable.Rows(0)(DefaultLanguage.Code).ToString If Len(LanguageText) > 0 Then ' We have a string in this language Return LanguageText Else ' Nothing in this language - return default language value Return DefaultLanguageText End If Else ' No record with this name - create a dummy one If DefaultText = "" Then DefaultText = Name Dim InsertSql As String = String.Format("Insert into LanguageStrings (Name, {0}) values (@Name, @Text)", DefaultLanguage.Code) ExecuteNonQuery(cs, CommandType.Text, InsertSql, New SqlParameter("@Name", Name), New SqlParameter("@Text", DefaultText)) Return Name End If End Function