从 TWebAction 中提取代码以在主线程中进行 Synchronize()ing?
Extracting code from TWebAction for Synchronize()ing in main thread?
我很难从 TWebActionItem
.
中使用 Synchronize。
我的网络服务是一个可视化程序,格式为 TFormWebServices
var FormWebServices: TFormWebServices;
这有一个属性FWebBrokerBridge: TIdHTTPWebBrokerBridge
FWebBrokerBridge
将 TWebModuleWebServices
注册为 classes 以用于每个来电:
FWebBrokerBridge.RegisterWebModuleClass(TWebModuleWebServices);
此 class 中的 TWebActionItem
项完成读取 TWebRequest
和写入 TWebResponse
的工作。
有一个处理程序需要使用一些 VCL 可视化渲染(与另一个应用程序共享代码),我想将其与主线程同步 (FormWebServices
)。
存根:
TWebModuleWebServices = class(TWebModule)
procedure WebModuleWebServicesTTGetDynReportAction(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
procedure WebModuleAfterDispatch(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
private
FResponse: TResBase; // JSON response object
end;
procedure TWebModuleWebServices.WebModuleWebServicesTTGetDynReportAction(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
var
lFrmDynRapport : TFormDynRapport; // A form containing the common code, has VCL components
begin
lResponse := (FResponse as TResGetDynReport); // TResGetDynReport = class(TResBase)
// ...
lFrmDynRapport := TFormDynRapport.Create(Self);
try
with lFrmDynRapport do
begin
// Do visual stuff with grids, read grid settings, fill lResponse with info specific for this webaction
end
finally
end
// ...
end;
procedure TWebModuleWebServices.WebModuleAfterDispatch(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
var lJSO: ISuperObject; // SuperObject library
begin
lJSO := FResponse.ToJson;
// ...
Response.Content := lJSO.AsString;
Handled := true;
end;
现在如何正确同步 try/finally 块?
我可以进入当前线程并做一些简单的事情,比如:
lThread := TThread.CurrentThread;
TThread.Synchronize(lThread,procedure
begin
FormWebServices.MmoLog.Lines.Add('Synchronize test');
end);
但是对于任何更复杂的事情我都卡住了。
定义本地过程并将它们提供给 Synchronize 不起作用(E2555 无法捕获符号)。
如何提取 try/finally 块以便我可以在 FormWebServices 的上下文中正确执行它?
诀窍是将整个块放在匿名方法中(感谢提示,David):
if lFlexRapDM.DesignerCustomOpenDoc(lFlexRapDM.TimeTellReport) then
begin
.....
lThread := TThread.CurrentThread;
TThread.Synchronize(lThread,procedure
var l,lIndex : integer;
...
begin
lFrmDynRapport := TFormDynRapport.Create(Self);
try
with lFrmDynRapport do
begin
...
end; // with FrmDynReport
finally
lFrmDynRapport.Free;
end;
end);
...
end // if lFlexRapDM.DesignerCustomOpenDoc
我很难从 TWebActionItem
.
我的网络服务是一个可视化程序,格式为 TFormWebServices
var FormWebServices: TFormWebServices;
这有一个属性FWebBrokerBridge: TIdHTTPWebBrokerBridge
FWebBrokerBridge
将 TWebModuleWebServices
注册为 classes 以用于每个来电:
FWebBrokerBridge.RegisterWebModuleClass(TWebModuleWebServices);
此 class 中的 TWebActionItem
项完成读取 TWebRequest
和写入 TWebResponse
的工作。
有一个处理程序需要使用一些 VCL 可视化渲染(与另一个应用程序共享代码),我想将其与主线程同步 (FormWebServices
)。
存根:
TWebModuleWebServices = class(TWebModule)
procedure WebModuleWebServicesTTGetDynReportAction(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
procedure WebModuleAfterDispatch(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
private
FResponse: TResBase; // JSON response object
end;
procedure TWebModuleWebServices.WebModuleWebServicesTTGetDynReportAction(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
var
lFrmDynRapport : TFormDynRapport; // A form containing the common code, has VCL components
begin
lResponse := (FResponse as TResGetDynReport); // TResGetDynReport = class(TResBase)
// ...
lFrmDynRapport := TFormDynRapport.Create(Self);
try
with lFrmDynRapport do
begin
// Do visual stuff with grids, read grid settings, fill lResponse with info specific for this webaction
end
finally
end
// ...
end;
procedure TWebModuleWebServices.WebModuleAfterDispatch(Sender: TObject; Request: TWebRequest; Response: TWebResponse; var Handled: Boolean);
var lJSO: ISuperObject; // SuperObject library
begin
lJSO := FResponse.ToJson;
// ...
Response.Content := lJSO.AsString;
Handled := true;
end;
现在如何正确同步 try/finally 块? 我可以进入当前线程并做一些简单的事情,比如:
lThread := TThread.CurrentThread;
TThread.Synchronize(lThread,procedure
begin
FormWebServices.MmoLog.Lines.Add('Synchronize test');
end);
但是对于任何更复杂的事情我都卡住了。
定义本地过程并将它们提供给 Synchronize 不起作用(E2555 无法捕获符号)。
如何提取 try/finally 块以便我可以在 FormWebServices 的上下文中正确执行它?
诀窍是将整个块放在匿名方法中(感谢提示,David):
if lFlexRapDM.DesignerCustomOpenDoc(lFlexRapDM.TimeTellReport) then
begin
.....
lThread := TThread.CurrentThread;
TThread.Synchronize(lThread,procedure
var l,lIndex : integer;
...
begin
lFrmDynRapport := TFormDynRapport.Create(Self);
try
with lFrmDynRapport do
begin
...
end; // with FrmDynReport
finally
lFrmDynRapport.Free;
end;
end);
...
end // if lFlexRapDM.DesignerCustomOpenDoc