Дубликаты во временной таблице истории

У нас есть JCC кормить, что качает данные из Oracle в SQL Server 2016, По неизвестным причинам в таблице истории есть дубликаты с ОДНИМ ЖЕ временем начала и окончания. Как это может случиться? Я пытался обновить запись с условием SET Column = Column, В этом случае у меня есть 2 записи, где все поля одинаковы, но время начала и окончания разные. Как может случиться, что есть такие же даты?

ОБНОВЛЕНИЕ:

DDL:

CREATE TABLE [dbo].[LEASES](
    [LEASE_NUMBER] [CHAR](7) NOT NULL,
    [CREDIT_DECISION_CODE] [CHAR](1) NULL,
    [LEASE_APPLICATION] [CHAR](7) NULL,
    [ACCOUNT_NUMBER] [CHAR](8) NULL,
    [CELLULAR_NUMBER] [CHAR](10) NULL,
    [DEALER_CODE] [CHAR](5) NULL,
    [USERNAME] [CHAR](12) NULL,
    [LEASE_DATE] [DATETIME2](7) NULL,
    [NEW_USED_FLAG] [CHAR](1) NULL,
    [MANUFACTURER_CODE] [CHAR](6) NULL,
    [MODEL] [CHAR](10) NULL,
    [SERIAL_NUMBER_ELECTRONIC] [INT] NULL,
    [SERIAL_NUMBER_MECHANICAL] [CHAR](10) NULL,
    [CONTROL_HEAD] [CHAR](12) NULL,
    [LEASE_TERM] [SMALLINT] NULL,
    [LESSEE_CITY] [CHAR](17) NULL,
    [LESSEE_ADDRESS_1] [CHAR](30) NULL,
    [LESSEE_ADDRESS_2] [CHAR](30) NULL,
    [LESSEE_STATE] [CHAR](2) NULL,
    [LESSEE_ZIP_CODE] [CHAR](9) NULL,
    [LESSEE_NAME] [CHAR](30) NULL,
    [KEY_NAME] [CHAR](12) NULL,
    [BASE_PAYMENT] [DECIMAL](10, 2) NULL,
    [MONTHLY_SALES_TAX] [DECIMAL](10, 2) NULL,
    [INSURANCE] [DECIMAL](10, 2) NULL,
    [MONTHLY_PAYMENT] [DECIMAL](10, 2) NULL,
    [SECURITY_DEPOSIT] [DECIMAL](10, 2) NULL,
    [INVOICES_GENERATED_COUNT] [SMALLINT] NULL,
    [DATE_LAST_INVOICED] [DATETIME] NULL,
    [DATE_LAST_LATE_FEE] [DATETIME] NULL,
    [SECURITY_DEPOSITS_INVOICED] [DECIMAL](10, 2) NULL,
    [SECURITY_DEPOSITS_REFUNDED] [DECIMAL](10, 2) NULL,
    [ADVANCE_RENT] [DECIMAL](10, 2) NULL,
    [ADVANCE_SALES_TAX] [DECIMAL](10, 2) NULL,
    [TOTAL_ADVANCE_PAYMENT] [DECIMAL](10, 2) NULL,
    [AUTO_LEASE_EXPIRATION_DATE] [CHAR](4) NULL,
    [PAYMENTS_REMAINING] [SMALLINT] NULL,
    [PV_PAYMENTS_REMAINING] [DECIMAL](10, 2) NULL,
    [TAX_RATE] [DECIMAL](10, 4) NULL,
    [TAX_STATE] [CHAR](2) NULL,
    [LEASE_FACTOR] [DECIMAL](10, 4) NULL,
    [AMOUNT_FINANCED] [DECIMAL](10, 2) NULL,
    [REMARKS] [CHAR](60) NULL,
    [VOUCHER_NUMBER] [CHAR](12) NULL,
    [BILL_METHOD_ADVANCE] [CHAR](1) NULL,
    [FINANCING_PACKAGE] [INT] NULL,
    [BUYOUT_AMOUNT] [DECIMAL](10, 2) NULL,
    [BUYOUT_DATE] [DATETIME] NULL,
    [DEPRECIATION_MONTHS] [SMALLINT] NULL,
    [SALVAGE_VALUE] [DECIMAL](10, 2) NULL,
    [LAST_DEPRECIATION_DATE] [DATETIME] NULL,
    [LAST_DEPRECIATION_AMOUNT] [DECIMAL](10, 2) NULL,
    [ACCUMULATED_DEPRECIATION] [DECIMAL](10, 2) NULL,
    [BILL_METHOD_BUYOUT] [CHAR](1) NULL,
    [BUYOUT_INVOICED] [CHAR](1) NULL,
    [RECEIVED_DATE] [DATETIME] NULL,
    [LEASE_PROGRAM] [CHAR](5) NULL,
    [PAYMENTS_INCLUDED_ADVANCE] [SMALLINT] NULL,
    [SALESPERSON_CODE] [CHAR](5) NULL,
    [UNGUARANTEED_RESIDUAL_VALUE] [DECIMAL](10, 2) NULL,
    [UNEARNED_INCOME] [DECIMAL](10, 2) NULL,
    [DIRECT_COST] [DECIMAL](10, 2) NULL,
    [AMORTIZABLE_UNEARNED_INCOME] [DECIMAL](10, 2) NULL,
    [AMORTIZED_FLAG] [CHAR](1) NULL,
    [RESIDUAL_VALUE_PERCENTAGE] [DECIMAL](10, 4) NULL,
    [MINIMUM_LEASE_PAYMENTS] [DECIMAL](10, 2) NULL,
    [IMPLICIT_MONTHLY_INTEREST_RATE] [DECIMAL](10, 8) NULL,
    [AP_POSTED_FLAG] [CHAR](1) NULL,
    [AP_POSTED_DATE] [DATETIME] NULL,
    [CAPITALIZED_LEASE_FLAG] [CHAR](1) NULL,
    [LEASE_STATUS] [CHAR](1) NULL,
    [GROSS_INVESTMENT] [DECIMAL](10, 2) NULL,
    [ADVANCE_BILLED_FLAG] [CHAR](1) NULL,
    [AP_VOUCHER_NUMBER] [CHAR](12) NULL,
    [BANK_PACKAGE] [CHAR](5) NULL,
    [INSURANCE_BINDER] [CHAR](1) NULL,
    [CURRENT_BUYOUT] [DECIMAL](10, 2) NULL,
    [LEASE_AGE_YEARS] [SMALLINT] NULL,
    [GUARANTOR_NAME] [CHAR](30) NULL,
    [GUARANTOR_ADDRESS_LINE_1] [CHAR](30) NULL,
    [GUARANTOR_ADDRESS_LINE_2] [CHAR](30) NULL,
    [GUARANTOR_CITY] [CHAR](17) NULL,
    [GUARANTOR_STATE] [CHAR](2) NULL,
    [GUARANTOR_ZIP] [CHAR](9) NULL,
    [GUARANTOR_TELEPHONE] [CHAR](18) NULL,
    [GUARANTOR_SS_NUMBER] [CHAR](9) NULL,
    [GUARANTOR] [CHAR](30) NULL,
    [BILL_CYCLES_DEFER] [INT] NULL,
    [REVENUE_ACCOUNT] [CHAR](5) NULL,
    [INVOICE_TYPE] [CHAR](5) NULL,
    [CORRESPONDENCE_FLAG] [CHAR](1) NULL,
    [DOWN_PAYMENT] [DECIMAL](10, 2) NULL,
    [ADVANCE_INSURANCE] [DECIMAL](10, 2) NULL,
    [ORIGINAL_EQUIPMENT_COST] [DECIMAL](10, 2) NULL,
    [SERVICING_DEALER_CODE] [CHAR](5) NULL,
    [DEALER_BUYOUT_DATE] [DATETIME] NULL,
    [LEASE_OWNER_CODE] [CHAR](5) NULL,
    [LEASE_OWNER_DATE] [DATETIME] NULL,
    [VENDOR_CODE] [CHAR](5) NULL,
    [SPLIT_FUNDING_COUNT] [SMALLINT] NULL,
    [DEALER_AMOUNT] [DECIMAL](10, 2) NULL,
    [VENDOR_AMOUNT] [DECIMAL](10, 2) NULL,
    [SALESPERSON_AMOUNT] [DECIMAL](10, 2) NULL,
    [DEALER_OFFICE] [SMALLINT] NULL,
    [ASSESSMENT_YEAR] [SMALLINT] NULL,
    [PROPERTY_TAX_RATE] [DECIMAL](10, 4) NULL,
    [ASSESSMENT_FACTOR] [DECIMAL](10, 4) NULL,
    [MONTHLY_PROPERTY_TAX] [DECIMAL](10, 2) NULL,
    [MANAGER_CODE] [CHAR](5) NULL,
    [DEALER_BUYOUT_PROGRAM] [CHAR](5) NULL,
    [SHARED_RESID_METHOD] [CHAR](1) NULL,
    [SHARED_RESID_AMOUNT] [DECIMAL](10, 2) NULL,
    [SHARED_RESID_PERCENT] [DECIMAL](10, 4) NULL,
    [SHARED_RESID_L_AND_D] [CHAR](1) NULL,
    [SHARED_RESID_COLLECTION_TYPE] [CHAR](1) NULL,
    [SHARED_RESID_MONTHS_OVERDUE] [SMALLINT] NULL,
    [ORIGINAL_LEASE_TERM] [SMALLINT] NULL,
    [ORIGINAL_LEASE_DATE] [DATETIME] NULL,
    [ORIGINAL_BASE_PAYMENT] [DECIMAL](10, 2) NULL,
    [ORIGINAL_MINIMUM_PAYMENTS] [DECIMAL](10, 2) NULL,
    [NEW_PAYMENT_PLAN_FLAG] [CHAR](1) NULL,
    [NEW_PAYMENT_PLAN_OFFSET] [SMALLINT] NULL,
    [NEW_PAYMENT_PLAN_DATE] [DATETIME] NULL,
    [NEW_MINIMUM_PAYMENTS] [DECIMAL](10, 2) NULL,
    [BILLING_PERIOD_NUMBER] [SMALLINT] NULL,
    [BILLING_PERIOD_1_INVOICES] [SMALLINT] NULL,
    [BILLING_PERIOD_1_PAYMENT] [DECIMAL](10, 2) NULL,
    [BILLING_PERIOD_2_INVOICES] [SMALLINT] NULL,
    [BILLING_PERIOD_2_PAYMENT] [DECIMAL](10, 2) NULL,
    [BILLING_PERIOD_3_INVOICES] [SMALLINT] NULL,
    [BILLING_PERIOD_3_PAYMENT] [DECIMAL](10, 2) NULL,
    [BILLING_PERIOD_4_INVOICES] [SMALLINT] NULL,
    [BILLING_PERIOD_4_PAYMENT] [DECIMAL](10, 2) NULL,
    [BILLING_PERIOD_5_INVOICES] [SMALLINT] NULL,
    [BILLING_PERIOD_5_PAYMENT] [DECIMAL](10, 2) NULL,
    [BILLING_PERIOD_6_INVOICES] [SMALLINT] NULL,
    [BILLING_PERIOD_6_PAYMENT] [DECIMAL](10, 2) NULL,
    [EQUIPMENT_AMOUNT] [DECIMAL](10, 2) NULL,
    [SERVICE_AMOUNT] [DECIMAL](10, 2) NULL,
    [MONTHS_OF_RECOURSE] [SMALLINT] NULL,
    [VENDOR_PAID_FLAG] [CHAR](1) NULL,
    [SALESPERSON_PAID_FLAG] [CHAR](1) NULL,
    [AP_ACCOUNT] [CHAR](5) NULL,
    [GL_AP_ACCOUNT] [CHAR](4) NULL,
    [GL_OWNER_COMPANY] [CHAR](4) NULL,
    [GL_BRANCH] [CHAR](1) NULL,
    [GL_DEPARTMENT] [CHAR](2) NULL,
    [GL_EQUIPMENT] [CHAR](2) NULL,
    [GL_STATE] [CHAR](2) NULL,
    [DEALER_RECOURSE_PERCENT] [DECIMAL](10, 4) NULL,
    [VENDOR_RECOURSE_PERCENT] [DECIMAL](10, 4) NULL,
    [SALESPERSON_RECOURSE_PERCENT] [DECIMAL](10, 4) NULL,
    [NUMBER_OF_UNITS] [SMALLINT] NULL,
    [INVOICES_SUBJECT_TO_DISCOUNT] [CHAR](1) NULL,
    [ORIGINAL_LEASE_PROGRAM] [CHAR](5) NULL,
    [MISSING_PAYMENT_COUNT] [SMALLINT] NULL,
    [BROKER_CODE] [CHAR](5) NULL,
    [REVENUE_SHARING_CODE] [CHAR](5) NULL,
    [REVENUE_SHARING_FACTOR] [DECIMAL](5, 2) NULL,
    [REVENUE_SHARING_FLAG] [CHAR](1) NULL,
    [DEALER_SHARING_CODE] [CHAR](5) NULL,
    [DEALER_SHARING_FACTOR] [DECIMAL](5, 2) NULL,
    [DEALER_SHARING_FLAG] [CHAR](1) NULL,
    [CHARGEBACK_RESERVE_FLAG] [CHAR](1) NULL,
    [FUNDING_FEE] [DECIMAL](10, 2) NULL,
    [FUNDING_FEE_INVOICED_FLAG] [CHAR](1) NULL,
    [LEASE_REFERENCE] [CHAR](30) NULL,
    [ORIGINAL_LEASE_NUMBER] [CHAR](12) NULL,
    [ORIGINAL_ACCOUNT_NUMBER] [CHAR](12) NULL,
    [BASE_PAYMENT_TAXABLE] [CHAR](1) NULL,
    [DAY_TO_CHARGE_BACK] [SMALLINT] NULL,
    [LESSEE_FED_ID_NUMBER] [CHAR](9) NULL,
    [ORIGINAL_PURCHASE_PRICE] [DECIMAL](10, 2) NULL,
    [ORIGINAL_PURCHASE_DATE] [DATETIME] NULL,
    [ACQUISITION_PURCHASE_PRICE] [DECIMAL](10, 2) NULL,
    [ACQUISITION_PURCHASE_DATE] [DATETIME] NULL,
    [BROKER_REV_SHAR_AMT_OVERRIDE] [DECIMAL](10, 2) NULL,
    [DEALER_REV_SHAR_AMT_OVERRIDE] [DECIMAL](10, 2) NULL,
    [UPFRONT_TAX_FLAG] [CHAR](1) NULL,
    [UPFRONT_TAX_AMOUNT] [DECIMAL](10, 2) NULL,
    [UPFRONT_TAX_BILLED] [CHAR](1) NULL,
    [SysStart] [DATETIME2](7) GENERATED ALWAYS AS ROW START NOT NULL,
    [SysEnd] [DATETIME2](7) GENERATED ALWAYS AS ROW END NOT NULL,
PRIMARY KEY CLUSTERED 
(
    [LEASE_NUMBER] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY],
    PERIOD FOR SYSTEM_TIME ([SysStart], [SysEnd])
) ON [PRIMARY]
WITH
(
SYSTEM_VERSIONING = ON ( HISTORY_TABLE = [dbo].[LEASES_HISTORY] )
)
GO

