Автоматизация обновления до последнего релиза

21.06.23

Разработка - DevOps и автоматизация разработки

Это механизм, который автоматически обновляет базы 1С до последнего релиза, при разработке в 1С:Enterprise Development Tools c использованием распределённой системы управления версиями GIT.

Скачать файлы

Наименование Файл Версия Размер
Автоматизация обновления до последнего релиза: Расширение с веб-сервисом
.cfe 9,07Kb
2
.cfe 9,07Kb 2 Скачать
Автоматизация обновления до последнего релиза: Файл скрипта на OneScript
.os 23,59Kb
1
.os 23,59Kb 1 Скачать

Введение.

Эта статья подойдет для тех, кто имеет по крайней мере базовые знания и навык работы с git. Она разработана для разработки с помощью модели ветвления Git Flow.

Формат версии конфигурации 1С это A.B.C.[h], где:

  • A – главный номер версии (major version number).
  • B – вспомогательный номер версии (minor version number).
  • C – номер сборки, номер логической итерации по работе над функционалом версии A.B (build number).
  • h – Немедленные изменения/исправления конфигурации (hotfix branches), при которых конфигурация обновляется вручную (незапланированно), и не приводят к автоматическому обновлению конфигурации.

Представленный механизм так же подойдет для интеграции в среду Jenkins, но выходит за пределы темы статьи и рассматриваться не будет.

Итак, начнем!

В конфигурацию нужно добавить http-сервис, с корневым url - api. Добавим ему шаблон "/v1/{action}/" с методом GET. Обработчик у метода будет следующий:

	Action = НРег(Запрос.ПараметрыURL["action"]);

	Если Action = "version" Тогда
		HTTPОтвет = Новый HTTPСервисОтвет(200);
		HTTPОтвет.УстановитьТелоИзСтроки(Метаданные.Версия);
		Возврат HTTPОтвет;
	ИначеЕсли Action = "telegram" И Не Запрос.Заголовки.Получить("Text") = Неопределено Тогда
		HTTPСоединение = Новый HTTPСоединение("api.telegram.org", 443, , , , , Новый ЗащищенноеСоединениеOpenSSL);
		ПараметрыЗапроса = Новый Соответствие;
		Текст = Запрос.Заголовки.Получить("Text");
		ПараметрыЗапроса.Вставить("Content-type", "application/json");
		TelegramBotID = Константы.Update_TelegramBotID.Получить();
		TelegramChatID = Константы.Update_TelegramChatID.Получить();
		Если ЗначениеЗаполнено(TelegramBotID) И ЗначениеЗаполнено(TelegramChatID) Тогда
			МассивЧатов = СтрРазделить(TelegramChatID, ";");
			Для Каждого ЧатID Из МассивЧатов Цикл
				HTTPЗапрос = Новый HTTPЗапрос(TelegramBotID + "/sendMessage?chat_id=" + ЧатID
					+ "&parse_mode=html&text=" + Текст, ПараметрыЗапроса);
				HTTPСоединение.Получить(HTTPЗапрос);
			КонецЦикла;
		КонецЕсли;
		HTTPОтвет = Новый HTTPСервисОтвет(200);
		Возврат HTTPОтвет;
	ИначеЕсли Action = "disconnect" Тогда

		Port = Запрос.Заголовки.Получить("Port");
		MainPort = Запрос.Заголовки.Получить("MainPort");
		AgentSrv = Запрос.Заголовки.Получить("AgentSrv");
		BaseName = Запрос.Заголовки.Получить("BaseName");
		login = Запрос.Заголовки.Получить("login");
		password = Запрос.Заголовки.Получить("password");

		СистемнаяИнфо = Новый СистемнаяИнформация;
		ПодстрокиВерсии = СтрРазделить(СистемнаяИнфо.ВерсияПриложения, ".");
		COMСоединитель = Новый COMОбъект("v" + ПодстрокиВерсии[0] + ПодстрокиВерсии[1] + ".COMConnector");

		СтрокаСоединенияСАгентомСервера = "tcp://" + AgentSrv + ":" + Port;
		СоединениеСАгентомСервера = COMСоединитель.ConnectAgent(СтрокаСоединенияСАгентомСервера);

		ПеремКластер = Неопределено;
		Для Каждого Кластер Из СоединениеСАгентомСервера.GetClusters() Цикл
			Если Формат(Кластер.MainPort, "ЧГ=0;") = MainPort Тогда
				СоединениеСАгентомСервера.Authenticate(Кластер, login, password);
				ПеремКластер = Кластер;
				Прервать;
			КонецЕсли;
		КонецЦикла;

		Если ПеремКластер = Неопределено Тогда
			HTTPОтвет = Новый HTTPСервисОтвет(400);
			HTTPОтвет.УстановитьТелоИзСтроки("ERROR: Не удалось найти кластер");
			Возврат HTTPОтвет;
		КонецЕсли;

		ПеремОписаниеИнформационнойБазы = Неопределено;
		Для Каждого ОписаниеИнформационнойБазы Из СоединениеСАгентомСервера.GetInfoBases(ПеремКластер) Цикл
			Если НРег(ОписаниеИнформационнойБазы.Name) = НРег(BaseName) Тогда
				ПеремОписаниеИнформационнойБазы = ОписаниеИнформационнойБазы;
				Прервать;
			КонецЕсли;
		КонецЦикла;

		Если ПеремОписаниеИнформационнойБазы = Неопределено Тогда
			HTTPОтвет = Новый HTTPСервисОтвет(400);
			HTTPОтвет.УстановитьТелоИзСтроки("ERROR: Не удалось найти базу");
			Возврат HTTPОтвет;
		КонецЕсли;

		ВсеПользователи = Истина;
		Сеансы = СоединениеСАгентомСервера.GetInfoBaseSessions(ПеремКластер, ПеремОписаниеИнформационнойБазы);
		Для Каждого Сеанс Из Сеансы Цикл
			Попытка
				СоединениеСАгентомСервера.TerminateSession(ПеремКластер, Сеанс);
			Исключение
				ВсеПользователи = Ложь;
			КонецПопытки;
		КонецЦикла;
		Если Не ВсеПользователи Тогда
			HTTPОтвет = Новый HTTPСервисОтвет(400);
			HTTPОтвет.УстановитьТелоИзСтроки("ERROR: Не удалось отключить всех пользователей");
			Возврат HTTPОтвет;
		КонецЕсли;
		HTTPОтвет = Новый HTTPСервисОтвет(200);
		Возврат HTTPОтвет;
	ИначеЕсли Action = "check" Тогда
		HTTPОтвет = Новый HTTPСервисОтвет(?(Константы.Update_ЗапретАвтообновления1С.Получить(), 400, 200));
		Возврат HTTPОтвет;
	КонецЕсли;
	
	HTTPОтвет = Новый HTTPСервисОтвет(200);
	Возврат HTTPОтвет;

