Inno Setup 툴은 윈도 애플리케이션을 패키징하는 툴이고, 스크립트 언어로 파스칼(Pascal)을 사용한다. 이 툴을 사용해서 애플리케이션을 패키징 하는 스크립트에서 애플리케이션 파일들을 복사하기 전/후에 외부 애플리케이션을 실행할 수 있다.
간단하게 스크립트 파일의 일부를 살펴보자.
[Files] Source: {#DefaultAssetFolderName}\NLog.dll; DestDir: {app}; Flags: ignoreversion . . . [Run] Filename: "{cmd}"; Parameters: "/c taskkill /f /im explorer.exe"; Flags:runhidden; Filename: "{cmd}"; Parameters: "/c explorer.exe & exit"; Flags:runhidden; [UninstallRun] Filename: "{cmd}"; Parameters: "/c taskkill /f /im explorer.exe"; Flags:runhidden; Filename: "{cmd}"; Parameters: "/c explorer.exe & exit"; Flags:runhidden; [UninstallDelete] Type: filesandordirs; Name: {app} . .
위 소스는 다음의 과정을 거치게 된다.
1. 설치
1.1 [Files] 부분에 있는 파일들을 복사한다.
1.2 [Run] 부분을 차례로 실행한다.
2. 삭제
2.1 [UninstallRun] 부분을 차례로 실행한다.
2.2 [UninstallDelete] 부분에 있는 폴더/파일을 삭제한다.
위의 1.2와 2.1에서는 외부 애플리케이션으로 cmd를 사용하고 있다. 이 과정을 거치다 보면 설치는 되는데 cmd 프로세스가 종료되지 않는 문제와 삭제 시에 [UninstallDelete]의 과정으로 진행하지 못하는 문제가 있다.
그래서 이 경우를 해결하기 위해서 C#으로 애플리케이션을 만들어서 위의 과정을 실행시켜야 한다.
// 5초뒤에 프로세스를 종료시키는 스레드 시작 Thread newThread = new Thread(new ThreadStart(Program.Run)); newThread.Start(); // cmd 실행 ProcessStartInfo cmd = new ProcessStartInfo(); Process process = new Process(); cmd.FileName = @"cmd"; cmd.WindowStyle = ProcessWindowStyle.Hidden; // cmd창이 숨겨지도록 하기 cmd.CreateNoWindow = true; // cmd창을 띄우지 안도록 하기 cmd.UseShellExecute = false; cmd.RedirectStandardOutput = true; // cmd창에서 데이터를 가져오기 cmd.RedirectStandardInput = true; // cmd창으로 데이터 보내기 cmd.RedirectStandardError = true; // cmd창에서 오류 내용 가져오기 process.EnableRaisingEvents = false; process.StartInfo = cmd; process.Start(); process.StandardInput.Write(@"taskkill /f /im explorer.exe" + Environment.NewLine); process.StandardInput.Write(@"explorer.exe & exit" + Environment.NewLine); process.StandardInput.Close(); string result = process.StandardOutput.ReadToEnd(); sb = new StringBuilder(); sb.Append("[Result Info]" + DateTime.Now + "\r\n"); sb.Append(result); sb.Append("\r\n"); // 10초 대기 process.WaitForExit(10 * 1000); public static void Run() { Thread.Sleep(5 *1000); Application.ExitThread(); Environment.Exit(0); }
위 소스로 간단하게 cmd_exec.exe 애플리케이션을 만들었다고 가정하고, 패키징 스크립트를 수정하고 실행하면 정상으로 실행된다. 위 패키징 스크립트를 아래와 같이 변경해서 {cmd}로 수행하는 과정을 애플리케이션으로 래핑해서 실행시키면 된다.
[Files] Source: {#DefaultAssetFolderName}\NLog.dll; DestDir: {app}; Flags: ignoreversion . . . [Run] Filename: "{app}\cmd_exec.exe"; Flags: runhidden waituntilterminated [UninstallRun] Filename: "{app}\cmd_exec.exe"; Flags: runhidden waituntilterminated [UninstallDelete] Type: filesandordirs; Name: {app} . .