ОБНОВЛЕНИЕ 2:

Я не могу предоставить реальные данные, однако этот запрос я использовал для получения дубликатов. Обратите внимание, что я группирую по всем столбцам таблицы, так что это определенные дубликаты:

SELECT LEASE_NUMBER
     , SysStart
     , SysEnd
     , cnt
  FROM
       (   SELECT *
                , COUNT(*) cnt
             FROM dbo.LEASES_HISTORY AS l
            GROUP BY l.LEASE_NUMBER
                   , l.CREDIT_DECISION_CODE
                   , l.LEASE_APPLICATION
                   , l.ACCOUNT_NUMBER
                   , l.CELLULAR_NUMBER
                   , l.DEALER_CODE
                   , l.USERNAME
                   , l.LEASE_DATE
                   , l.NEW_USED_FLAG
                   , l.MANUFACTURER_CODE
                   , l.MODEL
                   , l.SERIAL_NUMBER_ELECTRONIC
                   , l.SERIAL_NUMBER_MECHANICAL
                   , l.CONTROL_HEAD
                   , l.LEASE_TERM
                   , l.LESSEE_CITY
                   , l.LESSEE_ADDRESS_1
                   , l.LESSEE_ADDRESS_2
                   , l.LESSEE_STATE
                   , l.LESSEE_ZIP_CODE
                   , l.LESSEE_NAME
                   , l.KEY_NAME
                   , l.BASE_PAYMENT
                   , l.MONTHLY_SALES_TAX
                   , l.INSURANCE
                   , l.MONTHLY_PAYMENT
                   , l.SECURITY_DEPOSIT
                   , l.INVOICES_GENERATED_COUNT
                   , l.DATE_LAST_INVOICED
                   , l.DATE_LAST_LATE_FEE
                   , l.SECURITY_DEPOSITS_INVOICED
                   , l.SECURITY_DEPOSITS_REFUNDED
                   , l.ADVANCE_RENT
                   , l.ADVANCE_SALES_TAX
                   , l.TOTAL_ADVANCE_PAYMENT
                   , l.AUTO_LEASE_EXPIRATION_DATE
                   , l.PAYMENTS_REMAINING
                   , l.PV_PAYMENTS_REMAINING
                   , l.TAX_RATE
                   , l.TAX_STATE
                   , l.LEASE_FACTOR
                   , l.AMOUNT_FINANCED
                   , l.REMARKS
                   , l.VOUCHER_NUMBER
                   , l.BILL_METHOD_ADVANCE
                   , l.FINANCING_PACKAGE
                   , l.BUYOUT_AMOUNT
                   , l.BUYOUT_DATE
                   , l.DEPRECIATION_MONTHS
                   , l.SALVAGE_VALUE
                   , l.LAST_DEPRECIATION_DATE
                   , l.LAST_DEPRECIATION_AMOUNT
                   , l.ACCUMULATED_DEPRECIATION
                   , l.BILL_METHOD_BUYOUT
                   , l.BUYOUT_INVOICED
                   , l.RECEIVED_DATE
                   , l.LEASE_PROGRAM
                   , l.PAYMENTS_INCLUDED_ADVANCE
                   , l.SALESPERSON_CODE
                   , l.UNGUARANTEED_RESIDUAL_VALUE
                   , l.UNEARNED_INCOME
                   , l.DIRECT_COST
                   , l.AMORTIZABLE_UNEARNED_INCOME
                   , l.AMORTIZED_FLAG
                   , l.RESIDUAL_VALUE_PERCENTAGE
                   , l.MINIMUM_LEASE_PAYMENTS
                   , l.IMPLICIT_MONTHLY_INTEREST_RATE
                   , l.AP_POSTED_FLAG
                   , l.AP_POSTED_DATE
                   , l.CAPITALIZED_LEASE_FLAG
                   , l.LEASE_STATUS
                   , l.GROSS_INVESTMENT
                   , l.ADVANCE_BILLED_FLAG
                   , l.AP_VOUCHER_NUMBER
                   , l.BANK_PACKAGE
                   , l.INSURANCE_BINDER
                   , l.CURRENT_BUYOUT
                   , l.LEASE_AGE_YEARS
                   , l.GUARANTOR_NAME
                   , l.GUARANTOR_ADDRESS_LINE_1
                   , l.GUARANTOR_ADDRESS_LINE_2
                   , l.GUARANTOR_CITY
                   , l.GUARANTOR_STATE
                   , l.GUARANTOR_ZIP
                   , l.GUARANTOR_TELEPHONE
                   , l.GUARANTOR_SS_NUMBER
                   , l.GUARANTOR
                   , l.BILL_CYCLES_DEFER
                   , l.REVENUE_ACCOUNT
                   , l.INVOICE_TYPE
                   , l.CORRESPONDENCE_FLAG
                   , l.DOWN_PAYMENT
                   , l.ADVANCE_INSURANCE
                   , l.ORIGINAL_EQUIPMENT_COST
                   , l.SERVICING_DEALER_CODE
                   , l.DEALER_BUYOUT_DATE
                   , l.LEASE_OWNER_CODE
                   , l.LEASE_OWNER_DATE
                   , l.VENDOR_CODE
                   , l.SPLIT_FUNDING_COUNT
                   , l.DEALER_AMOUNT
                   , l.VENDOR_AMOUNT
                   , l.SALESPERSON_AMOUNT
                   , l.DEALER_OFFICE
                   , l.ASSESSMENT_YEAR
                   , l.PROPERTY_TAX_RATE
                   , l.ASSESSMENT_FACTOR
                   , l.MONTHLY_PROPERTY_TAX
                   , l.MANAGER_CODE
                   , l.DEALER_BUYOUT_PROGRAM
                   , l.SHARED_RESID_METHOD
                   , l.SHARED_RESID_AMOUNT
                   , l.SHARED_RESID_PERCENT
                   , l.SHARED_RESID_L_AND_D
                   , l.SHARED_RESID_COLLECTION_TYPE
                   , l.SHARED_RESID_MONTHS_OVERDUE
                   , l.ORIGINAL_LEASE_TERM
                   , l.ORIGINAL_LEASE_DATE
                   , l.ORIGINAL_BASE_PAYMENT
                   , l.ORIGINAL_MINIMUM_PAYMENTS
                   , l.NEW_PAYMENT_PLAN_FLAG
                   , l.NEW_PAYMENT_PLAN_OFFSET
                   , l.NEW_PAYMENT_PLAN_DATE
                   , l.NEW_MINIMUM_PAYMENTS
                   , l.BILLING_PERIOD_NUMBER
                   , l.BILLING_PERIOD_1_INVOICES
                   , l.BILLING_PERIOD_1_PAYMENT
                   , l.BILLING_PERIOD_2_INVOICES
                   , l.BILLING_PERIOD_2_PAYMENT
                   , l.BILLING_PERIOD_3_INVOICES
                   , l.BILLING_PERIOD_3_PAYMENT
                   , l.BILLING_PERIOD_4_INVOICES
                   , l.BILLING_PERIOD_4_PAYMENT
                   , l.BILLING_PERIOD_5_INVOICES
                   , l.BILLING_PERIOD_5_PAYMENT
                   , l.BILLING_PERIOD_6_INVOICES
                   , l.BILLING_PERIOD_6_PAYMENT
                   , l.EQUIPMENT_AMOUNT
                   , l.SERVICE_AMOUNT
                   , l.MONTHS_OF_RECOURSE
                   , l.VENDOR_PAID_FLAG
                   , l.SALESPERSON_PAID_FLAG
                   , l.AP_ACCOUNT
                   , l.GL_AP_ACCOUNT
                   , l.GL_OWNER_COMPANY
                   , l.GL_BRANCH
                   , l.GL_DEPARTMENT
                   , l.GL_EQUIPMENT
                   , l.GL_STATE
                   , l.DEALER_RECOURSE_PERCENT
                   , l.VENDOR_RECOURSE_PERCENT
                   , l.SALESPERSON_RECOURSE_PERCENT
                   , l.NUMBER_OF_UNITS
                   , l.INVOICES_SUBJECT_TO_DISCOUNT
                   , l.ORIGINAL_LEASE_PROGRAM
                   , l.MISSING_PAYMENT_COUNT
                   , l.BROKER_CODE
                   , l.REVENUE_SHARING_CODE
                   , l.REVENUE_SHARING_FACTOR
                   , l.REVENUE_SHARING_FLAG
                   , l.DEALER_SHARING_CODE
                   , l.DEALER_SHARING_FACTOR
                   , l.DEALER_SHARING_FLAG
                   , l.CHARGEBACK_RESERVE_FLAG
                   , l.FUNDING_FEE
                   , l.FUNDING_FEE_INVOICED_FLAG
                   , l.LEASE_REFERENCE
                   , l.ORIGINAL_LEASE_NUMBER
                   , l.ORIGINAL_ACCOUNT_NUMBER
                   , l.BASE_PAYMENT_TAXABLE
                   , l.DAY_TO_CHARGE_BACK
                   , l.LESSEE_FED_ID_NUMBER
                   , l.ORIGINAL_PURCHASE_PRICE
                   , l.ORIGINAL_PURCHASE_DATE
                   , l.ACQUISITION_PURCHASE_PRICE
                   , l.ACQUISITION_PURCHASE_DATE
                   , l.BROKER_REV_SHAR_AMT_OVERRIDE
                   , l.DEALER_REV_SHAR_AMT_OVERRIDE
                   , l.UPFRONT_TAX_FLAG
                   , l.UPFRONT_TAX_AMOUNT
                   , l.UPFRONT_TAX_BILLED
                   , l.SysStart
                   , l.SysEnd
           HAVING COUNT(*) > 1
       ) a;

