繁体   English   中英

使用c#从远程PC查找空闲时间

[英]Find idle time from remote pc using c#

我需要使用c#应用程序从服务器pc中找出远程pc的空闲时间。 我有一个在局域网中连接的IP地址和主机名列表。 我想找出LAN中连接的每台计算机的空闲时间超过30分钟。 我为本地电脑做过,但它不适用于远程电脑。 这是我的本地PC代码。

[DllImport("user32.dll")]
private static extern bool GetLastInputInfo(ref LASTINPUTINFO plii);

 private int GetIdleTime()
{
    LASTINPUTINFO lastone = new LASTINPUTINFO();
    lastone.cbSize = (uint)Marshal.SizeOf(lastone);
    lastone.dwTime = 0;

    int idleTime = 0;

    int tickCount = Environment.TickCount;
    if (GetLastInputInfo(ref lastone))
    {
        idleTime = tickCount - (int)lastone.dwTime;
        return idleTime;
    }
    else
        return 0;
}

根据MSDN ,这对于本地机器来说是不可能的,更不用说远程机器了。

此功能对输入空闲检测很有用。 但是,GetLastInputInfo不会在所有正在运行的会话中提供系统范围的用户输入信息。 相反,GetLastInputInfo仅为调用该函数的会话提供特定于会话的用户输入信息。

但是,您可以尝试以下方法之一:

  • 在每台PC上都有一个可以查询的进程。
  • 在每台PC上都有一个流程向您的中央流程报告。
  • 监视远程PC进程以确定屏幕保护程序是否处于活动状态。

如果您没有停用终端服务,并且客户端是xp或更高版本,您也可以使用

ITerminalServicesSession.LastInputTime

为此,您可以使用Cassia库或p / invoke

WTSQuerySessionInformation

我使用这个远程WMI查询:

object idleResult = Functions.remoteWMIQuery(machinename, "", "", "Select CreationDate From Win32_Process WHERE Name = \"logonUI.exe\"", "CreationDate", ref wmiOK);

Logonui.exe是锁屏。 在业务环境中,大多数系统在用户空闲时锁定。

您可以在DateTime格式中翻译这样的结果

DateTime idleTime = Functions.ParseCIM_DATETIME((string)idleResult);

ParseCIM_DATETIME是这个功能的地方:

public static DateTime ParseCIM_DATETIME(string date)
    {
        //datetime object to store the return value
        DateTime parsed = DateTime.MinValue;

        //check date integrity
        if (date != null && date.IndexOf('.') != -1)
        {
            //obtain the date with miliseconds
            string newDate = date.Substring(0, date.IndexOf('.') + 4);

            //check the lenght
            if (newDate.Length == 18)
            {
                //extract each date component
                int y = Convert.ToInt32(newDate.Substring(0, 4));
                int m = Convert.ToInt32(newDate.Substring(4, 2));
                int d = Convert.ToInt32(newDate.Substring(6, 2));
                int h = Convert.ToInt32(newDate.Substring(8, 2));
                int mm = Convert.ToInt32(newDate.Substring(10, 2));
                int s = Convert.ToInt32(newDate.Substring(12, 2));
                int ms = Convert.ToInt32(newDate.Substring(15, 3));

                //compose the new datetime object
                parsed = new DateTime(y, m, d, h, mm, s, ms);
            }
        }

        //return datetime
        return parsed;
    }

远程WMI查询功能如下:

public static object remoteWMIQuery(string machine, string username, string password, string WMIQuery, string property, ref bool jobOK)
    {
        jobOK = true;
        if (username == "")
        {
            username = null;
            password = null;
        }
        // Configure the connection settings.
        ConnectionOptions options = new ConnectionOptions();
        options.Username = username; //could be in domain\user format
        options.Password = password;
        ManagementPath path = new ManagementPath(String.Format("\\\\{0}\\root\\cimv2", machine));
        ManagementScope scope = new ManagementScope(path, options);

        // Try and connect to the remote (or local) machine.
        try
        {
            scope.Connect();
        }
        catch (ManagementException ex)
        {
            // Failed to authenticate properly.
            jobOK = false;
            return "Failed to authenticate: " + ex.Message;
            //p_extendederror = (int)ex.ErrorCode;
            //return Status.AuthenticateFailure;
        }
        catch (System.Runtime.InteropServices.COMException)
        {
            // Unable to connect to the RPC service on the remote machine.
            jobOK = false;
            return "Unable to connect to RPC service";
            //p_extendederror = ex.ErrorCode;
            //return Status.RPCServicesUnavailable;
        }
        catch (System.UnauthorizedAccessException)
        {
            // User not authorized.
            jobOK = false;
            return "Error: Unauthorized access";
            //p_extendederror = 0;
            //return Status.UnauthorizedAccess;
        }

        try
        {
            ObjectQuery oq = new ObjectQuery(WMIQuery);
            ManagementObjectSearcher searcher = new ManagementObjectSearcher(scope, oq);

            foreach (ManagementObject queryObj in searcher.Get())
            {
                if (property != null)
                {
                    return queryObj[property];
                }
                else return queryObj;
            }
        }
        catch (Exception e)
        {
            jobOK = false;
            return "Error: " + e.Message;
        }
        return "";
    }

如果您启用了屏幕保护程序,我建议您检查屏幕保护程序上的CreateDate,并从遥控器创建与创建时间的差异,您将获得空闲时间+屏幕保护程序超时

您可能希望将WMI用于此类事情

它是一个黑客,但它的工作原理

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM