如何跟踪应用程序的使用?

我想开发一个应用程序(我猜在后台运行的所有时间)来跟踪应用程序的使用情况(msword,excel,powerpoint,* .exe等)。

我可以处理将数据发布到数据库但是不知道从哪里开始监视正在运行的应用程序(当它们启动时,停止时)。 有人有任何线索吗?

您可以使用System.Diagnostics.Process.GetProcesses()定期轮询正在运行的进程列表。

以下代码输出有关启动和退出进程的信息。 退出系统进程将无法识别。

 class Program { struct ProcessStartTimePair { public Process Process { get; set; } public DateTime StartTime { get; set; } public DateTime ExitTime { get { return DateTime.Now; // approximate value } } public ProcessStartTimePair(Process p) : this() { Process = p; try { StartTime = p.StartTime; } catch (System.ComponentModel.Win32Exception) { StartTime = DateTime.Now; // approximate value } } } static void Main(string[] args) { List knownProcesses = new List(); while (true) { foreach (Process p in Process.GetProcesses()) { if (!knownProcesses.Select(x => x.Process.Id).Contains(p.Id)) { knownProcesses.Add(new ProcessStartTimePair(p)); Console.WriteLine("Detected new process: " + p.ProcessName); } } for (int i = 0; i < knownProcesses.Count; i++) { ProcessStartTimePair pair = knownProcesses[i]; try { if (pair.Process.HasExited) { Console.WriteLine(pair.Process.ProcessName + " has exited (alive from {0} to {1}).", pair.StartTime.ToString(), pair.ExitTime.ToString()); knownProcesses.Remove(pair); i--; // List was modified, 1 item less // TODO: Store in the info in the database } } catch (System.ComponentModel.Win32Exception) { // Would have to check whether the process still exists in Process.GetProcesses(). // The process probably is a system process. } } Console.WriteLine(); System.Threading.Thread.Sleep(1000); } } } 

您可能只是忽略了不允许您读取HasExited属性的系统进程。

编辑

这是一个.net 2.0版本:

  static void Main(string[] args) { List knownProcesses = new List(); while (true) { foreach (Process p in Process.GetProcesses()) { if (!ProcessIsKnown(knownProcesses, p.Id)) { knownProcesses.Add(new ProcessStartTimePair(p)); Console.WriteLine("Detected new process: " + p.ProcessName); } } for (int i = 0; i < knownProcesses.Count; i++) [...] } } static bool ProcessIsKnown(List knownProcesses, int ID) { foreach (ProcessStartTimePair pstp in knownProcesses) { if (pstp.Process.Id == ID) { return true; } } return false; } 

请注意,代码可以改进,只显示概念。

您可以定期轮询所有顶级窗口并记录窗口标题文本; 并在此基础上对哪个程序正在运行做出一些结论。

或者您可以通过流程名称或组合来完成。

有关枚举窗口的信息,请参阅http://msdn.microsoft.com/en-us/library/ms633497(VS.85).aspx ,以下是如何在托管代码中使用它 。 要枚举进程,请使用Process.GetProcesses方法或访问http://www.codeproject.com/KB/threads/enumprocess.aspx

进程启动/退出时,可以使用WMI进行通知

一个完整的工作示例在ASP.NET的博客文章中 。

它的基础知识(从后代的博客文章中复制):

创建一个inheritance自ManagementEventWatcher的类

在构造函数内部,设置:

 this.Query.QueryLanguage = "WQL"; this.Query.QueryString = @"SELECT * FROM __InstanceOperationEvent WITHIN 1 WHERE TargetInstance ISA 'Win32_Process'"; this.EventArrived += watcher_EventArrived; // Delegate for EventArrivedEventHandler 

创建一个EventArrivedEventHandler,如:

 private void watcher_EventArrived(object sender, EventArrivedEventArgs e) { string eventType = e.NewEvent.ClassPath.ClassName; Win32_Process proc = new Win32_Process(e.NewEvent["TargetInstance"] as ManagementBaseObject); switch (eventType) { case "__InstanceCreationEvent": Console.WriteLine("Process Created"); break; case "__InstanceDeletionEvent": Console.WriteLine("Process Deleted (Ended)"); break; case "__InstanceModificationEvent": Console.WriteLine("Process Modified (possibly still running)"); break; } } 

轮询很容易,但你应该真正挂钩win32事件,而是收到这些事情何时发生的通知。

我有一个类似的副项目来创建一个“任务栏”类型的应用程序。 我的目标是在移动/创建/关闭窗口时通知应用程序,以便我可以使用此信息来显示/更新UI。

bb4win app有这个“层”,它可以从系统中捕获不同类型的通知,并使用它来创建一个替代的桌面shell。 源代码可用,并以c编码。

这是我用来开始使用Win32 Hooks的链接 。