Qual o impacto do meu script?

Às vezes pode não parecer, mas tudo dentro de um banco de dados está interligado. Quando pensamos em interligações, é comum lembrar de duas tabelas associadas por uma chave estrangeira ou Foreign Key. No entanto, esta é apenas uma das possíveis relações de dependência dentro do SQL Server. Assim como no caso de uma FK, os objetos envolvidos numa relação de dependência podem ser afetados caso ocorra alguma alteração, seja nos objetos que dependem deles, seja nos objetos dos quais eles dependem. Vejamos um exemplo:

CREATE DATABASE DB1;
GO

USE DB1;
-- Cria uma tabela Tab1
CREATE TABLE dbo.Tab1 (id INT IDENTITY,col1 INT DEFAULT 99);
INSERT INTO dbo.Tab1 DEFAULT VALUES;
GO
-- Cria uma função func1 que depende de Tab1
CREATE FUNCTION dbo.func1 (@id INT)
RETURNS INT AS
BEGIN
DECLARE @col INT;
SELECT @col = col1 FROM dbo.Tab1 WHERE id = @id;
RETURN(@col);
END
GO
-- Cria a procedure sp1 que depende de func1
CREATE PROCEDURE dbo.sp1 (@id INT)
AS
BEGIN
SELECT dbo.func1(@id) + 1;
END
GO

Em nosso DB1, temos uma relação de dependência dos objetos. Então, caso ocorra uma alteração na tabela “dbo.Tab1” onde o nome da coluna “col1” seja alterado para “col2”, a função escalar “dbo.func1” deixará de funcionar e, por sua vez, a procedure “dbo.sp1” também deixará de funcionar. No entanto, a alteração poderia ser na função. Supondo que a função mude sua quantidade de parâmetros, nada será afetado na tabela “Tab1”, mas a procedure não funcionará mais.

Para uma base simples como esta, fica fácil observar esta relação entre os objetos. Já numa base com milhares de objetos, onde alguns deles se relacionam com objetos de outras bases (dependência cross database), esta não é uma tarefa trivial. Vejamos algumas formas de tornar esta verificação mais prática.

Método 1 – Object Explorer

A forma mais prática para verificar a relação de dependência entre os objetos é através do Object Explorer do SSMS. Basta abrir as pastas até o objeto que você quer avaliar, clicar com o botão direito e depois ir em “View Dependencies”.

img01

Assim, será aberta uma janela com duas opções. A primeira, selecionada por padrão, mostra os objetos que dependem de “Tab1”. Expandi o nó em “func1” para mostrar que “sp1” também depende de “Tab1” através da função. Na outra opção, “Objects on which [Tab1] depends”, são listados os objetos dos quais a “Tab1” depende e, neste caso, sabemos que esta tabela não depende de nenhum outro objeto.

img02

O principal ponto positivo deste método é a identificação de toda a relação de dependência. No entanto, além da permissão de SELECT na DMV “sys.sql_expression_dependencies [1]”, é necessária a permissão VIEW DEFINITION [2] em todos os bancos de dados que são referenciados por estes objetos e isso nem sempre é possível. Isso nos leva ao método 2.

Método 2 – T-SQL

Este método é documentado no Books Online [1] e traz dois scripts que servem como as duas opções do método anterior. Então, para retornar os objetos que dependem de “func1”, basta executar:

USE DB1;
GO
SELECT
OBJECT_SCHEMA_NAME ( referencing_id ) AS referencing_schema_name,
OBJECT_NAME(referencing_id) AS referencing_entity_name,
o.type_desc AS referencing_desciption,
COALESCE(COL_NAME(referencing_id, referencing_minor_id), '(n/a)') AS referencing_minor_id,
referencing_class_desc, referenced_class_desc,
referenced_server_name, referenced_database_name, referenced_schema_name,
referenced_entity_name,
COALESCE(COL_NAME(referenced_id, referenced_minor_id), '(n/a)') AS referenced_column_name,
is_caller_dependent, is_ambiguous
FROM sys.sql_expression_dependencies AS sed
INNER JOIN sys.objects AS o ON sed.referencing_id = o.object_id
WHERE referenced_id = OBJECT_ID(N'dbo.func1');
GO

Como resultado, temos o seguinte:

img03

O layout do resultado foi ajustado para caber na página e mostrar as informações interessantes. Na imagem acima, vemos que a procedure “sp1” faz referência à função. Para verificar quais objetos são referenciados por “func1”, ou seja, os objetos dos quais a função depende, executamos o seguinte script:

USE DB1;
GO
SELECT
OBJECT_NAME(referencing_id) AS referencing_entity_name,
o.type_desc AS referencing_desciption,
COALESCE(COL_NAME(referencing_id, referencing_minor_id), '(n/a)') AS referencing_minor_id,
referencing_class_desc,
referenced_server_name, referenced_database_name, referenced_schema_name,
referenced_entity_name,
COALESCE(COL_NAME(referenced_id, referenced_minor_id), '(n/a)') AS referenced_column_name,
is_caller_dependent, is_ambiguous
FROM sys.sql_expression_dependencies AS sed
INNER JOIN sys.objects AS o ON sed.referencing_id = o.object_id
WHERE referencing_id = OBJECT_ID(N'dbo.func1');
GO

Como esperado, o resultado é o seguinte:

img04

Assim vemos que “func1” depende de (ou faz referência à) “Tab1”. Vale lembrar que este método não irá listar toda a relação de dependência, mas apenas a relação direta de referências. Desta forma podemos verificar e saber qual será o impacto da mudança que teremos de fazer.

Próximos Passos

Agora que já sabemos quais objetos serão afetados com as alterações que faremos, precisamos tomar algumas providências como:

  • Entrar em contato com os responsáveis pelos objetos afetados conversando sobre as mudanças necessárias e os possíveis impactos;
  • Documentar as alterações necessárias juntamente com o objeto registrando quais foram as alterações, onde ocorreram, quando ocorreram e quem foi o autor da alteração;
  • Após a alteração do objeto no ambiente de desenvolvimento, realizar testes rigorosos tanto do objeto alterado como dos objetos afetados.

Desta forma, realizamos manutenções de código e alterações de objetos de uma maneira mais consciente e controlada. Lembre-se, o próximo código a quebrar pode ser o seu.

Links:

[1] sys.sql_expression_dependencies

[2] VIEW DEFINITION

 

O Caso dos Schedulers Off-line

Alta utilização de CPU nunca é legal… E como um DBA preguiçoso proativo, é interessante sempre manter esse contador sob controle. No entanto, vira e mexe e aparece um novo procedimento, um cubo ou um deploy da morte que te obriga a realizar uma análise do que está errado. Hoje eu não falarei exatamente sobre a causa deste problema, mas sobre o que o troubleshooting revelou.

O ambiente analisado é um servidor de relatórios que fora migrado recentemente do 2008 R2 para o 2014. Após algumas (poucas) batalhas com o novo Cardinality Estimator, os problemas de desempenho haviam sido sanados e nada mais foi relatado. Isso até o próximo deploy, claro.

Quando o comportamento não usual foi identificado, a consulta culpada foi isolada e mandada de volta para o desenvolvimento. No entanto, algo me deixou curioso sobre esse comportamento: Sempre que o procedimento era disparado, a CPU oscilava, mas nunca ultrapassava a linha de 75~77%. Nesse momento, abri o task manager e vi o seguinte:

CPU Usage

Ué… Só 20 das 26 CPUs estavam trabalhando. Isso geralmente é problema. Então, fui direto na DMV sys.dm_os_schedulers pra investigar e me deparei com isso:

schedulers

What the f…? Seis dos schedulers estão off-line! Como eu sei exatamente o que significa que o scheduler está visível e off-line, fui ao BOL e lá você encontra o seguinte:

OFFLINE schedulers map to processors that are offline in the affinity mask and are, therefore, not being used to process any requests. ONLINE schedulers map to processors that are online in the affinity mask and are available to process threads.