ОБНОВЛЕНИЕ 3: Хорошо, к этому времени это - новая информация, которую я смог получить. Мы пытались поймать rpc_completed события, чтобы увидеть, что на самом деле происходит. В файле трассировки было 7 разных операторов с разными event_sequence номера. Насколько я понимаю, это означает, что эти заявления были выполнены в разных транзакциях. Я постараюсь подготовить более подробное обновление позже, но пока операторы были следующими (Все операторы, кроме последнего, были выполнены с использованием sp_prepexec хранимые процедуры):

На самом деле есть 3 разных состояния, которые были в строке, давайте назовем их x,y,z

  • ОБНОВЛЕНИЕ записи по ПК с x состояние - на данный момент нет такой записи в БД
  • ОБНОВЛЕНИЕ записи по ПК с y состояние - на данный момент нет такой записи в БД
  • Вставить запись с x государство
  • Вставить запись с y состояние - это не удалось с нарушением ограничения PK
  • ОБНОВЛЕНИЕ записи в x состояние - это на самом деле не изменило ни одной строки, поэтому фактическая запись не изменилась
  • ОБНОВЛЕНИЕ записи в y состояние - фактическая запись изменилась
  • ОБНОВЛЕНИЕ записи в z состояние с помощью sp_execute процедура, в которой handle_id совпадает с предыдущим обновлением (обновление до z состояние) но значения, передаваемые через параметры разные

