Posts com Tag ‘sqlserver’

Recentemente ao realizar o acerto dos datafiles do tempdb em meus ambientes 2012+ me deparei com uma situação de erro onde eu não me deparo quando realizo a mesma tarefa em meus ambientes 2008/R2.

Ao executar o comando abaixo:


alter database tempdb remove file temp03

Retornou o seguinte erro:

Msg 5042, Level 16, State 1, Line 2
The file ‘temp03’ cannot be removed because it is not empty.

Como as mensagens de erro no SQL Server são claras, executei:


USE tempdb
GO
DBCC SHRINKFILE(temp03,EMPTYFILE)

E então me retornou o erro abaixo:

DBCC SHRINKFILE: Page 3:32 could not be moved because it is a work table page.
Msg 2555, Level 16, State 1, Line 4
Cannot move all contents of file “temp03” to other places to complete the emptyfile operation.
DBCC execution completed. If DBCC printed error messages, contact your system administrator.

Pesquisando, eu encontrei algumas formas para contornar esse problema da remoção dos datafiles do tempdb.

Primeiramente, vamos analisar como está feita a distribuição dos meus arquivos do tempdb e vamos a uma das soluções.

Arquivos do tempdb

Atualmente meu tempdb está com três arquivos de dados e eu quero deixá-lo com dois arquivos de dados e um de log.

tempdb

Solução: Habilitando Trace Flag 3608

Para esse post eu estou usando SQL Server 2017 Developer Edition.

Uma das possíveis soluções para contornar esse comportamento é iniciar a instância com a TF 3608.

A TF 3608 faz com que não ocorra o start e recovery de nenhuma base exceto a master. Nessa situação as bases de dados só passarão pelo start e recovery ao serem acessadas e com isso é possível executar o comando de exclusão dos arquivos do tempb sem receber o erro The file xxx cannot be removed because it is not empty”.

Referência: https://docs.microsoft.com/en-us/sql/t-sql/database-console-commands/dbcc-traceon-trace-flags-transact-sql?view=sql-server-2017

Obs: importante realizar essa operação com em ambiente controlado sem nenhum acesso além do seu, pois se alguma sessão usar o tempdb o recovery será executado e não será possível realizar a exclusão do arquivo.

Habilitando a TF 3608

A primeira coisa a fazer é acessar o SQL Server Configuration Manager, ir nas propriedades do serviço do SQL Server e selecionar a aba Startup Parameter.

SQLServerConfigurationManagerStartupParameter

No campo Specify a startup parameter adicione o parâmetro -T3608 e clique no botão Add.

3608

Feito isso, basta dar stop/start no serviço do SQL Server.

Com o SQL Server iniciado, podemos observar que a engine fez o recovery apenas na base de dados master.

errorlog3608

Com isso podemos observar que ao listar os arquivos do tempdb novamente, apenas os arquivos padrão de quando o SQL Server foi instalado será listado.

tempdb3608

Porém se listarmos os arquivos do tempdb pela sys.master_files iremos observar que os demais arquivos estão configurados, porém como o tempdb não foi realizado o recovery eles não estão em uso.

sysmasterfile3608

Feito os passos acima agora conseguimos realizar a exclusão dos arquivos do tempdb que queremos.

tempdb_removefile

Agora basta retirarmos a TD 3608 e dar stop/start no serviço do SQL Server para comprovarmos a remoção do arquivo temp03 de fato e ver que sem a TF 3608 todas as bases são startadas e o recovery é feito.

tempdb files

tempdb2

errorlog

errorlog_sem3608

Bom pessoal, espero que isso possa ajudá-los no dia a dia. Logo mais postarei uma segunda forma de contornar esse comportamento que começou no SQL Server 2012 e até onde eu pesquisei não encontrei o motivo dessa mudança de comportamento.

Olá pessoal,

Dias atrás meu amigo Leandro Ribeiro (blog | twitter) solicitou no Twitter dicas sobre o banco de dados do Protheus e como eu presto consultoria em banco de dados e muitos dos clientes trabalham com esse produto, resolvi compartilhar essas dicas para quem está começando agora a atuar com esse produto.

Para quem não conhece o Protheus é um ERP desenvolvido pela fabricante TOTVS e é um dos líderes de mercado no Brasil. Um diferencial do Protheus é que além dele atender diversos ramos de atividade do mercado brasileiro ele pode ser totalmente customizável. Muitos dos problemas de performance que ocorrem no banco de dados do Protheus está relacionado as customizações.

