AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • Início
  • system&network
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • Início
  • system&network
    • Recentes
    • Highest score
    • tags
  • Ubuntu
    • Recentes
    • Highest score
    • tags
  • Unix
    • Recentes
    • tags
  • DBA
    • Recentes
    • tags
  • Computer
    • Recentes
    • tags
  • Coding
    • Recentes
    • tags
Início / dba / Perguntas / 190344
Accepted
user5613506
user5613506
Asked: 2017-11-08 12:25:43 +0800 CST2017-11-08 12:25:43 +0800 CST 2017-11-08 12:25:43 +0800 CST

Internacionalização de um supertipo-subtipo

  • 772

Em primeiro lugar, peço desculpas por vincular esta pergunta a outra, mas essa foi a melhor maneira que pude pensar para mantê-la simples e focada

Meses atrás fui apresentado ao supertipo-subtipo como solução para um problema que era mais ou menos fácil de apresentar mas não estava conseguindo resolver

Eu entendi o conceito básico e consegui fazê-lo funcionar com meu modesto conhecimento e funcionou muito bem, considerando que a pergunta original tem mais de um ano.

Porém hoje me deparei com um problema que não consegui resolver: Internacionalização

Até agora eu tinha uma tabela nomeada i18ncom uma FOREIGN KEY apontando para a PRIMARY KEY da tabela do supertipo ( Items) assim como todos os subtipos ( Car, Boate Plane) e ao consultar, entre todas as colunas de todos os subtipos, incluo a coluna nesta tabela de internacionalização com as strings traduzidas juntando tudo pela chave do supertipo.

Algo assim:

Itemsestrutura:

+----+---------------------+---------------------+
| PK | Common Attribute #1 | Common Attribute #2 |
+----+---------------------+---------------------+

Carestrutura:

+----+-----------+--------------+--------------+
| PK | Reference | Attribute #1 | Attribute #2 |
+----+-----------+--------------+--------------+

Boatestrutura:

+----+-----------+--------------+--------------+--------------+
| PK | Reference | Attribute #1 | Attribute #2 | Attribute #3 |
+----+-----------+--------------+--------------+--------------+

Planeestrutura:

+----+-----------+--------------+--------------+--------------+--------------+
| PK | Reference | Attribute #1 | Attribute #2 | Attribute #3 | Attribute #4 |
+----+-----------+--------------+--------------+--------------+--------------+

i18nestrutura:

+----+-----------+------+
| PK | Reference | Text |
+----+-----------+------+

Referenceé a CHAVE ESTRANGEIRA

Não tenho certeza se essa é a melhor abordagem, mas funciona porque até agora apenas uma das colunas tinha texto passivo de internacionalização — digamos Attribute #1. No entanto, hoje, notei que um dos subtipos precisaria de duas colunas para ser traduzido e o jeito que eu estava fazendo era considerar apenas uma — digamos Attribute #4de PlanesTable.

Eu gostaria de fazer isso diretamente no nível do banco de dados, em vez de ter alguma palavra-chave representativa para substituir a linguagem do lado do servidor.

Tentei fazer uma subconsulta para que essa segunda coluna fosse traduzida mas, além de não funcionar, isso estava me cheirando mal.

Como eu poderia fazer isso?

[EDITAR]

Achei melhor postar minha última tentativa:

SELECT 
    `items`.`cid` AS `id`, `items`.`reference`, `items`.`GUID`,     # That's Users' Items Table

    `core`.`image`, `core`.`type`, `core`.`class` AS `classname`,   # That's the supertype

    `cars`.`attribute1`, `cars`.`attribute2`,

    `boats`.`attribute1`, `boats`.`attribute2`, `boats`.`attribute3`,

    `planes`.`attribute1`, `planes`.`attribute2`, `planes`.`attribute3`, `planes`.`attribute4`,

FROM `items`
    LEFT OUTER JOIN core ON( ( items.reference = core.iid ) )
        LEFT OUTER JOIN `catalog`.`cars` cars ON( items.reference = cars.reference )
            LEFT OUTER JOIN `catalog`.`boats` boats ON( items.reference = boats.reference OR items.reference = boats.attribute3 )
                LEFT OUTER JOIN `catalog`.`planes` planes ON( items.reference = planes.reference )
                    LEFT OUTER JOIN users ON( items.UserId = users.id )
                        LEFT OUTER JOIN i18n ON( items.reference = i18n.reference )

WHERE `i18n`.`langCode` = 'en'
        AND ( `items`.`GUID` = '4cca0b05-84b0-40af-8808-2379b32df35f' OR `items`.`GUID` = '41a0917e-8ccf-43a3-b52a-0ae0a09a2374' )

ORDER BY ( FIELD( `items`.`GUID`, '4cca0b05-84b0-40af-8808-2379b32df35f','41a0917e-8ccf-43a3-b52a-0ae0a09a2374' ) )

Para este exemplo, usei o subtipo Boatspara demonstrar a outra coluna que poderia/deveria ser traduzida.

Posso recuperar todos os dados necessários de todos os subtipos de uma só vez com esta consulta. Ele terá várias colunas, NULLmas ao buscar dados, com PHP ( PDO::FETCH_NAMED, para o que importa) tudo funciona.

Mas não estou conseguindo retornar a coluna com o texto ( i18n.text), apenas seu Reference ID que corresponde ao supertipo Table ( Items.reference).

