Я хочу отправить HTTP-запрос в веб-сервис из T-SQL.Если веб-сервис недоступен, я хочу отменить операцию, скажем, через 500 мс.Таким образом, процедура не застревает.
Поэтому я использую OLE-Object MXSML2.ServerXMLHttp и пытаюсь использовать метод setTimeouts (см. Документация Microsoft ).Это работает, но, к сожалению, возвращается только через 4 секунды.
Метод setTimeouts ожидает 4 параметра в миллисекундах, которые объявляют время ожидания для нескольких операций, связанных с http-запросом (см. Документацию).Даже когда я устанавливаю параметры на 1 мс, он возвращается только через 4 секунды.Чего мне не хватает?
Я вижу, что setTimeouts хотя бы что-то делает, потому что код состояния и состояние готовности http-запроса остаются равными 0. Если я закомментирую вызов метода setTimeouts, я получу обычный http-ответ с кодом состояния 200 и состоянием готовности 4.
Вот процедура, которую я использую:
ALTER PROCEDURE [dbo].[TestWebRequest]
AS
BEGIN
DECLARE @obj int,
@url VarChar(300),
@response VarChar(MAX),
@statusCode int = -1,
@readyState int = -1
DECLARE @t1 DateTime,
@t2 DateTime,
@elapsed_ms int
SET @url = 'http://httpstat.us/200?sleep=5000'
EXEC sp_OACreate 'MSXML2.ServerXMLHttp', @obj OUT
EXEC sp_OASetProperty @obj, 'setTimeouts', '1', '1', '1', '1'
EXEC sp_OAMethod @obj, 'Open', NULL, 'GET', @url, false
SET @t1 = GETDATE()
EXEC sp_OAMethod @obj, 'send'
SET @t2 = GETDATE()
SET @elapsed_ms = (SELECT DATEDIFF(millisecond,@t1,@t2))
EXEC sp_OAGetProperty @obj, 'readyState', @readyState OUT
EXEC sp_OAGetProperty @obj, 'status', @statusCode OUT
DECLARE @src nvarchar(200), @desc nvarchar(2000) = ''
EXEC sp_OAGetErrorInfo @obj, @src OUT, @desc OUT
EXEC sp_OADestroy @obj
PRINT 'Error: ' + @desc
PRINT 'Elapsed Time: ' + CONVERT(varchar, @elapsed_ms) + ' ms'
PRINT 'Ready State ' + CONVERT(varchar, @readyState)
PRINT 'StatusCode: ' + CONVERT(varchar, @statusCode)
END
Что я получаю, так это результат:
Error: The data necessary to complete this operation is not yet available.
Elapsed Time: 4636 ms
Ready State 1
StatusCode: -1
Iбудет ожидать, что истекшее время будет меньше 500 мс.
Если я закомментирую метод setTimeouts, появится следующий результат:
Elapsed Time: 5173 ms
Ready State 4
StatusCode: 200