Vamos as dicas:

  1. Quase sempre o banco de dados se chama DADOSADV ou pelo menos começa com DADOS, isso não é uma regra mas é o que eu costumo encontrar em meus clientes;
  2. A aplicação não acessa o banco de dados diretamente ela usa uma camada intermediária chamada Top Connect. O Top quase sempre é instalado no mesmo servidor que o banco de dados, porém há casos em que ele é instalado em uma máquina exclusiva e então a aplicação se conecta ao Top e o Top faz a conexão com o banco de dados. Devido a essa camada intermediária entre aplicação e banco de dados o Protheus trabalhar com várias tecnologias de banco de dados;
  3. O Protheus é um produto multi empresa, porém ao contrário do que estamos acostumado a ver nas modelagens onde a empresa é distinguida por um campo  identificador, no banco de dados do Protheus para cada empresa será criada uma tabela de produto, uma de cliente, uma de nota fiscal e assim suscetivamente até a versão 10 do Protheus. Imaginem isso para uma holding com mais de 100 empresas.
  4. A partir da versão 11 do Protheus é possível criar as empresas dentro da mesma tabela o que diminui significativamente o número de tabelas dentro do banco de dados.
  5. O nome das tabelas não ultrapassam 6 caracteres e são representados da seguinte maneira:
    • 3 primeiros caracteres representa a família da tabela.
      • Ex: SA1(Cliente) ou SA2(Fornecedor)
    • 2 próximos caracteres representa a empresa que a tabela pertence.
      • Ex: 01(empresa 1), 02(empresa 2) ou 99(empresa 99)
    • O último caractere é reservado ao sistema.
  6. A chave primária das tabelas é sempre o mesmo que é o R_E_C_N_O_ e é auto incrementado pelo próprio Top Connect;
  7. Os registros das tabelas nunca são deletados fisicamente. Todas as tabelas contém um campo chamado D_E_L_E_T_ e quando um registro é excluído no sistema, esse campo é preenchido com um literal “*”.
    • Dica: Ao fazer um SELECT lembrem-se de colocar na condição where D_E_L_E_T_ = ” ou D_E_L_E_T_ <> ‘*’
  8. Não existe campo DATETIME nas tabelas. Todos os campo data são VARCHAR(8), nunca são nulos e são sempre preenchidos com 8 caracteres em branco para informar que estão vazios;
    • Devido esse comportamento a compressão de dados vai muito bem 🙂
  9. Não existe valor NULL. Se o campo for numérico ele é preenchido com zero e se for String/Char é preenchido com espaços em branco. Em ambos os casos o preenchimento é feito via Constraint Default. Agora imaginem a quantidade de Constraint que cada tabela tem;
  10. Muito cuidado ao criar índices nas tabelas, pois se você criar em uma terá que criar em todas, por exemplo: Se criar um índice na tabela de cliente SA1XX0 lembre-se de replicar esse índice para as demais tabelas de cliente caso tenha;
  11. O Protheus trabalha com um dicionário de dados próprio onde são definidas as tabelas, campos e índices então em uma atualização de versão é feita uma checagem do dicionário de dados com a estrutura do banco de dados e tudo que não estiver definido no dicionário será apagado, seja campo, índice ou tabela, portanto ao criar um índice utilizado em um trabalho de Tuning é recomendado criar uma rotina que revalide se os índices customizados existem e caso não exista  recrie-os.
  12. Caso seja um campo em uma tabela sem estar no dicionário de dados do Protheus, ao abrir uma tela que use a tabela onde o campo foi criado, essa tela irá travar por não existir o campo no dicionário, portanto muito cuidado;
  13. O desempenho das queries do Protheus não é o forte da ferramenta, então há muita oportunidade de Tuning;
  14. Uma forma de ganhar espaço em disco com o banco do Protheus é usar a compressão de dados a nível de página caso o SQL Server seja Enterprise. Em testes realizados na tabela SB1(Produtos) com 28000 produtos, comprimindo apenas a tabela passou de 72 MB para 6 MB, ou seja, uma taxa de compressão de 91.66%;
  15. Os bancos geralmente são enormes então é válido pensar em uma estratégia de particionamento das tabelas, para facilitar o gerenciamento;
  16. Índices não utilizados para leitura e duplicados é quase uma regra, então é válido fazer uma análise dos índices que não são utilizados para leitura e alinhar com o time de desenvolvimento.
    • Nunca apague um índice sem antes apagar no dicionário, pois as telas fazem essa verificação também em sua abertura e caso não encontre no banco as telas irão travar;
  17. O Top Connect não funciona em cluster devido ao hardlock que é quem licencia o Protheus e como em alguns casos ele é instalado no mesmo servidor do banco de dados, não será possível colocar ele no Service and Application do Cluster e quando ocorrer um Failover será necessário reiniciar o servidor de licença que normalmente está em outro servidor;
  18. Não é possível fazer uma replicação merge das tabelas, devido fato da replicação merge adicionar um campo de controle de unicidade chamado rowguid e caso tenha um campo na tabela do banco e não tenha no dicionário do Protheus isso causa sérios impactos. Mesmo que não houvesse o impeditivo do campo rowguid, muitas tabelas ultrapassam 246 colunas e seria impossível replicar com merge devido o limite de 246 colunas por artigo;
  19. Devido o padrão das tabelas do Protheus não terem campos NULL e todos serem preenchidos com uma Constraint Default isso impede que as tabelas sejam colocadas In-Memory;
  20. Normalmente os bancos são muito grandes, então a rotina de manutenção de índices se torna uma tarefa árdua e difícil. Para esses casos eu costumo usar as rotinas de manutenção do Ola Hallengren.

Espero que essas dicas sejam úteis. Conforme eu for me lembrando de mais coisas eu vou atualizando o post.

Até mais.