Sunday, February 22, 2009

Build windows service program by C#

เขียน windows service ด้วย C#

# เนื่องด้วยปัญหาเรื่อง limit print job และได้แก้ปัญหาโดยใช้ static collection มาช่วยก็แก้ปัญหาได้แหละ

# นึกว่าปัญหาจะหมดแหละ มีปัญหาอีกอย่าง ที่พบนะคือ เมื่อ iis เริ่มทำงานใหม่เนื่องจากเครื่อง reboot ทำให้มีไฟล์ขยะเกิดขึ้นแน่ๆ ใน temp เรา

# ถ้าเผื่อมีใครไป stop และ start iis ใหม่ก็จะมีปัญหาเหมือนกันแฮะ แล้วจะแก้ไงหว่าเอาไว้ก่อนเรื่องนี้เพราะคงไม่มีคนมือไวไปเล่นหรอกมั้ง

# วันก่อนนั่งนึกวิธีแก้ ตอนแรกนึกว่าน่าจะเขียน bat ไฟล์ไปลบไฟล์ขยะซะ ตอนบูตระบบใหม่ ด้วยการนำไปวางไว้ใน folder Start up ^^' ลืมไปอย่างว่าไฟล์ที่อยู่ใน start up จะทำการก็ต่อเมื่อมีการ login เข้าระบบ

# แต่ไม่ค่อยมีใคร login เข้าระบบอ่ะดิ เพราะเครื่องนั้นเป็น Server

# เลยนึกออกอย่าง ถ้า iis ทำงานได้ทั้งที่ยังไม่ได้ login เราก็เขียนโปรแกรมเป็น service ตัวหนึ่งสิ เมื่อบูตระบบให้ service เราทำการ ลบไฟล์ขยะใน temp ไง ^^'

# หาข้อมูลอยู่ตั้งหลายชัวร์โมง เพราะไม่เคยเขียนอ่ะนะ ก็หาเจอหลายเว็บแต่อ่านไม่ค่อยออกเพราะมีแต่ภาษาอังกฤษ

# เว็บภาษาไทยก็เขียนไม่ค่อยเข้าใจ (ไม่ใช่เค้าเขียนไม่ดีนะ เราโง่เอง ไม่สามารถเข้าใจได้ ^^')

# ก็นั่งมั่วอยู่พักใหญ่แล้วมันก็ทำงานซะที service เราเกือบแย่

ขั้นตอนแบบง่า่ยๆ ก็ประมาณนี้สรุปแบบของตัวเอง



1. สร้างโปรแกรมใหม่โดยเลือกเป็นแบบ windows serivce เลือก ภาษาตามใจชอบในที่นี้ เขียนเป็นแต่ C# ^^'



2. เมื่อคลิก Ok แหละก็จะได้ไฟล์ Services1.cs[Design] โผล่ขึ้นมาเลยจากนั้นทำการเพิ่มตัว installer ก่อนเลยเดี๋ยวค่อยเขียน action ของ service โดยคลิกขวาที่พื้นที่ว่างสีเทาของ Services1.cs[Design] เลือก Add Installer



3. จะได้ 2 object ที่เค้าได้จากให้เราจากการ Add Installer คือ serviceProcessInstaller1 และ serviceInstall1



5. ที่แก้ไข properties ของ serviceProcessInstaller1 สักหน่อย ชื่อ Account ค่าเริ่มต้นจะเป็น user ให้เราแก้เป็น LocalSystem



6. แก้ไข properties ของ serviceInstall1 ซะหน่อย ที่ ServiceName คือชื่อของ service อันนี้แก้ตามสบาย ส่วนอีกอย่างที่น่าสนใจคือ StartType คือ เราจะกำหนดค่าเริ่มต้นเมื่อระบบเริ่มทำกงาน ให้ service เราเริ่มเลยหรือป่าว ถ้าเป็น manaul เราต้องมา start เองเมื่อบูตเข้าไปใช้ระบบ แต่ถ้าเราเลือก Automatic จะเป็นการรัน service อัตโนมัติเมื่อมีการบูตระบบ