Итак, в конце этих операций мы имеем:

Оригинальный стол находится в z состояние, и таблица истории имеет что-то вроде этого (datetime - реальные значения):

  • x столбцы состояния, 2017-11-01 16:55:31.3358248, 2017-11-01 16:55:31.3358248
  • x столбцы состояния, 2017-11-01 16:55:31.3358248, 2017-11-01 16:55:31.3358248
  • y столбцы состояния, 2017-11-01 16:55:31.3358248, 2017-11-01 16:55:41.9296659

2 ответа

Временные таблицы используют время начала транзакции в качестве временной отметки (см. Временные таблицы в MS Docs в разделах вставки, обновления и удаления). Сделав несколько обновлений в пределах вашей транзакции или вставку, за которой следует обновление в рамках одной и той же транзакции, вы получите несколько записей для данного значения первичного ключа с одинаковыми временами начала / окончания.

Выдержка из ссылки:

ОБНОВЛЕНИЯ: В ОБНОВЛЕНИИ система сохраняет предыдущее значение строки в таблице истории и устанавливает значение для столбца SysEndTime равным времени начала текущей транзакции (в часовом поясе UTC) на основе системных часов.

Вот пример, который будет воспроизводить поведение. Обратите внимание, что в миниатюрных виджетах есть 2 идентичные записи ProductsHistory стол для ProductId = 2, Также обратите внимание, что хотя обновления для ProductId = 1 не изменили значение, они все еще создали идентичные записи таблицы истории.

