Relatórios com Metamodelos – Complemento

Semana passada eu mostrei como montar um relatatório a partir de um metamodelo. Hoje eu vou encerrar o assunto com mais algumas dicas.

Concepts

Um dos pilares de um bom relatório é a qualidade da apresentação, e nesta qualidade inclui-se a consistência, ou seja, dados do mesmo tipo possuem a mesma aparência, ou no mínimo possuem algum padrão.

Um relatório ordinário, construído a partir de um SQL, tem seus campos formatados livremente. Se por um lado isso é bom, já que dá espaço irrestrito para o autor do relatório passar sua mensagem, por outra é ruim, porque obriga esse mesmo autor a uma formatação tediosa, repetitiva. Fora o aborrecimento de repetir sempre a mesma coisa, ainda podemos acabar esquecendo ou mudando algum detalhe ao longo do tempo.

Um concept, ou conceito, é um padrão de formatação definido dentro do metamodelo e obedecido integralmente pelo PRD. Acesse esta página para obter mais informações sobre concepts.

Vamos fazer um exercício: criaremos um conceito de texto destacado e aplicaremos ao relatório do post anterior. Primeiro, abrimos o PME e carregamos o metamodelo do Beltrano OLTP. Em seguida acessamos o editor de conceitos (concept editor):

Acessando editor de conceitos no PME.
Acessando editor de conceitos no PME.

Nele clicamos sobre o conceito Base e depois clicamos no sinal de + no canto superior direito dessa seção. Uma janela se abrirá, pedindo o nome do conceito – eu eu chamei de Destaque. Como criamos o novo conceito a partir do Base, Destaque herdou as propriedades deste. Caso contrário, se tívéssemos criado um conceito na raiz, ele teria nascido vazio e precisaria receber todos os atributos prentendidos.

Com o conceito Destaque selecionado, clique no elo ao lado do atributo Color of Text. Isso quebra a herança e nos permite redefinir aquele atributo, mantendo o restante:

Novo conceito: destaque (fonte em cor vermelha).
Novo conceito: destaque (fonte em cor vermelha).

Dê ok e, de volta à interface principal do PME, localize um campo na camada de apresentação – Neste exemplo eu selecionei Autor. Clique com o botão da direita sobre ele e selecione Set Parent Concept… para escolher o conceito desejado. Selecione Destaque na janela que se abrirá e Ok para aplicar.

Atribuindo conceito a campo Autor.
Atribuindo conceito a campo Autor.

Feito! Quando o campo Autor for usado no relatório, ele aparecerá em cor vermelha, em destaque:

Conceito entra em ação automaticamente.
Conceito entra em ação automaticamente.

Notou a festa do caqui que está o layout do relatório, na parte de cima da figura? Mas como o PRD vai respeitar o definido no metamodelo, o relatório vai sair arrumadinho, apenas com o nome do autor em vermelho!

Outro exemplo: digamos que precisamos formatar a coluna da direita como um valor monetário, usando a máscara R$ #.###,00. Alteramos ou criamos um conceito no metamodelo, exportamos e reaplicamos o metamodelo à consulta previamente criada:

Altere um conceito para alterar o relatório.
Altere um conceito para alterar o relatório.

Reaplicar o metamodelo a um relatório aberto no PRD é meio chato. Como o PRD não embute o metamodelo no relatório, bastaria purgar o cache ou fechar o relatório e recarregá-lo para forçar o PRD a reler o XMI. Por puro e simples hábito, eu apelo para força bruta: simplesmente apago e recrio a fonte e as consultas (apelando para um copy-paste básico, já que ninguém é de ferro…)

Para relatórios publicados no BA Server não é preciso nada: basta republicar o modelo a partir do PME, ou recarregá-lo no quadro Manage Data Sources e já está valendo. A série 5 do BA Server veio com purga e recarga automática de metamodelos na republicação.


Só essa simplicidade e praticidade, na minha opinião, já é o bastante para fazer valer a pena usar um MQL ao invés de SQL.

Prompts

Um recurso crucial para relatórios são os “prompts”, ou filtros, que permitem ao usuário escolher uma determinada fatia dos dados para apresentação. O PRD oferece esse recurso sob o nome de parameters. Um parameter – ou prompt – é uma variável preenchida pelo usuário em tempo de execução, que entra na consulta como algum tipo de restrição. Por exemplo, a consulta abaixo retorna todos os clientes de um determinado “tipo”, filtrando a consulta pelo conteúdo do prompt tipo_selecionado:

    SELECT cliente, estado, cidade
    WHERE tipo = ${tipo_selecionado}

Não é um mecanismo complicado, mas não é trivial o bastante para eu mostrá-lo aqui completamente. Assistam este vídeo que verão como fazer um prompt.

Quando usamos uma consulta MQL, de metadados, aplicar a restrinção é um pouco mais simples. Os passos são esses:

  1. Construa um relatório com MQL, como o que fizemos no post passado;
  2. Crie uma consulta (MQL, SQL, tanto faz) que retorne a lista de opções que o cliente pode selecionar;
  3. Crie o parâmetro no PRD usando essa consulta como fonte;
  4. Volte para a consulta principal e, usando a interface de criação de consultas, adicione o filtro e insira o parâmetro.

No nosso caso vamos filtrar o relatório de vendas do Alexandre por UF.

Primeiro, construímos uma consulta em MQL que traz a lista de estados:

Lista de UFs criada no construtor de consultas MQL.
Lista de UFs criada no construtor de consultas MQL.

O MQL dessa consulta é:

    <mql>
      <domain_type>relational</domain_type>
      <domain_id>BeltranoOLTP</domain_id>
      <model_id>BV_MODEL_1</model_id>
      <model_name>Beltrano OLTP</model_name>
      <options>
        <disable_distinct>false</disable_distinct>
        <limit>-1</limit>
      </options>
      <selections>
        <selection>
          <view>BC_CLIENTES_PF</view>
          <column>BC_ESTADOS_UF_2</column>
          <aggregation>none</aggregation>
        </selection>
      </selections>
      <constraints/>
      <orders>
        <order>
          <direction>asc</direction>
          <view_id>BC_CLIENTES_PF</view_id>
          <column_id>BC_ESTADOS_UF_2</column_id>
        </order>
      </orders>
    </mql>
    </pre>

Construímos um paramater alimentado por essa consulta, chamado UF:

Novo parâmetro UF, alimentado pela consulta Query 2 do metamodelo.
Novo parâmetro UF, alimentado pela consulta Query 2 do metamodelo.

Depois inserimos esse parâmetro, UF, na consulta que popula o relatório: colocamos a coluna que vai ser filtrada na seção constraints e aplicamos uma igualdade para o parâmetro.

Inserindo o parâmetro na consulta principal com o editor de MQL.
Inserindo o parâmetro na consulta principal com o editor de MQL.

O truque é envolver o parâmetro em chaves, { e }. Com isso o construtor de consultas reconhece que se trata de um parâmetro e não de um valor ordinário, e ajusta a consulta automaticamente. A título de comparação, observe o filtro para pegar apenas as vendas do Alexandre.


Ao adicionar um nome cercado por { e } nos filtros, o construtor de consulta realiza duas coisas:

  1. Define um parâmetro no início da consulta
    <mql>
      <domain_type>relational</domain_type>
      <domain_id>BeltranoOLTP</domain_id>
      <model_id>BV_MODEL_1</model_id>
      <model_name>Beltrano OLTP</model_name>
      <options>
        <disable_distinct>false</disable_distinct>
        <limit>-1</limit>
      </options>
      <parameters>
        <parameter defaultValue="XX" name="UF" type="STRING"/>
      </parameters>
      <selections>
        <selection>
          <view>BC_PEDIDOS</view>
    <...restante da consulta...>        
    
  2. E usa esse parâmetro na seção conditions:
    <...começo da consulta...>
      <constraints>
        <constraint>
          <operator>AND</operator>
          <condition>CONTAINS([BC_PEDIDOS.BC_VENDEDOR_NOME_COMPLETO];"Alexandre")</condition>
        </constraint>
        <constraint>
          <operator>OR</operator>
          <condition>[BC_CLIENTES_PJ.BC_ESTADOS_UF_3] = [param:UF]</condition>
        </constraint>
      </constraints>
    

Ao rodar o relatório o PRD cria e apresenta um controle do tipo drop-down, populado com a lista dos estados. Sempre que um estado é selecionado, o relatório é automaticamente filtrado:

Filtro aplicado em consulta MQL.
Filtro aplicado em consulta MQL.

Um bom uso dessas possibilidades é criar relatórios que se adequam a cada usuário: basta usar o parâmetro pré-definido env::username para filtrar a consulta pelo nome do usuário na plataforma desde que esse usuário possua um nome igual registrado no banco de dados.

Por exemplo, se eu registrar no Pentaho BA Server os vendedores com o mesmo nome que possuem no Beltrano OLTP, eu posso filtrar os dados montando uma constraint do tipo Vendedor CONTAINS {env::username}.

Experimente!

8.3 Segurança

Por fim, mas não menos importante, um metamodelo pode restringir o conteúdo de uma consulta em função das permissões de acesso – controle de segurança – dos dados.

Como sempre, a idéia é simples: definimos um filtro de dados no metamodelo que usa o nome do usuário e, eventualmente, seu papel, para montar um controle de exibição baseado no controle de acesso.

Como fazer:

  1. No Pentaho BA Server, usando o papel de administrador, registre todos seus usuários. Eu fiz isso com os usuários da Beltrano;
  2. Com Pentaho Metadata Editor edite o metamodelo e registre um filtro no nível do modelo de negócio, seção Data Constraints: qualquer consulta contra esse modelo de negócio vai embutir aquele filtro automaticamente. Salve e publique o metamodelo no servidor;

    Registrando filtro no PME.
    Registrando filtro no PME.
  3. No PRD basta remover qualquer filtro local. Por exemplo, eu removi o filtro de usuário “Alexandre”, deixando o relatório trazer dados de todos os vendedores, indistintamente. Salvei e publiquei o metamodelo.

Feito! :-)

Para testar, acessei a plataforma com duas contas: Fábio e Alexandre. Como o relatório consome metadados, e os metadados são completamente filtrados por meio do atributo Data Constraints no Business Model, os dados apresentados já estão filtrados.

Resultado do filtro por controle de segurança.
Resultado do filtro por controle de segurança.

8.4 Conclusão

“Nossa, Fábio! Que maravilha!”, dirão vocês, “e não tem nenhuma desvantagem?”

Sim, tem: justamente adicionar uma outra camada para manutenção. Se usamos apenas SQL, qualquer alteração no banco entra em efeito imediatamente para o relatório. Se usarmos um metamodelo vamos precisar atualizar a camada de metadados antes de poder sequer testar as mudanças no PRD. Fazer uma pequena alteração na formatação pode forçar o analista a quebrar o vínculo do campo com a metaconsulta, perdendo a vantagem do modelo centralizado, ou então obrigar a uma atualização do metamodelo, cascateando a publicação de uma nova versão.

Há uma segunda desvantagem, mas é mais sutil e, talvez, pior: aparentemente não há como fazer UNIONs! Isso não é um problema para modelos bem comportados, mas modelos como o do Beltrano – que nem é tão exótico assim – se quebram quando tentamos fazer certas combinações numa só consulta. Por exemplo, no modelo transacional, não é possível escrever um único SQL que traga todos os clientes PF e PJ. É preciso duas consultas, coladas a posteriori com UNION, para então chegar ao conjunto completo. E eu não achei como fazer isso com MQL.

Ou seja, as vantagens de uso de um metamodelo vêm com um preço: um processo de desenvolvimento com mais alguns passos. Se isso vai compensar no final é uma questão respondida projeto a projeto.

Até a próxima! :-)

Relatórios com Metamodelos

Hora de uma pausa na série de artigos sobre conceitos, e ver um pouco de Pentaho. Hoje vou mostrar uma coisa que já me pediram algumas vezes: como criar um relatório usando um metamodelo como fonte de dados.

Sério? Relatórios??

Sim, sério!! Relatórios são o solo fértil no qual germinam as primeiras idéias e hipóteses em BI. É com uma listagem simples que podemos fazer os primeiros testes, sem contar que, bem construídos, são uma excelente ferramenta de apresentação e acompanhamentos.

Um bom relatório tem o peso de um bom argumento. Não há motivo técnico para prescindir de um relatório se ele for o suficiente para seu propósito.

O Pentaho Report Designer

O Pentaho Report Designer (PRD) oferece uma vasta gama de recursos para criar relatórios visualmente atraentes e versáteis. A figura abaixo, por exemplo, mostra um relatório que lista o estoque de uma empresa.

Relatório de estoque, que buscas fotos do produto no Google.
Relatório de estoque, que buscas fotos do produto no Google.

Neste relatório:

  • Cada item é apresentado com seu nome, código de barra e outros atributos;
  • Uma barra colorida, abaixo do item, mostra a quantidade em estoque através do seu tamanho e de um número;
  • A cor da barra, e o fundo da coluna On Hand, indicam por cores se a quantidade em estoque é adequada (verde ou amarelo), ou se é preciso reabastecer com um novo pedido para o fornecedor (vermelho;)
  • As colunas SKU e Name são URLs. Clicar em um deles leva a um outro relatório ou a algo mais. Clicando no item na coluna Name, por exemplo, dispara uma consulta por imagens no Google, abrindo o navegador web padrão para mostrar imagens do produto;
  • A imagem não mostra, mas o relatório possui um filtro por linha de produtos. Veja no canto superior esquerdo o filtro ativo: Line: Classic Cars.

Figuras, fontes, funções, fórmulas, prompts, saída em HTML, Excel, CSV ou PDF…. o PRD tem tudo, incluindo a pia da cozinha e mais um pouco. E como ele é parte da Suite Pentaho, podemos publicar os relatórios no Pentaho BA Server, onde os usuários conseguem acessá-los, agendá-los ou executá-los em background.

E ainda tem o lado das fontes de dados: o PRD consegue ler desde bancos de dados relacionais a Hadoop, de uma tabela hardcoded no relatório a resultados de scripts em Groovy ou JavaScript, de MDX (consultas OLAP) a SQLs gerados em tempo real com scripts, sem contar transformações, que por si só também permitem ler de qualquer coisa.

Uma destas fontes de dados é o metamodelo, um padrão definido por um consórcio de empresas de BI. A ferramenta da Suite Pentaho que gera esse arquivo é Metadata Editor (PME.)

Pentaho Metadata Editor.
Pentaho Metadata Editor.

Relatórios são construídos, em sua maioria, com SQL, que até que é uma linguagem bem prática. O que quase sempre complica as consultas é o modelo de dados. Raramente podemos deixar nosso cliente construir seus próprios relatórios por dois motivos:

  1. Falta de conhecimento em SQL;
  2. Desconhecimento do modelo de dados.

Se o primeiro item dificulta a construção da consulta em si, o segundo compromete o resultado. Pois mesmo que o cliente consiga montar o SQL que traga a listagem desejada, apenas um conhecimento íntimo dos dados, das tabelas e dos relacionamentos é que pode garantir que a consulta trará o resultado correto. E mesmo conhecendo bem os dados, o risco de uma consulta trazer dados inconsistentes ou incorretos nunca é zero.

Tanto é assim que a principal justificativa para construção de um [Data Mart][datamart_bitly] em formato dimensional (ou [esquema estrela][modim_bitly]) é justamente reduzir a complexidade do modelo on-line a ponto de permitir a exploração dos dados por um profissional não-técnico, que nem domina SQL nem conhece em profundidade o modelo de dados transacional.


Na minha opinião, essa é a única justificativa para construirmos um modelo dimensional.


Outro caminho para superar essas dificuldades é deixar que o computador resolva as consultas para você, algo muito em moda hoje em dia com a onda das ferramentas de Data Discovery.

E esse é justamente o propósito do metamodelo: esconder a complexidade da base de dados e permitir a construção de consultas por usuários de negócio, que sabem pouco ou nada de SQL, e menos ainda de modelos de dados, relacionamentos, chaves estrangeiras etc. etc. etc.

Meta… Meta… Meta…

Criado em 2003, o Commom Warehouse Metamodel é uma proposta para eliminar a complexidade de consultas a bancos de dados por meio de uma camada de relacionamentos (camada de negócio) que senta entre a camada física (bancos de dados) e a camada de apresentação (interface de usuário.)

As camadas de um metamodelo CWM.
As camadas de um metamodelo CWM.

A forma mais comum de consumir esses dados é usando um aplicativo que até pouco tempo atrás vinha embutido no Pentaho BA Server, o Web Ad Hoc Query and Reporting, ou WAQR:

Usando o WAQR para construir um relatório a partir de um metamodelo.
Usando o WAQR para construir um relatório a partir de um metamodelo.

O WAQR ainda está disponível, mas como um plugin sem suporte. A falta de manutenção, aliás, está começando a mostrar seus efeitos – já não é mais possível editar relatórios salvos, por exemplo.


Entre vários recursos incorporados por um CWM, ou um metamodelo, estão o controle de acesso aos dados. Um CWM pode, por exemplo, bloquear o acesso de um determinado usário a um conjunto de tabelas, ou que um grupo de usuários (um papel) veja essas tabelas, mas apenas parte do conteúdo (controle de acesso no nível de linha.) Veja essa página para saber um pouco mais sobre segurança em metamodelos do Pentaho Infocenter.

