Posso forçar as consultas de um usuário a sempre serem executadas com a dica NOLOCK? por exemplo, eles digitam
select * from customer
Mas o que é executado no servidor é
select * from customer with (nolock)
Esta pergunta não é:
Sobre os vários prós e contras do NOLOCK, respeitosamente. Eu sei o que são, este não é o lugar para discuti-los.
A verdadeira resposta é:
Pare de usar NOLOCK
OUTRAS INFORMAÇÕES QUE PODEM SER ÚTEIS:
Claro, negue o acesso direto às tabelas/exibições e imponha o acesso aos dados por meio de procedimentos armazenados (ou exibições - obrigado Martin) - que você pode codificar para usar
NOLOCK
.Se você precisa que seja por usuário e pode impor o acesso aos dados por meio de procedimentos, pode usar a ideia sugerida aqui por SQLMenace :
Ou você também pode fazer isso:
Se isso não for possível, pensei em sugerir um guia de plano , mas não os usei para fazer valer
NOLOCK
. Além disso , este documento nos Manuais Online sugere que isso é reservado paraINDEX
,FORCESCAN
eFORCESEEK
dicas. Usar um guia de plano para tentar adicionarNOLOCK
se ainda não estiver presente no texto da consulta levará a um erro. No entanto, o código mostrado no Exemplo K parece contradizer isso, então talvez valha a pena tentar, afinal. Obviamente, você precisará definir um guia de plano para cada consulta, o que pode ser proibitivo (ou impossível) e não é exatamente para os fracos de coração.E eu sei que você não quer ouvir os contras de
NOLOCK
, mas seria muito mais fácil (e melhor!) Forçar todos a usar o snapshot.Para abordar a sugestão de Kenneth de usar um gatilho de logon: em meus testes, essa opção SET pode ser especificada em um gatilho de logon, mas, como defini-la em um procedimento armazenado, a configuração reverte para o padrão do servidor quando o gatilho sai do escopo. Portanto, não parece haver uma maneira de definir o nível de isolamento de uma sessão de um gatilho de logon.
Como outros já disseram: não use NOLOCK quer queira quer não. Há certos momentos em que é apropriado, e 'cada consulta de um usuário específico' provavelmente não é um deles. Use uma das opções melhores e mais seguras para lidar com a simultaneidade, ou seu LART favorito se você tiver um DBA/desenvolvedor rotineiramente sobrecarregando o sistema de produção com consultas terríveis.
Sim, você pode ajustar a segurança para que eles possam selecionar apenas a partir de exibições que selecionam tabelas de base com dicas NOLOCK, e posso imaginar algumas situações em que isso pode ser necessário (a equipe de suporte operacional precisa examinar ocasionalmente os dados de produção em tempo real, talvez com algumas informações/colunas confidenciais omitidas também).
Mas considere esta discussão semelhante:
"Como posso levar meu carro até o terceiro andar?"
"Por que você gostaria de fazer isso?"
Se a resposta for "Porque minha empresa fica no terceiro andar e preciso exibir o carro para uma promoção / sorteio", comece a procurar maneiras de colocá-lo lá em cima.
Mas se a resposta for "Porque eu gostaria de ir para casa, para meu apartamento no terceiro andar", então a recomendação adequada é "Estacione o carro no estacionamento, saia e pegue o elevador até o terceiro andar".
Não transforme suposições e preconceitos em requisitos técnicos e não se prenda à sua primeira tentativa de solução. Dê um passo para trás e reavalie o que você deseja realizar.
Parece que o mais próximo que você pode obter sem usar SPs é usar
SET READ_COMMITTED_SNAPSHOT
, o que afetará todos os usuários do banco de dados.A
READ_COMMITTED_SNAPSHOT
opção de banco de dados controla se o nível de isolamentoREAD_COMMITTED
é implementado como suas contrapartes em PostgreSQL e FirebirdSQL (instantâneo de registros em nível de instrução) ou usando bloqueio. Leia mais sobre isso na documentação:Bloqueio e controle de versão de linha
Você comentou em resposta a outra resposta:
Você deve certificar-se de que todas as instalações estão definidas como Read Uncommitted em Tools/Options/Query Execution/SQL Server/Advanced. Eu não sou um SysAdmin de rede, então não sei se uma política pode resolver isso.
Semelhante à opção Database Snapshot ou com um espelho de relatório, mas que tal usar AlwaysOn e roteamento somente leitura com o SQL 2012? Você pode redirecionar uma conexão para o secundário legível por meio da faceta ApplicationIntent=ReadOnly da string de conexão.
Faça com que seu aplicativo determine a cadeia de conexão, dependendo do nome do usuário, para que seja completamente transparente para o usuário. O secundário é mantido relativamente atualizado, dependendo da latência, sem a sobrecarga de manter um instantâneo do banco de dados.
Cenário 1 O usuário sênior efetua login no aplicativo, o aplicativo determina que o usuário deve ter permissão de leitura/gravação. String de conexão criada para o banco de dados primário.
Cenário 2 O usuário efetua login no aplicativo, o aplicativo determina que o usuário deve ter permissão somente leitura. Cadeia de conexão criada incluindo ApplicatonIntent=ReadOnly. Conexão feita ao banco de dados secundário legível. Se a atividade de gravação for necessária, será necessária uma conexão separada com o primário.
Ouvintes de grupo de disponibilidade, conectividade de cliente e failover de aplicativo http://msdn.microsoft.com/en-us/library/hh213417.aspx#connecttosecondary