create table test.Products (
        ProductId       int not null primary key,
        ProductName     nvarchar(100) not null,
        EffectiveDate   datetime2(7) generated always as row start hidden not null,
        EndingDate      datetime2(7) generated always as row end hidden not null,
        period for system_time (EffectiveDate, EndingDate)
        )
        with (system_versioning = on (history_table = test.ProductsHistory));

go

begin tran

insert  test.Products (ProductId, ProductName) values
        (1, N'Widgets'),
        (2, N'Miniature Widgets');

update  test.Products set ProductName = 'Tiny Widgets' where ProductId = 2;
update  test.Products set ProductName = 'Miniature Widgets' where ProductId = 2;
update  test.Products set ProductName = 'Tiny Widgets' where ProductId = 2;
update  test.Products set ProductName = 'Widgets' where ProductId = 1;
update  test.Products set ProductName = 'Widgets' where ProductId = 1;

commit tran

select  p.ProductId, p.ProductName, p.EffectiveDate, p.EndingDate
from    test.Products for system_time all p;

select  *
from    test.ProductsHistory;

Я собираюсь добавить еще одну возможность в качестве отдельного ответа, хотя я думаю, что это гораздо менее вероятно - часы сервера изменились. Я видел случаи (больше с файлами текстового журнала, чем с SQL, но все еще возможно) с временным перекрытием, где время сервера / ПК изменилось. Это может произойти, когда переход на летнее время начинается / заканчивается (хотя в этом сценарии это маловероятно, поскольку поля начала / окончания указаны в формате UTC). Более отдаленная возможность состоит в том, что у вас есть смещение тактовой частоты сервера. Я сомневаюсь, что вы увидели бы это на сервере - мы видели это на одноядерных промышленных ПК, которые работали нагрето, а процессор часто работал с максимальной нагрузкой. Даже синхронизируя часы ежедневно, мы можем быть короткими на одну или две минуты в конце дня.

Другие вопросы по тегам