2017-06-02 57 views
1

後立即啓動和停止我正在創建一個無法與我的財政打印機通信的pos應用程序。因此,我決定將收據存儲在文本文件中作爲Json對象,並使用FileSystemWatch製作Windows Service應用程序以檢查文件更新並將其轉發給打印機。我正在使用第三方庫與打印機進行通信。下面是該服務的代碼:帶有FileSystemWatcher的Windows服務在

Program.cs的

static void Main(string[] args) 
{ 
    var program = new Watcher(); 
    if (Environment.UserInteractive) 
    { 
     program.Start(); 
    } 
    else 
    { 
     ServiceBase.Run(new ServiceBase[] 
     { 
      program 
     }); 
    } 
    //ServiceBase[] ServicesToRun; 
    //ServicesToRun = new ServiceBase[] 
    //{ 
    // new Watcher() 
    //}; 
    //ServiceBase.Run(ServicesToRun); 
} 

Watcher.cs

public partial class Watcher : ServiceBase 
{ 

    [DllImport("advapi32.dll", SetLastError = true)] 
    private static extern bool SetServiceStatus(IntPtr handle, ref ServiceStatus serviceStatus); 

    public static OICFiscalPrinter printer { get; set; } 

    [StructLayout(LayoutKind.Sequential)] 
    public struct ServiceStatus 
    { 
     public long dwServiceType; 
     public ServiceState dwCurrentState; 
     public long dwControlsAccepted; 
     public long dwWin32ExitCode; 
     public long dwServiceSpecificExitCode; 
     public long dwCheckPoint; 
     public long dwWaitHint; 
    }; 

    public enum ServiceState 
    { 
     SERVICE_STOPPED = 0x00000001, 
     SERVICE_START_PENDING = 0x00000002, 
     SERVICE_STOP_PENDING = 0x00000003, 
     SERVICE_RUNNING = 0x00000004, 
     SERVICE_CONTINUE_PENDING = 0x00000005, 
     SERVICE_PAUSE_PENDING = 0x00000006, 
     SERVICE_PAUSED = 0x00000007, 
    } 


    public Watcher() 
    { 
     InitializeComponent(); 

    } 

    public void CheckReceipt(object e, FileSystemEventArgs args) 
    { 
     printer = new OICFiscalPrinter(); 
     var name = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile); 
     string text = null; 
     try 
     { 
      text = System.IO.File.ReadAllText(name + "\\Pictures\\test.txt"); 
      var BasketList = JsonConvert.DeserializeObject<List<ItemsOnFacture>>(text); 
      printer.PortConfigString = "PortName=COM4;DataBits=8;Speed=9600;" + 
             "Parity = N; StopBits = 1; FlowControl = X;" + 
             "ReadTimeout = 6000;" + 
             "WriteTimeout = 500; UseReadBuffer = 1"; 
      printer.Active = true; 
      var t = printer.Open(); 
      if (!t) return; 
      printer.OpenReceipt(); 
      foreach (var item in BasketList) 
      { 
       printer.ReceiptItem(item.ItemName, item.VatFee == 5 ? "B" : item.VatFee == 8 ? "A" : "D", 
        (decimal)item.PriceBrutto, 
        item.Amount, "unit", (decimal)item.PriceBruttoSum); 
      } 
      printer.CloseReceipt((decimal)BasketList.Sum(w => w.PriceBruttoSum), 
       (decimal)BasketList.Sum(w => w.PriceBruttoSum)); 
      printer.Close(); 
      File.Delete(name + "\\Pictures\\test.txt"); 
     } 
     catch 
     { 

     } 

    } 

    public void Start() 
    { 
     //Start Logic here 
     var serviceStatus = new ServiceStatus 
     { 
      dwCurrentState = ServiceState.SERVICE_START_PENDING, 
      dwWaitHint = 100000 
     }; 


     this.fileSystemWatcher1 = new System.IO.FileSystemWatcher(); 
     ((System.ComponentModel.ISupportInitialize)(this.fileSystemWatcher1)).BeginInit(); 
     // 
     // fileSystemWatcher1 
     // 
     this.fileSystemWatcher1.EnableRaisingEvents = true; 
     var name = Environment.GetFolderPath(Environment.SpecialFolder.UserProfile); 
     fileSystemWatcher1 = new FileSystemWatcher(name + "\\Pictures", "test.txt") 
     { 
      EnableRaisingEvents = true, 
      IncludeSubdirectories = false, 
      NotifyFilter = NotifyFilters.DirectoryName 
     }; 


     SetServiceStatus(this.ServiceHandle, ref serviceStatus); 

     this.fileSystemWatcher1.Changed += new System.IO.FileSystemEventHandler(this.CheckReceipt); 

     ((System.ComponentModel.ISupportInitialize)(this.fileSystemWatcher1)).EndInit(); 

     // Update the service state to Running. 
     serviceStatus.dwCurrentState = ServiceState.SERVICE_RUNNING; 
     SetServiceStatus(this.ServiceHandle, ref serviceStatus); 
    } 

    protected override void OnStart(string[] args) 
    { 
     Start(); 
    } 

    protected override void OnContinue() 
    { 

    } 

    protected override void OnStop() 
    { 

    } 

    private FileSystemWatcher fileSystemWatcher1; 

    /// <summary> 
    /// Required designer variable. 
    /// </summary> 
    private System.ComponentModel.IContainer components = null; 
    /// <summary> 
    /// Clean up any resources being used. 
    /// </summary> 
    /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param> 
    protected override void Dispose(bool disposing) 
    { 
     if (disposing && (components != null)) 
     { 
      components.Dispose(); 
     } 
     base.Dispose(disposing); 
    } 

    #region Component Designer generated code 

    /// <summary> 
    /// Required method for Designer support - do not modify 
    /// the contents of this method with the code editor. 
    /// </summary> 
    private void InitializeComponent() 
    { 
     // 
     // Watcher 
     // 
     components = new System.ComponentModel.Container(); 
     this.ServiceName = "WATTOFP"; 

    } 

    #endregion 
} 

ProjectInstaller.cs

[RunInstaller(true)] 
public class ProjectInstaller : System.Configuration.Install.Installer 
{ 
    public ProjectInstaller() 
    { 
     InitializeComponent(); 
    } 

    /// <summary> 
    /// Required designer variable. 
    /// </summary> 
    private System.ComponentModel.IContainer components = null; 

    /// <summary> 
    /// Clean up any resources being used. 
    /// </summary> 
    /// <param name="disposing">true if managed resources should be disposed; otherwise, false.</param> 
    protected override void Dispose(bool disposing) 
    { 
     if (disposing && (components != null)) 
     { 
      components.Dispose(); 
     } 
     base.Dispose(disposing); 
    } 

    #region Component Designer generated code 

    /// <summary> 
    /// Required method for Designer support - do not modify 
    /// the contents of this method with the code editor. 
    /// </summary> 
    private void InitializeComponent() 
    { 
     this.serviceProcessInstaller1 = new System.ServiceProcess.ServiceProcessInstaller(); 
     this.serviceInstaller1 = new System.ServiceProcess.ServiceInstaller(); 
     // 
     // serviceProcessInstaller1 
     // 
     this.serviceProcessInstaller1.Account = System.ServiceProcess.ServiceAccount.LocalSystem; 
     this.serviceProcessInstaller1.Password = null; 
     this.serviceProcessInstaller1.Username = null; 
     // 
     // serviceInstaller1 
     // 
     this.serviceInstaller1.Description = "WATTO Fiscal Printer"; 
     this.serviceInstaller1.DisplayName = "WATTO Fiscal Printer"; 
     this.serviceInstaller1.ServiceName = "WATTOFP"; 
     this.serviceInstaller1.StartType = System.ServiceProcess.ServiceStartMode.Automatic; 
     // 
     // ProjectInstaller 
     // 
     this.Installers.AddRange(new System.Configuration.Install.Installer[] { 
     this.serviceProcessInstaller1, 
     this.serviceInstaller1}); 

    } 

    #endregion 

    private System.ServiceProcess.ServiceProcessInstaller serviceProcessInstaller1; 
    private System.ServiceProcess.ServiceInstaller serviceInstaller1; 
} 

問題是,安裝後,當我嘗試運行服務時,它啓動並立即停止,因爲警告出現。如何使服務運行並監視變更文件?

+0

你檢查了Windows事件日誌嗎?應該記錄一個異常。另外您是否調試過該服務? –

+0

你手動更新服務狀態的原因是什麼?所有這些工作都應該自動完成。 –

回答

0

問題可能是服務默認情況下正在系統帳戶下運行。因此用戶文件夾不是你所期望的,並且那裏沒有文件。

通常,當服務無法啓動時,在事件日誌中會出現異常。請在此處張貼以獲得進一步的幫助。

+0

謝謝,那實際上是一個問題。該服務在系統帳戶下運行時查找錯誤目錄中的文件。該文件夾只是一個測試位置,但對我來說這是一個教訓,不要不小心挑選位置! –