Livro sobre as melhores práticas no redimensionamento e melhoramento da MS SQL Server BOX

Este é um dos projectos que tenho para este segundo semestre, o outro ainda é segredo provavelmente sobre o outro SGBDR, mas mais prático. Estes dois projectos serão de livre distribuição e em formato electrónico. Aliás a estruração e planificação dos mesmos manteram-me afastado da “lides” bloguistas.

João Paulino

Nota: Projecto alterado, aguardem as novidades!!!

João Paulino

Change Data Capture (CDC) chegou ao MS SQL Server na Versão 2008

CDC (Change Data Capture) é uma das novas e interessantes funcionalidades que chegou ao SQL Server (alguns de nós já a conhecíamos do ORACLE), permite detectar alterações (INSERT, DELETE, UPDATE) relativamente aos dados de uma tabela e replicá-las noutra tabela, sem recorrer aos tradicionais triggers ou outras metodologias mais rebuscadas.

MS SQL Server 2008 CDC
MS SQL Server 2008 CDC

 

 

Link

João Paulino

MS SQL Server versus Oracle Database, tão diferentes e ao mesmo tempo tão próximos (1.ª Parte)

Este artigo pretende alertar para o cumprimento de boas práticas ao nível de programação SQL nos seus dialectos T-SQL para o caso do MS SQL Server e PL/SQL para o caso do Oracle Database, independentemente do SGBDR, estas práticas têm elevadíssimos benefícios.

 

Boas práticas de codificação em SQL, são muitas vezes simplesmente ignoradas, mas originam imensos custos para o projecto, aplicação ou sistema e até para a organização.  

 

Na minha opinião, um Programador de SQL,  possuir esta qualidade ou mesmo habilidade é uma atitude orientada aos objectivos, alinhamento com as necessidades do cliente ou negócio, profissionalismo e um óptimo estilo de programação em SQL e seus dialectos.

 

E refiro-me concretamente, no caso do Oracle à utilização de BIND VARIABLES, são fundamentais para o desempenho de um sistema.

 

Para se entender melhor passarei a explicar.

 

Imagine uma aplicação que é alvo de milhares de instruções de SQL numa tabela de Base de Dados, como as apresentadas a seguir:

 

SELECT u_nome, p_nome, c_postal FROM t_fornecedor WHERE id_fornecedor = 10735;

SELECT u_nome, p_nome, c_postal FROM t_fornecedor WHERE id_fornecedor = 10840;

SELECT u_nome, p_nome, c_postal FROM t_fornecedor WHERE id_fornecedor = 10987;

 

Cada vez que a consulta é executada, o SGBDR Oracle primeiro analisa a SHARED POOL (zona de memória) a verificar se a instrução de SQL já foi alguma vez executada. Caso tenha já tenha sido executada, o plano de execução utilizado na anterior instância é reutilizado, e a instrução de SQL é executada.

 

No caso da instrução de SQL não ser encontrada na SHARED POOL, o SGBDR Oracle terá executar o processo de “parsing” ou seja análise da instrução de SQL e posteriormente realizar o estudo dos vários planos de execução para encontrar o melhor plano de acordo com as suas parametrizações, antes de executar a instrução propriamente dita. Este processo denomina-se “HARD PARSE”, e para uma Base de Dados OLTP (Online Transaction Processing) poderá consumir mais tempo do que a própria instrução de SQL.

 

