Je voudrais faire une insertion en utilisant un select, mais je sais que certaines lignes peuvent échouer (ce qui est attendu). Existe-t-il un moyen de désactiver les transactions implicites de SQL Server 2008 afin que celles qui n'ont pas échoué ne soient pas annulées?Désactiver les transactions implicites
-- get the count of the customers to send the sms to
SELECT @count = COUNT(*)
FROM PreCampaignCustomer
WHERE Processed = 0 AND CampaignID = @campaignid
AND ErrorCount < 5
WHILE (@count > 0)
BEGIN
DECLARE @customerid INT,
@carrierid INT,
@merchantcustomerid INT,
@smsnumber NVARCHAR(50),
@couponcode NVARCHAR(20)
SELECT TOP 1 @customerid = pcc.CustomerID, @merchantcustomerid = pcc.MerchantCustomerID,
@carrierid = c.CarrierID, @smsnumber = c.SMSNumber
FROM PreCampaignCustomer pcc
INNER JOIN Customer c ON c.ID = pcc.CustomerID
WHERE pcc.Processed = 0 AND pcc.CampaignID = @campaignid
AND pcc.ErrorCount < 5
ORDER BY pcc.ErrorCount
--set the couponcode
IF @couponlength = -1
BEGIN
SET @couponcode = 'NOCOUPON'
END
ELSE
BEGIN
EXEC [GenerateCouponCode]
@length = 9,
@couponcode = @couponcode OUTPUT
END
BEGIN TRY
--use try/catch just in case the coupon code is repeated or any other error
--Set the coupon text
DECLARE @coupontext NVARCHAR(200),
@smsrequestxml XML
IF @coupontypecode = 1 --NONE
BEGIN
SET @coupontext = @merchantname + ': ' + @smsmessage + ', Use Code: ' + dbo.FormatCouponCode(@couponcode, @couponcodegrouping) + '. Reply STOP to quit'
END
ELSE
BEGIN
SET @coupontext = @merchantname + ': ' + @smsmessage + '. Reply STOP to quit'
END
EXEC GetSMSRequest @config = @smsconfig,
@smsType = 1, --Submit
@address = @smsnumber,
@carrierID = @carrierid,
@message = @coupontext,
@xml = @smsrequestxml OUTPUT
BEGIN TRAN
--create the CampaignCustomer record
INSERT INTO CampaignCustomer
(CampaignID, CustomerID, CouponCode, Active)
VALUES
(@campaignid, @customerid, @couponcode, 1)
--Add the record to the queue
INSERT INTO SMSQueue
(CarrierID, [Address], [Message], TimeToSend, RequestXML, QueueID, HTTPStatusCode, Retries)
VALUES
(@carrierid, @smsnumber, @coupontext, @timetosend, @smsrequestxml, @queueid, 0, 0)
--Create Outgoing SMS Log
INSERT INTO SMSOutgoingLog
(MerchantID, MerchantGroupID, MessageTypeCode, CreatedDate, Active)
VALUES
(@merchantid, @merchantgroupid, @messagetypecode, GETDATE(), 1)
--Update the LastSentSMSTime of the MerchantCustomer
UPDATE MerchantCustomer
SET LastSentSMS = GETDATE(),
ModifiedDate = GETDATE()
WHERE ID = @merchantcustomerid
UPDATE PreCampaignCustomer
SET Processed = 1,
ModifiedDate = GETDATE()
WHERE CustomerID = @customerid
AND CampaignID = @campaignid
COMMIT TRAN
END TRY
BEGIN CATCH
ROLLBACK TRAN
-- Set the error
UPDATE PreCampaignCustomer
SET ErrorCount = ErrorCount + 1,
ModifiedDate = GETDATE(),
ErrorMessage = ERROR_MESSAGE(),
ErrorNumber = ERROR_NUMBER()
WHERE CustomerID = @customerid
AND CampaignID = @campaignid
END CATCH
SELECT @count = COUNT(*)
FROM PreCampaignCustomer
WHERE Processed = 0 AND CampaignID = @campaignid
AND ErrorCount < 5
END
Je génère un code coupon aléatoire pour chaque ligne et il y a une contrainte unique sur le code coupon. Au lieu de faire une sélection pour voir si elle existe, je laisse SQL Server gérer la contrainte et laisser échouer. Pensez-vous que la vérification du compte (*) avec ce code promo sera plus rapide? –
êtes-vous en boucle, avec un insert par itération? si c'est le cas, affichez le code afin que je puisse voir exactement ce qui se passe. Il existe des moyens de générer un ensemble de nombres aléatoires: http://stackoverflow.com/questions/183124/multiple-random-values-in-sql-server-2005/183183#183183. Aussi COUNT (*) est lent (il fait plus de travail) que juste un EXISTS uni. –
oui, je suis en boucle. J'ai ajouté le code. Bottom line J'ai besoin de rendre cette requête aussi efficace que possible. Peut-être qu'au lieu d'obtenir le compte à chaque itération, exécutez le select top 1 et faites WHILE NOT @customerid est nul. D'autres suggestions? –