quinta-feira, 5 de maio de 2011

Access to Multivalued Fields for Dummies

Olá pessoal!
Como primeiro post, preciso de algo que demonstre exatamente o que é a idéia desse blog. Por isso, caçei no nosso histórico de atualizações aqui da empresa o SQL que motivou a criação do SeQueLado. Essa idéia, na verdade, nasceu da cabeça devastadoramente pensante de Bonifacio Segundo, um amigo e funcionário da Connect, empresa da qual sou sócio.
Pois bem, Bonifacio ficou perturbado durante algumas semanas depois que bolamos um SQL que mapeia um campo multivalorado de uma tabela para registros de uma tabela de relacionamento. Para situar-vos, grande parte do nosso trabalho na Connect está relacionado a integração das nossas soluções móveis com os sistemas de retaguarda dos nossos clientes. E nesse caso, o cliente tinha em seu banco de dados, um campo na tabela de clientes que listava as formas de pagamento permitidas para cada cliente. Esse campo era um campo de texto contendo os códigos das formas permitidas entre aspas e separados por vírgulas. Exemplo: "'001','002','003'" - cliente pode usar as formas de pagamento '001', '002' e '003'.
Não faz parte do nosso trabalho questionar a não-normatização do banco de dados do cliente. Precisamos apenas nos integrar a ele. Na nossa base de dados, essa regra é mapeada através de uma tabela de relacionamento (agradecimentos à Nilton Freire Santos, professor que me ensinou normatização de banco de dados).
Para mapearmos esse campo multivalorado em uma tabela de relacionamento, usamos a seguinte infâmia: fizemos uma junção entre as tabelas de clientes (CadParceiro) e formas de pagamento (CadTipoEvento), usando como critério de junção a ocorrência do código de pagamento (frm.CODIGOTIPOEVENTO) no campo multivalorado de cliente (cli.TIPOSEVENTOSPERMITIDOS). Como esses valores são separados por vírgulas no campo, concatenamos uma vírgula antes e outra depois do campo multivalorado para facilitar a comparação através do operador LIKE do SQL.
A consulta, simplificada para facilitar a compreensão, é essa aí abaixo. A maioria das pessoas vai achar essa consulta feia, mas eu acho que feio mesmo é usar campo multivalorado...

SeQueLem-se!

---

SELECT
        cli.CODIGOPARCEIRO          AS cod_cliente,
        frm.CODIGOTIPOEVENTO        AS cod_frm_pagamento
    FROM CadParceiro cli
    JOIN CADTIPOEVENTO frm
        ON ',' + cli.TIPOSEVENTOSPERMITIDOS + ',' LIKE '%,''' + frm.CODIGOTIPOEVENTO + ''',%'