■ 윈도우즈 서비스 내에서 사용자 계정 변경하기
------------------------------------------------------------------------------------------------------------------------
▶ ImpersonationHelper.cs
using System; using System.Runtime.InteropServices; using System.Security.Principal;
namespace TestService { /// <summary> /// 가장 헬퍼 /// </summary> public class ImpersonationHelper : IDisposable { //////////////////////////////////////////////////////////////////////////////////////////////////// Import ////////////////////////////////////////////////////////////////////////////////////////// Static //////////////////////////////////////////////////////////////////////////////// Private
#region 사용자 로그온 하기 - LogonUser(userAccount, domain, password, logonType, logonProvider, tokenHandle)
/// <summary> /// 사용자 로그온 하기 /// </summary> /// <param name="userAccount">사용자 계정</param> /// <param name="domain">도메인</param> /// <param name="password">패스워드</param> /// <param name="logonType">로그온 타입</param> /// <param name="logonProvider">로그온 제공자</param> /// <param name="tokenHandle">토큰 핸들</param> /// <returns>처리 결과</returns> [DllImport("advapi32.dll", SetLastError = true)] private static extern bool LogonUser(string userAccount, string domain, string password, int logonType, int logonProvider, ref IntPtr tokenHandle);
#endregion #region 핸들 닫기 - CloseHandle(tokenHandle)
/// <summary> /// 핸들 닫기 /// </summary> /// <param name="tokenHandle">토큰 핸들</param> /// <returns>처리 결과</returns> [DllImport("kernel32.dll", CharSet = CharSet.Auto)] private extern static bool CloseHandle(IntPtr tokenHandle);
#endregion
//////////////////////////////////////////////////////////////////////////////////////////////////// Field ////////////////////////////////////////////////////////////////////////////////////////// Private
#region Field
/// <summary> /// 토큰 핸들 /// </summary> private IntPtr tokenHandle = IntPtr.Zero;
/// <summary> /// 윈도우즈 식별자 /// </summary> private WindowsIdentity windowsIdentity;
/// <summary> /// 윈도우즈 가장 컨텍스트 /// </summary> private WindowsImpersonationContext windowsImpersonationContext;
#endregion
//////////////////////////////////////////////////////////////////////////////////////////////////// Constructor ////////////////////////////////////////////////////////////////////////////////////////// Public
#region 생성자 - ImpersonationHelper(domain, userAccount, password)
/// <summary> /// 생성자 /// </summary> /// <param name="domain">도메인</param> /// <param name="userAccount">사용자 계정</param> /// <param name="password">패스워드</param> public ImpersonationHelper(string domain, string userAccount, string password) { if(LogonUser(userAccount, domain, password, 3, 0, ref this.tokenHandle)) { this.windowsIdentity = new WindowsIdentity(this.tokenHandle);
this.windowsImpersonationContext = this.windowsIdentity.Impersonate(); } }
#endregion
//////////////////////////////////////////////////////////////////////////////////////////////////// Method ////////////////////////////////////////////////////////////////////////////////////////// Public
#region 리소스 해제하기 - Dispose()
/// <summary> /// 리소스 해제하기 /// </summary> public void Dispose() { this.windowsImpersonationContext.Undo();
this.windowsImpersonationContext.Dispose();
this.windowsIdentity.Dispose();
if(this.tokenHandle != IntPtr.Zero) { CloseHandle(this.tokenHandle); }
this.tokenHandle = IntPtr.Zero; }
#endregion } }
|
▶ WindowService.cs
using System; using System.Security.Principal; using System.ServiceProcess;
namespace TestService { /// <summary> /// 윈도우 서비스 /// </summary> public partial class WindowService : ServiceBase { //////////////////////////////////////////////////////////////////////////////////////////////////// Constructor ////////////////////////////////////////////////////////////////////////////////////////// Public
#region 생성자 - WindowService()
/// <summary> /// 생성자 /// </summary> public WindowService() { AutoLog = false; ServiceName = "ServiceName"; }
#endregion
//////////////////////////////////////////////////////////////////////////////////////////////////// Method ////////////////////////////////////////////////////////////////////////////////////////// Public
#region 테스트 하기 - Test(argumentArray)
/// <summary> /// 테스트 하기 /// </summary> /// <param name="argumentArray">인자 배열</param> /// <remarks>디버그 모드시 실행된다.</remarks> public void Test(string[] argumentArray) { OnStart(argumentArray);
Console.ReadLine();
OnStop(); }
#endregion
////////////////////////////////////////////////////////////////////////////////////////// Protected
#region 시작시 처리하기 - OnStart(argumentArray)
/// <summary> /// 시작시 처리하기 /// </summary> /// <param name="argumentArray">인자 배열</param> protected override void OnStart(string[] argumentArray) { FileLogHelper logHelper = new FileLogHelper("d:\\", "service.log");
WindowsIdentity windowsIdentity;
windowsIdentity = WindowsIdentity.GetCurrent();
logHelper.WriteLog("현재 윈도우즈 신원"); logHelper.WriteLog("----------------------------------------" ); logHelper.WriteLog("사용자 계정 : {0}", windowsIdentity.Name ); logHelper.WriteLog("사용자 SDDL : {0}", windowsIdentity.User.Value);
using(ImpersonationHelper helper = new ImpersonationHelper("kingdom", "test", "1234")) { windowsIdentity = WindowsIdentity.GetCurrent();
logHelper.WriteLog("현재 윈도우즈 신원"); logHelper.WriteLog("----------------------------------------" ); logHelper.WriteLog("사용자 계정 : {0}", windowsIdentity.Name ); logHelper.WriteLog("사용자 SDDL : {0}", windowsIdentity.User.Value); }
windowsIdentity = WindowsIdentity.GetCurrent();
logHelper.WriteLog("현재 윈도우즈 신원"); logHelper.WriteLog("----------------------------------------" ); logHelper.WriteLog("사용자 계정 : {0}", windowsIdentity.Name ); logHelper.WriteLog("사용자 SDDL : {0}", windowsIdentity.User.Value); }
#endregion #region 중단시 처리하기 - OnStop()
/// <summary> /// 중단시 처리하기 /// </summary> protected override void OnStop() { }
#endregion } }
|
------------------------------------------------------------------------------------------------------------------------
'C# > Common' 카테고리의 다른 글
[C#/COMMON] DataTable 클래스 : Select 메소드에서 DateTime 조건문 사용하기 (0) | 2019.06.30 |
---|---|
[C#/COMMON] 한글 오토마타 사용하기 (0) | 2019.06.28 |
[C#/COMMON] Math 클래스 : Round 정적 메소드를 사용해 반올림하기 (0) | 2019.06.25 |
[C#/COMMON] 현재 실행하고 있는 메소드명 구하기 (0) | 2019.06.25 |
[C#/COMMON] 윈도우즈 서비스를 특정 계정으로 시작하기 (0) | 2019.06.20 |
[C#/COMMON] 윈도우즈 서비스 내에서 사용자 계정 변경하기 (0) | 2019.06.20 |
[C#/COMMON] AppDomain 클래스 : 별도 애플리케이션 도메인에서 특정 어셈블리 로드하기 (0) | 2019.06.18 |
[C#/COMMON] AppDomain 클래스 : 애플리케이션 그림자 복사(Shadow Copy) 사용하기 (0) | 2019.06.18 |
[C#/COMMON] SpeechSynthesizer 클래스 : GetInstalledVoices 메소드를 사용해 설치 음성 목록 구하기 (0) | 2019.06.11 |
[C#/COMMON] UNIX 타임 스탬프 구하기 (0) | 2019.06.09 |
[C#/COMMON] WIN32 API를 사용해 최상위 윈도우 여부 구하기 (0) | 2019.06.06 |
댓글을 달아 주세요