Компоненты ADO CommandTimeout
У меня проблема с настройками таймаута выполнения запроса с TADOQuery, TADOCommand или TADODataSet (я пробовал это с каждым). У меня есть маленькое приложение, которое подключается к базе данных и периодически выполняет хранимые процедуры, которые возвращают dataset в результате. Моя цель-держать это приложение всегда в сети, но моя проблема в том, что когда соединение потеряно, тайм-аут только что выполненной команды (через один из упомянутых компонентов) принимает по умолчанию 30 секунд. Я искал решение, но ничего не работает. не могли бы вы дать мне совет, как установить CommandTimeout, например, на 5 секунд или лучше сказать, как изменить ADODB.pas за уважение моего собственного тайм-аута, пожалуйста ?
для этого было много "решений", таких как set DataComponent.Соединение.CommandTimeout: = 1; но на самом деле ничего не работает. Я использую D2009, MSSQL2005, и соединение вместе с компонентом данных создается динамически в нитка.
последнее, что я пробовал это
// protected variable owned and created in the thread with its own connection
var Query_Object: TADODataSet;
// connection timeout is set to 3 seconds
Query_Object.Connection.ConnectionTimeout := 3;
...
// this piece of code I'm calling periodically in the only one existing thread
...
SQL_Query := 'EXEC my_procedure_which_returns_dataset'
with Query_Object do
begin
Close;
CommandType := cmdText;
CommandText := SQL_Query;
CommandTimeout := 5; // doesn't affect the timeout
CursorLocation := clUseServer; // let the dataset retreives prepared data
Open;
end;
// and here I need to get faster than in the default 15 seconds to let the user
// know that the reading takes more than mentioned 5 seconds
...
Спасибо большое :)
3 ответов
CommandTimeout
срабатывает, когда у вас есть длительные запросы. Есть CommandTimeout
собственность TADOConnection
но это не работает. Вы должны использовать CommandTimeout
на .
если сервер недоступен, ваш вопрос говорит "соединение потеряно", вам нужно указать ConnectionTimeout
на
ниже то, что мы используем, чтобы установить тайм-аут 300 для наших длительных отчетов.
//***** Fix setting CommandTimeOut.
// CommandTimeOut "should" get the timeout value from its connection.
// This is not supported in ADODB (using Delphi5)
TADODataSet(qryReport).CommandTimeout := ADOConnection.CommandTimeout;
редактировать
выполнение следующего фрагмента кода на моей машине разработки истекает через 1 секунду.
- запрос имеет connectionstring к нашей производственной базе данных SQLServer.
- сценарий (пытается) работает в течение 10 секунд
- через секунду я получаю тайм-аут исключение
тест
procedure TForm1.btn1Click(Sender: TObject);
const
SSQL: string =
'DECLARE @intLoop int '#13#10
+ 'SET @intLoop = 10 '#13#10
+ 'WHILE @intLoop > 1 '#13#10
+ 'BEGIN '#13#10
+ ' SELECT @intLoop, GetDate() '#13#10
+ ' WAITFOR DELAY ''00:00:01'' '#13#10
+ ' SELECT @intLoop = @intLoop -1 '#13#10
+ 'END ';
begin
qry1.SQL.Text := SSQL;
TADODataSet(qry1).CommandTimeout := 1;
qry1.ExecSQL;
end;
Я всегда использовал следующий код для установки значения CommandTimeout в TADOQuery. Если вы измените имя класса, он также должен работать с другими.
type
TADOQueryHack = class(TADOQuery);
...
TADOQueryHack(Qry).CommandTimeout := COMM_TIMEOUT;