1

我有一个 Windows 网络(peer-2-peer)以及 Active Directory,我需要记录向服务器发送任何类型打印的用户的名称。我想编写一个程序来记录他们的用户名和/或他们各自的 IP,并且我熟悉 c#.net 和 c++,但我还没有找到任何关于如何解决我的问题的线索。

有没有什么方法可以在 WMI 的帮助下抓住他们的名字,或者应该用 API 弄脏我的手(但我不知道哪个 API)?

问候。

4

4 回答 4

1

我过去使用过它,如果它没有你需要的所有东西,它至少应该负责监控打印队列。

http://www.merrioncomputing.com
http://www.merrioncomputing.com/Download/PrintQueueWatch/PrinterQueueWatchLicensing.htm

源代码链接(来自 OP 的评论): http:
//www.codeproject.com/KB/printing/printwatchvbnet.aspx

于 2010-01-15T19:52:39.223 回答
1

这些功能在Spooler API下公开。

EnumJobs将枚举给定打印机的所有当前作业。它将返回一个JOB_INFO_1结构,其中包括与给定打印作业关联的用户名:

typedef struct _JOB_INFO_1 {
  DWORD      JobId;
  LPTSTR     pPrinterName;
  LPTSTR     pMachineName;
  LPTSTR     pUserName;
  LPTSTR     pDocument;
  LPTSTR     pDatatype;
  LPTSTR     pStatus;
  DWORD      Status;
  DWORD      Priority;
  DWORD      Position;
  DWORD      TotalPages;
  DWORD      PagesPrinted;
  SYSTEMTIME Submitted;
}JOB_INFO_1, *PJOB_INFO_1;

如果您更喜欢 WMI,则可以wmic.exe/node开关(或您喜欢的变体)和Win32_PrintJob类一起使用。大致:

c:\> wmic /node 10.0.0.1 
wmic> SELECT * FROM Win32_PrintJob

...将返回一个结构,其中包含所选服务器的所有打印作业信息。您可以根据需要使用WHERE子句进行过滤。

于 2010-01-15T19:53:40.317 回答
1

我会选择使用 WMI。这使您能够查询与您的系统关联的打印机批次以及提取所有支持属性。这很简单...

System.Management.ObjectQuery oq = new System.Management.ObjectQuery("SELECT * FROM Win32_PrintJob");

...创建一个 WMI 对象搜索器并枚举结果。

这是一个例子:

WMI 查询打印机

于 2010-01-15T19:57:25.860 回答
0

找出哪个用户在 Windows 中使用 C++ 发送了打印作业。

#include <WinSpool.h>

wstring GetUserNameFromPrintJob(wstring m_strFriendlyName)
{
  wstring strDocName = L"";
  wstring strMachineName = L"";
  wstring strUserName = L"";

  HANDLE hPrinter ;
  if ( OpenPrinter(const_cast<LPWSTR>(m_strFriendlyName.c_str()), &hPrinter, NULL) == 0 )
  {    
    /*OpenPrinter call failed*/    
  }

  DWORD dwBufsize = 0;
  PRINTER_INFO_2* pinfo = 0;
  GetPrinter(hPrinter, 2,(LPBYTE)pinfo, dwBufsize, &dwBufsize); //Get dwBufsize

  PRINTER_INFO_2* pinfo2 = (PRINTER_INFO_2*)malloc(dwBufsize); //Allocate with dwBufsize
  GetPrinter(hPrinter, 2,(LPBYTE)pinfo2, dwBufsize, &dwBufsize);

  DWORD numJobs = pinfo2->cJobs;
  free(pinfo2); 

  JOB_INFO_1 *pJobInfo = 0;
  DWORD bytesNeeded = 0, jobsReturned = 0;

  //Get info about jobs in queue.
  EnumJobs(hPrinter, 0, numJobs, 1, (LPBYTE)pJobInfo, 0,&bytesNeeded,&jobsReturned);
  pJobInfo = (JOB_INFO_1*) malloc(bytesNeeded);
  EnumJobs(hPrinter, 0, numJobs, 1, (LPBYTE)pJobInfo, bytesNeeded, &bytesNeeded, &jobsReturned);


  JOB_INFO_1 *pJobInfoInitial = pJobInfo;
  for(unsigned short count = 0; count < jobsReturned; count++)
  {
    if (pJobInfo != NULL)
    {
      strUserName  = pJobInfo->pUserName  //username
      strMachineName = pJobInfo->pMachineName;   //machine name
      strDocName  = pJobInfo->pDocument; // Document name
      DWORD dw = pJobInfo->Status;         
    }
    pJobInfo++;
  }

  free(pJobInfoInitial);
  ClosePrinter( hPrinter );
  return strUserName ;
}
于 2012-10-16T05:12:04.717 回答