线程和在Windows服务中调用方法

时间:2015-12-17 14:00:03

标签: c# multithreading windows-services invoke wmi-query

我正在将此项目实现为Windows服务。我正在尝试找出本地的开放网络接口并记录它们。当网络接口发生变化时,会触发newAdapterNotifier方法

    public void newAdapterNotifier(object sender, EventArrivedEventArgs e) //Change in network
    {
        checkNetworkAdapters();
    }

此方法由WMI触发我的意思是;

ManagementEventWatcher watcher = null;
query = new WqlEventQuery();
query.EventClassName = "__InstanceOperationEvent";
query.WithinInterval = new TimeSpan(0, 0, 1);
query.Condition = @"TargetInstance ISA 'Win32_NetworkAdapter' AND TargetInstance.NetConnectionStatus IS NOT NULL";
watcher = new ManagementEventWatcher(scope, query);
watcher.EventArrived += new EventArrivedEventHandler(newAdapterNotifier);

在newAdapterNotifier中,我正在调用checkNetworkAdapters,它没有给出任何错误但也没有工作。在WindowsForms中,我只使用相同的代码执行相同的代码,这是工作!!!;

public delegate void ControlNetworkAdapter();
public void newAdapterNotifier(object sender, EventArrivedEventArgs e) //Change in network
{
    this.Invoke(new ControlNetworkAdapter(checkNetworkAdapters));
}

由于Windows服务应用程序中没有Invoke方法,因此无效。我该如何解决?

CLASS的完整代码(如果在允许打开的情况下打开任何其他网络接口。发送邮件)

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Management;
using System.Net.NetworkInformation;

namespace newInternetNotifier
{
    class newNetworkInterfaceNotifier
    {
        ManagementEventWatcher watcher = null;
        WqlEventQuery query;
        ManagementOperationObserver observer = new ManagementOperationObserver();
        ManagementScope scope = new ManagementScope("root\\CIMV2");
        DbManager sqlConn;
        string cameras1IP = "10.0.0.102";
        string cameras2IP = "10.0.0.103";

        public newNetworkInterfaceNotifier(DbManager _sqlConn)
        {
            sqlConn = _sqlConn;
            getPingableIPs();
            System.Threading.Thread thr = System.Threading.Thread.CurrentThread;
            tmr.Tick +=new EventHandler(tmr_Tick);

            stopTimer();

            checkNetworkAdapters();
            prepareEvent();
        }

        void getPingableIPs() {
            cameras1IP = sqlConn.GetScalarValue("SELECT dbo.GetIP(1)").ToString();
            cameras2IP = sqlConn.GetScalarValue("SELECT dbo.GetIP(2)").ToString();
        }

        int elapsedTime;
        System.Windows.Forms.Timer tmr = new System.Windows.Forms.Timer();
        void startTimer() 
        {
            elapsedTime = 0;
            tmr.Interval = 1000;
            tmr.Start();
        }

        void stopTimer()
        {
            tmr.Stop();
        }

        void tmr_Tick(object sender, EventArgs e)
        {
            elapsedTime += 1;
            if (elapsedTime == 10) {
                stopTimer();
                MailSend();
            }
        }

        public void MailSend() {
            //Send mail code here
        }

        bool sendMail = false;
        protected bool SendMail
        {
            set 
            {
                if (value && !sendMail)
                    startTimer();
                else if (!value && sendMail)
                    stopTimer();

                sendMail = value; 
            }
            get { return sendMail; }
        }

        public void prepareEvent()
        {
            scope.Options.EnablePrivileges = true;
            try
            {
                query = new WqlEventQuery();
                query.EventClassName = "__InstanceOperationEvent";
                query.WithinInterval = new TimeSpan(0, 0, 1);
                query.Condition = @"TargetInstance ISA 'Win32_NetworkAdapter' AND TargetInstance.NetConnectionStatus IS NOT NULL";
                watcher = new ManagementEventWatcher(scope, query);
                watcher.EventArrived += new EventArrivedEventHandler(newAdapterNotifier);
                watcher.Start();                   
            }
            catch
            {
                System.Threading.Thread.Sleep(100000);
                prepareEvent();
            }
        }

        public void watcherStop()
        {
            watcher.Stop();
        }

        Ping p = new Ping();
        public HashSet<NetworkInterface> upAndReal;
        public void checkNetworkAdapters()
        {
            if (upAndReal == null)
                upAndReal = new HashSet<NetworkInterface>();
            else if (upAndReal.Count > 0)
                upAndReal.Clear();

            string desc = "";
            string name = "";

            foreach (NetworkInterface netInt in NetworkInterface.GetAllNetworkInterfaces())
            {
                desc = netInt.Description;
                name = netInt.Name;

                if (netInt.OperationalStatus == OperationalStatus.Up && desc.IndexOf("virtual", StringComparison.OrdinalIgnoreCase) < 0 && name.IndexOf("virtual", StringComparison.OrdinalIgnoreCase) < 0 && desc.IndexOf("Microsoft", StringComparison.OrdinalIgnoreCase) < 0 && name.IndexOf("Microsoft", StringComparison.OrdinalIgnoreCase) < 0 && (desc.IndexOf("Loopback", StringComparison.OrdinalIgnoreCase) < 0) && name.IndexOf("Loopback", StringComparison.OrdinalIgnoreCase) < 0)
                {
                    upAndReal.Add(netInt);
                }
            }

            if (upAndReal.Count <= 1 || (upAndReal.Count == 2 && p.Send(cameras1IP).Status == IPStatus.Success && p.Send(cameras2IP).Status == IPStatus.Success)){
                SendMail = false;
                return;
            }

            SendMail = true;
        }

        public void newAdapterNotifier(object sender, EventArrivedEventArgs e) //Change in network
        {

            checkNetworkAdapters();
        }
    }
}

1 个答案:

答案 0 :(得分:0)

我解决了这个问题。这是关于计时器。我们无法在Windows服务中使用System.Windows.Forms.Timer。我们需要使用其他的..但是它是哪一个?