Este tópico possui um enunciado um tanto confuso: ensure code non regression by keeping consistent signature for procedure, views and function (interfaces); security implications. Inicialmente precisamos perceber que o tópico vai além de views, abordando também procedures e functions. Por conseguinte, vale destacar que o conteúdo a ser estudado para o exame 70-461 possui escopo mais amplo que DML, envolvendo temas como objetos programáveis (views, sp, functions, triggers) e assuntos avançados como transações, manipulação de XML, dentre outros. Assim, não se iluda: estude e se prepare para uma prova desafiadora que lhe exigirá além do conhecimento de consultas T-SQL e modificação de dados.

Quanto ao conteúdo do tópico 3 vamos quebrá-lo em duas partes, visando dirimir quaisquer confusões:
1) Não regressão de código mantendo consistentes assinaturas nas interfaces dos objetos (view, sp, function)
2) Implicações de segurança

Não regressão de código mantendo consistentes assinaturas nas interfaces dos objetos (view, sp, function)

Pode até parecer confuso, mas a idéia por trás dessas palavras é bem simples: quebrar a dependência. Imaginemos uma view que retorna 3 colunas: CODIGO, NOME, DT_NASCIMENTO, sendo todas recuperadas a partir de uma tabela de candidatos a ofertas de emprego. Agora imagine que o DBA renomeou na tabela (e também na view) a coluna DT_NASCIMENTO para DATA_NASCIMENTO. Enquanto não forem recompiladas, as aplicações que utilizam a view passarão a apresentar erro, vez que ainda referenciam a coluna como DT_NASCIMENTO. Este é um problema típico de dependência: os nomes expostos pela view para as colunas são exatamente os mesmos utilizados nas tabelas. Sendo assim, tudo o que precisamos fazer é tratar a assinatura do objeto, expondo nomes que serão mantidos independente de quaisquer modificações nas tabelas referenciadas, de modo a garantir a não necessidade de manutenção nas aplicações ou em outros objetos programáveis do BD que consomem a view. Vejamos o exemplo da tabela CANDIDATO.

[et_pb_dmb_code_snippet _builder_version=”4.0.6″ code=”VVNFIERCRXhhbWU3MDQ2MQpHTwrigJQgQ3JpYSBhIHRhYmVsYSBkZSBjYW5kaWRhdG9zCkNSRUFURSBUQUJMRSBkYm8uQ2FuZGlkYXRvCiggQ09ESUdPIElOVCwKTk9NRSBWQVJDSEFSKDUwKSwKRFRfTkFTQ0lNRU5UTyBEQVRFVElNRSk7CkdPCgpJTlNFUlQgZGJvLkNhbmRpZGF0byBWQUxVRVMoMSwg4oCYTWFyaWFuYSBQZXJlaXJhIGRhIFNpbHZh4oCZLCDigJgxOTgwMTIyNOKAmSk7CkdPCgrigJQgQ3JpYSBhIHZpZXcKQ1JFQVRFIFZJRVcgZGJvLnZ3Q2FuZGlkYXRvcwpBUwpTRUxFQ1QgQ29kaWdvLCBOb21lLCBEdF9OYXNjaW1lbnRvCkZST00gZGJvLkNhbmRpZGF0bzsKZ28KCuKAlCBDcmlhIHVtYSBzcCBwYXJhIGNvbnN1bWlyIGEgdmlldwpDUkVBVEUgUFJPQ0VEVVJFIGRiby51c3BPYnRlckNhbmRpZGF0b3MKQVMKU0VMRUNUIENvZGlnbywgTm9tZSwgRHRfTmFzY2ltZW50byBGUk9NIGRiby52d0NhbmRpZGF0b3M7CkdP” hover_enabled=”0″]VVNFIERCRXhhbWU3MDQ2MQpHTwrigJQgQ3JpYSBhIHRhYmVsYSBkZSBjYW5kaWRhdG9zCkNSRUFURSBUQUJMRSBkYm8uQ2FuZGlkYXRvCiggQ09ESUdPIElOVCwKTk9NRSBWQVJDSEFSKDUwKSwKRFRfTkFTQ0lNRU5UTyBEQVRFVElNRSk7CkdPCgpJTlNFUlQgZGJvLkNhbmRpZGF0byBWQUxVRVMoMSwg4oCYTWFyaWFuYSBQZXJlaXJhIGRhIFNpbHZh4oCZLCDigJgxOTgwMTIyNOKAmSk7CkdPCgrigJQgQ3JpYSBhIHZpZXcKQ1JFQVRFIFZJRVcgZGJvLnZ3Q2FuZGlkYXRvcwpBUwpTRUxFQ1QgQ29kaWdvLCBOb21lLCBEdF9OYXNjaW1lbnRvCkZST00gZGJvLkNhbmRpZGF0bzsKZ28KCuKAlCBDcmlhIHVtYSBzcCBwYXJhIGNvbnN1bWlyIGEgdmlldwpDUkVBVEUgUFJPQ0VEVVJFIGRiby51c3BPYnRlckNhbmRpZGF0b3MKQVMKU0VMRUNUIENvZGlnbywgTm9tZSwgRHRfTmFzY2ltZW50byBGUk9NIGRiby52d0NhbmRpZGF0b3M7CkdP[/et_pb_dmb_code_snippet]

Neste exemplo criamos uma procedure que consome a view. Note que esta procedure produz um result set, ou seja, apresenta o resultado de uma query. A SP (stored procedure) tem uma dependência direta com a view, enquanto que esta usa os mesmos nomes de colunas da tabela referenciada. Para executarmos a SP basta fazer como abaixo:

[et_pb_dmb_code_snippet _builder_version=”4.0.6″ code=”RVhFQyBkYm8udXNwT2J0ZXJDYW5kaWRhdG9zOw==” hover_enabled=”0″]RVhFQyBkYm8udXNwT2J0ZXJDYW5kaWRhdG9zOw==[/et_pb_dmb_code_snippet]

Agora vamos renomear a coluna DT_NASCIMENTO para DATA_NASCIMENTO, na tabela.

[et_pb_dmb_code_snippet _builder_version=”4.0.6″ code=”4oCUIFJlbm9tZWFuZG8gYSBjb2x1bmEgbmEgdGFiZWxhCkVYRUMgc3BfcmVuYW1lIOKAmGRiby5DYW5kaWRhdG8uRFRfTkFTQ0lNRU5UT+KAmSwg4oCYREFUQV9OQVNDSU1FTlRP4oCZOw==” hover_enabled=”0″]4oCUIFJlbm9tZWFuZG8gYSBjb2x1bmEgbmEgdGFiZWxhCkVYRUMgc3BfcmVuYW1lIOKAmGRiby5DYW5kaWRhdG8uRFRfTkFTQ0lNRU5UT+KAmSwg4oCYREFUQV9OQVNDSU1FTlRP4oCZOw==[/et_pb_dmb_code_snippet]

Observe a mensagem que aparece após a execução desta sp builtin: “Caution: Changing any part of an object name could break scripts and stored procedures”. Neste momento a view não está mais funcionando, sendo necessário alterar a view.

[et_pb_dmb_code_snippet _builder_version=”4.0.6″ code=”4oCUIFJlbm9tZWFuZG8gbmEgdmlldwpBTFRFUiBWSUVXIGRiby52d0NhbmRpZGF0b3MKQVMKU0VMRUNUIENvZGlnbywgTm9tZSwgRGF0YV9OYXNjaW1lbnRvCkZST00gZGJvLkNhbmRpZGF0bzsKZ28=” hover_enabled=”0″]4oCUIFJlbm9tZWFuZG8gbmEgdmlldwpBTFRFUiBWSUVXIGRiby52d0NhbmRpZGF0b3MKQVMKU0VMRUNUIENvZGlnbywgTm9tZSwgRGF0YV9OYXNjaW1lbnRvCkZST00gZGJvLkNhbmRpZGF0bzsKZ28=[/et_pb_dmb_code_snippet]

Como consequência a SP também parou de funcionar, sendo necessário recompilá-la de modo a refletir o novo nome da coluna. Tente executar o código abaixo e veja o resultado:

