AskOverflow.Dev

AskOverflow.Dev Logo AskOverflow.Dev Logo

AskOverflow.Dev Navigation

  • Início
  • system&network
  • Ubuntu
  • Unix
  • DBA
  • Computer
  • Coding
  • LangChain

Mobile menu

Close
  • Início
  • system&network
    • Recentes
    • Highest score
    • tags
  • Ubuntu
    • Recentes
    • Highest score
    • tags
  • Unix
    • Recentes
    • tags
  • DBA
    • Recentes
    • tags
  • Computer
    • Recentes
    • tags
  • Coding
    • Recentes
    • tags
Início / user-5273

Heinzi's questions

Martin Hope
Heinzi
Asked: 2021-09-18 06:37:17 +0800 CST

Função OBJECT_ID(...) vs junção em sys.tables e sys.schemas

  • 2

Ao consultar metadados para uma tabela específica, posso

  1. use a OBJECT_IDfunção ou
  2. juntar as tabelas de sistema relevantes ( sys.tablese sys.schemas).

Por exemplo, ambas as consultas retornarão todos os gatilhos DML para table myTable:

SELECT *
  FROM sys.triggers AS t
 WHERE t.parent_id = OBJECT_ID('[dbo].[myTable]', 'U')

SELECT *
  FROM sys.triggers AS tr
       INNER JOIN sys.tables AS tab ON tr.parent_id = tab.object_id 
       INNER JOIN sys.schemas AS s ON tab.schema_id = s.schema_id 
 WHERE s.name = 'dbo' AND tab.name = 'myTable';

É puramente uma questão de gosto, ou há uma boa razão para preferir um ao outro (se ambos resolverem seu problema)?

Minha análise preliminar é que:

  • A opção 1 é mais curta (obviamente).
  • Com a Opção 2, não preciso me preocupar em citar/escapar o nome da tabela/esquema (se contiver caracteres especiais).
  • Os planos de consulta são diferentes (mas é improvável que façam uma grande diferença, já que essa não é uma operação que pretendo fazer com frequência).

Eu perdi alguma coisa importante?

sql-server metadata
  • 1 respostas
  • 343 Views
Martin Hope
Heinzi
Asked: 2020-04-28 02:28:48 +0800 CST

SQL Server 2019 executa código inacessível

  • 34

[Atualização: esta pergunta descreve um bug que foi corrigido na atualização cumulativa 5 para SQL Server 2019. ]


Considere o seguinte exemplo de reprodução ( fiddle ):

CREATE FUNCTION dbo.Repro (@myYear int)
RETURNS datetime
AS
BEGIN
    IF @myYear <> 1990
    BEGIN
        RETURN NULL
    END

    DECLARE @firstOfYear datetime;
    SET @firstOfYear = DATEFROMPARTS(@myYear, 1, 1);
    
    IF DATEDIFF(day, @firstOfYear, @firstOfYear) <> 0
    BEGIN
        RETURN NULL
    END

    RETURN @firstOfYear
END
SELECT dbo.Repro(0);

Obviamente, essa função deve retornar o primeiro de janeiro de 1990 se a entrada for 1990, e NULLcaso contrário. Sim, eu sei que DATEDIFF(day, @firstOfYear, @firstOfYear) <> 0é uma operação sem sentido. Este é um mcve para demonstrar um possível bug, não o código de produção.

Agora vamos executar SELECT dbo.Repro(0)no SQL Server 2017 e SQL Server 2019.

Resultado esperado : NULL.

Resultado real no SQL Server 2017 :NULL

Resultado real no SQL Server 2019 :

Msg 289 Nível 16 Estado 1 Linha 1
Não é possível construir o tipo de dados data, alguns dos argumentos possuem valores que não são válidos.

Aparentemente, o SQL Server 2019 executa parte do código abaixo da cláusula de guarda inicial ( IF @myYear <> 1990), mesmo que não devesse.

Minhas perguntas:

  • Esse comportamento é esperado ou encontrei um bug no SQL Server 2019?
  • Se esse for o comportamento esperado, como escrever corretamente uma cláusula de guarda validando os parâmetros de entrada?
sql-server functions
  • 1 respostas
  • 2394 Views
Martin Hope
Heinzi
Asked: 2019-03-30 06:27:07 +0800 CST

Soma não determinística de floats

  • 11

Deixe-me dizer o primeiro: eu entendo completamente que os tipos de ponto flutuante não podem representar valores decimais com precisão . Não se trata disso! No entanto, os cálculos de ponto flutuante devem ser determinísticos .

Agora que isso está resolvido, deixe-me mostrar o caso curioso que observei hoje. Eu tenho uma lista de valores de ponto flutuante e quero resumi-los:

CREATE TABLE #someFloats (val float);
INSERT INTO #someFloats (val) VALUES (1), (1), (1.2), (1.2), (1.2), (3), (5);

