Question

How would you build your domain objects and create its respective NHibernate mapping files for a multi language application. The UI part is stored in resource files but user data needs to go into the database.

I want to do the following:

Product p = DALProduct.getByID(2)
p.name //results in the language of the current UICulture

I have found the following article which is really close: http://ayende.com/Blog/archive/2006/12/26/LocalizingNHibernateContextualParameters.aspx As I am new to NHibernate I am not sure if that will perfectly work for enterprise solutions.

Do you have other suggestions? How do you solve such scenario?

It should be flexible to:

  • Inserting, Updating and selecting
  • Collections
Was it helpful?

Solution

Ayendes post is a great start how it should be designed.

It will perfectly work for enterprise solutions. The names in a separate table is like any other list of values. The special thing is, that it is filtered in the mapping.

Edit - Options:

Use another entity to edit the data

There is Product entity that has all the names as list. LocalizedProduct has only the current languages name.

Get the filtered entity

  • by either mapping it as described in the blog, with the filter.
  • by selecting it with a result transformer (Transformers.AliasToBean) or with 'select new LocalizedProduct(id, name, prize ...)'. LocalizedProduct would not be mapped in this case. Should be second-level-cache-friendly.

If you have many references to Product, it is probably not so nice to have two classes, because you don't know which class the reference should have.

Use the same entity for editing and displaying

class Product
{
  string LocalizedName 
  { 
    get { return AllProductNames[Thread.CurrentThread.CurrentCulture.LCID]; }
  }

  IDictionary<int, string> AllProductNames { get; private set; }
}

There are properties for a localized product name (get) and all product names.

  • don't filter them at all :-) There is a bit of network overhead. if you have only 3 to 5 languages, it is not so bad. if you have 20 or more, it's probably better to filter the names.
  • use a (optional) filter as described in the blog, but on the product names
  • use a (optional) ResultTransformer (CriteriaUtil.AliasToEntityMap) to filter the names.

To be honest, I would choose a option that dies not need filters in the mapping files. Filters belong to queries where they are more maintainable.

OTHER TIPS

Here is Gavin King's Post I which seems to offer a different solution.

The approach mentioned as an answer has been explained in detail here

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top