【问题标题】:Remote Desktop Connection - C# Events远程桌面连接 - C# 事件
【发布时间】:2012-09-27 09:30:00
【问题描述】:

有个小问题。

我们有一个来自 Netgear 的面向互联网的 VPN,允许教职员工和教师在家中使用 RDC 访问学校网络。

他们使用 Web 浏览器登录 VPN,点击我们的远程服务器之一,他们就被 RDC 加入了。

人们有一个很大的问题,即注销。它似乎逃脱了他们的头脑。所有用户正在做的只是单击 RDC 客户端上的关闭按钮,这不会将他们注销。

我们正在构建一个程序来解决这个问题,这个想法是“挂钩”到远程桌面 API,然后检查会话是否断开,如果是,我们注销用户。

程序将作为服务或物理最小化的 EXE 在后台运行。

我们正在用 C# 构建它。那么有人知道可以使用 .NET 4 调用的任何 RDC 事件吗?可以让我们知道用户何时关闭会话。

如果您需要这方面的更多信息,请告诉我。

干杯

【问题讨论】:

标签: c# .net rdp


【解决方案1】:

知道了。

打电话

SystemEvents.SessionSwitch += new SessionSwitchEventHandle SystemEvents_SessionSwitch);

然后

        static void SystemEvents_SessionSwitch(object sender, SessionSwitchEventArgs e)
    {
        if (e.Reason == SessionSwitchReason.RemoteDisconnect || e.Reason == SessionSwitchReason.ConsoleDisconnect)
        {
            // Log off the user...

        }
        else
        {
            // Physical Logon
        }
    }

【讨论】:

  • 只是出于好奇,该事件是否仅针对运行应用程序的用户触发,还是针对任何与计算机断开连接的用户触发?
  • 我认为只有运行应用程序的用户。所以我会在他们登录到远程服务器时使用组策略来运行它,然后当他们关闭 rdp 会话时,它应该会触发应用程序
  • 如果我使用远程桌面登录/注销,我也会收到此事件。由于某种原因,使用 TeamViewer 时不会发生该事件。唉,SystemParameters.IsRemoteSessionSystemParameters.IsRemoteControlled 都没有给出真正的价值
【解决方案2】:

这比上面的其他答案效果更好。

        public Form1()
    {
        InitializeComponent();

        if (!WTSRegisterSessionNotification(this.Handle, NOTIFY_FOR_THIS_SESSION))
        {
            Marshal.ThrowExceptionForHR(Marshal.GetLastWin32Error());
        }
    }

    [DllImport("user32.dll")]
    public static extern int ExitWindowsEx(int uFlags, int dwReason);

    [DllImport("WtsApi32.dll")]
    private static extern bool WTSRegisterSessionNotification(IntPtr hWnd, [MarshalAs(UnmanagedType.U4)]int dwFlags);

    [DllImport("WtsApi32.dll")]
    private static extern bool WTSUnRegisterSessionNotification(IntPtr hWnd);

    // constants that can be passed for the dwFlags parameter
    const int NOTIFY_FOR_THIS_SESSION = 0;
    const int NOTIFY_FOR_ALL_SESSIONS = 1;

    // message id to look for when processing the message (see sample code)
    const int WM_WTSSESSION_CHANGE = 0x2b1;

    // WParam values that can be received: 
    const int WTS_CONSOLE_CONNECT = 0x1; // A session was connected to the console terminal.
    const int WTS_CONSOLE_DISCONNECT = 0x2; // A session was disconnected from the console terminal.
    const int WTS_REMOTE_CONNECT = 0x3; // A session was connected to the remote terminal.
    const int WTS_REMOTE_DISCONNECT = 0x4; // A session was disconnected from the remote terminal.
    const int WTS_SESSION_LOGON = 0x5; // A user has logged on to the session.
    const int WTS_SESSION_LOGOFF = 0x6; // A user has logged off the session.
    const int WTS_SESSION_LOCK = 0x7; // A session has been locked.
    const int WTS_SESSION_UNLOCK = 0x8; // A session has been unlocked.
    const int WTS_SESSION_REMOTE_CONTROL = 0x9; // A session has changed its remote controlled status.

    protected override void OnHandleDestroyed(EventArgs e)
    {
        // unregister the handle before it gets destroyed
        WTSUnRegisterSessionNotification(this.Handle);
        base.OnHandleDestroyed(e);
    }

    protected override void WndProc(ref Message m)
    {
        if (m.Msg == WM_WTSSESSION_CHANGE)
        {
            int value = m.WParam.ToInt32();
            if (value == WTS_REMOTE_DISCONNECT)
            {
                ExitWindowsEx(4, 0); // Logout the user on disconnect
            }
            else if (value == WTS_REMOTE_CONNECT)
            {
                MessageBox.Show("Welcome to the VPN. There is no need to Logout anymore, as when you close this session it will automatically log you out");
            }
        }
        base.WndProc(ref m);
    }

【讨论】:

  • 这比other answer 有什么优势? (我认为答案是(a)您不需要引用任何额外的 DLL,并且(b)您可以更好地控制您正在收听的内容)。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2010-11-01
  • 2015-02-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-05-04
相关资源
最近更新 更多