Есть ли способ для программы перезаписывать себя, когда она открыта в памяти?

ОШИБКА:

The process cannot access the file because it is being used by another process. (os error 32)

Я создаю программу в ржавчине, и в настоящее время я работаю над «автоматической программой обновления».

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

Моя текущая работа заключается в том, что программа обновления находится в «лаунчере», который выполняет проверки и обновления перед запуском программы. Таким образом, он может перезаписывать основную программу, поскольку в настоящее время она не открыта в памяти. Однако было бы НАМНОГО лучше иметь только один исполняемый файл.

Некоторый код:

// Installs the update - writing over the currently installed version.
fs::write(env::current_dir().unwrap().join("program.exe"), program).unwrap();

Привет и добро пожаловать в Stack Overflow. Вы на винде? Какая файловая система?

Schwern 01.04.2022 04:59

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

g-radam 01.04.2022 05:04

Пока программа выполняется, она должна иметь доступ для чтения к своему исполняемому файлу. Это нужно для получения кода, а также справочных данных, таких как строки и числа. Windows использует обязательную блокировку файлов, что означает, что если у одного процесса есть файл, открытый для чтения, никакой другой процесс не может писать в этот файл. Возможно, вы сможете что-то сделать с std::os::windows::fs::OpenOptionsExt, но есть веские причины, по которым программы Windows должны закрываться перед обновлением.

Schwern 01.04.2022 05:07

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

Gabe Sechan 01.04.2022 05:13

@Schwern В настоящее время ОС Windows, но программа сделана кроссплатформенной.

Austin Hamner 01.04.2022 05:24
Стоит ли изучать PHP в 2023-2024 годах?
Стоит ли изучать PHP в 2023-2024 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
0
5
83
1
Перейти к ответу Данный вопрос помечен как решенный

Ответы 1

Ответ принят как подходящий

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

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

Austin Hamner 01.04.2022 05:44

Любой может работать. Сложность лаунчера в том, что иногда нужно обновить и лаунчер. Но он обеспечивает хорошее разделение задач и позволяет вам писать две более простые программы вместо одной более крупной.

Gabe Sechan 01.04.2022 06:17

Возможно, вы захотите посмотреть, как это делают другие известные приложения, например Mozilla Firefox.

the busybee 01.04.2022 08:50

Другие вопросы по теме