далее короткое описание для каждого Action в методе:

  1. version - Основной метод, возвращает текущую версию конфигурации
  2. telegram - метод, который оповещает о процессе обновления, с помощью bota. Можно заменить на оповещения по электронной почте, смс и тд.
  3. disconnect - метод, который завершает работу пользователей перед обновлением (позволяет отключать пользователей в конфигурациях без БСП)
  4. check - метод, в который можно добавить нужные проверки перед обновлением. Например, проверку создания backup обновляемой базы, дня недели, выполнение важных регламентных заданий при которых нельзя обновлять конфигурацию и тд

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

Файл update1C.os

#Использовать irac
#Использовать cmdline
#Использовать 1commands

Функция ПолучитьМассивБазДляОбновления()

	МассивНастроеек = Новый Массив();
		
	МассивБазДляОбновления = Новый Массив();
	СтруктураНастроеек = Новый Структура();
	//Расположение проекта 
	СтруктураНастроеек.Вставить("КаталогПроекта", "C:\Users\admin\git\test_base_1");
	//Файлы конфигурации проекта edt
	СтруктураНастроеек.Вставить("PROJECT", "C:\Users\admin\git\test_base_1\conf");
	
	БазаДанных = Новый Структура();
	//Заголовок для сообщения в телеграмме
	БазаДанных.Вставить("Заголовок", " TEST UPDATE BASE");
	//Сервер публикации информационной базы
	БазаДанных.Вставить("СерверHttp", "localhost");
	//Сервер БД
	БазаДанных.Вставить("СерверБазыДанных", "192.168.1.1\SQL1");
	//Кластер сервера 
	БазаДанных.Вставить("СерверКластера", "localhost");
	//Имя базы данных
	БазаДанных.Вставить("ИмяБазыДанных", "test_developer");
	//Пользователь БД
	БазаДанных.Вставить("ПользовательБазыДанных", "sql_login");
	//Пароль пользователя БД
	БазаДанных.Вставить("ПарольБазыДанных", "sql_password");
	//Пользователь 1С
	БазаДанных.Вставить("Пользователь1С", "update1C");
	//Пароль пользоватлея 1С
	БазаДанных.Вставить("Пароль1С", "update1C");
	//URL http-сервиса
	БазаДанных.Вставить("АдресHttp", "test_developer/hs/api/v1");
	//Порт агента сервера
	БазаДанных.Вставить("Port", "1540");
	//Порт менеджера кластрера
	БазаДанных.Вставить("MainPort", "1541");
	//Логин кластера сервера 1С
	БазаДанных.Вставить("ClustersLogin", "log");
	//Пароль кластера сервера 1С
	БазаДанных.Вставить("ClustersPassword", "pswd");
	МассивБазДляОбновления.Добавить(БазаДанных);
	
	БазаДанных = Новый Структура();
	БазаДанных.Вставить("Заголовок", " TEST UPDATE BASE 2");
	БазаДанных.Вставить("СерверHttp", "localhost");
	БазаДанных.Вставить("СерверБазыДанных", "192.168.1.2\SQL2");
	БазаДанных.Вставить("СерверКластера", "localhost");
	БазаДанных.Вставить("ИмяБазыДанных", "test_developer2");
	БазаДанных.Вставить("ПользовательБазыДанных", "sql_login");
	БазаДанных.Вставить("ПарольБазыДанных", "sql_password");
	БазаДанных.Вставить("Пользователь1С", "update1C");
	БазаДанных.Вставить("Пароль1С", "update1C");
	БазаДанных.Вставить("АдресHttp", "test_developer2/hs/api/v1");
	БазаДанных.Вставить("Port", "1540");
	БазаДанных.Вставить("MainPort", "1541");
	БазаДанных.Вставить("ClustersLogin", "log");
	БазаДанных.Вставить("ClustersPassword", "pswd");
	МассивБазДляОбновления.Добавить(БазаДанных);
		
	СтруктураНастроеек.Вставить("МассивБазДляОбновления", МассивБазДляОбновления);
	
	МассивБазДляОбновления = Новый Массив();
	СтруктураНастроеек = Новый Структура();
	СтруктураНастроеек.Вставить("КаталогПроекта", "C:\Users\admin\git\test_base_2");
	СтруктураНастроеек.Вставить("PROJECT", "C:\Users\admin\git\test_base_2\conf");
	
	БазаДанных = Новый Структура();
	БазаДанных.Вставить("Заголовок", " TEST UPDATE BASE 3");
	БазаДанных.Вставить("СерверHttp", "localhost");
	БазаДанных.Вставить("СерверБазыДанных", "192.168.1.3\SQL3");
	БазаДанных.Вставить("СерверКластера", "localhost");
	БазаДанных.Вставить("ИмяБазыДанных", "test_developer3");
	БазаДанных.Вставить("ПользовательБазыДанных", "sql_login");
	БазаДанных.Вставить("ПарольБазыДанных", "sql_password");
	БазаДанных.Вставить("Пользователь1С", "update1C");
	БазаДанных.Вставить("Пароль1С", "update1C");
	БазаДанных.Вставить("АдресHttp", "test_developer3/hs/api/v1");
	БазаДанных.Вставить("Port", "1540");
	БазаДанных.Вставить("MainPort", "1541");
	БазаДанных.Вставить("ClustersLogin", "log");
	БазаДанных.Вставить("ClustersPassword", "pswd");
	МассивБазДляОбновления.Добавить(БазаДанных);
		
	СтруктураНастроеек.Вставить("МассивБазДляОбновления", МассивБазДляОбновления);

	МассивНастроеек.Добавить(СтруктураНастроеек);
		
	Возврат МассивНастроеек;

КонецФункции

// Получает ветку текущего релиза
//
// Параметры:
//   ТекстовыйДокумент - ТекстовыйДокумент - данные по веткам
//	 АктуальнаяВерсияЧислом - Число - Версия текущего релиза числом
//
// Возвращаемое значение:
//  - Строка - Имя ветки текщего релиза
Функция ПолучитьНачалоЛога(ТекстовыйДокумент,АктуальнаяВерсияЧислом)

	Ветки = ТекстовыйДокумент.КоличествоСтрок();
	Для к=1 По Ветки Цикл
		Ветка = СокрЛП(ТекстовыйДокумент.ПолучитьСтроку(к));
		Если СтрНачинаетсяС(Ветка, "origin/release/") Тогда
			СтрокаВетки = СтрЗаменить(Ветка, "origin/release/", "");
			ПроверяемаяВерсия = ВерсияЧислом(СтрокаВетки);
			Если ПроверяемаяВерсия = АктуальнаяВерсияЧислом Тогда
				Возврат Ветка;
			КонецЕсли;
		КонецЕсли;
	КонецЦикла;
	
	Возврат "";
	
КонецФункции

// Преобразует строку версии в число, сокращая до 3-го разряда
//
// Параметры:
//   ВерсияСтрокой - Строка - Версия в формате ХХ.ХХ.ХХ.ХХ
//
// Возвращаемое значение:
//  - Число - Версия в числовом эквиваленте
Функция ВерсияЧислом(Знач ВерсияСтрокой)
	
	Разрядность = СтрНайти(ВерсияСтрокой, ".", , , 3);
	Если Разрядность > 0 Тогда
		ВерсияСтрокой = Лев(ВерсияСтрокой, Разрядность-1);
	КонецЕсли;

	Если ПустаяСтрока(ВерсияСтрокой) Или ВерсияСтрокой = "0.0.0.0" Тогда
		Возврат 0;
	КонецЕсли;
	
	Разряд = 0;
	
	Результат = 0;
	
	ОписаниеТипаЧисло = Новый ОписаниеТипов("Число");
	Остаток = ВерсияСтрокой;
	ПозицияТочки = СтрНайти(Остаток, ".");
	Пока ПозицияТочки > 0 Цикл
		ЧислоСтрокой = Лев(Остаток, ПозицияТочки - 1);
		Число = ОписаниеТипаЧисло.ПривестиЗначение(ЧислоСтрокой);
		Результат = Результат * 1000 + Число;
		Остаток = Сред(Остаток, ПозицияТочки + 1);
		ПозицияТочки = СтрНайти(Остаток, ".");
		Разряд = Разряд + 1;
	КонецЦикла;
	
	Число = ОписаниеТипаЧисло.ПривестиЗначение(Остаток);
	Результат = Результат * 1000 + Число;
	Разряд = Разряд + 1;
	
	// Номера версии после 4 точки возвращает после запятой.
	// Например, для версии "1.2.3.4.5.6.7" вернет 1002003004,005006007.
	Если Разряд > 4 Тогда
		Результат = Результат / Pow(1000, Разряд - 4);
	КонецЕсли;
	
	Возврат Результат;
КонецФункции

//Глобальные переменные (общие для всех баз)
СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ = "🟢";
СМАЙЛ_КРАСНЫЙ_КРУГ = "🔴";
СМАЙЛ_ИТОГ_ЗЕЛЕНЫЙ = "c89;";
СМАЙЛ_ИТОГ_КРАСНЫЙ = "c40;";

WORKSPACE = "C:\Users\admin\git\WS";
XML = "C:\Users\admin\git\XML";
LOGFILE="C:\Users\admin\workspace\log.txt";
BRANCH="C:\Users\admin\workspace\branch.txt";
LOGCOMMIT="C:\Users\admin\workspace\log_commit.txt";
//xx.xxxx заменить на версию 1С (например 22.1923)
ibcmd = "C:\Program Files\1cv8\8.3.xx.xxxx\bin\ibcmd.exe";
dir_backup = "D:\BACKUP\";

МассивБаз = ПолучитьМассивБазДляОбновления();

Для Каждого СтруктураОбновления ИЗ МассивБаз Цикл
			
	Команда = Новый Команда;
	
	Релиз = "0.0.0";
	НачалоЛога = "";
	ОкончаниеЛога = "";
	
	ТекстовыйДокументBRANCH = Новый ТекстовыйДокумент;
	
	//Переходи в кактлог проекта и загружаем коммиты, скачиваем все удаленные ветки. 
	//	Ищем релизные и записываем их в файл
	Команда.УстановитьСтрокуЗапуска("cd " 
		+ СтруктураОбновления.КаталогПроекта
		+ " & git fetch & git branch -r |  find ""origin/release/"" > """
		+ BRANCH + """ 2>&1");
	КодВозврата = Команда.Исполнить();
	ТекстовыйДокументBRANCH.Прочитать(BRANCH);
	
	МаксВерсияЧислом = ВерсияЧислом("0.0.0");
	
	Ветки = ТекстовыйДокументBRANCH.КоличествоСтрок();
	Для к=1 По Ветки Цикл
		Ветка = СокрЛП(ТекстовыйДокументBRANCH.ПолучитьСтроку(к));
		Если СтрНачинаетсяС(Ветка, "origin/release/") Тогда
			СтрокаВетки = СтрЗаменить(Ветка, "origin/release/", "");
			ПроверяемаяВерсия = ВерсияЧислом(СтрокаВетки);
			Если ПроверяемаяВерсия > МаксВерсияЧислом Тогда
				МаксВерсияЧислом = ПроверяемаяВерсия;
				ОкончаниеЛога = Ветка;
				Релиз = СтрокаВетки;
			КонецЕсли;
		КонецЕсли;
	КонецЦикла;

	//проверка что релиз обновился
	Если НЕ Релиз = "0.0.0" Тогда
	
		КонфигурацияГотоваКЗагрузке = Ложь;
	
		Для Каждого База ИЗ СтруктураОбновления.МассивБазДляОбновления Цикл
		
			HTTPСоединение = Новый HTTPСоединение(База.СерверHttp);
		
			Заголовки = Новый Соответствие();
			HTTPЗапрос = Новый HTTPЗапрос(База.АдресHttp + "/version", Заголовки);
			Результат = HTTPСоединение.Получить(HTTPЗапрос);
			
			//если сервис недоступен, проверяем след базу
			Если НЕ Результат.КодСостояния = 200 Тогда
				Продолжить;
			КонецЕсли;		
			
			АктуальнаяВерсия = Результат.ПолучитьТелоКакСтроку();
			АктуальнаяВерсияЧислом = ВерсияЧислом(АктуальнаяВерсия);
			
			//Начинаем формировать сообщения для отправки в теелграмм
			СообщениеТелеграм = " Релиз: " + Релиз + "</b>";
			
			Если АктуальнаяВерсияЧислом < МаксВерсияЧислом Тогда
				
				Если НЕ КонфигурацияГотоваКЗагрузке Тогда
						
					//Переключаемся на релизную ветку и обновляем ее с сервера
					Команда.УстановитьСтрокуЗапуска("cd " + СтруктураОбновления.КаталогПроекта 
						+ " & git checkout " + ОкончаниеЛога + " & git pull");
					КодВозврата_checkout = Команда.Исполнить();

					СообщениеТелеграм = СообщениеТелеграм + Символы.ПС 
						+ ?(КодВозврата_checkout <= 1, СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ, СМАЙЛ_КРАСНЫЙ_КРУГ) 
						+ " получение данных с GitHub";
					
					//Очищаем каталоги для сборки. Удалив их и создав заново
					Команда.УстановитьСтрокуЗапуска("rd /S /Q """ + WORKSPACE 
						+ """ & rd /S /Q """ + XML+ """");
					КодВозврата_rd = Команда.Исполнить();
						
					Команда.УстановитьСтрокуЗапуска("md """ + WORKSPACE 
						+ """ & md """ + XML+ """");
					КодВозврата_md = Команда.Исполнить();
					СообщениеТелеграм = СообщениеТелеграм + Символы.ПС 
						+ ?(КодВозврата_rd+КодВозврата_md = 0, СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ, СМАЙЛ_КРАСНЫЙ_КРУГ) 
						+ " подготовка структуры каталогов";

					//Экспорт проекта в xml-выгрузку конфигурации
					//xxxx.x.x заменить на версию edt (например 2022.2.5)
					Команда.УстановитьСтрокуЗапуска("ring edt@xxxx.x.x:x86_64 workspace export --project """
						+ СтруктураОбновления.PROJECT 
						+ """ --configuration-files """ + XML
						+ """ --workspace-location """ + WORKSPACE + """ >> """
						+ LOGFILE + """ 2>&1");
					КодВозврата_export = Команда.Исполнить();
					СообщениеТелеграм = СообщениеТелеграм + Символы.ПС 
						+ ?(КодВозврата_export = 0, СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ, СМАЙЛ_КРАСНЫЙ_КРУГ) 
						+ " выгрузка конфигурации в XML";

					КонфигурацияГотоваКЗагрузке = Истина;

				КонецЕсли;
				
				СообщениеЛогаКоммитов = "";
				КодВозврата_apply = 1;
				КодВозврата_import = 1;
				Если КонфигурацияГотоваКЗагрузке Тогда
				
					НачалоЛога = ПолучитьНачалоЛога(ТекстовыйДокументBRANCH, АктуальнаяВерсияЧислом);
					
					//получаем для отображения информацию о коммитах
					Если ЗначениеЗаполнено(НачалоЛога) И ЗначениеЗаполнено(ОкончаниеЛога) Тогда
						ТекстовыйДокумент = Новый ТекстовыйДокумент;
						Команда.УстановитьСтрокуЗапуска("cd " + СтруктураОбновления.КаталогПроекта 
							+ " & git shortlog --pretty=format:""%an: %b"" --merges "
							+ НачалоЛога + ".." + ОкончаниеЛога
							+ " --grep=""release"" --invert-grep > """ 
							+ LOGCOMMIT + """ 2>&1");
						КодВозврата_log = Команда.Исполнить();
						ТекстовыйДокумент.Прочитать(LOGCOMMIT);
						СообщениеЛогаКоммитов = Символы.ПС + "<code>Задачи в релизе:"
							+ Символы.ПС + ТекстовыйДокумент.ПолучитьТекст() + "</code>";
					КонецЕсли;
				
					//для удобства разделим в логе базы
					Команда.УстановитьСтрокуЗапуска("echo %date% " + База.ИмяБазыДанных 
						+ " >> """ + LOGFILE + """ 2>&1");
					КодВозврата = Команда.Исполнить();
				
					//Завершение работы активных пользователей
					Заголовки = Новый Соответствие();
					Заголовки.Вставить("Port",  База.Port);
					Заголовки.Вставить("MainPort",  База.MainPort);
					Заголовки.Вставить("BaseName",  База.ИмяБазыДанных);
					Заголовки.Вставить("login",  База.ClustersLogin);
					Заголовки.Вставить("password",  База.ClustersPassword);
					Заголовки.Вставить("AgentSrv",  База.СерверКластера);
					HTTPЗапрос = Новый HTTPЗапрос(База.АдресHttp + "/disconnect",Заголовки);
					Результат = HTTPСоединение.Получить(HTTPЗапрос);
					СообщениеТелеграмБаза = СообщениеТелеграм + Символы.ПС 
						+ ?(Результат.КодСостояния = 200, СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ, СМАЙЛ_КРАСНЫЙ_КРУГ) 
						+ " завершение активных сеансов";
					//получаем имя файла бекапа
					ИмяБД = База.ИмяБазыДанных;
					//если нужно добавлять, а не перезаписывать 
					//ИмяБД = База.ИмяБазыДанных+Формат(ТекущаяДата(),"ДФ=_ггггММдд");
					
					//Делаем бекап базы перед обновлением
					Команда.УстановитьСтрокуЗапуска("sqlcmd -S " + База.СерверБазыДанных
						+ " -U """ + База.ПользовательБазыДанных
						+ """ -P """ + База.ПарольБазыДанных
						+ """ -b -Q ""BACKUP DATABASE " + База.ИмяБазыДанных
						+ " TO DISK = N'"+dir_backup+ИмяБД+".bak' WITH COMPRESSION, NOFORMAT, INIT, NAME = N'"
						+ ИмяБД + "', SKIP, NOREWIND, NOUNLOAD, STATS = 10, CHECKSUM"" >> """ + LOGFILE + """ 2>&1");
					КодВозврата_backup = Команда.Исполнить();
										
					Если КодВозврата_backup = 0 Тогда
						СообщениеТелеграмБаза = СообщениеТелеграмБаза + Символы.ПС
							+ ?(КодВозврата_backup = 0, СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ, СМАЙЛ_КРАСНЫЙ_КРУГ)
							+ " BACKUP: " + ИмяБД;

						//Импорт конфигурации из XML с помощью утилиты ibcmd
						Команда.УстановитьСтрокуЗапуска(""""+ibcmd
							+""" infobase config import --dbms=MSSQLServer --db-server=" + База.СерверБазыДанных
							+ " --db-name=" + База.ИмяБазыДанных
							+ " --db-user="+База.ПользовательБазыДанных
							+ " --db-pwd="""+База.ПарольБазыДанных
							+ """ --user="+База.Пользователь1С
							+ " --password="+База.Пароль1С
							+ " """+XML+""" >> """+LOGFILE+""" 2>&1");
						КодВозврата_import = Команда.Исполнить();
						СообщениеТелеграмБаза = СообщениеТелеграмБаза + Символы.ПС
							+ ?(КодВозврата_import = 0, СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ, СМАЙЛ_КРАСНЫЙ_КРУГ) 
							+ " загрузка конфигурации в базу из XML";
						
						//Обновление конфигурации 
						Команда.УстановитьСтрокуЗапуска(""""+ibcmd
							+ """ infobase config apply --dbms=MSSQLServer --db-server="+База.СерверБазыДанных
							+ " --db-name="+База.ИмяБазыДанных
							+ " --db-user="+База.ПользовательБазыДанных
							+ " --db-pwd="""+База.ПарольБазыДанных
							+ """ --user="+База.Пользователь1С
							+ " --password="+База.Пароль1С
							+ " --force >> """+LOGFILE+""" 2>&1");
						КодВозврата_apply = Команда.Исполнить();
						СообщениеТелеграмБаза = СообщениеТелеграмБаза + Символы.ПС 
							+ ?(КодВозврата_apply = 0, СМАЙЛ_ЗЕЛЕНЫЙ_КРУГ, СМАЙЛ_КРАСНЫЙ_КРУГ) 
							+ " обновление конфигурации";	
					Иначе
						СообщениеЛогаКоммитов = "";
						СообщениеТелеграмБаза = СообщениеТелеграм + Символы.ПС 
							+ СМАЙЛ_КРАСНЫЙ_КРУГ + " ОШИБКА создания BACKUP";
					КонецЕсли;	
				Иначе
					СообщениеТелеграмБаза = СообщениеТелеграм + Символы.ПС 
						+ СМАЙЛ_КРАСНЫЙ_КРУГ + " ОШИБКА экспорта конфигурации в файл";					
				КонецЕсли;
								
				СообщениеТелеграмБаза = "<b>" + ?(КодВозврата_md+КодВозврата_export+КодВозврата_import+КодВозврата_apply = 0, 
					СМАЙЛ_ИТОГ_ЗЕЛЕНЫЙ, СМАЙЛ_ИТОГ_КРАСНЫЙ) 
					+ База.Заголовок + СообщениеТелеграмБаза + СообщениеЛогаКоммитов;
				
				//Отправка сообщения в телеграмм
				Заголовки = Новый Соответствие();
				Заголовки.Вставить("Text",  КодироватьСтроку(СообщениеТелеграмБаза, СпособКодированияСтроки.КодировкаURL));
				HTTPЗапрос = Новый HTTPЗапрос(База.АдресHttp + "/telegram",Заголовки);
				Результат = HTTPСоединение.Получить(HTTPЗапрос);
			
			КонецЕсли;
			
		КонецЦикла;	
		
	КонецЕсли;

КонецЦикла;

Краткое описание работы скрипта.

Сначала формируется список параметров и массив баз для обновления. В дальнейшем что бы добавить или удалить базу редактируем в файле функцию ПолучитьМассивБазДляОбновления. Далее получаем актуальные данные веток и коммитов из git-а (который подключен по ssh). Получаем текущий релиз базы (версию в 1С), и сравниваем его с релизными ветками (release/*). Если есть новый релиз, тогда переключаемся на ветку релиза и скачиваем изменения. Подготавливаем структуру каталогов и экспортируем в нее проект edt в виде xml файлов. Перед обновлением делаем бекап базы. Если все прошло без ошибок, тогда в каждую конфигурацию, из массива, мы загружаем данные проекта из xml-файлов, и обновляем ее. В самом конце отправляем сообщение из 1С в зависимости от настроек.

Пример.

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

Запускаем выполнение скрипта командой из cmd или вешаем на планировщик заданий в ОС Windows. Например, запуск из командной строке выглядит так

oscript C:\scripts\update1C.os

После выполнения скрипта получаем сообщение в чат с ботом и обновленную конфигурацию до 0.1.10. На скриншоте видно что сначала скачиваются данные и из них обновляются первые 2 базы, при чем вторая с некритической ошибкой. А вот третяя база не обновлеяется из за ошибки создания бекапа.

Если что-то не работает, смотрим логи в файле %LOGFILE%

 

Ссылки:

EDT Git GitFlow release OneScript version автоматическое обновление HTTP-сервис Telegram Bot DevOps

См. также

Обновление для КА 1.1, ЗУП 2.5, БУХ 2.0: НДС, ЕФС-1, Расчет страховых взносов, Мобилизация, Статистика, Электронные трудовые книжки, 2-НДФЛ, Регламентированная отчетность, Кадровый учет, Прослеживаемость импортных товаров

Зарплата Регламентированный учет и отчетность Кадровый учет Обновление 1С Платформа 1С v8.3 Сложные периодические расчеты 1С:Комплексная автоматизация 1.х 1С:Бухгалтерия 2.0 1С:Зарплата и Управление Персоналом 2.5 Бухгалтерский учет Налоговый учет Управленческий учет Акцизы ЕНВД ЕСН Земельный налог ИП, ПБОЮЛ, КФХ Налог на имущество Налог на прибыль НДС НДФЛ ФОМС, ЕФС Транспортный налог УСН ПСН (патентная система налогообложения) Платные (руб)

Обновления для конфигураций: КА 1.1; ЗУП 2.5; БУХ 2.0; КА 1.1 Комплексная автоматизация торговли алкогольной продукцией; КА 1.1 Комплексный учет сельскохозяйственного предприятия

19900 руб.

01.04.2020    139915    670    352    

231

Системы контроля версий для 1С-разработчиков.

1С-программирование DevOps и автоматизация разработки Групповая разработка (Git, хранилище) DevOps для 1С Платформа 1С v8.3 Платные (руб)

Основы командной разработки на 1С. Использование систем контроля версий при разработке на платформе 1С:Предприятие 8

4900 руб.

29.06.2022    8748    78    4    

105

Автотесты для типовых конфигураций Бухгалтерия предприятия КОРП 3.0 и Бухгалтерия предприятия 3.0 (vanessa automation)

Тестирование QA DevOps и автоматизация разработки Платформа 1С v8.3 1С:Бухгалтерия 3.0 Россия Бухгалтерский учет Налоговый учет Платные (руб)

Готовые тестовые сценарии, предназначенные для регресс-тестирования функционала конфигурации после обновления типовым релизом. Сценарии проверяют интерактивное заполнение форм документов, справочников и результат проведения документов. Сценарий – feature-файл, разработанный с помощью vanessa-automation. Запуск сценария выполняется интерактивно с помощью vanessa-automation или с помощью vanessa-runner в CI-системах. Доступно тестирование тонкого клиента. Поддерживаемые версии конфигураций 1С:Бухгалтерия предприятие 3.0 и версии КОРП: 3.0.144.49.

1728 руб.

20.01.2022    6426    10    0    

9

Автотесты для типовых конфигураций ERP Управление предприятием 2 и Комплексная автоматизация 2 (для vanessa automation)

Тестирование QA DevOps и автоматизация разработки Платформа 1С v8.3 1С:ERP Управление предприятием 2 1С:Комплексная автоматизация 2.х Россия Бухгалтерский учет Налоговый учет Платные (руб)

Готовые тестовые сценарии, предназначенные для регресс-тестирования функционала конфигурации после обновления типовым релизом. Сценарии проверяют интерактивное заполнение форм документов, справочников и результат проведения документов. Сценарии возможно использовать как для vanessa-automation, так и для СППР. Поддерживаемые версии конфигураций ERP2 и КА2: 2.5.15.111.

2220 руб.

04.07.2022    6453    21    0    

22

Автоматическое подтверждение легальности обновления базы или как обновить 100 типовых баз 1С за 5 часов

DevOps и автоматизация разработки Обновление 1С Платформа 1С v8.3 Конфигурации 1cv8 Платные (руб)

Расширение для конфигураций 1С для автоматического подтверждения легальности обновления и выполнения обработчиков обновления при пакетном автоматическом обновлении большого числа баз 1С. А также сам модуль обработки по автоматическому обновлению баз.

2400 руб.

08.05.2019    23936    57    26    

24

1С, СППР и Архитектура как код

DevOps и автоматизация разработки Бесплатно (free)

Можно ли идеи подхода «Архитектура как код» положить на 1С или иную платформу, чтобы не изобретать ещё какой-то язык и сразу получить множество готовых библиотек функций и инструмент достижения главной цели подхода AaC.

01.02.2024    2136    roman72    9    

6

Скрипт для обновления базы с расширением из хранилища

Обновление 1С Платформа 1С v8.3 Бесплатно (free)

Небольшая оптимизация рабочего времени через скрипт обновления базы 1С с расширением из хранилища конфигураций.

22.01.2024    928    ke.92@mail.ru    2    

22

TCP прокси-сервер хранилища конфигурации 1С

DevOps и автоматизация разработки Групповая разработка (Git, хранилище) OneScript Платформа 1С v8.3 Бесплатно (free)

Продолжение истории с прокси хранилища, но уже не на HTTP, а на TCP и без падений по памяти веб-сервера. Проверяем комментарии хранилища, вызываем веб-хуки, старты пайплайнов, gitsync по событию помещения версии в хранилище. И все это полностью на знакомом и понятном OneScript.

17.01.2024    2361    kamisov    17    

55
Оставьте свое сообщение