具有默认回退的SQL连接

时间:2016-10-13 08:56:19

标签: sql database postgresql

我有一个名为movies的表,其中包含两列descriptionlonger_description。这些列包含用于获取翻译的翻译键。我设法通过使用连接来获取翻译,但是如果没有找到翻译,我想回退到默认语言环境。

我有这样的数据库结构:

电影表

movies
---------------------------------------
name | description | longer_description

本地化表

localizations 
------------------------------
textkey | locale | translation

将textkey + locale作为主键。

电影的示例数据:

name         | description        | longer_description
-------------------------------------------------------------
Batman movie | batman.description | batman.longer_description

这些值用于匹配本地化表中的textkey:

本地化的示例数据:

textkey                   | locale | translation
---------------------------------------------------------------
batman.description        | en     | english description
batman.longer_description | en     | english longer description

我想要实现的是使用给定的textkey + locale进行查询,如果存在翻译:select,如果不存在:回退到默认en语言环境。

SELECT
    m.name,
    t1.translation AS description,
    t2.translation AS long_description
FROM
    movies m
LEFT OUTER JOIN
    localizations t1
ON
    t1.language = 'sv' AND
    t1.text_key = m.description
LEFT OUTER JOIN
    localizations t2
ON
    t2.language = 'sv' AND
    t2.text_key = m.long_description
ORDER BY
    m.name

这将为我提供我想要的翻译,但它不会解决翻译不存在的情况,我需要回退到en语言环境。

2 个答案:

答案 0 :(得分:1)

使用存储的功能:

create function fn_get_translation(p_key text, p_language text) returns text static strict language sql as $$
  select
    translation
  from
    localizations l join 
      (values(1,p_language),(2,'en')) as lng(ord,code) on (l.locale = lng.code)
  where
    l.text_key = p_key
  order by
    lng.ord
  limit 1
$$;

免责声明:功能未经测试但我相信您将能够解决可能的错误。

然后查询会更简单:

select
  m.name,
  fn_get_translation(m.description, 'sv') as description,
  fn_get_translation(m.long_description, 'sv') as long_description
from
  movies m;

答案 1 :(得分:0)

您可以更改语句的选择部分并包含“案例”。然后,当找不到翻译时,将使用en语言环境。

SELECT
     m.name,
     case when t1.translation is null then m.description else t1.translation end AS description,
     case when t2.translation is null then m.longer_description else t2.translation end AS long_description
FROM 
    movies m
LEFT OUTER JOIN
    localizations t1
ON
    t1.language = 'sv' AND
    t1.text_key = m.description
LEFT OUTER JOIN
    localizations t2
ON
    t2.language = 'sv' AND
    t2.text_key = m.long_description
ORDER BY
    m.name