Esta seção descreve como implementar suporte a idioma nativo em um programa ou biblioteca que faça parte da distribuição do PostgreSQL. Atualmente somente se aplica a programas C.
Adicionar suporte a idioma nativo ao programa
O código abaixo deve ser inserido na seqüência de inicialização do programa:
#ifdef ENABLE_NLS #include <locale.h> #endif ... #ifdef ENABLE_NLS setlocale(LC_ALL, ""); bindtextdomain("nome_do_programa", LOCALEDIR); textdomain("nome_do_programa"); #endif
(Na verdade o nome_do_programa pode ser escolhido livremente)
Sempre que for encontrada uma mensagem candidata a ser traduzida deve ser inserida uma chamada a gettext(). Por exemplo,
fprintf(stderr, "panic level %d\n", lvl);
deve ser alterada para
fprintf(stderr, gettext("panic level %d\n"), lvl);
(gettext é definida como nenhuma operação se não for configurado suporte a idioma nativo)
Isto tende a tornar o código confuso. Uma forma abreviada comum é:
#define _(x) gettext(x)
Quando o programa faz grande parte da sua comunicação através de uma ou de poucas funções, tal como ereport() no servidor, existe uma outra solução possível. Neste caso faz-se a função chamar gettext internamente para todas as cadeias de caracteres.
O arquivo nls.mk deve ser adicionado ao diretório com os fontes do programa. Este arquivo é lido como um Makefile. Devem ser feitas as seguintes atribuições de variáveis:
O nome do programa, conforme fornecido na chamada a textdomain().
Lista das traduções existentes — inicialmente vazia.
Lista dos arquivos que contêm cadeias de caracteres traduzíveis, ou seja, àquelas marcadas com gettext ou por uma solução alternativa. No final esta lista acaba incluindo praticamente todos os arquivos fonte do programa. Se esta lista ficar muito longa, pode ser feito com que o primeiro "arquivo" seja um +, e a segunda palavra seja um arquivo que contém um nome de arquivo por linha.
As ferramentas que geram catálogos de mensagem para os tradutores trabalharem precisam saber que chamadas de função contêm cadeias de caracteres traduzíveis. Por padrão, só são conhecidas as chamadas a gettext(). Se for utilizado _ ou outros identificadores estes devem ser listados aqui. Se a cadeia de caracteres traduzível não for o primeiro argumento, o item deve estar na forma func:2 (para o segundo argumento).
O sistema de construção toma conta automaticamente da construção e da instalação dos catálogos de mensagem.
Abaixo estão algumas diretrizes para escrever mensagens facilmente traduzíveis.
Não deve ser construídos enunciados em tempo de execução do tipo:
printf("Files were %s.\n", flag ? "copied" : "removed");
A ordem das palavras na frase pode ser diferente em outro idioma. Também, mesmo que seja chamado gettext() para cada fragmento, os fragmentos separados podem não ficar com uma tradução boa. É melhor duplicar um pequeno código para que cada mensagem traduzida se torne um todo coerente. Somente devem ser inseridos no texto da mensagem em tempo de execução números, nomes de arquivos, e variáveis em tempo de execução deste tipo.
Por motivos semelhantes, o que vem a seguir também não funciona
printf("copied %d file%s", n, n!=1 ? "s" : "");
porque assume uma regra de formação de plural. Se houver numeração pode ser resolvido desta maneira
if (n==1) printf("copied 1 file"); else printf("copied %d files", n);
e depois ficar desapontado. Alguns idiomas possuem mais de duas formas, com algumas regras peculiares. Pode ser encontrada uma solução para este caso no futuro, mas no momento é melhor evitar este problema. Pode ser escrito:
printf("number of copied files: %d", n);
Se for desejado comunicar algo ao tradutor, tal como a mensagem deve se posicionar em relação a outras saídas, a ocorrência da cadeia de caracteres deve ser precedida por um comentário que começa por translator, como, por exemplo,
/* translator: This message is not what it seems to be. */
Estes comentários são copiados para os arquivos de catálogo de mensagens para que os tradutores possam vê-los.