Cara… Alguém mexeu no affinity mask [1] desta instância?! Que mente diabólica arquitetaria plano tão maligno?! Fui confirmar a configuração do mal e…

affinity

Não tou entendendo mais nada… Nesta hora você recorre ao único cara que nunca te esconde nada, o errorlog. E, usando seu novo melhor amigo “Get-SqlErrorLog”:

errorlog

Ok. Este servidor nunca teve problema de licenciamento… Por que ela está sendo limitado a 20 processadores agora? Aí, você sabe que terá de consultar o oráculo. Meio minuto se passa e você descobre através de vários blog posts [2][3] que, desde o SQL Server 2012, o licenciamento mudou e o tipo de licença CAL até permite que seja realizado o upgrade do seu SQL Server Enterprise, mas o limita a 20 processadores lógicos.

Mas é claro que você já sabia disso. Obviamente, você leu isso durante o processo de planejamento da migração de versão, né…?! Não. Eu não li. Se você leu, deixa um recado na sessão de comentários. Quero estudar você ser seu amigo bater um papo contigo.

Enfim, este novo licenciamento parece ter pegado muita gente de surpresa e pode até causar problemas de desempenho por desbalanceamento dos schedulers entre os NUMA nodes [4]!

Então, depois desse post, espero que você entenda a importância do licenciamento e leia sobre todas as suas nuances para cada nova versão do SQL Server.

E, por favor, depois me conte.

[]’s

Links:

[1] affinity mask Server Configuration Option

[2] A cautionary tale about grandfathering CAL licenses in SQL Server 2012 Enterprise

[3] SQL SERVER – Using 20 Logical Processors Based on SQL Server Licensing

[4] Performance Problems with SQL Server 2012 Enterprise Edition Under CAL Licensing

Encontro SQL Server DF XXXIV – Material

Dia 12/07/2016 aconteceu mais um encontro do grupo SQLServerDF! Neste 34º encontro, falei um pouco a nova feature do SQL Server 2016: Always Encrypted.

Titulo

Apesar de um imprevisto com uma VM ter atrapalhado algumas demos, consegui mostrar o comportamento deste recurso tanto em memória como na rede. Isso é sempre divertido!

Agradeço a presença de todos e todo o feedback que recebi!

Segue o link com o material da apresentação, divirta-se!

https://drive.google.com/folderview?id=0B2dIfMDfAh7JQWlaZHBOSW8yczQ&usp=sharing

 

Encontro SQL Server DF XXXIV

Depois de um longo e tenebroso inverno, um post breve para avisar sobre o trigésimo quarto encontro do grupo SQL Server DF, o Local Chapter de Brasília, um dos mais (se não o mais) ativos do Brasil.

Dia 29/06/2016, tivemos o encontro de número 33 com uma excelente apresentação do Rodrigo Gomes (blog|twitter) intitulada “SQL Server CPU Foundations”. Esta sessão, que ele também realizou no SQL Saturday #512 no Rio de Janeiro, entrega de uma forma simples e clara algumas definições e diferentes métricas acerca do tema CPU. Recomendo à todos que tenham a oportunidade.

O evento que acontecerá dia 12/07/2016 é a edição de número 34 e eu estarei lá falando um pouco sobre Always Encrypted. Veremos como funciona esta nova feature do SQL Server 2016 e implantaremos ela simulando um ambiente real de cliente/servidor. Também pretendo mostrar como os novos cmdlets de Always Encrypted da atualização de Julho do SSMS facilitaram o trabalho na hora da criação das chaves. Ainda iremos ver como se comportam os dados criptografados tanto na rede como em memória.

Quando e onde será?

  • Data e Hora: 12/07/2016, das 18:30 às 20:30;
  • Local: Xperts Training Center (SHIS QI 15, Área Especial Subsolo, Conjunto 8/9, Próximo ao Hospital Brasília).

Demais detalhes podem ser encontrados no anúncio do encontro no blog do Luti.

Espero vocês lá!

Os números de 2015

