Перезапустите приложение самостоятельно - PullRequest
17 голосов
/ 07 марта 2012

Я хочу собрать свое приложение с функцией перезапуска.Я нашел на codeproject

ProcessStartInfo Info=new ProcessStartInfo();
Info.Arguments="/C choice /C Y /N /D Y /T 3 & Del "+
               Application.ExecutablePath;
Info.WindowStyle=ProcessWindowStyle.Hidden;
Info.CreateNoWindow=true;
Info.FileName="cmd.exe";
Process.Start(Info); 
Application.Exit();

Это не работает вообще ... И другая проблема, как запустить его снова, как это?Возможно, есть также аргументы для запуска приложений.

Редактировать:

http://www.codeproject.com/script/Articles/ArticleVersion.aspx?aid=31454&av=58703

Ответы [ 9 ]

40 голосов
/ 08 марта 2012

Я использую код, аналогичный коду, который вы пробовали при перезапуске приложений.Я посылаю команду timed cmd для перезапуска приложения для меня так:

ProcessStartInfo Info = new ProcessStartInfo();
Info.Arguments = "/C ping 127.0.0.1 -n 2 && \"" + Application.ExecutablePath + "\"";
Info.WindowStyle = ProcessWindowStyle.Hidden;
Info.CreateNoWindow = true;
Info.FileName = "cmd.exe";
Process.Start(Info);
Application.Exit(); 

Команда отправляется в ОС, ping приостанавливает выполнение скрипта на 2-3 секунды, после чего приложение выходит из программы.начиная с Application.Exit(), затем следующая команда после пинга запускает ее снова.

Примечание: \" помещает кавычки вокруг пути, если в нем есть пробелы, которые cmd не может обработать без кавычек.

Надеюсь, это поможет!

28 голосов
/ 07 марта 2012

Почему бы не использовать

Application.Restart();

??

Подробнее о Перезагрузка

9 голосов
/ 07 марта 2012

Почему не просто следующее?

Process.Start(Application.ExecutablePath); 
Application.Exit();

Если вы хотите убедиться, что приложение не запускается дважды, используйте Environment.Exit(-1), который мгновенно завершает процесс (не очень хороший способ), или что-то вроде запуска второго приложения, которое проверяет процесс основного приложения и запускает его снова, как только процесс завершится.

6 голосов
/ 07 марта 2012

У вас есть начальное приложение A, которое вы хотите перезапустить. Итак, когда вы хотите убить A, запускается небольшое приложение B, B убивает A, затем B запускает A и убивает B.

Чтобы запустить процесс:

Process.Start("A.exe");

Чтобы убить процесс, это что-то вроде этого

Process[] procs = Process.GetProcessesByName("B");

foreach (Process proc in procs)
   proc.Kill();
3 голосов
/ 07 марта 2012

Многие люди предлагают использовать Application.Restart. На самом деле эта функция редко выполняет должным образом. Я никогда не закрывал приложение, из которого звоню. Мне всегда приходилось закрывать приложение другими способами, например закрывать основную форму.

У вас есть два способа справиться с этим. У вас либо есть внешняя программа, которая закрывает вызывающий процесс и запускает новую,

или

у вас при запуске вашего нового программного обеспечения уничтожаются другие экземпляры того же приложения, если в качестве перезапуска передается аргумент.

        private void Application_Startup(object sender, StartupEventArgs e)
        {
            try
            {
                if (e.Args.Length > 0)
                {
                    foreach (string arg in e.Args)
                    {
                        if (arg == "-restart")
                        {
                            // WaitForConnection.exe
                            foreach (Process p in Process.GetProcesses())
                            {
                                // In case we get Access Denied
                                try
                                {
                                    if (p.MainModule.FileName.ToLower().EndsWith("yourapp.exe"))
                                    {
                                        p.Kill();
                                        p.WaitForExit();
                                        break;
                                    }
                                }
                                catch
                                { }
                            }
                        }
                    }
                }
            }
            catch
            {
            }
        }
3 голосов
/ 07 марта 2012

Winforms имеет метод Application.Restart(), который делает именно это.Если вы используете WPF, вы можете просто добавить ссылку на System.Windows.Forms и вызвать ее.

1 голос
/ 05 июля 2016

Мое решение:

        private static bool _exiting;
    private static readonly object SynchObj = new object();

        public static void ApplicationRestart(params string[] commandLine)
    {
        lock (SynchObj)
        {
            if (Assembly.GetEntryAssembly() == null)
            {
                throw new NotSupportedException("RestartNotSupported");
            }

            if (_exiting)
            {
                return;
            }

            _exiting = true;

            if (Environment.OSVersion.Version.Major < 6)
            {
                return;
            }

            bool cancelExit = true;

            try
            {
                List<Form> openForms = Application.OpenForms.OfType<Form>().ToList();

                for (int i = openForms.Count - 1; i >= 0; i--)
                {
                    Form f = openForms[i];

                    if (f.InvokeRequired)
                    {
                        f.Invoke(new MethodInvoker(() =>
                        {
                            f.FormClosing += (sender, args) => cancelExit = args.Cancel;
                            f.Close();
                        }));
                    }
                    else
                    {
                        f.FormClosing += (sender, args) => cancelExit = args.Cancel;
                        f.Close();
                    }

                    if (cancelExit) break;
                }

                if (cancelExit) return;

                Process.Start(new ProcessStartInfo
                {
                    UseShellExecute = true,
                    WorkingDirectory = Environment.CurrentDirectory,
                    FileName = Application.ExecutablePath,
                    Arguments = commandLine.Length > 0 ? string.Join(" ", commandLine) : string.Empty
                });

                Application.Exit();
            }
            finally
            {
                _exiting = false;
            }
        }
    }
1 голос
/ 15 мая 2012

Еще один способ сделать это, который кажется немного чище, чем эти решения, - запустить пакетный файл, который включает определенную задержку для ожидания завершения текущего приложения.Это дает дополнительное преимущество, заключающееся в предотвращении одновременного открытия двух экземпляров приложения.

Пример командного файла Windows ("restart.bat"):

sleep 5
start "" "C:\Dev\MyApplication.exe"

В приложениидобавить этот код:

// Launch the restart batch file
Process.Start(@"C:\Dev\restart.bat");

// Close the current application (for WPF case)
Application.Current.MainWindow.Close();

// Close the current application (for WinForms case)
Application.Exit();
0 голосов
/ 17 августа 2016

Для приложения .Net решение выглядит так:

System.Web.HttpRuntime.UnloadAppDomain()

Я использовал это для перезапуска своего веб-приложения после изменения настроек приложения в файле myconfig.

System.Configuration.Configuration configuration = WebConfigurationManager.OpenWebConfiguration("~");
configuration.AppSettings.Settings["SiteMode"].Value = model.SiteMode.ToString();
configuration.Save();
...