Iis 7 无法将类型(未知)的变量转换为类型(分派)

Iis 7 无法将类型(未知)的变量转换为类型(分派),iis-7,inno-setup,pascalscript,Iis 7,Inno Setup,Pascalscript,我正在尝试将以下javascript代码移植到inno setup pascal脚本: var adminManager = new ActiveXObject('Microsoft.ApplicationHost.AdminManager'); var appPoolsSection = adminManager.GetAdminSection('system.applicationHost/applicationPools', 'MACHINE/WEBROOT/APPHOST'); var

我正在尝试将以下javascript代码移植到inno setup pascal脚本:

var adminManager = new ActiveXObject('Microsoft.ApplicationHost.AdminManager');
var appPoolsSection = adminManager.GetAdminSection('system.applicationHost/applicationPools', 'MACHINE/WEBROOT/APPHOST');
var appPoolsCollection = applicationPoolsSection.Collection;
for (var i = 0; i < appPoolsCollection.Count; i++)
{
    var appPool = appPoolsCollection.Item(i);
    // doing someting with the application pool
}
但它在第
行AppPoolsCollection:=AppPoolsSection.Collection
上引发了以下错误:

Exception: Could not convert variant of type (Unknown) into type (Dispatch).

我可以做任何事情来通知pascal scritp,
AppPoolsSection
对象是一个
IDisPath
,而不仅仅是一个
IUnknown

我找到了一个比“导入”接口定义更简单的解决方案

这段代码中使用的所有COM组件都实现了IDispatch(在VBScript或JScript上使用它是必需的),然后我导入了将IUnknown引用转换为IDispatch引用的函数(因为pascal脚本似乎不支持它)

遵循最终代码:

function VariantChangeType(out Dest: Variant; Source: Variant; Flags, vt: Word): HRESULT; external 'VariantChangeType@oleaut32.dll stdcall';

function VarToDisp(Source: Variant): Variant;
begin
  Result := Unassigned;
  OleCheck(VariantChangeType(Result, Source, 0, varDispatch));
end; 

procedure EnumerateAppPools(AppPools: TStrings);
var AdminManager, Section, Collection, Item, Properties: Variant;
    i: Integer;
begin
  AdminManager := CreateOleObject('Microsoft.ApplicationHost.AdminManager');
  Section := VarToDisp(AdminManager.GetAdminSection('system.applicationHost/applicationPools', 'MACHINE/WEBROOT/APPHOST'));
  Collection := VarToDisp(Section.Collection);
  for i := 0 to Collection.Count-1 do begin
    Item := VarToDisp(Collection.Item(i));
    Properties := VarToDisp(Item.Properties);
    if (VarToDisp(Properties.Item('managedPipelineMode')).Value = 1) and 
       (VarToDisp(Properties.Item('managedRuntimeVersion')).Value = 'v4.0') then
      AppPools.Add(VarToDisp(Properties.Item('name')).Value);
  end;
end;

我觉得你的方法调用有点奇怪。它应该有3个参数,其中第3个参数是
AppPoolsSection
变量和类型
HRESULT
的结果。似乎您的代码在将
HRESULT
值传递到
AppPoolsSection
变量时失败,假设它稍后是一个集合。它是来自的javascript示例的直接端口。我将使用接口声明对其进行trey。谢谢
function VariantChangeType(out Dest: Variant; Source: Variant; Flags, vt: Word): HRESULT; external 'VariantChangeType@oleaut32.dll stdcall';

function VarToDisp(Source: Variant): Variant;
begin
  Result := Unassigned;
  OleCheck(VariantChangeType(Result, Source, 0, varDispatch));
end; 

procedure EnumerateAppPools(AppPools: TStrings);
var AdminManager, Section, Collection, Item, Properties: Variant;
    i: Integer;
begin
  AdminManager := CreateOleObject('Microsoft.ApplicationHost.AdminManager');
  Section := VarToDisp(AdminManager.GetAdminSection('system.applicationHost/applicationPools', 'MACHINE/WEBROOT/APPHOST'));
  Collection := VarToDisp(Section.Collection);
  for i := 0 to Collection.Count-1 do begin
    Item := VarToDisp(Collection.Item(i));
    Properties := VarToDisp(Item.Properties);
    if (VarToDisp(Properties.Item('managedPipelineMode')).Value = 1) and 
       (VarToDisp(Properties.Item('managedRuntimeVersion')).Value = 'v4.0') then
      AppPools.Add(VarToDisp(Properties.Item('name')).Value);
  end;
end;