Eu sei, eu sei, não estou incluindo isso como uma coluna a ser recuperada, mas, se o fizer, a primeira coluna traduzível ( ) funciona, mas attribute1qualquer outra, que qualquer subtipo possa ter (aqui boats.attribute3) duplica o valor de atribute1de puxar seu próprio valor referenciado.

mysql database-design
  • 2 2 respostas
  • 241 Views

2 respostas

  • Voted
  1. Best Answer
    World Wide DBA
    2017-11-08T14:05:55+08:002017-11-08T14:05:55+08:00

    Pessoalmente, odeio ter que juntar várias tabelas para obter a variante internacional de algum valor de texto, então faço cada atributo que precisa ser internacionalizado uma coluna XML ou uma coluna JSON e, em seguida, uso as funções relevantes para retornar o valor que corresponde ao idioma que eu precisar. Esta é uma solução extremamente extensível no sentido de que você pode adicionar vários idiomas com muita facilidade sem adicionar novas tabelas, mas exige que você modifique sua inserção, atualização e seleções para lidar com isso.

    Exemplo de XML:

    '<?xml version="1.0"?>
     <translations>
        <text key="en-US" value="pants"/>
        <text key="en-UK" value="trousers"/>
     </translations>'
    
    SELECT ExtractValue([column], '/translations/text[@key="en-US"]');
    

    Exemplo JSON:

    '{
        "en-US" : "pants",
        "en-UK" : "trousers"
     }'
    
    SELECT JSON_EXTRACT([column], '$."en-US"');
    

    Prefiro usar JSON porque consome menos armazenamento, mas acho que qualquer uma das abordagens é melhor do que preencher seu banco de dados com tabelas de pesquisa. Você só precisa ter certeza de usar um conjunto de caracteres para XML ou JSON que dará suporte a Unicode.

    • 3
  2. Rick James
    2017-11-08T13:50:04+08:002017-11-08T13:50:04+08:00

    Conjunto de caracteres?

    Você está dizendo que todo VARCHARé latin1hoje? Mas amanhã você precisa utf8mb4?

    Plano A:

    1. Desabilitar chaves estrangeiras
    2. ALTER TABLE ... CONJUNTO DE CARACTERES utf8mb4
    3. Habilite FKs.

    Plano B:

    1. Despeje os esquemas; alterar manualmente o charset
    2. despejar dados sem esquemas
    3. em esquemas de carregamento de máquina novos, então os dados

    Atenção: "o diabo está nos detalhes".

    Frases?

    Se você está dizendo que tem um monte de frases em inglês hoje, mas amanhã você precisa de cada frase em vários idiomas, então há muito mais a fazer do que apenas modificar o charset.

    • Altere as frases para ter um ID independente do idioma.
    • Tenha uma tabela de pesquisa que mapeie esses ids em cada idioma ( phrase_id, language, phrase)
    • Sugira as linguagens padrão de 5 caracteres (ASCII), como EN-US, EN-UK, etc. Não se preocupe em fazer ids separadas para elas, use-as como estão.
    • Escreva um monte de código para escolher a(s) frase(s) certa(s).
    • 2

relate perguntas

  • Existem ferramentas de benchmarking do MySQL? [fechado]

  • Onde posso encontrar o log lento do mysql?

  • Como posso otimizar um mysqldump de um banco de dados grande?

  • Quando é o momento certo para usar o MariaDB em vez do MySQL e por quê?

  • Como um grupo pode rastrear alterações no esquema do banco de dados?

Sidebar

Stats

  • Perguntas 205573
  • respostas 270741
  • best respostas 135370
  • utilizador 68524
  • Highest score
  • respostas
  • Marko Smith

    conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host

    • 12 respostas
  • Marko Smith

    Como fazer a saída do sqlplus aparecer em uma linha?

    • 3 respostas
  • Marko Smith

    Selecione qual tem data máxima ou data mais recente

    • 3 respostas
  • Marko Smith

    Como faço para listar todos os esquemas no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Listar todas as colunas de uma tabela especificada

    • 5 respostas
  • Marko Smith

    Como usar o sqlplus para se conectar a um banco de dados Oracle localizado em outro host sem modificar meu próprio tnsnames.ora

    • 4 respostas
  • Marko Smith

    Como você mysqldump tabela (s) específica (s)?

    • 4 respostas
  • Marko Smith

    Listar os privilégios do banco de dados usando o psql

    • 10 respostas
  • Marko Smith

    Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Como faço para listar todos os bancos de dados e tabelas usando o psql?

    • 7 respostas
  • Martin Hope
    Jin conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host 2014-12-02 02:54:58 +0800 CST
  • Martin Hope
    Stéphane Como faço para listar todos os esquemas no PostgreSQL? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh Por que o log de transações continua crescendo ou fica sem espaço? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland Listar todas as colunas de uma tabela especificada 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney O MySQL pode realizar consultas razoavelmente em bilhões de linhas? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx Como posso monitorar o andamento de uma importação de um arquivo .sql grande? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison Como você mysqldump tabela (s) específica (s)? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Jonas Como posso cronometrar consultas SQL usando psql? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas Como faço para listar todos os bancos de dados e tabelas usando o psql? 2011-02-18 00:45:49 +0800 CST

Hot tag

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • Início
  • Perguntas
    • Recentes
    • Highest score
  • tag
  • help

Footer

AskOverflow.Dev

About Us

  • About Us
  • Contact Us

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve