Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[WIP] Исправил ошибку, которая приводила к удалению установленного пакета при его неудачном обновлении #185

Closed
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
// заглушка
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Зачем это?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

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

Есть ли более простой способ воспроизвести ситуацию, когда пакет обновляется на меньшей версии среды, чем требует обновленный манифест?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Не понял вопроса. Зачем нужен файл src.dll и как он связан с "воспроизведением ситуации" и обновлением манифестов

Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
// заглушка
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Зачем это?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

см. выше

81 changes: 81 additions & 0 deletions features/step_definitions/fixtures/testpackage_v999/packagedef
Original file line number Diff line number Diff line change
@@ -0,0 +1,81 @@
////////////////////////////////////////////////////////////
// Описание пакета для сборки и установки
// Полную документацию см. на hub.oscript.io/packaging
//

///////////////////////////////////////////////////////////////////
// Процедуры установки пакета с клиентской машины
///////////////////////////////////////////////////////////////////

// Вызывается пакетным менеджером перед установкой пакета на клиентскую машину.
//
// Параметры:
// КаталогУстановкиПакета - строка. Путь в который пакетный менеджер устанавливает текущий пакет.
// ЧтениеZipФайла - ЧтениеZipФайла. Архив пакета.
//
Процедура ПередУстановкой(Знач КаталогУстановкиПакета, Знач ЧтениеZipФайла) Экспорт
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Требуется ли здесь полный packagedef со всеми процедурами?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

возможно, не требуется. попробую его упростить.

Сообщить(СтрШаблон("Событие установки - ПередУстановкой - КаталогУстановкиПакета %1",
КаталогУстановкиПакета));
КонецПроцедуры

// Вызывается пакетным менеджером после распаковки пакета на клиентскую машину.
//
// Параметры:
// КаталогУстановкиПакета - строка. Путь в который пакетный менеджер устанавливает текущий пакет.
//
Процедура ПриУстановке(Знач КаталогУстановкиПакета, СтандартнаяОбработка) Экспорт

Сообщить(СтрШаблон("Событие установки - ПриУстановке - КаталогУстановкиПакета %1",
КаталогУстановкиПакета));

КонецПроцедуры

///////////////////////////////////////////////////////////////////
// Процедуры сборки пакета
///////////////////////////////////////////////////////////////////


// Вызывается пакетным менеджером перед началом сборки пакета.
//
// Параметры:
// РабочийКаталог - Строка - Текущий рабочий каталог с исходниками пакета.
//
Процедура ПередСборкой(Знач РабочийКаталог) Экспорт

Сообщить(СтрШаблон("Событие установки - ПередСборкой - рабочий каталог %1",
РабочийКаталог));

КонецПроцедуры

// Вызывается пакетным менеджером после помещения файлов в пакет.
//
// Параметры:
// РабочийКаталог - Строка - Текущий рабочий каталог с исходниками пакета.
// АрхивПакета - ЗаписьZIPФайла - ZIP-архив с содержимым пакета (включаемые файлы).
//
Процедура ПриСборке(Знач РабочийКаталог, Знач АрхивПакета) Экспорт

Сообщить(СтрШаблон("Событие установки - ПриСборке - рабочий каталог %1",
РабочийКаталог));

КонецПроцедуры


// Вызывается пакетным менеджером после сборки пакета.
//
// Параметры:
// РабочийКаталог - Строка - Текущий рабочий каталог с исходниками пакета.
// ПутьКФайлуПакета - Строка - Полный путь к собранному файлу пакета.
//
Процедура ПослеСборки(Знач РабочийКаталог, Знач ПутьКФайлуПакета) Экспорт

Сообщить(СтрШаблон("Событие установки - ПослеСборки - рабочий каталог %1, ПутьКФайлуПакета %2",
РабочийКаталог, ПутьКФайлуПакета));

КонецПроцедуры

Описание.Имя("test")
.Версия("0.3.1")
.ВерсияСреды("999.1.0")
.ВключитьФайл("packagedef")
.ВключитьФайл("folder");
41 changes: 41 additions & 0 deletions features/update-env-failure.feature
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
# language: ru

Функциональность: Настройки продукта

Как разработчик
Я хочу при возникновении ошибки во время обновления пакета сохранять в каталоге ранее установленный пакет
Чтобы избежать ошибок, связанных с отсутствием пакетов, которые ранее были установлены


Контекст: Тестовый контекст
Допустим Я создаю временный каталог и сохраняю его в переменной "РабочийКаталог"

Допустим Я очищаю параметры команды "opm" в контексте
И Я устанавливаю путь выполнения команды "opm" к текущей библиотеке
И Я создаю временный каталог и сохраняю его в переменной "КаталогСборкиПакета"
И Я выполняю сборку пакета "fixtures/testpackage" в каталог из переменной "КаталогСборкиПакета"
И Я сохраняю файл пакета из каталога "КаталогСборкиПакета" в переменную "ИмяФайлаПакета"

Допустим Я очищаю параметры команды "opm" в контексте
И Я устанавливаю путь выполнения команды "opm" к текущей библиотеке
И Я создаю временный каталог и сохраняю его в переменной "КаталогСборкиПакета_v999"
И Я выполняю сборку пакета "fixtures/testpackage_v999" в каталог из переменной "КаталогСборкиПакета_v999"
И Я сохраняю файл пакета из каталога "КаталогСборкиПакета_v999" в переменную "ИмяФайлаПакета_v999"

Сценарий: Установка пакета с последующим обновлением из файла в локальном каталоге
Допустим Я установил рабочий каталог из переменной "РабочийКаталог"
И Я добавляю параметр "install" для команды "opm"
И Я добавляю параметр "--local" для команды "opm"
И Я добавляю опцию "-f" для команды "opm" из переменной "ИмяФайлаПакета"
И Я выполняю команду "opm"
И Код возврата команды "opm" равен 0

И Я очищаю параметры команды "opm" в контексте
И Я добавляю параметр "update" для команды "opm"
И Я добавляю опцию "-f" для команды "opm" из переменной "ИмяФайлаПакета_v999"
Когда Я выполняю команду "opm"
И я вижу в консоли вывод
| Требуемая версия: 999.1.0 |
И Вывод команды "opm" не содержит "Внешнее исключение"
И В каталоге из переменной "РабочийКаталог" создается файл или каталог "oscript_modules"
И В каталоге из переменной "РабочийКаталог" создается файл или каталог "oscript_modules/test"
3 changes: 2 additions & 1 deletion src/cmd/Классы/КомандаOpm_Update.os
Original file line number Diff line number Diff line change
Expand Up @@ -49,11 +49,12 @@
НастройкаУстановки.УстанавливатьЗависимости = НеобходимУстановитьЗависимости;
НастройкаУстановки.СоздаватьФайлыЗапуска = СоздаватьФайлыЗапуска;
НастройкаУстановки.ИмяСервера = ИмяСервера;
НастройкаУстановки.УдалятьКаталогПриОшибкеУстановки = Ложь;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

В каких случаях может быть Истина? Т.е. почему это настройка, а не жесткое поведение?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Судя по истории, такое поведение закладывалось изначально. Не смогли установить - очистили каталог.
@artbear в свое время исправил баг, когда opm пытался очистить несуществующий каталог типа "" или Неопределено. При установке пакета такое поведение может и подходит, но вот при обновлении - нет.

Попутно обнаружил, что даже с учетом моего PR opm может отрабатывать некорректно, т.к. в процессе обновления часть файлов может успеть перезаписаться. По-моему, уж лучше случайно удалить библиотеку, чем "побить" ее. Займусь этим вопросом.

Попутно также обнаружил, что билды на CI уже давно не билдятся, исправлю сперва это.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

по поводу ci - может заодно на GA переедем? пример работающих пайплайнов можно подсмотреть в entity, я ее недавно перевел.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Я за. Будет и win, и linux, и macOS сразу. Отдельным PR пульну.


Если ОбновлениеВсехПакетов Тогда
РаботаСПакетами.ОбновитьУстановленныеПакеты(РежимУстановки, , НастройкаУстановки);
ИначеЕсли НЕ ПустаяСтрока(ФайлПакетаУстановки) Тогда
РаботаСПакетами.УстановитьПакетИзФайла(ФайлПакетаУстановки, РежимУстановки, НастройкаУстановки);
РаботаСПакетами.УстановитьПакетИзФайла(ФайлПакетаУстановки, РежимУстановки, Неопределено, НастройкаУстановки);
Иначе

Для каждого ИмяПакета Из МассивПакетовКОбновлению Цикл
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,8 @@

Если Не ВходящийКаталогУстановки = Неопределено Тогда
УстановитьЦелевойКаталог(ВходящийКаталогУстановки);
ИначеЕсли ТекущийРежимУстановкиПакетов = РежимУстановкиПакетов.Локально Тогда
ИначеЕсли ВходящийКаталогУстановки = Неопределено
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

зачем? выше же идет проверка на "не неопределено"

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Вот поэтому и не надо в операторах ИначеЕсли одного уровня проверять совершенно разные условия. 😄

Сейчас видится, что правильнее вложить Если с режимом установки внутрь Если с входящим каталогом. Парой строчек ниже это фрагмента так и сделано. Исправлю.

Или ТекущийРежимУстановкиПакетов = РежимУстановкиПакетов.Локально Тогда
УстановитьЦелевойКаталог(ПутьККаталогуЛокальнойУстановки);
Иначе
КаталогСистемныхБиблиотек = ПолучитьКаталогСистемныхБиблиотек();
Expand Down Expand Up @@ -117,7 +118,9 @@

