使用 Windows 服务在 FileSystemEventHandler 上插入数据库
Database insert on FileSystemEventHandler with Windows Service
我已经设法使服务正常工作,并将 FileSystemEventHandler 插入到文本文件中,但现在需要将其更改为插入到数据库和文本文件中。
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Configuration;
using System.Data;
using System.Data.SqlClient;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.ServiceProcess;
using System.Text;
using System.Threading.Tasks;
using System.Timers;
namespace WindowsServiceTest
{
public partial class Service1 : ServiceBase
{
Timer timer = new Timer(); // name space(using System.Timers;)
public static string path = ConfigurationManager.AppSettings["findpath"];
public Service1()
{
InitializeComponent();
}
protected override void OnStart(string[] args)
{
WriteToFile("Service is started at " + DateTime.Now);
timer.Elapsed += new ElapsedEventHandler(OnElapsedTime);
timer.Interval = 10000; //number in milisecinds
timer.Enabled = true;
FileSystemWatcher watcher = new FileSystemWatcher
{
Path = path,
NotifyFilter = NotifyFilters.LastWrite,
};
watcher.Created += new FileSystemEventHandler(FileSystemWatcher_Changed);
watcher.Renamed += new RenamedEventHandler(FileSystemWatcher_Renamed);
watcher.Changed += new FileSystemEventHandler(FileSystemWatcher_Changed);
watcher.EnableRaisingEvents = true;
}
public static void FileSystemWatcher_Changed(object source, FileSystemEventArgs e)
{
using (SqlConnection con = new SqlConnection("Data Source=localhost\SQLEXPRESS;Database=ServiceTest;Integrated Security=True;"))
{
try
{
con.Open();
var command = new SqlCommand("Insert into test(URL, Location) values(@URL, @agendaname);", con);
command.Parameters.Add("@URL", System.Data.SqlDbType.VarChar, 100).Value = e.Name;
command.Parameters.Add("@agendaname", System.Data.SqlDbType.VarChar, 100).Value = "Case History";
command.ExecuteNonQuery();
}
catch
{
WriteToFile($"Failed to insert: {e.Name} into the database");
}
}
}
public static void FileSystemWatcher_Renamed(object source, RenamedEventArgs e)
{
WriteToFile($"File Renamed: {e.OldFullPath} renamed to {e.FullPath}");
}
private void OnElapsedTime(object source, ElapsedEventArgs e)
{
WriteToFile("Service is recalled at " + DateTime.Now);
}
protected override void OnStop()
{
WriteToFile("Service is stopped at " + DateTime.Now);
}
public static void WriteToFile(string Message)
{
string path = AppDomain.CurrentDomain.BaseDirectory + "\Logs";
if (!Directory.Exists(path))
{
Directory.CreateDirectory(path);
}
string filepath = AppDomain.CurrentDomain.BaseDirectory + "\Logs\ServiceLog_" + DateTime.Now.Date.ToShortDateString().Replace('/', '_') + ".txt";
if (!File.Exists(filepath))
{
// Create a file to write to.
using (StreamWriter sw = File.CreateText(filepath))
{
sw.WriteLine(Message);
}
}
else
{
using (StreamWriter sw = File.AppendText(filepath))
{
sw.WriteLine(Message);
}
}
}
}
}
我认为我做错了数据库插入,因为 catch 块被插入到文本文件中。但是,我 运行 代码本身在一个单独的项目中,并在控制台应用程序中插入到数据库中。
感谢任何帮助,谨致问候。
Windows 服务 运行 在与控制台应用程序不同的安全环境下。正如评论所披露的那样,异常与您的连接字符串有关。
如果我们分析 connectiong 字符串,我们可以看到您正在使用 IntegratedSecurity="True".
进行身份验证,因为您的 windows 服务在 运行ning 下
服务帐户身份验证失败。我已经指定了 2 个选项来解决这个问题。
选项 1:将服务 运行 作为 windows 帐户(不推荐,但可用于测试)
- 打开运行箱子(胜利标志+R)
- 类型Services.MSC
- 找到您的服务并右键单击属性
- 选择登录选项卡
- 输入您的 windows 身份验证用户名和密码,以便为 运行 提供服务
选项 2:创建 SQL 服务器帐户
- 在SQL 中为数据库
创建用户名和密码
- 更新连接字符串以指定创建的新用户名和密码
我已经设法使服务正常工作,并将 FileSystemEventHandler 插入到文本文件中,但现在需要将其更改为插入到数据库和文本文件中。
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Configuration;
using System.Data;
using System.Data.SqlClient;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.ServiceProcess;
using System.Text;
using System.Threading.Tasks;
using System.Timers;
namespace WindowsServiceTest
{
public partial class Service1 : ServiceBase
{
Timer timer = new Timer(); // name space(using System.Timers;)
public static string path = ConfigurationManager.AppSettings["findpath"];
public Service1()
{
InitializeComponent();
}
protected override void OnStart(string[] args)
{
WriteToFile("Service is started at " + DateTime.Now);
timer.Elapsed += new ElapsedEventHandler(OnElapsedTime);
timer.Interval = 10000; //number in milisecinds
timer.Enabled = true;
FileSystemWatcher watcher = new FileSystemWatcher
{
Path = path,
NotifyFilter = NotifyFilters.LastWrite,
};
watcher.Created += new FileSystemEventHandler(FileSystemWatcher_Changed);
watcher.Renamed += new RenamedEventHandler(FileSystemWatcher_Renamed);
watcher.Changed += new FileSystemEventHandler(FileSystemWatcher_Changed);
watcher.EnableRaisingEvents = true;
}
public static void FileSystemWatcher_Changed(object source, FileSystemEventArgs e)
{
using (SqlConnection con = new SqlConnection("Data Source=localhost\SQLEXPRESS;Database=ServiceTest;Integrated Security=True;"))
{
try
{
con.Open();
var command = new SqlCommand("Insert into test(URL, Location) values(@URL, @agendaname);", con);
command.Parameters.Add("@URL", System.Data.SqlDbType.VarChar, 100).Value = e.Name;
command.Parameters.Add("@agendaname", System.Data.SqlDbType.VarChar, 100).Value = "Case History";
command.ExecuteNonQuery();
}
catch
{
WriteToFile($"Failed to insert: {e.Name} into the database");
}
}
}
public static void FileSystemWatcher_Renamed(object source, RenamedEventArgs e)
{
WriteToFile($"File Renamed: {e.OldFullPath} renamed to {e.FullPath}");
}
private void OnElapsedTime(object source, ElapsedEventArgs e)
{
WriteToFile("Service is recalled at " + DateTime.Now);
}
protected override void OnStop()
{
WriteToFile("Service is stopped at " + DateTime.Now);
}
public static void WriteToFile(string Message)
{
string path = AppDomain.CurrentDomain.BaseDirectory + "\Logs";
if (!Directory.Exists(path))
{
Directory.CreateDirectory(path);
}
string filepath = AppDomain.CurrentDomain.BaseDirectory + "\Logs\ServiceLog_" + DateTime.Now.Date.ToShortDateString().Replace('/', '_') + ".txt";
if (!File.Exists(filepath))
{
// Create a file to write to.
using (StreamWriter sw = File.CreateText(filepath))
{
sw.WriteLine(Message);
}
}
else
{
using (StreamWriter sw = File.AppendText(filepath))
{
sw.WriteLine(Message);
}
}
}
}
}
我认为我做错了数据库插入,因为 catch 块被插入到文本文件中。但是,我 运行 代码本身在一个单独的项目中,并在控制台应用程序中插入到数据库中。
感谢任何帮助,谨致问候。
Windows 服务 运行 在与控制台应用程序不同的安全环境下。正如评论所披露的那样,异常与您的连接字符串有关。
如果我们分析 connectiong 字符串,我们可以看到您正在使用 IntegratedSecurity="True".
进行身份验证,因为您的 windows 服务在 运行ning 下
服务帐户身份验证失败。我已经指定了 2 个选项来解决这个问题。
选项 1:将服务 运行 作为 windows 帐户(不推荐,但可用于测试)
- 打开运行箱子(胜利标志+R)
- 类型Services.MSC
- 找到您的服务并右键单击属性
- 选择登录选项卡
- 输入您的 windows 身份验证用户名和密码,以便为 运行 提供服务
选项 2:创建 SQL 服务器帐户
- 在SQL 中为数据库 创建用户名和密码
- 更新连接字符串以指定创建的新用户名和密码