Ошибка при вставке данных в неуникальный индекс.

У меня есть пакетное задание, которое синхронизирует данные между двумя идентичными базами данных, используя инструкцию MERGE. Иногда я получаю следующую ошибку: не может вставить строку повторяющегося ключа в объект 'dbo.MatchPlayerStatistics' с уникальным индексом 'IX_MatchPlayerStatistics_Player' . Это не имеет смысла, потому что IX_MatchPlayerStatistics_Player не является уникальным индексом, и я могу вставить те же самые данные вручную. Если я удаляю индекс, вставляю данные, а затем воссоздаю индекс, он работает нормально.

Почему возникает эта ошибка и как ее предотвратить?

Дополнительная информация

Сценарий создания таблицы следующий:

CREATE TABLE [dbo].[MatchPlayerStatistics](
    [ExternalID] [nvarchar](50) NULL,
    [ProviderID] [int] NOT NULL,
    [MatchID] [int] NOT NULL,
    [PlayerPersonID] [int] NOT NULL,
    [TeamID] [int] NOT NULL,
    [YellowCards] [smallint] NULL,
    [DoubleYellowCards] [smallint] NULL,
    [RedCards] [smallint] NULL,
    [Fouls] [smallint] NULL,
    [Goals] [smallint] NULL,
    [PenaltyGoals] [smallint] NULL,
    [PenaltiesMissed] [smallint] NULL,
    [PenaltiesSaved] [smallint] NULL,
    [Shots] [smallint] NULL,
    [Attacks] [smallint] NULL,
    [Corners] [smallint] NULL,
    [Offsides] [smallint] NULL,
    [Assists] [smallint] NULL,
    [OwnGoals] [smallint] NULL,
    [GoalsConcedeed] [smallint] NULL,
    [CreatedBy] [int] NOT NULL,
    [CreatedOn] [datetime] NOT NULL,
    [ModifiedBy] [int] NOT NULL,
    [ModifiedOn] [datetime] NOT NULL,
 CONSTRAINT [PK_MatchPlayerStatistics] PRIMARY KEY CLUSTERED 
(
    [ProviderID] ASC,
    [MatchID] ASC,
    [PlayerPersonID] ASC
)WITH (PAD_INDEX  = OFF, STATISTICS_NORECOMPUTE  = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS  = ON, ALLOW_PAGE_LOCKS  = ON) ON [PRIMARY]
) ON [PRIMARY]


CREATE NONCLUSTERED INDEX [IX_MatchPlayerStatistics_Player] ON [dbo].[MatchPlayerStatistics] 
(
    [ProviderID] ASC,
    [PlayerPersonID] ASC
)WITH (PAD_INDEX  = OFF, STATISTICS_NORECOMPUTE  = OFF, SORT_IN_TEMPDB = OFF, IGNORE_DUP_KEY = OFF, DROP_EXISTING = OFF, ONLINE = OFF, ALLOW_ROW_LOCKS  = ON, ALLOW_PAGE_LOCKS  = ON) ON [PRIMARY]

Оператор MERGE следующий:

MERGE MatchPlayerStatistics AS M
USING   (
    SELECT [ExternalID]
          ,[ProviderID]
          ,[MatchID]
          ,[PlayerPersonID]
          ,[TeamID]
          ,[YellowCards]
          ,[DoubleYellowCards]
          ,[RedCards]
          ,[Fouls]
          ,[Goals]
          ,[PenaltyGoals]
          ,[PenaltiesMissed]
          ,[PenaltiesSaved]
          ,[Shots]
          ,[Attacks]
          ,[Corners]
          ,[Offsides]
          ,[Assists]
          ,[OwnGoals]
          ,[GoalsConcedeed]
          ,[CreatedBy]
          ,[CreatedOn]
          ,[ModifiedBy]
          ,[ModifiedOn]
     FROM [Replication].MatchPlayerStatistics 
     WHERE ProviderID = 1 

        ) AS R
