Слияние приводит к ошибке приведения DATETIME --> INT

Я не могу понять, почему эта ошибка возникает. Может ли кто-нибудь еще помочь мне найти ошибку? Я пытаюсь объединиться с временной таблицей и получаю сообщение об ошибке

Неявное преобразование из типа данных datetime в int не допускается. Используйте функцию CONVERT для выполнения этого запроса. Ошибка идентифицируется как возникающая в строке, где начинается MERGE.

Запрос:

SELECT 
    BookID AS KTSID,
    ResourceID AS FLRID,
    ls.ID AS SiteShelfID,
    ls.CustomerNumber AS SiteCustNum,
    ls.DivisionID AS SiteDivID,
    st.DateCreated AS SiteBibDateAdded,
    st.TotalCopies AS SiteQtyOwned,
    ls.ParentLibraryShelfID AS ProviderShelfID,
    NULL AS ProviderCustNum,
    NULL AS ProviderDivID,
    NULL AS ProviderBibDateAdded,
    NULL AS ProviderQtyOwned
INTO #TitleData
FROM dapadmin.ShelfTitle st
    JOIN dapadmin.LibraryShelf ls ON st.LibraryShelfID = ls.ID
    JOIN #TitlesToInclude tti     ON st.ID = tti.ShelfTitleId


MERGE #TitleData WITH(HOLDLOCK) AS td
    USING (SELECT 
            st.BookID AS KTSID,
            st.ResourceID AS FLRID,         
            st.LibraryShelfID AS SiteShelfID,   
            ls2.CustomerNumber AS SiteCustNum,
            ls2.DivisionID AS SiteDivID,
            s.ProviderShelfID,
            ls.CustomerNumber AS ProviderCustNum,
            ls.DivisionID AS ProviderDivID,
            st.DateCreated AS ProviderBibDateAdded,
            st.TotalCopies AS ProviderQtyOwned
        FROM @ShelfIdsToSearch s
        JOIN dapadmin.ShelfTitle st 
            ON s.ProviderShelfId = st.LibraryShelfID
        JOIN #TitleData td 
            ON td.KTSID = st.BookID 
            AND td.FLRID = st.ResourceID
            AND td.SiteShelfId = s.LibraryShelfId
            AND td.ProviderShelfID = st.LibraryShelfID      
        JOIN #TitlesToInclude tti 
            ON st.ID = tti.ShelfTitleId
            OR s.ProviderHasChanged = 1
        JOIN dapadmin.LibraryShelf ls
            ON s.ProviderShelfId = ls.ID
        JOIN dapadmin.LibraryShelf ls2
            ON s.LibraryShelfId = ls.ID
        ) AS pt

    ON td.KTSID = pt.KTSID 
        AND td.FLRID = pt.FLRID
        AND pt.SiteShelfID = td.SiteShelfID
WHEN MATCHED THEN
    UPDATE
        SET ProviderCustNum      = pt.ProviderCustNum,
            ProviderDivID        = pt.ProviderDivID,
            ProviderBibDateAdded = pt.ProviderBibDateAdded,
            ProviderQtyOwned     = pt.ProviderQtyOwned
WHEN NOT MATCHED THEN
    INSERT (KTSID, FLRID, SiteShelfID, SiteCustNum, SiteDivID, 
            SiteBibDateAdded, SiteQtyOwned, ProviderShelfID, 
            ProviderCustNum, ProviderDivID, 
            ProviderBibDateAdded, ProviderQtyOwned)
    VALUES (pt.KTSID, pt.FLRID, pt.SiteShelfID, pt.SiteCustNum, pt.SiteDivID, 
            NULL, NULL, pt.ProviderShelfID, 
            pt.ProviderCustNum, pt.ProviderDivID, 
            pt.ProviderBibDateAdded, pt.ProviderQtyOwned)
;

person Mike Kantor    schedule 15.05.2014    source источник


Ответы (1)


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

UPDATE
    SET ProviderCustNum      = pt.ProviderCustNum,
        ProviderDivID        = pt.ProviderDivID,
        ProviderBibDateAdded = Cast(pt.ProviderBibDateAdded as Integer),
        ProviderQtyOwned     = pt.ProviderQtyOwned

и ваш оператор вставки к этому:

INSERT (KTSID, FLRID, SiteShelfID, SiteCustNum, SiteDivID, 
        SiteBibDateAdded, SiteQtyOwned, ProviderShelfID, 
        ProviderCustNum, ProviderDivID, ProviderBibDateAdded, 
        ProviderQtyOwned)
VALUES (pt.KTSID, pt.FLRID, pt.SiteShelfID, pt.SiteCustNum, 
        pt.SiteDivID, NULL, NULL, pt.ProviderShelfID, 
        pt.ProviderCustNum, pt.ProviderDivID, 
        cast(pt.ProviderBibDateAdded as Integer), 
        pt.ProviderQtyOwned)

Если это действительно проблема, то вы можете вместо этого создать свою временную таблицу с явными типами данных для начала, прежде чем что-либо вставлять в нее.

Declare @TitleData (
     KTSID integer not null,
     FLRID integer not null,
     SiteShelfID integer not null,
     SiteCustNum varChar(??),
     SiteDivID integer not null,
     SiteBibDateAdded Datetime not null,
     SiteQtyOwned smallInt,
     ProviderShelfID integer not null,
     ProviderCustNum varChar(??) Null,
     ProviderDivID Integer null,
     ProviderBibDateAdded Datetime null,
     ProviderQtyOwned null)

Insert @TitleData (KTSID, FLRID, SiteShelfID, 
    SiteCustNum, SiteDivID, SiteBibDateAdded,
    SiteQtyOwned, ProviderShelfID)
SELECT BookID, ResourceID, ls.ID,
   ls.CustomerNumber, ls.DivisionID,
   st.DateCreated, st.TotalCopies,
   ls.ParentLibraryShelfID
From dapadmin.ShelfTitle st
    JOIN dapadmin.LibraryShelf ls 
       ON st.LibraryShelfID = ls.ID
    JOIN #TitlesToInclude tti     
       ON st.ID = tti.ShelfTitleId
person Charles Bretana    schedule 15.05.2014
comment
Но ProviderBibDateAdded — это DATETIME, а не целое число. Теперь я вижу, что когда я создал первую таблицу, я передал NULL для ProviderBibDateAdded, поэтому я предполагаю, что тип по умолчанию — INT. Есть ли способ указать DATETIME в качестве типа столбца во временной таблице, созданной с помощью SELECT...INTO? Или мне нужно явно СОЗДАТЬ таблицу, чтобы сделать это? - person Mike Kantor; 15.05.2014
comment
Кроме того, предлагаемое изменение не устраняет ошибку... НО, если я также применяю приведение в предложении UPDATE, ошибка ДЕЙСТВИТЕЛЬНО исчезает. Так что ваше указание на источник проблемы верное. Спасибо за быстрый ответ! - person Mike Kantor; 15.05.2014
comment
это было просто предположение, основанное на предположении, что ProviderBibDateAdded вводится как целое число, и вы пытаетесь вставить в него дату и время. Если ProviderBibDateAdded - это дата и время, то это тупик, извините. Что-то еще пытается вставить дату и время в поле или переменную памяти, которая ожидает целое число. Но это единственное место, которое я вижу в вашем коде, где могло быть ошибочное присваивание. - person Charles Bretana; 15.05.2014
comment
Я думаю, вы, должно быть, прокомментировали, прежде чем увидеть мое редактирование второго комментария. Вы правы в том, что проблема в ProviderBibDateAdded. Итак, теперь мой вопрос заключается в том, что при создании исходной таблицы я могу сказать что-то вроде NULL AS DATETIME, чтобы позже я мог вставлять значения DATETIME в этот столбец. - person Mike Kantor; 15.05.2014
comment
Да, это именно то, что нужно сделать. Но почему бы не создать временную таблицу (или табличную переменную с явными опечатками данных для начала? См. мое редактирование, см. ... o - person Charles Bretana; 15.05.2014
comment
Да, я перейду к явному определению временной таблицы, чтобы я мог указать тип данных для этого столбца. Спасибо еще раз! - person Mike Kantor; 15.05.2014