Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to identify Ole object Interface?

It's a bit difficult to explain my exact scenario, but I will try:

I'm inspecting a DOM interface that was created via late binding, and at some point selecting a range which returns an interfaced OleVariant Element (this I know for sure).

I was expecting an IHTMLElement2 but it is not (I get an exception that the object does not have a tagName property). Which made me later suspect (not tested yet) its a Node element (which has nodeName property) - but I don't want to guess, and ask:

if Supports(IDispatch(v), IWhatEver1)... else if Supports(IDispatch(v), IWhatEver2)...

I don't know which interface it supports. how do I know the interface name/guid from an OleVariant interface object?

The problem is not only specific to DOM, if for example, I have an OleVariant that was created via:

SomeObject := CreateOleObject('WinHttp.WinHttpRequest.5.1'); 
or
SomeObject := CreateOleObject('Msxml.ServerXMLHTTP'); 
or
SomeObject := CreateOleObject('Msxml.XMLHTTP'); 
etc...

v := SomeObject;

How do I later know which IDispatch is behind v?

I hope the question is clear.


Seems like IE11 changed its behavior when using FEATURE_BROWSER_EMULATION = 8000 for my application -> when you use TWebBrowser in design mode and select a range vElement (the Element in the selected Range) returns as JScriptTypeInfo... I don't know why, and I don't know still how to deal with this b.s, but at least I know which Interface I have!

Here is the code I used to examine the Element:

if SysUtils.Supports(IUnknown(vElement), IDispatch, LDispatch) then
  begin
    debug('vElement Supports IDispatch');
    if LDispatch.GetTypeInfo(0, 0, ti) = S_OK then
      if ti.GetDocumentation(MEMBERID_NIL, @pbstrName, @pbstrDocString, nil, nil) = S_OK then
        debug(pbstrName + ';' + pbstrDocString); // <- JScriptTypeInfo;JScript TypeInfo
  end;
like image 670
kobik Avatar asked Dec 27 '13 09:12

kobik


1 Answers

COM interfaces do not provide any generic way to retrieve their CLSID or ProgID. You are expected to know what sort of object you are dealing with. The documentation for the COM object should tell you that information.

If for whatever reason, you have an IDispatch whose type you do not know, you may be able to work it out by inspection using IDispatch.GetTypeInfo. Once you have the ITypeInfo reference, call ITypeInfo.GetDocumentation passing MEMBERID_NIL to find out information on the object's class.

As for the example in the second part of your question, again you are expected to know what type of object you have. You know that information at the point where you call CreateOleObject and you are simply expected to remember.

like image 156
David Heffernan Avatar answered Oct 23 '22 09:10

David Heffernan