ON (M.MatchID = R.MatchID AND M.PlayerPersonID = R.PlayerPersonID  AND  M.ProviderID = R.ProviderID ) 
WHEN NOT MATCHED 
    THEN 
        INSERT  ([ExternalID]
                ,[ProviderID]
                ,[MatchID]
                ,[PlayerPersonID]
                ,[TeamID]
                ,[YellowCards]
                ,[DoubleYellowCards]
                ,[RedCards]
                ,[Fouls]
                ,[Goals]
                ,[PenaltyGoals]
                ,[PenaltiesMissed]
                ,[PenaltiesSaved]
                ,[Shots]
                ,[Attacks]
                ,[Corners]
                ,[Offsides]
                ,[Assists]
                ,[OwnGoals]
                ,[GoalsConcedeed]
                ,[CreatedBy]
                ,[CreatedOn]
                ,[ModifiedBy]
                ,[ModifiedOn])
         VALUES
               ( R.[ExternalID]
                ,R.[ProviderID]
                ,R.[MatchID]
                ,R.[PlayerPersonID]
                ,R.[TeamID]
                ,R.[YellowCards]
                ,R.[DoubleYellowCards]
                ,R.[RedCards]
                ,R.[Fouls]
                ,R.[Goals]
                ,R.[PenaltyGoals]
                ,R.[PenaltiesMissed]
                ,R.[PenaltiesSaved]
                ,R.[Shots]
                ,R.[Attacks]
                ,R.[Corners]
                ,R.[Offsides]
                ,R.[Assists]
                ,R.[OwnGoals]
                ,R.[GoalsConcedeed]
                ,R.[CreatedBy]
                ,R.[CreatedOn]
                ,R.[ModifiedBy]
                ,R.[ModifiedOn])


WHEN MATCHED 
    THEN 
        UPDATE 
               SET   [ExternalID] = R.[ExternalID]
                    ,[ProviderID] = R.[ProviderID]
                    ,[MatchID] = R.[MatchID]
                    ,[PlayerPersonID] = R.[PlayerPersonID]
                    ,[TeamID] = R.[TeamID]
                    ,[YellowCards] = R.[YellowCards]
                    ,[DoubleYellowCards] = R.[DoubleYellowCards]
                    ,[RedCards] = R.[RedCards]
                    ,[Fouls] = R.[Fouls]
                    ,[Goals] = R.[Goals]
                    ,[PenaltyGoals] = R.[PenaltyGoals]
                    ,[PenaltiesMissed] = R.[PenaltiesMissed]
                    ,[PenaltiesSaved] = R.[PenaltiesSaved]
                    ,[Shots] = R.[Shots]
                    ,[Attacks] = R.[Attacks]
                    ,[Corners] = R.[Corners]
                    ,[Offsides] = R.[Offsides]
                    ,[Assists] = R.[Assists]
                    ,[OwnGoals] = R.[OwnGoals]
                    ,[GoalsConcedeed] = R.[GoalsConcedeed]
                    ,[CreatedBy] = R.[CreatedBy]
                    ,[CreatedOn] = R.[CreatedOn]
                    ,[ModifiedBy] = R.[ModifiedBy]
                    ,[ModifiedOn] = R.[ModifiedOn]

WHEN NOT MATCHED BY SOURCE AND M.ProviderID = 1
    THEN DELETE;

[Репликация] Таблица .MatchPlayerStatistics является промежуточной таблицей, которая заполняется данными из таблицы [dbo] .MatchPlayerStatistics другой копии базы данных. Схема для всех этих таблиц одинакова.

1
задан Antoine Aubry 16 August 2010 в 10:26
поделиться

1 ответ

У меня есть одна идея - проверить, есть ли в таблице триггеры и не вставляется ли один из них в другую таблицу с уникальным индексом.

Глядя на ваш код, можно сделать совершенно безумную догадку. Вы используете IGNORE_DUP_KEY = OFF, который обычно используется только для уникальных ограничений, поэтому мне интересно, считает ли он это уникальным ограничением даже без уникального ключевого слова. Попробуйте создать индекс без этой фразы и посмотрите, что произойдет.

2
ответ дан 2 September 2019 в 22:08
поделиться
Другие вопросы по тегам:

Похожие вопросы: