Mitch has asked for the wisdom of the Perl Monks concerning the following question:

Hi,

OS: Windows 2000 SP2, Perl 5.6.1, 622

Problem:

I'm trying to use WMI to loop through events in Event Viewer's Application log. I am purposely trying to use WMI instead of Win32::EventLog. I'm trying to duplicate results from a vbscript I found on the web by using Win32::OLE. The program creates the object, but fails at the foreach loop. Once created $avents has a value of Win32::OLE=HASH(0x1ab5264), I don't know what this means exactly. The eventcode 1000 (event ID) does exist in the application log.

Sample Code:

use Win32::OLE qw (in); $Computername = 'servername'; $Win32_Class ='Win32_NTLogEvent'; $Class = "WinMgmts://$Computername"; $Wmi = Win32::OLE->GetObject ($Class); $if ($aevents = $Wmi->ExecQuery("SELECT * FROM $Win32_Class WHERE Logf +ileName=Application AND Eventcode=1000")) { print "yeah...$aevents\n"; # prints yeah...Win32::OLE=HASH(0x1ab5264) } foreach $aevent (in($aevents)) { # Fails here. print "$aevent{TimeGenerated}\n"; } exit;


Any help would be much appreciated. Thank you.

Mitch

Replies are listed 'Best First'.
Re: WMI EventLog
by VSarkiss (Monsignor) on Feb 11, 2003 at 19:25 UTC

    I'm not familiar with WMI, but here are a few pointers that may help:

    • The string you're seeing is OK, it just means that $aevents is a Win32::OLE object, as it should be.
    • Check for an error after the ExecQuery call by calling Win32::OLE->LastError. Something like:
      $aevents = $Wmi->ExecQuery(...); print "The error code is ", Win32::OLE->LastError(), "\n";
    • I assume the $if thing is just a copy-and-paste-o.
    • One of the best resources I know for working with Perl on Win32 is Dave Roth's web site. A look over there usually turns up useful info. Give it a shot.
    Good luck.

      Thanks for getting back to me so quickly. The $if is just a copy-and paste-o. The error code returned after the ExecQuery is 0, which should mean it worked. I'm thinking the loop and "in" structure may not be a clean translation from vb to perl. I looked on Roth's sight; he does have some WMI examples, but not with looping through events.

      Thanks.
      Mitch
Re: WMI EventLog
by Solo (Deacon) on Feb 11, 2003 at 20:00 UTC
    A few ideas:

    print "$aevent{TimeGenerated}\n";

    should probably be

    print $aevent->{TimeGenerated} . "\n";

    Next, try replacing $Wmi->ExecQuery("...")

    with the InstancesOf method

    $aevents = $Wmi->InstancesOf($Win32_Class)

    While this should return all events (not what is wanted), it might reveal the query statement is the problem. I mean, let's try to get something back, and then we can narrow it down. ;)

    --Solo

    --
    You said you wanted to be around when I made a mistake; well, this could be it, sweetheart.
      You got it, thanks. There were two problems...1) The property should be LogFile not LogFileName. The source I used had it listed wrong. 2) LogFile is a string so it needs to be in ' '. The line should read:
      if ($aevents = $Wmi->ExecQuery("SELECT * FROM $Win32_Class WHERE LogF +ile='Application' AND Eventcode=1000")) {


      Thanks for the insight.

      Mitch
Re: WMI EventLog
by theorbtwo (Prior) on Feb 11, 2003 at 21:52 UTC

    BTW, IIRC, there's an ODBC driver for WMI availabe, which you could access using DBD::ODBC, thus avoiding Win32::OLE entirely. You might have covered this under "I am purposely trying to use WMI..."... Just an idle thought.


    Warning: Unless otherwise stated, code is untested. Do not use without understanding. Code is posted in the hopes it is useful, but without warranty. All copyrights are relinquished into the public domain unless otherwise stated. I am not an angel. I am capable of error, and err on a fairly regular basis. If I made a mistake, please let me know (such as by replying to this node).

      Does anyone actually have source code examples of using the WMI ODBC interface?

      I've just spent the last six hours scouring Google and the best I could find was the sourceforge project Cricket that formerly had a module that used the ODBC interface, but was switched to the Win32::OLE for performance reasons.

      (Maybe someone knows how to fetch the old module out of CVS, but I couldn't find it.)

      --Solo

      --
      May the Source be with you.

        Perl source? No. MSDN has plenty of VB and C source, though, and it shouldn't be too hard to translate them. It was just an idea -- I've never actualy used WMI or it's ODBC interface.

        Sorry


        Warning: Unless otherwise stated, code is untested. Do not use without understanding. Code is posted in the hopes it is useful, but without warranty. All copyrights are relinquished into the public domain unless otherwise stated. I am not an angel. I am capable of error, and err on a fairly regular basis. If I made a mistake, please let me know (such as by replying to this node).