7. เรามาเริ่ม เขียน action กันโดยเปิดไฟล์ Service1.cs ขึ้นมา จะเห็น onstart และ onstop ซึ่ง onstart คือ เมื่อเรา start service เมธอด onstart ก็จะถูกเรียกขึ้นมาทำงาน เมื่อเราทำการ stop เมธอด onstop ก็จะถูกเรียกทำงานก่อนหยุด service นั้นไป

8. ทำการเขียนโค้ดใส่ใน onstart ได้เลยในที่นี้ทดสอบเขียนบรรทัดคำสั่งสร้าง directory ชื่อ a ขึ้นมาที่ c: เมื่อบูตระบบทุกครั้งก็เขียนโค้ดประมาณนี้ใส่ในเมธอด onstart และ เราสามารถเพิ่ม เมธอดของเราใส่ใน class Service1 ได้เลย ในที่นี้ขอเขียน code execute command เพิ่มด้วย 1 เมธอด ^^'

protected override void OnStart(string[] args){
// TODO: Add code here to start your service.
string cmd = @"mkdir C:\a";
Service1.ExecuteCommandSync(cmd);

}

// อันนี้คือ เมธอดที่เพิ่มเอง
public static void ExecuteCommandSync(object command)
{
try
{

// create the ProcessStartInfo using "cmd" as the program to be run,
// and "/c " as the parameters.

// Incidentally, /c tells cmd that we want it to execute the
command that follows,
// and then exit.
System.Diagnostics.ProcessStartInfo procStartInfo =

new System.Diagnostics.ProcessStartInfo("cmd", "/c " +
command);

// The following commands are needed to redirect the standard output.
// This means that it will be redirected to the Process.StandardOutput StreamReader.
procStartInfo.RedirectStandardOutput = true;

procStartInfo.UseShellExecute = false;


// Do not create the black window.
procStartInfo.CreateNoWindow = true;


// Now we create a process, assign its ProcessStartInfo and
start it
System.Diagnostics.Process proc = new System.Diagnostics.Process();
proc.StartInfo = procStartInfo;
proc.Start();


// Get the output into a string

string result = proc.StandardOutput.ReadToEnd();


// Display the command
output.
Console.WriteLine(result);

}

catch (Exception objException)
{
// Log the exception

}

}

9. เมื่อเราเขียน action ต่างๆ ให้ service ตัวนี้แหละทำการ compile (Build Soluiton) สิครับ ก็จะทำให้ได้ตัวWindowsService2.exe ซึ่งจะอยู่ใน Debug

สมมุติว่า:
  • เราทำการเพิ่ม C:\WINDOWS\Microsoft.NET\Framework\v2.0.50727 เข้าไปในพาธของระบบแล้ว
  • และได้คัดลอก WindowsService2.exe มาวางไว้ที่ D: แล้วนะ


10. ทำการติดตั้ง service ให้ windows ด้วยคำสั่ง

installutil d:\WindowsService2.exe

# ถ้าติดตั้ง service สำเร็จก็จะขึ้นประมาณว่า The transacted insatll has completed.



11. เข้าไป start service เราได้เลย

Notes:
  • ถ้าจะถอน service เราก็แค่ประมาณนี้ installutil d:\WindowsService2.exe -u หรือ /u ก็ได้
  • อ้างอิงบน studio.net 2005 นะ 2008 ยังไม่เคยใช้น่าจะทำคล้ายกันมั้ง
  • แ่ต่คิดไปแล้วนะ ใช้แค่ task schedule ก็น่าจะพอหว่า ^^'
  • ถ้าเราใช้ task schedule ให้เราเลือกแบบ When my computer starts
References:

No comments:

Post a Comment