Depois de mais um ano de blog, muito conteúdo que julgamos interessante foi compartilhado gratuitamente. Esperamos que tenham gostado de nos acompanhar assim como gostamos de escrever para vocês. Agora é mandar ver em 2016!

Os duendes de estatísticas do WordPress.com prepararam um relatório para o ano de 2015 deste blog. Para os interessados no progresso do blog, vale comparar com os números de 2014!

Aqui está um resumo:

Um comboio do metrô de Nova Iorque transporta 1.200 pessoas. Este blog foi visitado cerca de 4.600 vezes em 2015. Se fosse um comboio, eram precisas 4 viagens para que toda gente o visitasse.

Clique aqui para ver o relatório completo

SQL Family e minha primeira palestra

Quando você começa a participar da comunidade SQL Server (pois é, tem o trocadilho com o nome do blog também! ops… =) uma das primeiras coisas que nota é como todos são amigáveis. É claro que todos também são muito prestativos com qualquer tipo de dúvida e querem dividir o que sabem pelo simples prazer de compartilhar, mas todos são notavelmente amistosos.

Quando assisti minha primeira sessão no SQL Server DF (grupo local), pensei que havia algum tipo de pegadinha. No primeiro momento em que me distraísse, haveria um time vendedores em cima de mim. Como poderia ser diferente? Tanto conhecimento sendo dividido com tanta qualidade e gratuitamente num ambiente bem descontraído?

Posso ter sido azarado, mas minha primeira experiência com banco de dados foi enquanto ainda era estagiário e qualquer pergunta que fazia ao sempre emburrado DBA era respondida laconicamente. Cada pedaço de informação era obtido através de uma série exaustiva de perguntas respondidas impacientemente com o mínimo de detalhes possível.

Então, quando tive oportunidade de fazer parte da comunidade técnica e aprender com especialistas sobre os mais diversos assuntos, agarrei esta chance com todas as minhas forças. “Ok, Gustavo e o que isso tem a ver com o título?!”

Acredito que no instante em que percebi este sentimento que o PASS tanto fala – Connect. Share. Learn -, senti o espírito de retribuição pelo que esta comunidade me ajudou. Com isso decidi submeter a minha sessão sobre replicação transacional (pare de fazer caretas) ao SQL Saturday #469 – DF e dividir um pouco sobre o pouco que sei.

Tirando todo o nervosismo – pavor e pânico -, minha primeira palestra foi bem legal pois pude contar com meus amigos Nane Flores (também autora deste blog), Renato Siqueira (blog|twitter), Sulamita Dantas (blog|twitter) e Patrocínio Maia (blog) para me dar apoio ou ao menos um rosto amigo sempre que precisei. Por isso, agradeço muito a vocês!

O evento foi perfeitamente organizado e todo suporte foi dado aos que participaram do evento e sei que todos os voluntários e palestrantes gostaram bastante. O engraçado é que por mais novo que eu seja dentro deste circulo de profissionais, todos me fazem sentir como membro desta SQL Family.

Deixo algumas fotos da minha palestra e do evento:

DSC07003

DSC07000.JPG

IMG_1488

IMG_1494.JPG

SQL Saturday #469 – Brasília

Boa noite!

No dia 21 de novembro (sábado agora!) ocorrerá o segundo SQL Saturday de Brasília na Faculdade Projeção. Ainda dá tempo de se inscrever! Basta acessar o site do evento e se cadastrar. O evento é completamente gratuito!

sqlsat469_header

O evento contará com 5 sessões simultâneas durante todo o dia falando sobre administração, desenvolvimento, BI, data science e muito mais!

A agenda completa você pode conferir abaixo:

SQLSaturday #469 - Brasilia 2015  Sessions  Schedule

Este evento também marca minha primeira oportunidade de palestrar para a comunidade técnica! Após enviar uma proposta de sessão à organização do evento, tive o imenso prazer de ser selecionado! Falarei um pouco sobre como configurar uma replicação transacional de forma bem prática.

Então, se estiver no Sat Brasília, apareça por lá!