PRD com Metamodelos

Lembra-se dos motivos para um usuário de negócio não construir seus próprios relatórios? Bom, ao usar um metamodelo como fonte de dados para um relatório, ambas somem!

  1. Falta de conhecimento em SQL: ao contrário de um modelo de dados em banco relacional, que usa SQL, a construção de uma consulta com metamodelo é feita por uma interface gráfica amigável, sem comandos técnicos – escolha os campos, as agregações, ordenações e filtros e pronto! O engine do PRD vai usar o metamodelo para construir a consulta SQL sozinho;
  2. Desconhecimento do modelo de dados: como o metamodelo embute as regras de negócio, uma consulta construída sobre o metamodelo elimina a necessidade de o autor do relatório conhecer e entender bem o modelo e os relacionamentos entre as tabelas. O risco de consultas erradas ou mal-feitas vai virtualmente a zero.

Mas não pára por aí! Ainda teremos:

  • Controle de acesso: todas as regras de acesso implementadas no metamodelo são aplicadas automaticamente nos relatórios do PRD;
  • Padrão de formatação: um metamodelo impõe, e o PRD respeita, um padrão de formatação para a camada de apresentação. Ou seja, se um campo monetário for definido como “Arial-12, Itálico, Verde-Água”, então todos as vezes que esse campo for usado em um relatório ele vai aparecer em Arial itálico, tamanho 12, verde-água, mesmo que o autor do relatório altere o elemento! (Dá para contornar, e não é acidentalmente – é preciso ter a intenção de sair do padrão.)

E você não perde (quase) nenhuma vantagem do PRD: continua podendo usar parâmetros (prompts), gráficos, sub-relatórios, fontes, funções, scripts etc. etc. etc.


Aparentemente, existem duas limitações em consultas MQL (Metadata Query Language) parametrizadas: o controle de calendário não funciona 100% e não é possível filtrar consultas com parâmetros que retornam listas. Eu li en passant sobre isso em uma thread do fórum internacional, mas não achei evidência. Vou testar e voltarei ao assunto quanto tiver informação concreta.


Como Fazer

É simples, muito simples: registre seu metamodelo como uma fonte de dados no PRD, e use-a para construir as consultas. Pré-requisitos:

  • O PRD instalado e funcionando e, é claro, saber usar o básico para construir um relatório;
  • Uma base de dados, com o respectivo servidor de banco de dados no ar, e todas as informações para conexão (string de conexão, IP, usuário e senha;)
  • Um metamodelo sobre a base acima, construído com o Metadata Editor (PME), exportado para um arquivo XMI.

Instalar PRD e PME

Para instalar o PRD e o PME clique aqui, baixe e leia o capítulo de degustação do Pentaho na Prática. Ele foi feito para a baseline 4.8 do Pentaho, mas ainda serve para a série 5 ou 6: troque o Java de 1.6 para 1.7 (baseline 5.x) ou 1.8 (série 6) e fique atento para as diferenças entre as telas.

Base de Dados: Beltrano S/A

Se você não tiver uma base contra a qual construir o seu metamodelo, consulte este post para baixar e instalar a Beltrano S/A. Artigo completo, incluindo instruções para instalar o Postgres no Windows (livro gratuito!) e Linux.

Diagrama de tabelas do sistema transacional (OLTP) da Beltrano S/A.
Diagrama de tabelas do sistema transacional (OLTP) da Beltrano S/A.

Metamodelo Beltrano OLTP

Com um pouco de trabalho construímos um metamodelo a partir do diagrama anterior. A figura abaixo mostra a cara do metamodelo que eu vou usar no exemplo:

Metamodelo sobre banco de dados transacional (OLTP) da Beltrano S/A.
Metamodelo sobre banco de dados transacional (OLTP) da Beltrano S/A.

Daí, usando o comando File -> Export to XMI File no menu do PME, eu gerei o arquivo XMI necessário para o PRD.

Não veremos como montar o metamodelo inteiro, pois é muita coisa. Você pode usar algum que já possua, ou clicar aqui e baixar o metamodelo do Beltrano S/A.


Deixe um comentário se não conseguir ou se tiver alguma dúvida. Faz tempo que eu montei esses arquivos e algo pode estar desregulado.


Registrar Metamodelo como Fonte de Dados