SELECT STR(SUM(#someFloats.val), 30, 15) FROM #someFloats;

DROP TABLE #someFloats;

-- yields:
--   13.600000000000001

Até agora, tudo bem - sem surpresas aqui. Todos nós sabemos que isso 1.2não pode ser representado exatamente em representação binária, então o resultado "impreciso" é esperado.

Agora, a seguinte coisa estranha acontece quando eu saio de outra tabela:

CREATE TABLE #A (a int);
INSERT INTO #A (a) VALUES (1), (2);

CREATE TABLE #someFloats (val float);
INSERT INTO #someFloats (val) VALUES (1), (1), (1.2), (1.2), (1.2), (3), (5);

SELECT #A.a, STR(SUM(#someFloats.val), 30, 15)
  FROM #someFloats LEFT JOIN #A ON 1 = 1
 GROUP BY #A.a;

DROP TABLE #someFloats;
DROP TABLE #A;

-- yields
--   1   13.600000000000001
--   2   13.599999999999998

( sql fiddle , você também pode ver o plano de execução lá)

Eu tenho a mesma soma sobre os mesmos valores, mas um erro de ponto flutuante diferente . Se eu adicionar mais linhas à tabela #A, podemos ver que o valor alterna entre esses dois valores. Só consegui reproduzir esse problema com um LEFT JOIN; INNER JOINfunciona como esperado aqui.

Isso é inconveniente, porque significa que a DISTINCT, GROUP BYou PIVOTos vê como valores diferentes (que é realmente como descobrimos esse problema).

A solução óbvia é arredondar o valor, mas estou curioso: existe uma explicação lógica para esse comportamento?

sql-server floating-point
  • 1 respostas
  • 1366 Views
Martin Hope
Heinzi
Asked: 2018-07-18 05:03:29 +0800 CST

A resiliência a falhas do SQL Server pode ser melhorada?

  • 23

Temos PCs com SQL Server (2008 SP4 e 2016 SP1) que perdem energia regularmente. Obviamente, isso às vezes leva à corrupção (índice) do banco de dados SQL Server, que precisamos restaurar posteriormente.

Estou ciente de que o SQL Server não foi projetado para esses cenários e a solução correta é corrigir a causa da perda de energia (mais sobre isso abaixo, se você estiver curioso). No entanto, existem opções de ajuste no SQL Server que eu possa definir para reduzir o risco de corrupção do banco de dados na perda de energia ?


Background: O "PC" é um tablet Windows montado em uma empilhadeira. Quando o usuário desliga a empilhadeira, o tablet fica sem energia. Tentamos ensinar os usuários a desligar corretamente o Windows antes de desligar a empilhadeira, mas falhamos (provavelmente porque apenas desligá-lo "funciona" na maioria das vezes). No momento, também estamos investigando outras opções, como adicionar um no-break que avisa o tablet para desligar em caso de perda de energia.

sql-server crash
  • 5 respostas
  • 4218 Views
Martin Hope
Heinzi
Asked: 2018-06-09 01:53:20 +0800 CST

O SQL Server divide A <> B em A < B OR A > B, produzindo resultados estranhos se B não for determinístico

  • 26

Encontramos um problema interessante com o SQL Server. Considere o seguinte exemplo de reprodução:

CREATE TABLE #test (s_guid uniqueidentifier PRIMARY KEY);
INSERT INTO #test (s_guid) VALUES ('7E28EFF8-A80A-45E4-BFE0-C13989D69618');

SELECT s_guid FROM #test
WHERE s_guid = '7E28EFF8-A80A-45E4-BFE0-C13989D69618'
  AND s_guid <> NEWID();

DROP TABLE #test;

violino

Por favor, esqueça por um momento que a s_guid <> NEWID()condição parece totalmente inútil - este é apenas um exemplo mínimo de reprodução. Como a probabilidade de NEWID()corresponder a um determinado valor constante é extremamente pequena, ela deve ser avaliada como TRUE todas as vezes.

Mas não. A execução dessa consulta geralmente retorna 1 linha, mas às vezes (com bastante frequência, mais de 1 vez em 10) retorna 0 linhas. Eu o reproduzi com o SQL Server 2008 no meu sistema e você pode reproduzi-lo on-line com o violino vinculado acima (SQL Server 2014).

Observar o plano de execução revela que o analisador de consultas aparentemente divide a condição em s_guid < NEWID() OR s_guid > NEWID():

captura de tela do plano de consulta

...o que explica completamente por que às vezes falha (se o primeiro ID gerado for menor e o segundo maior que o ID fornecido).

O SQL Server tem permissão para avaliar A <> Bcomo A < B OR A > B, mesmo se uma das expressões não for determinística? Se sim, onde está documentado? Ou encontramos um bug?

Curiosamente, AND NOT (s_guid = NEWID())produz o mesmo plano de execução (e o mesmo resultado aleatório).

Encontramos esse problema quando um desenvolvedor queria excluir opcionalmente uma linha específica e usou:

s_guid <> ISNULL(@someParameter, NEWID())

como um "atalho" para:

(@someParameter IS NULL OR s_guid <> @someParameter)

Estou procurando documentação e/ou confirmação de um bug. O código não é tão relevante, portanto, não são necessárias soluções alternativas.

sql-server optimization
  • 3 respostas
  • 1414 Views
Martin Hope
Heinzi
Asked: 2018-02-28 02:27:05 +0800 CST

sp_cursoropen escolhe um plano de execução terrível

  • 2

Se eu executar minha consulta (simples) diretamente no SQL Server Management Studio...

SELECT auftrag_prod_soll.ID 
  FROM auftrag_prod_soll 
 WHERE auftrag_prod_soll.auftrag_produktion = 51621 
   AND auftrag_prod_soll.prod_soll_über = 539363
 ORDER BY auftrag_prod_soll.reihenfolge

... está tudo bem e rápido ...

Table 'auftrag_prod_soll'. Scan count 2, logical reads 6, physical reads 0, read-ahead reads 0, lob logical reads 0, lob physical reads 0, lob read-ahead reads 0.

SQL Server Execution Times:
  CPU time = 0 ms,  elapsed time = 102 ms.

...porque o SQL Server escolhe um plano de execução sensato com base nos dois critérios de filtragem:

Boa


Por outro lado, se meu aplicativo executa a mesma consulta com um cursor...

declare @p1 int
declare @p3 int
set @p3=4
declare @p4 int
set @p4=1
declare @p5 int
set @p5=-1
exec sp_cursoropen @p1 output,N' SELECT auftrag_prod_soll.ID  FROM auftrag_prod_soll  WHERE auftrag_prod_soll.auftrag_produktion =  51621   AND auftrag_prod_soll.prod_soll_über =  539363 ORDER BY auftrag_prod_soll.reihenfolge',@p3 output,@p4 output,@p5 output

exec sp_cursorfetch @p1,2,0,1

exec sp_cursorclose @p1

... o desempenho é terrível ...

Table 'auftrag_prod_soll'. Scan count 1, logical reads 1118354, physical reads 0, read-ahead reads 0, lob logical reads 0, lob physical reads 0, lob read-ahead reads 0.

SQL Server Execution Times:
  CPU time = 1094 ms,  elapsed time = 1231 ms.

...porque o SQL Server escolhe um plano de execução terrível:

mau


Eu sei que posso contornar isso usando uma dica de índice. No entanto, quero entender por que isso acontece.

Eu tentei:

  • DBCC FREEPROCCACHE
  • UPDATE STATISTICS auftrag_prod_soll

mas não fez diferença.

Também observei os histogramas dos dois índices em prod_soll_über e auftrag_produktion: Eles são bem distribuídos, portanto o SQL Server deve ser capaz de deduzir que a consulta retornará no máximo algumas linhas e, assim, a pesquisa de chave e a operação de classificação ser muito mais rápido do que a varredura de índice.

Também tentei criar um índice não clusterizado contendo auftrag_produktion e prod_soll_über, mas isso não alterou o plano de execução do cursor (mas tornou a consulta direta ainda mais rápida).


Aqui está a definição completa da tabela, caso seja relevante:

CREATE TABLE [auftrag_prod_soll](
    [auftrag_produktion] [int] NULL,
    [losgrößenunabh] [smallint] NOT NULL,
    [stückliste_vorh] [smallint] NOT NULL,
    [erledigt] [smallint] NOT NULL,
    [ext_wert_ueberst] [smallint] NOT NULL,
    [ID] [int] IDENTITY(1,1) NOT NULL,
    [prod_soll_über] [int] NULL,
    [artikel] [int] NULL,
    [gesamtmenge_soll] [float] NULL,
    [produktionstext] [nvarchar](max) NULL,
    [reihenfolge] [int] NULL,
    [reihenfolge_druck] [int] NULL,
    [infkst_unter] [int] NULL,
    [ebene] [smallint] NULL,
    [bezeichnung] [varchar](50) NULL,
    [extern_text] [nvarchar](max) NULL,
    [intern_preis] [float] NULL,
    [intern_wert] [float] NULL,
    [extern_preis] [float] NULL,
    [extern_wert] [float] NULL,
    [extern_proz] [float] NULL,
    [dummyfeld] [varchar](50) NULL,
    [mengeneinheit] [varchar](50) NULL,
    [artikel_art] [smallint] NULL,
    [s_insert] [float] NULL,
    [s_update] [float] NULL,
    [s_user] [varchar](255) NULL,
    [preiseinheit] [float] NULL,
    [memo] [nvarchar](max) NULL,
    [lager_nummer] [int] NULL,
    [zweitmenge] [float] NULL,
    [zweit_einheit] [float] NULL,
    [zweit_mengeneinh] [varchar](50) NULL,
    [kst_preis1] [float] NULL,
    [kst_preis2] [float] NULL,
    [kst_preis3] [float] NULL,
    [kst_preis4] [float] NULL,
    [p_position] [int] NULL,
    [zeilen_status] [int] NULL,
    [fs_adresse_lief] [uniqueidentifier] NULL,
    [t_artikel_stückliste] [int] NULL,
    [div_text1] [varchar](255) NULL,
    [div_text2] [varchar](255) NULL,
    [menge_urspr] [float] NULL,
    [fs_artikel_index] [uniqueidentifier] NULL,
    [s_guid] [uniqueidentifier] ROWGUIDCOL  NOT NULL,
    [gemein_kosten] [float] NULL,
    [fs_leistung] [uniqueidentifier] NULL,
    [sonderlogik_ok_rech] [smallint] NOT NULL,
    [sonderlogik_ok_manuell] [int] NULL,
    [menge_inkl_frei] [float] NULL,
    [art_einheit] [int] NULL,
    [drittmenge] [float] NULL,
 CONSTRAINT [PK__auftrag_prod_sol__50E5F592] PRIMARY KEY CLUSTERED ([ID] ASC)
) 

CREATE NONCLUSTERED INDEX [artikel] ON [auftrag_prod_soll] ([artikel] ASC)
CREATE NONCLUSTERED INDEX [auftrag_produktion] ON [auftrag_prod_soll] ([auftrag_produktion] ASC)
CREATE NONCLUSTERED INDEX [dummyfeld] ON [auftrag_prod_soll] ([dummyfeld] ASC)
CREATE NONCLUSTERED INDEX [fs_adresse_lief] ON [auftrag_prod_soll] ([fs_adresse_lief] ASC)
CREATE NONCLUSTERED INDEX [fs_artikel_index] ON [auftrag_prod_soll] ([fs_artikel_index] ASC)
CREATE NONCLUSTERED INDEX [fs_leistung] ON [auftrag_prod_soll] ([fs_leistung] ASC)
CREATE NONCLUSTERED INDEX [lager_nummer] ON [auftrag_prod_soll] ([lager_nummer] ASC)
CREATE NONCLUSTERED INDEX [prod_soll_über] ON [auftrag_prod_soll] ([prod_soll_über] ASC)
CREATE NONCLUSTERED INDEX [reihenfolge] ON [auftrag_prod_soll] ([reihenfolge] ASC)
CREATE UNIQUE NONCLUSTERED INDEX [s_guid] ON [auftrag_prod_soll] ([s_guid] ASC)
CREATE NONCLUSTERED INDEX [s_insert] ON [auftrag_prod_soll] ([s_insert] ASC)
CREATE NONCLUSTERED INDEX [u_test] ON [auftrag_prod_soll] ([auftrag_produktion] ASC,
    [prod_soll_über] ASC)
CREATE NONCLUSTERED INDEX [zeilen_status] ON [auftrag_prod_soll] ([zeilen_status] ASC)
ALTER TABLE [auftrag_prod_soll] ADD  DEFAULT ((0)) FOR [losgrößenunabh]
ALTER TABLE [auftrag_prod_soll] ADD  DEFAULT ((0)) FOR [stückliste_vorh]
ALTER TABLE [auftrag_prod_soll] ADD  DEFAULT ((0)) FOR [erledigt]
ALTER TABLE [auftrag_prod_soll] ADD  DEFAULT ((0)) FOR [ext_wert_ueberst]
ALTER TABLE [auftrag_prod_soll] ADD  CONSTRAINT [DF__auftrag_p__s_gui__28A2FA0E]  DEFAULT (newid()) FOR [s_guid]
ALTER TABLE [auftrag_prod_soll] ADD  DEFAULT ((0)) FOR [sonderlogik_ok_rech]

Como posso ajudar o SQL Server a encontrar o bom plano de consulta, mesmo que os cursores sejam usados?

Eu "consertei" temporariamente esse problema desabilitando o índice "reihenfolge", mas ainda quero entender por que isso acontece, para evitar tais problemas no futuro.

Os valores de @p3, @p4, e @p5permanecem em seus valores iniciais (4, 1, -1) após a chamada para sp_cursoropen, mas assim que eu "resolvo" o problema removendo o índice reihenfolge, eles mudam para (1, 1, 0) .

sql-server performance
  • 2 respostas
  • 1022 Views
Martin Hope
Heinzi
Asked: 2017-09-28 01:40:49 +0800 CST

INSERT e UPDATE "não relacionados" bloqueando um ao outro

  • 4

Cenário de reprodução:

CREATE TABLE test (
  ID int IDENTITY(1,1),
  mykey nvarchar(255) NOT NULL,
  exp_date datetime,
PRIMARY KEY (ID));
GO

CREATE INDEX not_expired_keys ON test (exp_date, mykey);

INSERT INTO test (mykey, exp_date) VALUES ('A', NULL);

Eu começo a transação 1:

-- add key B
BEGIN TRANSACTION;
INSERT INTO test (mykey, exp_date) VALUES ('B', NULL);
...

e, em seguida, execute a transação 2 em paralelo:

-- expire key A
BEGIN TRANSACTION;
UPDATE test SET exp_date = GETDATE() WHERE exp_date IS NULL AND mykey = 'A'; -- <-- Blocking
ROLLBACK;

Como se vê, o INSERT não confirmado da transação 1 bloqueia o UPDATE da transação 2, mesmo que eles afetem conjuntos disjuntos de linhas ( mykey = 'B'vs. mykey = 'A').

Observações:

  • O bloqueio também ocorre no nível de isolamento de transação mais baixo READ UNCOMMITTED.
  • O bloqueio desaparece se eu colocar um índice exclusivo em mykey. Infelizmente, não posso fazer isso, pois os nomes das chaves podem ser reutilizados quando uma chave expira.

Minhas perguntas:

  • (Por curiosidade:) Por que essas declarações bloqueiam umas às outras mesmo no READ UNCOMMITTEDnível?

  • Existe uma maneira fácil e confiável de fazer com que eles não se bloqueiem?

sql-server locking
  • 2 respostas
  • 2677 Views
Martin Hope
Heinzi
Asked: 2017-06-03 04:57:36 +0800 CST

Como faço para traduzir um SID do Windows para um server_user_sid do SQL Server?

  • 8

Existe essa função do SQL Server SUSER_SNAMEque traduz um server_user_sid para um nome de usuário. Isso é útil para traduzir SIDs do Windows conhecidos para nomes de usuário (potencialmente localizados).

Exemplo:

SELECT SUSER_SNAME(0x01020000000000052000000021020000)

-- yields 'BUILTIN\USERS' (or, on a German system, 'VORDEFINIERT\Benutzer')

Com alguma pesquisa no Google e tentativa e erro (= criar o usuário manualmente e verificar sys.server_principalsdepois), determinei as seguintes equivalências:

Built-in User/Group    Windows SID      SQL Server server_user_sid

BUILTIN\USERS          S-1-5-32-545     0x01020000000000052000000021020000
NT AUTHORITY\SYSTEM    S-1-5-18         0x010100000000000512000000

Qual é o algoritmo para converter SIDs do Windows em server_user_sids do SQL Server?

sql-server windows
  • 2 respostas
  • 13080 Views
Martin Hope
Heinzi
Asked: 2017-05-27 05:20:49 +0800 CST

Por que é recomendado armazenar BLOBs em tabelas separadas do SQL Server?

  • 32

Esta resposta SO altamente votada recomenda colocar imagens em tabelas separadas, mesmo que haja apenas uma relação 1:1 com outra tabela:

Se você decidir colocar suas imagens em uma tabela do SQL Server, eu recomendo usar uma tabela separada para armazenar essas imagens - não armazene a foto do funcionário na tabela do funcionário - mantenha-as em uma tabela separada. Dessa forma, a tabela Employee pode permanecer enxuta, média e muito eficiente, supondo que você nem sempre precise selecionar a foto do funcionário também como parte de suas consultas.

Por quê? Fiquei com a impressão de que o SQL Server armazena apenas um ponteiro para alguma estrutura de dados BLOB dedicada na tabela, então por que se preocupar em criar manualmente outra camada de indireção? Realmente melhora o desempenho significativamente? Se sim, por quê?

sql-server blob
  • 3 respostas
  • 24374 Views
Martin Hope
Heinzi
Asked: 2017-04-11 04:53:59 +0800 CST

Como cancelo uma solicitação de bloqueio de aplicativo no SQL Server?

  • 25

O procedimento armazenado sp_getapplock tem os seguintes valores de retorno:

0: O bloqueio foi concedido com sucesso de forma síncrona.
1: O bloqueio foi concedido com sucesso após aguardar a liberação de outros bloqueios incompatíveis.
-1: A solicitação de bloqueio expirou.
-2: A solicitação de bloqueio foi cancelada.
-3: A solicitação de bloqueio foi escolhida como vítima de deadlock.
-999: Indica uma validação de parâmetro ou outro erro de chamada.

Estou escrevendo um wrapper para chamar sp_getapplocknossa camada de acesso a dados e quero saber em quais circunstâncias -2 pode ser retornado para que eu possa lançar uma exceção descritiva e útil. É óbvio o que os valores de retorno de -1 e -3 significam e posso facilmente criar condições de teste que fazem com que esses valores sejam retornados. Como eu conseguiria obter um valor de retorno de -2?

sql-server locking
  • 3 respostas
  • 2928 Views
Martin Hope
Heinzi
Asked: 2016-03-22 03:38:38 +0800 CST

Pesquise com eficiência um intervalo de prefixo no SQL Server

  • 4

Digamos que eu queira todos os registros com um prefixo entre dois valores alfanuméricos fornecidos pelo usuário com o mesmo comprimento. Assim, se o usuário digitar A010e A025, quero retornar A0101, A0200e A0259.

O que eu tentei:

  1. Obviamente, não posso usar WHERE myText BETWEEN @from and @to, porque isso não retornará A0259.

  2. Tecnicamente, WHERE LEFT(myText, @len) BETWEEN @from AND @toseria exatamente o que eu quero, mas isso mata o SARGability .

  3. Eu poderia usar WHERE myText BETWEEN @from and @to + 'zzzzzzzzzzz', mas esse é um hack feio e potencialmente sujeito a erros. (É zrealmente o caractere mais alto? Usei caracteres de "preenchimento" suficientes?)

  4. Eu poderia "explodir" o intervalo e procurar todos os prefixos possíveis, por exemplo WHERE (myText LIKE 'A01%' OR myText LIKE 'A020%' OR myText LIKE 'A021%' ...), mas isso dá muito trabalho.

Existe alguma solução inteligente que eu perdi? Provavelmente usarei a opção 3 para resolver o problema (já que sei sobre o comprimento e o intervalo de caracteres permitidos), mas estou curioso sobre o caso geral.

sql-server performance
  • 1 respostas
  • 393 Views
Martin Hope
Heinzi
Asked: 2015-11-28 00:58:15 +0800 CST

Violação repentina de PRIMARY KEY na coluna IDENTITY

  • 7

Eu tenho uma logtabela com uma IDcoluna de identidade. Tudo funciona bem por anos; então, ontem, vejo o seguinte erro nos logs:

A instrução foi encerrada.
Violação da restrição PRIMARY KEY 'PK__log__ID__3B40CD36'. Não é possível inserir chave duplicada no objeto 'dbo.log'. O valor da chave duplicada é (295992).

INSERT INTO log (datum, zeit, benutzer, modul, prozedur, code, zeile, bez1, bez2, tech_info) VALUES ('20151126 00:00:00.000', '19000101 18:26:45.121', 'Customer', '' , '', 'WShop-Trans', 0, '1 Datensätze für Tabelle adresse gesendet.', '', '')

Eu verifiquei a semente IDENTITY e parece OK:

Consulta: DBCC CHECKIDENT(log)

Resultado: Verificando informações de identidade: valor de identidade atual '296021', valor de coluna atual '296021'.
Execução DBCC concluída. Se o DBCC imprimir mensagens de erro, entre em contato com o administrador do sistema.

Consulta: SELECT MAX(ID) FROM log

Resultado: 296021

Não há gatilhos na tabela e ninguém está mexendo com os valores iniciais (sou eu quem administra o servidor de banco de dados, então tenho certeza disso).

Até agora, este é um evento único e não posso reproduzi-lo.

Parece apenas uma falha do SQL Server, mas estou curioso: isso é um bug conhecido ou existe alguma outra explicação plausível para isso? A versão do SQL Server é Microsoft SQL Server 2012 - 11.0.2100.60 (X64).

Para completar, aqui está o script de tabela completo:

CREATE TABLE [log](
    [datum] [datetime] NULL,
    [ID] [int] IDENTITY(1,1) NOT NULL,
    [zeit] [datetime] NULL,
    [benutzer] [varchar](255) NULL,
    [modul] [varchar](255) NULL,
    [prozedur] [varchar](255) NULL,
    [code] [varchar](255) NULL,
    [zeile] [int] NULL,
    [bez1] [text] NULL,
    [bez2] [text] NULL,
    [tech_info] [text] NULL,
    [pc_name] [varchar](255) NULL,
    [app_name] [varchar](255) NULL,
    [s_insert_user] [nvarchar](255) NULL,
    [s_insert_dat] [datetime] NULL,
    [s_update_user] [nvarchar](255) NULL,
    [s_update_dat] [datetime] NULL,
    [fs_mandant] [uniqueidentifier] NULL,
 CONSTRAINT [PK__log__ID__3B40CD36] PRIMARY KEY CLUSTERED ([ID] ASC)
)

CREATE NONCLUSTERED INDEX [code] ON [log] ([code] ASC)
CREATE NONCLUSTERED INDEX [datum_zeit] ON [log] ([datum] ASC, [zeit] ASC)
CREATE NONCLUSTERED INDEX [fs_mandant] ON [log] ([fs_mandant] ASC)
CREATE NONCLUSTERED INDEX [modul] ON [log] ([modul] ASC)
sql-server sql-server-2012
  • 1 respostas
  • 5600 Views
Martin Hope
Heinzi
Asked: 2015-08-25 05:39:59 +0800 CST

"Especificar administradores do SQL Server" - valor padrão incomum

  • 3

Ao instalar o SQL Server, você especifica os administradores do SQL Server , ou seja, a lista de usuários inicialmente na função sysadmin. Por padrão, esta lista contém o usuário atual.

Configuração do mecanismo de banco de dados

(Imagem citada em https://msdn.microsoft.com/en-us/library/dd578652.aspx .)

Esse valor padrão me parece estranho. Não BUILTIN\Administratorsseria uma escolha mais sensata do que o usuário atual? Afinal, o objetivo da autenticação do Windows não é não ter que gerenciar dois diretórios de usuários/grupos separados? E os administradores locais podem obter direitos de administrador de sistema de qualquer maneira, se quiserem, portanto, também não é realmente um recurso de segurança.

Por outro lado, o SQL Server foi escrito por pessoas muito mais inteligentes do que eu, portanto, pode haver uma boa razão para esse valor padrão. O que é isso?

sql-server permissions
  • 3 respostas
  • 3062 Views
Martin Hope
Heinzi
Asked: 2015-07-28 05:29:41 +0800 CST

Estatísticas que não são criadas automaticamente nem criadas pelo usuário

  • 2

Até agora, eu tinha a impressão de que existem dois tipos de objetos estatísticos no SQL Server:

  • estatísticas criadas automaticamente , que são criadas pelo SQL Server em colunas de índice ou colunas únicas para melhorar o desempenho e

  • estatísticas criadas pelo usuário , que são criadas manualmente com uma CREATE STATISTICSinstrução.

Assim, fiquei bastante surpreso ao ver a seguinte consulta:

SELECT s.name, s.stats_id, s.auto_created, s.user_created
  FROM sys.stats AS s
       INNER JOIN sys.stats_columns AS sc ON s.object_id = sc.object_id AND s.stats_id = sc.stats_id
       INNER JOIN sys.columns AS c ON sc.object_id = c.object_id AND sc.column_id = c.column_id
       INNER JOIN sys.tables AS t ON c.object_id = t.object_id
 WHERE t.name = 'mytable'

dê o seguinte resultado:

name                    stats_id   auto_created   user_created
--------------------------------------------------------------
PK__mytable__7A73B1B8       1          0              0
SomeIndex                   2          0              0
SomeIndexedColumn1          3          0              0
SomeIndexedColumn2          4          0              0
SomeIndexedColumn3          5          0              0
SomeColumn                  6          0              1

Quais são essas estatísticas, que não são nem auto_created nem user_created? Eu olhei a documentação de sys.stats , mas não encontrei uma resposta lá.

sql-server statistics
  • 2 respostas
  • 358 Views
Martin Hope
Heinzi
Asked: 2014-08-23 00:13:13 +0800 CST

Que relevância tem a configuração ANSI_NULL em nível de tabela?

  • 1

Aparentemente, o SQL Server armazena a configuração ANSI_NULL atual ao criar uma tabela (consulte as perguntas relacionadas aqui e aqui ).

No entanto, quando eu executo

SELECT * FROM myVeryOldTable WHERE someFieldWithNullValues = NULL

Obtenho zero resultados, mesmo que a tabela antiga tenha sido criada com ANSI_NULL OFF . Portanto, aparentemente, o SQL Server usa a configuração de conexão atual , que é ANSI_NULL ON.

Se for esse o caso, que diferença faz a configuração armazenada na tabela (exceto para causar problemas em vários casos)? Por que ele é armazenado, se a configuração da conexão sempre substitui a configuração da mesa?

sql-server t-sql
  • 1 respostas
  • 134 Views
Martin Hope
Heinzi
Asked: 2013-11-07 02:50:49 +0800 CST

O NOT IN deve ser evitado?

  • 14

Entre alguns desenvolvedores do SQL Server, é uma crença amplamente aceita que NOT INé terrivelmente lento e as consultas devem ser reescritas para que retornem o mesmo resultado, mas não usem as palavras-chave "malvadas". ( exemplo ).

Há alguma verdade nisso?

NOT INExiste, por exemplo, algum bug conhecido no SQL Server (qual versão?)

  • a LEFT JOINcombinado com um NULLcheque ou
  • (SELECT COUNT(*) ...) = 0na WHEREcláusula?
sql-server performance
  • 1 respostas
  • 398 Views
Martin Hope
Heinzi
Asked: 2013-06-07 07:14:57 +0800 CST

Posso dizer ao SQL Server para "fazer algo" quando uma conexão é fechada?

  • 4

Posso dizer ao SQL Server para "fazer algo" (por exemplo, liberar um bloqueio no nível do aplicativo ) quando a conexão for fechada por qualquer motivo?


Histórico : desejo bloquear um registro no nível do aplicativo , não no nível do banco de dados. No entanto, estou tendo problemas para liberar o bloqueio quando o aplicativo trava. Basicamente, estou implementando o seguinte algoritmo em meu aplicativo:

function editRecord(recordId):
    begin transaction
    if (select lockedBy from myTable where id = recordId) is not empty:
        commit
        show "Sorry, record already in use by ..."
    else
        update myTable set lockedBy = current_user() where id = recordId
        commit
        show UI window to let user edit and update record
        update myTablet set lockedBy = empty where id = recordId

Estou tentando descobrir se existe uma maneira fácil de se livrar do bloqueio no nível do aplicativo quando a conexão falha.

sql-server locking
  • 1 respostas
  • 449 Views
Martin Hope
Heinzi
Asked: 2012-10-18 04:29:10 +0800 CST

GROUP BY em um campo dependente

  • 5

Digamos que eu tenha uma instrução SELECT da seguinte forma:

SELECT ..., field1
  FROM ...
 GROUP BY field1

Agora digamos que eu queira retornar um segundo campo, field2. Acontece que campo2 é funcionalmente dependente de campo1 (por exemplo, campo1 e campo2 podem ser da mesma tabela e campo1 é a chave primária dessa tabela). Agora tenho duas maneiras equivalentes de adicionar field2 à consulta:

Opção 1:

SELECT ..., field1, field2
  FROM ...
 GROUP BY field1, field2

Opção 2:

SELECT ..., field1, MIN(field2)  /* or some other, arbitrary aggregate function */
  FROM ...
 GROUP BY field1

Novamente, como field2 depende funcionalmente de field1, ambas as consultas devem retornar o mesmo conjunto de resultados.

Existem boas razões para preferir uma opção sobre a outra?

aggregate group-by
  • 1 respostas
  • 442 Views
Martin Hope
Heinzi
Asked: 2012-10-05 08:49:05 +0800 CST

Por que ANSI SQL define SUM (sem linhas) como NULL?

  • 30

O padrão ANSI SQL define (capítulo 6.5, especificação de função definida) o seguinte comportamento para funções agregadas em conjuntos de resultados vazios:

COUNT(...) = 0
AVG(...) = NULL
MIN(...) = NULL
MAX(...) = NULL
SUM(...) = NULL

Retornar NULL para AVG, MIN e MAX faz todo o sentido, já que a média, mínimo e máximo de um conjunto vazio é indefinido.

A última, porém, me incomoda: Matematicamente, a SOMA de um conjunto vazio está bem definida: 0. Usando 0, o elemento neutro da adição, como o caso base torna tudo consistente:

SUM({})        = 0    = 0
SUM({5})       = 5    = 0 + 5
SUM({5, 3})    = 8    = 0 + 5 + 3
SUM({5, NULL}) = NULL = 0 + 5 + NULL

Definir SUM({})como nullbasicamente torna "sem linhas" um caso especial que não se encaixa nos outros:

SUM({})     = NULL  = NULL
SUM({5})    = 5    != NULL + 5 (= NULL)
SUM({5, 3}) = 8    != NULL + 5 + 3 (= NULL)

Existe alguma vantagem óbvia da escolha que foi feita (SUM sendo NULL) que eu perdi?

null aggregate
  • 3 respostas
  • 7346 Views
Martin Hope
Heinzi
Asked: 2012-05-17 05:09:14 +0800 CST

Como descubro *por que* um usuário tem certas permissões efetivas?

  • 15

Eu sei que posso consultar permissões efetivas usando sys.fn_my_permissions:

USE myDatabase;
SELECT * FROM fn_my_permissions('dbo.myTable', 'OBJECT') 

 entity_name | subentity_name | permission_name 
------------------------------------------------
 dbo.myTable |                | SELECT          
 dbo.myTable |                | UPDATE          
 ...

Isso me diz se o usuário atual tem permissões SELECT, INSERT, UPDATE, etc. myTableno banco de dados myDatabase.

É possível descobrir facilmente por que o usuário tem essas permissões? Por exemplo, eu adoraria ter uma função fn_my_permissions_exque gerasse uma reasoncoluna adicional:

USE myDatabase;
SELECT * FROM fn_my_permissions_ex('dbo.myTable', 'OBJECT') 

 entity_name | subentity_name | permission_name | reason
------------------------------------------------------------------------------------------------------------------------------------
 dbo.myTable |                | SELECT          | granted to database role public
 dbo.myTable |                | UPDATE          | member of group MYDOMAIN\Superusers, which belongs to database role db_datawriter
 ...

Infelizmente, não consegui encontrar essa função na documentação do SQL Server. Existe uma ferramenta ou script que fornece essa funcionalidade?

sql-server security
  • 1 respostas
  • 4489 Views

Sidebar

Stats

  • Perguntas 205573
  • respostas 270741
  • best respostas 135370
  • utilizador 68524
  • Highest score
  • respostas
  • Marko Smith

    conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host

    • 12 respostas
  • Marko Smith

    Como fazer a saída do sqlplus aparecer em uma linha?

    • 3 respostas
  • Marko Smith

    Selecione qual tem data máxima ou data mais recente

    • 3 respostas
  • Marko Smith

    Como faço para listar todos os esquemas no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Listar todas as colunas de uma tabela especificada

    • 5 respostas
  • Marko Smith

    Como usar o sqlplus para se conectar a um banco de dados Oracle localizado em outro host sem modificar meu próprio tnsnames.ora

    • 4 respostas
  • Marko Smith

    Como você mysqldump tabela (s) específica (s)?

    • 4 respostas
  • Marko Smith

    Listar os privilégios do banco de dados usando o psql

    • 10 respostas
  • Marko Smith

    Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL?

    • 4 respostas
  • Marko Smith

    Como faço para listar todos os bancos de dados e tabelas usando o psql?

    • 7 respostas
  • Martin Hope
    Jin conectar ao servidor PostgreSQL: FATAL: nenhuma entrada pg_hba.conf para o host 2014-12-02 02:54:58 +0800 CST
  • Martin Hope
    Stéphane Como faço para listar todos os esquemas no PostgreSQL? 2013-04-16 11:19:16 +0800 CST
  • Martin Hope
    Mike Walsh Por que o log de transações continua crescendo ou fica sem espaço? 2012-12-05 18:11:22 +0800 CST
  • Martin Hope
    Stephane Rolland Listar todas as colunas de uma tabela especificada 2012-08-14 04:44:44 +0800 CST
  • Martin Hope
    haxney O MySQL pode realizar consultas razoavelmente em bilhões de linhas? 2012-07-03 11:36:13 +0800 CST
  • Martin Hope
    qazwsx Como posso monitorar o andamento de uma importação de um arquivo .sql grande? 2012-05-03 08:54:41 +0800 CST
  • Martin Hope
    markdorison Como você mysqldump tabela (s) específica (s)? 2011-12-17 12:39:37 +0800 CST
  • Martin Hope
    Jonas Como posso cronometrar consultas SQL usando psql? 2011-06-04 02:22:54 +0800 CST
  • Martin Hope
    Jonas Como inserir valores em uma tabela de uma consulta de seleção no PostgreSQL? 2011-05-28 00:33:05 +0800 CST
  • Martin Hope
    Jonas Como faço para listar todos os bancos de dados e tabelas usando o psql? 2011-02-18 00:45:49 +0800 CST

Hot tag

sql-server mysql postgresql sql-server-2014 sql-server-2016 oracle sql-server-2008 database-design query-performance sql-server-2017

Explore

  • Início
  • Perguntas
    • Recentes
    • Highest score
  • tag
  • help

Footer

AskOverflow.Dev

About Us

  • About Us
  • Contact Us

Legal Stuff

  • Privacy Policy

Language

  • Pt
  • Server
  • Unix

© 2023 AskOverflow.DEV All Rights Reserve