[et_pb_dmb_code_snippet _builder_version=”4.0.6″ code=”ZXhlYyBkYm8udXNwT2J0ZXJDYW5kaWRhdG9zCkludmFsaWQgY29sdW1uIG5hbWUg4oCYRHRfTmFzY2ltZW50b+KAmQ==” hover_enabled=”0″]ZXhlYyBkYm8udXNwT2J0ZXJDYW5kaWRhdG9zCkludmFsaWQgY29sdW1uIG5hbWUg4oCYRHRfTmFzY2ltZW50b+KAmQ==[/et_pb_dmb_code_snippet]

Para evitar essa “regressão de código”, vamos modificar a assinatura da view e quebrar a dependência (pelo menos no nível da interface). Isso pode ser feito de duas maneiras.

[et_pb_dmb_code_snippet _builder_version=”4.0.6″ code=”4oCUIENyaWFuZG8gQUxJQVMgcGFyYSBhcyBjb2x1bmFzIGRpcmV0YW1lbnRlIG5hIGxpc3RhIGRvIFNFTEVDVApBTFRFUiBWSUVXIGRiby52d0NhbmRpZGF0b3MKQVMKU0VMRUNUCkNvZGlnbyBBcyBDb2RpZ28sCk5vbWUgYXMgTm9tZSwKRGF0YV9OYXNjaW1lbnRvIEFzIER0X05hc2NpbWVudG8KRlJPTSBkYm8uQ2FuZGlkYXRvOwpnbwoK4oCUIERlY2xhcmFuZG8gZXh0ZXJuYW1lbnRlIG9zIEFMSUFTIHBhcmEgYXMgY29sdW5hcwpBTFRFUiBWSUVXIGRiby52d0NhbmRpZGF0b3MgKENvZGlnbywgTm9tZSwgRHRfTmFzY2ltZW50bykKQVMKU0VMRUNUCkNvZGlnbywKTm9tZSwKRGF0YV9OYXNjaW1lbnRvCkZST00gZGJvLkNhbmRpZGF0bzsKZ28=” hover_enabled=”0″]4oCUIENyaWFuZG8gQUxJQVMgcGFyYSBhcyBjb2x1bmFzIGRpcmV0YW1lbnRlIG5hIGxpc3RhIGRvIFNFTEVDVApBTFRFUiBWSUVXIGRiby52d0NhbmRpZGF0b3MKQVMKU0VMRUNUCkNvZGlnbyBBcyBDb2RpZ28sCk5vbWUgYXMgTm9tZSwKRGF0YV9OYXNjaW1lbnRvIEFzIER0X05hc2NpbWVudG8KRlJPTSBkYm8uQ2FuZGlkYXRvOwpnbwoK4oCUIERlY2xhcmFuZG8gZXh0ZXJuYW1lbnRlIG9zIEFMSUFTIHBhcmEgYXMgY29sdW5hcwpBTFRFUiBWSUVXIGRiby52d0NhbmRpZGF0b3MgKENvZGlnbywgTm9tZSwgRHRfTmFzY2ltZW50bykKQVMKU0VMRUNUCkNvZGlnbywKTm9tZSwKRGF0YV9OYXNjaW1lbnRvCkZST00gZGJvLkNhbmRpZGF0bzsKZ28=[/et_pb_dmb_code_snippet]

Execute novamente a sp abaixo e veja que o problema foi resolvido.

[et_pb_dmb_code_snippet _builder_version=”4.0.6″ code=”ZXhlYyBkYm8udXNwT2J0ZXJDYW5kaWRhdG9z” hover_enabled=”0″]ZXhlYyBkYm8udXNwT2J0ZXJDYW5kaWRhdG9z[/et_pb_dmb_code_snippet]

A adoção deste tipo de abordagem diminui intervenções em aplicações e ou objetos que consomem uma view. A mesma estratégia pode ser aplicada em SP’s que retornem  result set ou em TVF’s – Table Valued Functions (funções que retornam tabelas).Ainda vale destacar o uso da opção SCHEMABINDING. Ao usarmos tal opção o DBA simplesmente não conseguiria alterar a estrutura da tabela, vez que a opção SCHEMABINDING “prende” a tabela à view ou a function (não existe opção SCHEMABINDING em SP), produzindo uma dependência que não pode ser quebrada. Neste caso, o DBA precisaria alterar a view/function e remover a opção SCHEMABINDING para, em seguida, alterar a tabela.

Conclusão
No próximo post falaremos a respeito das considerações de segurança no projeto de views. Até lá.