Abra o PRD e crie um relatório vazio. No lado direito da interface há duas abas: Structure e Data. Selecione a aba Data e clique com o botão da direita sobre o cilindro amarelo. Escolha Metadata no menu que vai aparecer.

Criando uma fonte de dados para metamodelo.
Criando uma fonte de dados para metamodelo.

Vai aparecer a janela abaixo. Use o botão Browse ao lado do campo XMI File para localizar e selecionar o arquivo XMI do metamodelo. Informe um nome para domínio (campo Domain Id/BI-Server Solution Name.)

(A consulta que aparece na imagem é resultado do exercício. Já, já mostro como ela apareceu.)

Fonte de dados baseada em metamodelo registrada.
Fonte de dados baseada em metamodelo registrada.

Se você prentende publicar os relatórios em um BA Server, certifique-se de usar o mesmo nome de domínio no PRD e no BA Server (isso é feito no momento da publicação via PME ou na importação em Manage Data Sources no BA Server.) Caso sejam diferentes, executar o relatório no BA Server vai gerar uma mensagem de erro sobre “fonte de dados inexistente”.


Pronto! A fonte de dados está configurada e, a partir daí, vida normal: crie uma consulta e desenhe um relatório.

Criando uma Consulta MQL

A figura anterior mostra uma consulta já criada. Eis como chegaremos até ali:

  1. Clique no botão + (verde) que fica ao lado do texto “Avaliable Queries” na janela de conexão;
  2. Aparecerá uma Query 1 na lista de consultas. Clique nela para selecioná-la;
  3. Clique no ícone de lápis (destacado por uma seta vermelha) para abrir a janela de construção de consultas. Consulte esta página do Infocenter para mais informações sobre o “construtor de consultas de metadados”;
  4. Veja a figura a seguir: cada um dos campos desejados no relatório foi selecionado e transferido para a seção Selected Columns clicando-se na primeira seta verde, de cima para baixo;
  5. Um filtro foi definido transferindo-se para a segunda seção, Conditions, o campo que filtrará os dados. Usamos a Comparison (comparação) “contains” (contém) e Alexandre na coluna Value;
  6. Finalmente definimos a ordem de listagem desses dados: por Vendedor, por Curso, ambos em ordem alfabética crescente (ASC), na seção Order By.

Ao clicar no Ok volta-se para a janela anterior, e consulta aparece na seção Static Query. Neste ponto você pode testá-la, clicando em Preview, ou só clicar em Ok e voltar para o relatório.

Construir uma consulta em MQL é muito fácil e simples!
Construir uma consulta em MQL é muito fácil e simples!

Note que acabamos de cumprir as duas promessas: criamos uma consulta sem saber nada de SQL ou do modelo de dados.

Montando um Relatório

O relatório é desenhado da mesma forma que se usássemos uma consulta SQL: inclua os elementos que deseja (como títulos e gráficos), arraste os campos da consulta para a lona, posicione-os, configure os detalhe e salve.

Um relatório baseado em metamodelo pode ter qualquer recurso.
Um relatório baseado em metamodelo pode ter qualquer recurso.

Pressione o ícone de olho ou o botão de play para renderizar seu relatório. O meu ficou assim:

Vendas do Alexandre Costa, Beltrano S/A.
Vendas do Alexandre Costa, Beltrano S/A.

Uma última dica! O PRD vai aplicar, aos campos trazidos da consulta, as regras de formatação definidas no metamodelo e você não vai conseguir alterá-las na mão, no PRD. Se você quiser forçar a formatação de um campo, use um elemento do tipo Message ao invés do tipo padrão que o PRD escolher para o campo. A forma mais fácil de entender como funciona esse tipo de campo é arrastar da consulta um campo qualquer para a lona, selecioná-lo e, no menu Format do PRD, acionar a opção Morph -> message-field. A partir daí o campo vai aceitar qualquer formatação que você aplicar.

Conclusão

Sentiu a facilidade da coisa? Uma vez que um metamodelo seja criado, usá-lo para construir um relatório é muito fácil e, muito importante, tem altíssima produtividade, já que todo trabalho de escrever e testar a consulta SQL foi passado para o motor de metadados.

Indo um pouco além, suponha que seu banco de dados, que serve de fonte para o metamodelo, sofreu alguma alteração. O usuário não precisa saber de nada: apenas atualize o metamodelo e distribua a nova versão. Se não houver acontecido nenhuma mudança drástica, tudo que existia continuará funcionando e ainda terá consistência com as alterações da base!

Até a próxima! :-)