Quando é procurada na SHARED POOL a exacta correspondência de uma instrução de SQL, só instruções exactamente iguais são consideradas. Se como no exemplo das Instruções SQL acima colocadas, forem submetidas instruções  de SQL únicas, em que o predicado da cláusula WHERE é sempre diferente (id_fornecedor = 10735, id_fornecedor = 10840, etc.) nunca será encontrada uma correspondência e será necessário realizar um “HARD PARSE”. O “HARD PARSE” é muito intensivo na utilização de CPU e envolve operações de como “LATCH” de chaves nas áreas de memórias partilhadas. Esta situação poderá não originar problemas num sistema com poucos dados e pouco solicitado, mas num sistema com bastantes dados, multi-utilizador e com muitas transacções e muitas delas distribuídas, poderá simplesmente colocá-lo de rastos, com centenas ou milhares de instruções a necessitarem de ser analisadas “HARD PARSE” em simultâneo. Associado a esta situação surge um problema, a contenção que é o resultado dos inúmeros “HARD PARSE” realizados, o “HARD PARSE” é imune a medidas reactivas tais como aumento da memória física, incremento do n.º de CPU’s e muitas outras mediadas de reacção. O “HARD PARSE” é um problema encontrado em muitos sistemas e aplicações empresariais.

 

A solução para este problema é a reutilização dos planos de execução, e esta pode ser alcançada recorrendo a “BIND VARIABLES”. As “BIND VARIABLES” não são mais nem menos do que variáveis de substituição que são colocadas nas posições dos literais (10735, 10840, 10987). Exemplo da mesma instrução, desta vez recorrendo a “BIND VARIABLE”:

 

SELECT u_nome, p_nome, c_postal FROM t_fornecedor WHERE id_fornecedor =: fornecedor_numero;

 

Exemplo de SQL PLUS

 

SQL> variable fornecedor_numero number

SQL> exec :fornecedor_numero := 10987

SQL> SELECT u_nome, p_nome, c_postal FROM t_fornecedor WHERE id_fornecedor =: fornecedor_numero;

 

É muito fácil implementar a utilização de “BIND VARIABLES” em Java, C++ C# ou mesmo em VB.net. E como disse no início este problema não é só para o SGDBR Oracle, acontece ao mesmo ao MS SQL Server ou qualquer outro SGDBR. O MS SQL Server e SQL Bind Parameters serão abordados na 2.ª parte.

 

Continua…

 

 João Paulino

Terminar com o SELECT COUNT(*) FROM schema_name.table_name

Esta simples instrução ( SELECT COUNT(*) FROM schema_name.table_name) para tabelas de pequena dimensão não tem grande impacto, mas para tabelas grandes é muito prejudicial ao desempenho. Recomendo vivamente que não o utilizem nestas situações, porque para obter o número de linhas é realizado um full table scan à tabela em questão.

Apresento aqui algumas alternativas:

SQL Server BOX

/*******************************************************************************/

SQL Server 2000 e 2005
SP_MSTABLESPACE ‘schema_name.table_name’;

SQL Server 2005
SELECT TOTAL_ROWS = SUM(P_ST.ROW_COUNT)
FROM   SYS.DM_DB_PARTITION_STATS P_ST
WHERE  OBJECT_NAME(OBJECT_ID) = ‘table_name’
AND (INDEX_ID < 2);

/*******************************************************************************/

Oracle BOX

/*******************************************************************************/

SELECT OWNER,
TABLE_NAME,
NUM_ROWS
FROM DBA_TABLES
WHERE TABLE_NAME = ‘table_name’
AND OWNER = ‘schema_name; 

/*******************************************************************************/

Nota:É imprescindível que as tabelas possuam estatísticas actualizadas. Senão não há alternativa ao SELECT COUNT(*) FROM schema_name.table_name ou seus derivados. Ou há SELECT COUNT(1) FROM FROM schema_name.table_name ou seus derivados, escolha um campo que seja índex e not null.

João Paulino

Oracle Data Guard versus Microsoft SQL Server 2005 Database Mirroring

Coloco aqui um link para um artigo, que de um modo mais ou menos imparcial ( É da Oracle) compara duas propostas de funcionalidades de ”High Availability” distintas, mas como finalidades semelhantes. http://www.oracle.com/technology/deploy/availability/htdocs/DataGuardDatabaseMirroring.html

João Paulino

Base de Dados Microsoft SQL Server e Segurança