КонецПроцедуры

Процедура УстановитьПакетИзАрхива(Знач ФайлПакета, Знач ЭтоЗависимыйПакет = Ложь) Экспорт
Процедура УстановитьПакетИзАрхива(Знач ФайлПакета,
Знач ЭтоЗависимыйПакет = Ложь,
Знач УдалятьКаталогПриОшибкеУстановки = Истина) Экспорт
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Когда можем ХОТЕТЬ чтобы каталог удалился несмотря на ошибки?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

см. выше

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Я не понял, что написано выше (
Если мы удаляем каталог - надо удалять его всегда. Зачем нужен флаг, кто будет менять его значение?


КаталогУстановки = ?(ЭтоЗависимыйПакет, КаталогУстановкиЗависимостей, ЦелевойКаталогУстановки);
УстановкаПакета = Новый УстановкаПакета();
Expand All @@ -131,7 +134,7 @@
УстановкаПакета.УстановитьРежимУстановкиПакета(ТекущийРежимУстановкиПакетов);

Попытка
УстановкаПакета.УстановитьПакетИзАрхива(ФайлПакета);
УстановкаПакета.УстановитьПакетИзАрхива(ФайлПакета, УдалятьКаталогПриОшибкеУстановки);
Исключение
ВызватьИсключение ОписаниеОшибки();
КонецПопытки;
Expand Down
5 changes: 3 additions & 2 deletions src/core/Классы/УстановкаПакета.os
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
Перем мЦелевойКаталог;
Перем Метаданные;

Процедура УстановитьПакетИзАрхива(Знач ФайлАрхива) Экспорт
Процедура УстановитьПакетИзАрхива(Знач ФайлАрхива, Знач УдалятьКаталогПриОшибкеУстановки = Истина) Экспорт

Лог.Отладка("Устанавливаю пакет из архива: " + ФайлАрхива);
Если мЗависимостиВРаботе = Неопределено Тогда
Expand Down Expand Up @@ -64,7 +64,8 @@

Исключение
Лог.Предупреждение("Обрабатываю возникшую ошибку...");
Если ЗначениеЗаполнено(ПутьУстановки) Тогда
Если ЗначениеЗаполнено(ПутьУстановки)
И УдалятьКаталогПриОшибкеУстановки Тогда
УдалитьКаталогУстановкиПриОшибке(ПутьУстановки);
КонецЕсли;
ЧтениеПакета.Закрыть();
Expand Down
10 changes: 6 additions & 4 deletions src/core/Модули/РаботаСПакетами.os
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@
Настройка.Вставить("УстанавливатьЗависимостиРазработчика", Ложь);
Настройка.Вставить("СоздаватьФайлыЗапуска", Истина);
Настройка.Вставить("ИмяСервера", "");
Настройка.Вставить("УдалятьКаталогПриОшибкеУстановки", Истина);

Возврат Настройка;

Expand All @@ -86,9 +87,10 @@

КонецПроцедуры

Процедура УстановитьПакетИзФайла(Знач ИмяФайлаПакета, Знач РежимУстановки,
Знач ЦелевойКаталог = Неопределено,
Знач НастройкаУстановки = Неопределено) Экспорт
Процедура УстановитьПакетИзФайла(Знач ИмяФайлаПакета,
Знач РежимУстановки,
Знач ЦелевойКаталог = Неопределено,
Знач НастройкаУстановки = Неопределено) Экспорт

Если НастройкаУстановки = Неопределено Тогда
НастройкаУстановки = ПолучитьНастройкуУстановки();
Expand All @@ -98,7 +100,7 @@
МенеджерУстановки.УстанавливатьЗависимости(НастройкаУстановки.УстанавливатьЗависимости);
МенеджерУстановки.УстанавливатьЗависимостиРазработчика(НастройкаУстановки.УстанавливатьЗависимостиРазработчика);
МенеджерУстановки.СоздаватьФайлыЗапуска(НастройкаУстановки.СоздаватьФайлыЗапуска);
МенеджерУстановки.УстановитьПакетИзАрхива(ИмяФайлаПакета);
МенеджерУстановки.УстановитьПакетИзАрхива(ИмяФайлаПакета, , НастройкаУстановки.УдалятьКаталогПриОшибкеУстановки);

КонецПроцедуры

Expand Down
2 changes: 1 addition & 1 deletion tests/download.os
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@

МенеджерПолучения = Неопределено;

РаботаСПакетами.УстановитьПакетИзОблака("test", РежимУстановкиПакетов.Локально, Неопределено);
РаботаСПакетами.УстановитьПакетИзОблака("test", РежимУстановкиПакетов.Локально, ".");

КэшЛокальный = Новый КэшУстановленныхПакетов;
Пакеты = КэшЛокальный.ПолучитьУстановленныеПакеты();
Expand Down