当前位置: 首页 > 面试题库 >

多语言数据库,默认回退

司徒墨竹
2023-03-14
问题内容

我知道一个问题已经得到广泛讨论,但是我认为仍有一个方面需要澄清。

我正在创建一个具有多语言数据库的Web应用程序,我已经找到了一些很好的实践文章(例如
this),

因此,我决定使用一个包含项目ID的主表,以及一个包含每个项目的翻译的表,例如

Content
ContentTranslation

要么

Category
CategoryTranslation

等等。

现在我在做什么?我只是从数据库中获取所有翻译的项目,然后遍历每个翻译,以根据当前用户的本地来查找正确的翻译,如果找到正确的本地,则将其设置到页面的翻译的主对象中进行渲染,否则我只会得到标记为“默认”的翻译。

但是,在有大量对象和转换的情况下,服务器响应时间可能会增加,即使用户可能没有注意到,我也不希望这样。

因此,此用例是否也有良好的做法?例如,一些特定的查询说“选择语言环境为“ it”的翻译,但如果找不到,只需获取设置了“默认”标志的查询?

现在,对于该技术,我正在将Spring MVC与Hibernate和JPA结合使用(通过JPARepository)。

我的对象都扩展了我通过这种方式创建的基本Translatable类

@MappedSuperclass
public abstract class Translatable<T extends Translation> extends BaseDTO {

    private static final long serialVersionUID = 562001309781752460L;

    private String title;

    @OneToMany(fetch=FetchType.EAGER, orphanRemoval=true, cascade=CascadeType.ALL)
    private Set<T> translations = new HashSet<T>();

    @Transient private T currentLocale;

    public void addLocale(T translation, boolean edit) {
        if (!edit)
            getTranslations().add(translation);
    }

    public void remLocale(String locale) {
        T tr = null;
        for (T candidate: getTranslations()) {
            if (candidate.getLocale().equals(locale))
                tr = candidate;
        }

        getTranslations().remove(tr);
    }

    public T getLocaleFromString(String locale) {
        if (locale == null)
            return null;
        for (T trans: translations) {
            if (trans.getLocale().equals(locale))
                return trans;
        }
        return null;
    }

    public T getDefaultLocale() {
        for (T tr: translations) {
            if (tr.isDefaultLocale())
                return tr;
        }
        return null;
    }

    public Set<T> getTranslations() {
        return translations;
    }

    public void setTranslations(Set<T> translations) {
        this.translations = translations;
    }

    public T getCurrentLocale() {
        return currentLocale;
    }

    public void setCurrentLocale(T currentLocale) {
        this.currentLocale = currentLocale;
    }

    public String getTitle() {
        return title;
    }

    public void setTitle(String title) {
        this.title = title;
    }
}

因此,在我的控制器中,我遍历翻译,找到具有正确语言环境的翻译,然后填充“
currentLocale”属性,在我的页面中,我接受了该内容,并且用户获得了所需的正确语言。

我希望我很清楚并且不会凌乱,但是如果您需要更多信息,我很乐意告诉您更多信息。


问题答案:

预先注意一些事项:

  • 我的回答更多是对这个问题的回答,您在其中添加了评论,然后导致了这个问题
  • 在我的答案中,我使用的是C#和MS SQL Server(并且我将省略所有OR映射的特定代码)

在我的应用程序中,根据使用情况,我使用两种不同的方法来加载多语言数据:

行政/ CRUD

在用户输入数据或编辑现有数据(例如带有翻译的产品)的情况下,我使用的是与您在问题中上面显示的方法相同的方法,例如:

public class Product
{
    public int ID {get; set;}
    public string SKU {get; set;}
    public IList<ProductTranslation> Translations {get; set;}
}
public class ProductTranslation
{
    public string Language {get; set;}
    public bool IsDefaultLanguage {get; set;}
    public string Title {get; set;}
    public string Description {get; set;}
}

即,我将让OR映射器加载带有所有翻译的产品实例。然后,我遍历翻译并选择所需的翻译。

前端/只读

在这种情况下(主要是前端代码),我通常只向用户显示信息(最好以用户的语言显示),因此我使用了另一种方法:

首先,我使用的是不同的数据模型,该模型不支持/不知道多重翻译的概念。相反,它只是当前用户使用“最佳”语言表示的产品:

public class Product
{
    public int ID {get; set;}
    public string SKU {get; set;}

    // language-specific properties
    public string Title {get; set;}
    public string Description {get; set;}
}

为了加载此数据,我使用了不同的查询(或存储过程)。例如,要加载ID @Id为该语言的产品@Language,我将使用以下查询:

SELECT
    p.ID,
    p.SKU,
    -- get title, description from the requested translation,
    -- or fall back to the default if not found:
    ISNULL(tr.Title, def.Title) Title,
    ISNULL(tr.Description, def.Description) Description
  FROM Products p
  -- join requested translation, if available:
  LEFT OUTER JOIN ProductTranslations tr
    ON p.ID = tr.ProductId AND tr.Language = @Language
  -- join default language of the product:
  LEFT OUTER JOIN ProductTranslations def
    ON p.ID = def.ProductId AND def.IsDefaultLanguage = 1
  WHERE p.ID = @Id

如果存在该语言的翻译版本,则会以html" target="_blank">请求的语言返回产品的标题和说明。如果不存在翻译,则将返回默认语言的标题和描述。



 类似资料:
  • 我们正忙于一个需要支持多种语言的CakePHP项目。但有一个问题....有些页面不支持其他语言。因此,有西班牙网页,需要隐藏的意大利版本的网站。在CakePHP中对此有什么更好的解决方案? 只要您切换语言,我们就可以切换数据库,但问题是,作为用户,我们将错过重要的数据,如果我们这样做的话。如果只搜索西班牙文、意大利文、德文、英文、荷兰文和瑞典文的文章,可能会使数据库负荷过重。或者如果我们索引语言栏

  • 问题内容: 我正在开发一种多语言软件。就应用程序代码而言,可本地化性不是问题。我们可以使用特定于语言的资源,并拥有与之配合使用的各种工具。 但是,定义多语言数据库架构的最佳方法是什么?假设我们有很多表(100个或更多),每个表可以有多个可以本地化的列(大多数nvarchar列应该可以本地化)。例如,其中一个表可能包含产品信息: 我可以想到三种支持NAME和DESCRIPTION列中的多语言文本的方

  • 主要内容:1. 数据定义语言,2. 数据操作语言,3. 数据控制语言,4. 事务控制语言DBMS具有适当的语言和接口来表达数据库查询和更新。 数据库语言可用于读取,存储和更新数据库中的数据。 数据库语言的类型 1. 数据定义语言 DDL代表数据定义语言。它用于定义数据库结构或模式。 用于在数据库中创建模式,表,索引,约束等。 使用DDL语句,可以创建数据库的框架。 数据定义语言用于存储元数据的信息,如表和模式的数量,它们的名称,索引,每个表中的列,约束等。 以下是DDL下的一些任务:

  • 在我的quarkus应用程序中有两个命名的数据源,我们称之为A和B: Quarkus.datasource.a.db-kind=Oracle Quarkus.datasource.b.db-kind=Oracle 因此,每次应用程序启动时,我都会收到这样的通知: 警告:无法确定默认数据源的数据库类型

  • 问题内容: 我刚刚安装了jre7,很惊讶地看到我的默认语言环境现在是en_US。对于jre6,它是de_CH。 jre7有什么不同?默认语言环境不再是操作系统之一吗?(顺便说一句,我正在使用Windows7) 谢谢你的回答。 编辑:我已经看到了 Category.FORMAT 的语言环境是“旧”的(de_CH)。区域设置为 Category.DISPLAY 从OS的语言的语言(在Windows中,

  • 问题内容: 我有一个需要支持多语言界面的应用程序,确切地说是五种语言。对于接口的主要部分,可以使用标准的Res​​ourceBundle方法来处理。 但是,数据库包含许多表,这些表的元素包含人类可读的名称,描述,摘要等。必须有可能以所有五种语言输入每一个。 虽然我想我可以简单地在每个表上都有字段 我认为在编写代表每个表的bean时,这会导致大量的很大程度上相同的代码。 从纯粹面向对象的角度来看,解