Практикум по созданию обменов данными через протокол oData «за полдня»

Программирование - Практика программирования

oData REST HTTP статья

91
Про oData и 1С было довольно много написано, однако же описания работы и с чтением, и с записью данных через JSON я так и не встретил ни на этом ресурсе ни на других. Попробую раскрыть эту тему.

Реализация REST-интерфейса от 1С – песня долгая, унылая, про борьбу нещадную и Пирровы победы… Но всё же применение ему есть, и в некоторых случаях он не просто производительнее и выгоднее в реализации других технологий обмена, но и просто незаменим.

При этом, до сих пор порядка 50% специалистов или вообще об oData не слышали или «что-то слышали», но «нужен обмен – COM forever», при том что более тормозной технологии обмена, по-моему, вообще на текущий момент не существует.

Описание теории в этой статье давать не буду, как и описание публикации базы данных на web-сервере, на все необходимые (и весьма интересные) для прочтения статьи ссылки приведу в конце статьи, сейчас займемся жёсткой практикой, и поймем, что «полдня» - это вполне реально)

Решение задач на получение данных (например получение остатков по банковским счетам) вообще делается «на лету», поэтому разберем случай с выгрузкой данных в приемник.

Итак, имеем две БД «управленческая» сильно переписаная КА 1.1 и самописная БД для учета контрагентов и банковских счетов «юрбаза», в которой работают юристы и финансовый отдел. Первичный ввод информации о контрагенте производится в юрбазе, нам же нужно оперативно выгрузить из нее информацию в управленческую. В данном случае весь код отрабатывается в юрбазе посредством GET и POST запросов в управленческую.

Оговорюсь, код не претендует на безукоризненность и соответствие стандартам, т.к. писалось «на скорую руку», надеюсь что сильно пинать за это меня не будут)

Для начала добавляем регистр сведений, скажем «Измененные объекты» для регистрации объектов при их записи, пишем процедуры регистрации, в модулях выгрузки будем обращаться к данным регистра. Ессно добавляем рег.задание для запуска выгрузки, оставляем за собой возможность интерактивной обработки данных из обработки. Для хранения данных для соединения с управленческой базой добавляем регистр сведений «Серверы oData». Описание действий дано, дабы код запросов был более читабелен.

Итак, код:

Процедура ВыполнитьВыгрузкуИзмененныхОбъектов(ИнтерактивныйРежим = Ложь) Экспорт

	// если ничего нет не соединяемся
	Запрос = Новый Запрос;
	Запрос.Текст = 
		"ВЫБРАТЬ ПЕРВЫЕ 1
		|	ИзмененныеОбъекты.Объект КАК Объект
		|ИЗ
		|	РегистрСведений.ИзмененныеОбъекты КАК ИзмененныеОбъекты";
	
	Если Запрос.Выполнить().Пустой() Тогда
		Возврат;
	КонецЕсли;
	
	Если ИнтерактивныйРежим Тогда
		ТекстСообщения = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(НСтр("ru = 'Старт обработки: %1'"), ТекущаяДатаСеанса());
		СообщениеТрассировки(ТекстСообщения, ИнтерактивныйРежим);
	КонецЕсли;
	
	СтруктураПодключения = Новый Структура("Сервер,БазаДанных,Пользователь,Пароль");
	
	Запрос = Новый Запрос;
	Запрос.Текст = 
		"ВЫБРАТЬ
		|	СерверыOData.Сервер КАК Сервер,
		|	СерверыOData.БазаДанных КАК БазаДанных,
		|	СерверыOData.Пользователь КАК Пользователь,
		|	СерверыOData.Пароль КАК Пароль
		|ИЗ
		|	РегистрСведений.СерверыOData КАК СерверыOData
		|ГДЕ
		|	СерверыOData.Идентификатор = ЗНАЧЕНИЕ(Перечисление.ИдентификаторыБазДанных.Управленческая)";
	
	Выборка = Запрос.Выполнить().Выбрать();
	Если Выборка.Следующий() Тогда
		ЗаполнитьЗначенияСвойств(СтруктураПодключения, Выборка);
	Иначе
		ТекстСообщения = НСтр("ru = 'Запись регистра сведений Серверы oData для управленческой БД не обнаружена.'");
		СообщениеТрассировки(ТекстСообщения, ИнтерактивныйРежим, УровеньЖурналаРегистрации.Ошибка);
		Возврат;
	КонецЕсли;
	
    ЗаголовокHTTP = Новый Соответствие();
	ЗаголовокHTTP.Вставить("Accept", "application/json");
	
    ЗаголовокHTTP2 = Новый Соответствие();
	ЗаголовокHTTP2.Вставить("Content-Type", "application/json; charset=utf-8");
	
	Попытка
		Соединение = Новый HTTPСоединение(СтруктураПодключения.Сервер, , СтруктураПодключения.Пользователь, СтруктураПодключения.Пароль);
	Исключение
		ТекстСообщения = НСтр("ru = 'Ошибка соединения с WEB-сервером управленческой БД.'");
		СообщениеТрассировки(ТекстСообщения, ИнтерактивныйРежим, УровеньЖурналаРегистрации.Ошибка);
		Соединение = Неопределено;
		Возврат;
	КонецПопытки;
	
	ПараметрыHTTP = Новый Структура("ИнтерактивныйРежим,Соединение,АдресРесурса,ТекстЗапроса,ЗаголовокHTTP,КодСостояния,Ответ,ТекущийОбъект,КритическаяОшибка,Метод",
		ИнтерактивныйРежим, Соединение, "", "", ЗаголовокHTTP, 0, "", Неопределено, Ложь, Неопределено);
	
	// Контрагенты
	
	Запрос = Новый Запрос;
	Запрос.Текст = 
		"ВЫБРАТЬ РАЗЛИЧНЫЕ
		|	ИзмененныеОбъекты.Объект КАК Объект,
		|	ИзмененныеОбъекты.Объект.Наименование КАК Description,
		|	ИзмененныеОбъекты.Объект.Наименование КАК НаименованиеПолное,
		|	ИзмененныеОбъекты.Объект.ИНН КАК ИНН,
		|	ИзмененныеОбъекты.Объект.КПП КАК КПП,
		|	ИзмененныеОбъекты.Объект.ОГРН КАК ОГРН,
		|	ВЫБОР
		|		КОГДА ИзмененныеОбъекты.Объект.ФормаСобственности.Сокращение = ""ИП""
		|			ТОГДА ""ФизЛицо""
		|		ИНАЧЕ ""ЮрЛицо""
		|	КОНЕЦ КАК ЮрФизЛицо,
		|	ВЫБОР
		|		КОГДА ИзмененныеОбъекты.Объект.СистемаНалогообложения = ЗНАЧЕНИЕ(Справочник.СистемаНалогообложения.УСН)
		|			ТОГДА ""Упрощенная""
		|		ИНАЧЕ ""Общая""
		|	КОНЕЦ КАК СистемаНалогообложения
		|ИЗ
		|	РегистрСведений.ИзмененныеОбъекты КАК ИзмененныеОбъекты
		|ГДЕ
		|	ИзмененныеОбъекты.Объект ССЫЛКА Справочник.Контрагенты";
	
	Выборка = Запрос.Выполнить().Выбрать();
	
	Пока Выборка.Следующий() Цикл
		
		// Сначала поищем контрагента в базе-приемнике для определения типа запроса POST или PATCH
		// По правильному хорошо бы хранить GUID существующих в другой базе объектов и искать по нему, но...
		ПараметрыHTTP.ТекущийОбъект = Выборка.Объект;
		ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
			НСтр("ru = '%1/odata/standard.odata/Catalog_Контрагенты?$select=Ref_Key&$filter=ИНН eq %2%3%2 and КПП eq %2%4%2'"), 
			СтруктураПодключения.БазаДанных, "'", Выборка.ИНН, Выборка.КПП);
		
		СоздатьЗапрос(ПараметрыHTTP); // Оптимизируем код
		Если ПараметрыHTTP.КритическаяОшибка Тогда
			Возврат;
		ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
			Продолжить;
		КонецЕсли;
			
		ЧтениеJSON = Новый ЧтениеJSON; 
		ЧтениеJSON.УстановитьСтроку(ПараметрыHTTP.Ответ);
		СоответствиеJSON = ПрочитатьJSON(ЧтениеJSON, Истина);
		МассивРеквизитов = СоответствиеJSON["value"]; // GET возвращает нам соответствие с массивом внутри
		
		СоответствиеРеквизитов = Новый Соответствие;
		СоответствиеРеквизитов.Вставить("odata.metadata", СоответствиеJSON["metadata"] + "/@Element");
		СтруктураНаименований = Новый Структура("Description,ИНН,КПП,ОГРН,НаименованиеПолное", );
		
		// Иногда в базе-источнике некорректно определена форма собственности контрагента, правят уже в управленческой, хаос)
		Если НЕ МассивРеквизитов.Количество() = 0 Тогда
			НовыйОбъект = Ложь;
			Ref_Key = МассивРеквизитов[0]["Ref_Key"];
		Иначе
			НовыйОбъект = Истина;
			СоответствиеРеквизитов.Вставить("ЮрФизЛицо", Выборка.ЮрФизЛицо); 
		КонецЕсли;
		
		Для каждого КлючИЗначение Из СтруктураНаименований Цикл
			СоответствиеРеквизитов.Вставить(КлючИЗначение.Ключ, Выборка[КлючИЗначение.Ключ]);
		КонецЦикла;
		
		ЗаписьJSON = Новый ЗаписьJSON;
		ЗаписьJSON.УстановитьСтроку();
		ЗаписатьJSON(ЗаписьJSON, СоответствиеРеквизитов,,,,);
		ПараметрыHTTP.ТекстЗапроса = ЗаписьJSON.Закрыть();
		
		Если НовыйОбъект Тогда
			ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
				НСтр("ru = '%1/odata/standard.odata/Catalog_Контрагенты'"), 
				СтруктураПодключения.БазаДанных);
			ПараметрыHTTP.Метод = "POST";
		Иначе
			ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
				НСтр("ru = '%1/odata/standard.odata/Catalog_Контрагенты(guid%2%3%2)'"), 
				СтруктураПодключения.БазаДанных, "'", Ref_Key);
			ПараметрыHTTP.Метод = "PATCH";
		КонецЕсли;
				
		СоздатьЗапрос(ПараметрыHTTP);
		ПараметрыHTTP.Метод = Неопределено;
		Если ПараметрыHTTP.КритическаяОшибка Тогда
			Возврат;
		ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
			Продолжить;
		ИначеЕсли ПараметрыHTTP.КодСостояния = 200 ИЛИ ПараметрыHTTP.КодСостояния = 201 Тогда
			
			// Если был POST нужно сбросить флаг отражения в регламентированном учете, есть у нас такой
			// Суть в том, что мы не можем управлять процедурами ПередЗаписью и ПриЗаписи в приемнике, 
			// указание флага 1C_OData_DataLoadMode = true (ОбменДанными.Загрузка) в заголовке запроса результата не дает
			Если НовыйОбъект Тогда
			
				ЧтениеJSON = Новый ЧтениеJSON; 
				ЧтениеJSON.УстановитьСтроку(ПараметрыHTTP.Ответ);
				СоответствиеJSON = ПрочитатьJSON(ЧтениеJSON, Истина);
				Ref_Key = СоответствиеJSON["Ref_Key"];
				
				СоответствиеРеквизитов = Новый Соответствие;
				СоответствиеРеквизитов.Вставить("odata.metadata", СоответствиеJSON["metadata"]);
				СоответствиеРеквизитов.Вставить("ОтражатьВРегламентированномУчете", Ложь);
				
				ЗаписьJSON = Новый ЗаписьJSON;
				ЗаписьJSON.УстановитьСтроку();
				ЗаписатьJSON(ЗаписьJSON, СоответствиеРеквизитов,,,,);
				ПараметрыHTTP.ТекстЗапроса = ЗаписьJSON.Закрыть();
		
				ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
					НСтр("ru = '%1/odata/standard.odata/Catalog_Контрагенты(guid%2%3%2)'"), 
					СтруктураПодключения.БазаДанных, "'", Ref_Key);
				ПараметрыHTTP.Метод = "PATCH";
			
				СоздатьЗапрос(ПараметрыHTTP);
				ПараметрыHTTP.Метод = Неопределено;
				Если ПараметрыHTTP.КритическаяОшибка Тогда
					Возврат;
				ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
					Продолжить;
				КонецЕсли;
				
			КонецЕсли;
			
			НаборДанных = РегистрыСведений.ИзмененныеОбъекты.СоздатьНаборЗаписей();
			НаборДанных.Отбор.Объект.Установить(Выборка.Объект);
			НаборДанных.Записать(Истина);
			
		КонецЕсли;
		
	КонецЦикла;

	// Ищем валюту рубли в приемнике. Если не найдена - продолжать смысла нет, т.к. б/с не запишется.
	ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
		НСтр("ru = '%1/odata/standard.odata/Catalog_Валюты?$select=Ref_Key&$filter=Code eq %2643%2'"), 
		СтруктураПодключения.БазаДанных, "'");
		
	СоздатьЗапрос(ПараметрыHTTP);
	Если ПараметрыHTTP.КритическаяОшибка ИЛИ ПараметрыHTTP.КодСостояния > 299 Тогда
		Возврат;
	КонецЕсли;
	
	ЧтениеJSON = Новый ЧтениеJSON; 
	ЧтениеJSON.УстановитьСтроку(ПараметрыHTTP.Ответ);
	СоответствиеJSON = ПрочитатьJSON(ЧтениеJSON, Истина);
	МассивРеквизитов = СоответствиеJSON["value"];
	
	Если НЕ МассивРеквизитов.Количество() = 0 Тогда
		ВалютаРубли = МассивРеквизитов[0]["Ref_Key"];
	Иначе
		ТекстСообщения = НСтр("ru = 'В базе-приемнике не найдена валюта с кодом 643. Выгрузка банковских счетов невозможна'");
		СообщениеТрассировки(ТекстСообщения, ИнтерактивныйРежим, УровеньЖурналаРегистрации.Ошибка);
		Соединение = Неопределено;
		Возврат;
	КонецЕсли;
	
	// Банки и контрагенты для банковских счетов
	
	Запрос = Новый Запрос;
	Запрос.Текст = 
		"ВЫБРАТЬ РАЗЛИЧНЫЕ
		|	ИзмененныеОбъекты.Объект.Владелец КАК Объект,
		|	ИзмененныеОбъекты.Объект.Владелец.ИНН КАК ИНН,
		|	ИзмененныеОбъекты.Объект.Владелец.КПП КАК КПП,
		|	ВЫРАЗИТЬ("""" КАК СТРОКА(36)) КАК Ref_Key
		|ИЗ
		|	РегистрСведений.ИзмененныеОбъекты КАК ИзмененныеОбъекты
		|ГДЕ
		|	ИзмененныеОбъекты.Объект ССЫЛКА Справочник.БанковскиеСчета";
	
	ТаблицаКонтрагенты = Запрос.Выполнить().Выгрузить();
	
	Для каждого СтрокаТаблицы Из ТаблицаКонтрагенты Цикл
	
		// Контрагентов только ищем, если все корректно они уже должны быть в приемнике
		ПараметрыHTTP.ТекущийОбъект = СтрокаТаблицы.Объект;
		ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
			НСтр("ru = '%1/odata/standard.odata/Catalog_Контрагенты?$select=Ref_Key&$filter=ИНН eq %2%3%2 and КПП eq %2%4%2'"), 
			СтруктураПодключения.БазаДанных, "'", СтрокаТаблицы.ИНН, СтрокаТаблицы.КПП);
			
		СоздатьЗапрос(ПараметрыHTTP);
		Если ПараметрыHTTP.КритическаяОшибка Тогда
			Возврат;
		ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
			Продолжить;
		КонецЕсли;
		
		ЧтениеJSON = Новый ЧтениеJSON; 
		ЧтениеJSON.УстановитьСтроку(ПараметрыHTTP.Ответ);
		СоответствиеJSON = ПрочитатьJSON(ЧтениеJSON, Истина);
		МассивРеквизитов = СоответствиеJSON["value"];
		
		Если НЕ МассивРеквизитов.Количество() = 0 Тогда
			СтрокаТаблицы.Ref_Key = МассивРеквизитов[0]["Ref_Key"];
		КонецЕсли;
		
	КонецЦикла;
	
	Запрос = Новый Запрос;
	Запрос.Текст = 
		"ВЫБРАТЬ РАЗЛИЧНЫЕ
		|	ИзмененныеОбъекты.Объект.Банк.Ссылка КАК Объект,
		|	ИзмененныеОбъекты.Объект.Банк.БИК КАК Code,
		|	ИзмененныеОбъекты.Объект.Банк.Наименование КАК Description,
		|	ИзмененныеОбъекты.Объект.Банк.КоррСчет КАК КоррСчет,
		|	ИзмененныеОбъекты.Объект.Банк.Адрес КАК Адрес,
		|	ИзмененныеОбъекты.Объект.Банк.Телефоны КАК Телефоны,
		|	ВЫРАЗИТЬ("""" КАК СТРОКА(36)) КАК Ref_Key
		|ИЗ
		|	РегистрСведений.ИзмененныеОбъекты КАК ИзмененныеОбъекты
		|ГДЕ
		|	ИзмененныеОбъекты.Объект ССЫЛКА Справочник.БанковскиеСчета";
	
	ТаблицаБанки = Запрос.Выполнить().Выгрузить();
	
	Для каждого СтрокаТаблицы Из ТаблицаБанки Цикл
	
		// Банки ищем и создаем отсутствующие
		ПараметрыHTTP.ТекущийОбъект = СтрокаТаблицы.Объект;
		ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
			НСтр("ru = '%1/odata/standard.odata/Catalog_Банки?$select=Ref_Key&$filter=Code eq %2%3%2'"), 
			СтруктураПодключения.БазаДанных, "'", СтрокаТаблицы.Code);
		
		СоздатьЗапрос(ПараметрыHTTP);
		Если ПараметрыHTTP.КритическаяОшибка Тогда
			Возврат;
		ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
			Продолжить;
		КонецЕсли;
		
		ЧтениеJSON = Новый ЧтениеJSON; 
		ЧтениеJSON.УстановитьСтроку(ПараметрыHTTP.Ответ);
		СоответствиеJSON = ПрочитатьJSON(ЧтениеJSON, Истина);
		МассивРеквизитов = СоответствиеJSON["value"];
		
		// Существующий банк не обновляем, это нужно делать регламентной процедурой Загрузка классификатора
		Если НЕ МассивРеквизитов.Количество() = 0 Тогда
			СтрокаТаблицы.Ref_Key = МассивРеквизитов[0]["Ref_Key"];
			Продолжить;
		КонецЕсли;
		
		СоответствиеРеквизитов = Новый Соответствие;
		СоответствиеРеквизитов.Вставить("odata.metadata", СоответствиеJSON["metadata"] + "/@Element");
		СтруктураНаименований = Новый Структура("Code,Description,КоррСчет,Адрес,Телефоны", );
		
		Для каждого КлючИЗначение Из СтруктураНаименований Цикл
			СоответствиеРеквизитов.Вставить(КлючИЗначение.Ключ, СтрокаТаблицы[КлючИЗначение.Ключ]);
		КонецЦикла;
		
		ЗаписьJSON = Новый ЗаписьJSON;
		ЗаписьJSON.УстановитьСтроку();
		ЗаписатьJSON(ЗаписьJSON, СоответствиеРеквизитов,,,,);
		ПараметрыHTTP.ТекстЗапроса = ЗаписьJSON.Закрыть();
		
		ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
			НСтр("ru = '%1/odata/standard.odata/Catalog_Банки'"), 
			СтруктураПодключения.БазаДанных);
		ПараметрыHTTP.Метод = "POST";
			
		СоздатьЗапрос(ПараметрыHTTP);
		ПараметрыHTTP.Метод = Неопределено;
		Если ПараметрыHTTP.КритическаяОшибка Тогда
			Возврат;
		ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
			Продолжить;
		ИначеЕсли ПараметрыHTTP.КодСостояния = 200 ИЛИ ПараметрыHTTP.КодСостояния = 201 Тогда
			ЧтениеJSON = Новый ЧтениеJSON; 
			ЧтениеJSON.УстановитьСтроку(ПараметрыHTTP.Ответ);
			СоответствиеJSON = ПрочитатьJSON(ЧтениеJSON, Истина);
			СтрокаТаблицы.Ref_Key = СоответствиеJSON["Ref_Key"];
		КонецЕсли;
		
	КонецЦикла;
	
	// БанковскиеСчета
	
	Запрос = Новый Запрос;
	Запрос.Текст = 
		"ВЫБРАТЬ
		|	ТаблицаБанки.Объект КАК Банк,
		|	ТаблицаБанки.Ref_Key КАК Ref_Key
		|ПОМЕСТИТЬ Банки
		|ИЗ
		|	&ТаблицаБанки КАК ТаблицаБанки
		|;
		|
		|////////////////////////////////////////////////////////////////////////////////
		|ВЫБРАТЬ
		|	ТаблицаКонтрагенты.Объект КАК Контрагент,
		|	ТаблицаКонтрагенты.Ref_Key КАК Ref_Key
		|ПОМЕСТИТЬ Контрагенты
		|ИЗ
		|	&ТаблицаКонтрагенты КАК ТаблицаКонтрагенты
		|;
		|
		|////////////////////////////////////////////////////////////////////////////////
		|ВЫБРАТЬ РАЗЛИЧНЫЕ
		|	ИзмененныеОбъекты.Объект КАК Объект,
		|	""StandardODATA.Catalog_Контрагенты"" КАК Owner_Type,
		|	Контрагенты.Ref_Key КАК Owner,
		|	ИзмененныеОбъекты.Объект.НомерСчета + "", "" + ИзмененныеОбъекты.Объект.Банк.Наименование КАК Description,
		|	ИзмененныеОбъекты.Объект.НомерСчета КАК НомерСчета,
		|	Банки.Ref_Key КАК Банк_Key,
		|	""Расчетный"" КАК ВидСчета,
		|	ИзмененныеОбъекты.Объект.ДатаОткрытия КАК ДатаОткрытия,
		|	ИзмененныеОбъекты.Объект.ДатаЗакрытия КАК ДатаЗакрытия,
		|	&ВалютаРубли КАК ВалютаДенежныхСредств,
		|	ВЫБОР
		|		КОГДА ИзмененныеОбъекты.Объект.СтатусСчета = ЗНАЧЕНИЕ(Справочник.СтатусыРасчетныхСчетов.Закрыт)
		|				ИЛИ ИзмененныеОбъекты.Объект.СтатусСчета = ЗНАЧЕНИЕ(Справочник.СтатусыРасчетныхСчетов.Блок)
		|			ТОГДА ИСТИНА
		|		ИНАЧЕ ЛОЖЬ
		|	КОНЕЦ КАК ВременноНеиспользуется
		|ИЗ
		|	РегистрСведений.ИзмененныеОбъекты КАК ИзмененныеОбъекты
		|		ВНУТРЕННЕЕ СОЕДИНЕНИЕ Контрагенты КАК Контрагенты
		|		ПО ИзмененныеОбъекты.Объект.Владелец = Контрагенты.Контрагент
		|		ВНУТРЕННЕЕ СОЕДИНЕНИЕ Банки КАК Банки
		|		ПО ИзмененныеОбъекты.Объект.Банк = Банки.Банк
		|ГДЕ
		|	ИзмененныеОбъекты.Объект ССЫЛКА Справочник.БанковскиеСчета
		|	И НЕ Банки.Ref_Key = """"
		|	И НЕ Контрагенты.Ref_Key = """"";
	
	Запрос.УстановитьПараметр("ТаблицаБанки", ТаблицаБанки);
	Запрос.УстановитьПараметр("ТаблицаКонтрагенты", ТаблицаКонтрагенты);
	Запрос.УстановитьПараметр("ВалютаРубли", ВалютаРубли);
	
	Выборка = Запрос.Выполнить().Выбрать();
	
	Пока Выборка.Следующий() Цикл
		
		ПараметрыHTTP.ТекущийОбъект = Выборка.Объект;
		ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
			НСтр("ru = '%1/odata/standard.odata/Catalog_БанковскиеСчета?$select=Ref_Key,Owner&$filter=НомерСчета eq %2%3%2'"), //  с isof и cast совместно в 8.3.10 не работает
			СтруктураПодключения.БазаДанных, "'", Выборка.НомерСчета);
		
		СоздатьЗапрос(ПараметрыHTTP);
		Если ПараметрыHTTP.КритическаяОшибка Тогда
			Возврат;
		ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
			Продолжить;
		КонецЕсли;
		
		ЧтениеJSON = Новый ЧтениеJSON; 
		ЧтениеJSON.УстановитьСтроку(ПараметрыHTTP.Ответ);
		СоответствиеJSON = ПрочитатьJSON(ЧтениеJSON, Истина);
		МассивРеквизитов = СоответствиеJSON["value"];
		
		СоответствиеРеквизитов = Новый Соответствие;
		СоответствиеРеквизитов.Вставить("odata.metadata", СоответствиеJSON["metadata"] + "/@Element");
		СтруктураНаименований = Новый Структура("Description,Банк_Key,ДатаОткрытия,ДатаЗакрытия,ВременноНеиспользуется", );
		
		НовыйОбъект = Истина;
		Если НЕ МассивРеквизитов.Количество() = 0 Тогда
			Для каждого Элемент Из МассивРеквизитов Цикл
				Если Элемент["Owner"] = Выборка.Owner Тогда
					НовыйОбъект = Ложь;
					Ref_Key = Элемент["Ref_Key"];
					Прервать;
				КонецЕсли;
			КонецЦикла;
		КонецЕсли;
		
		Если НовыйОбъект Тогда
			СоответствиеРеквизитов.Вставить("Owner_Type", Выборка.Owner_Type);
			СоответствиеРеквизитов.Вставить("Owner", Выборка.Owner);
			СоответствиеРеквизитов.Вставить("НомерСчета", Выборка.НомерСчета);
			СоответствиеРеквизитов.Вставить("ВидСчета", Выборка.ВидСчета);
			СоответствиеРеквизитов.Вставить("ВалютаДенежныхСредств_Key", Выборка.ВалютаДенежныхСредств);
		КонецЕсли;
		
		Для каждого КлючИЗначение Из СтруктураНаименований Цикл
			СоответствиеРеквизитов.Вставить(КлючИЗначение.Ключ, Выборка[КлючИЗначение.Ключ]);
		КонецЦикла;
		
		ЗаписьJSON = Новый ЗаписьJSON;
		ЗаписьJSON.УстановитьСтроку();
		ЗаписатьJSON(ЗаписьJSON, СоответствиеРеквизитов,,,,);
		ПараметрыHTTP.ТекстЗапроса = ЗаписьJSON.Закрыть();
		
		Если НовыйОбъект Тогда
			ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
				НСтр("ru = '%1/odata/standard.odata/Catalog_БанковскиеСчета'"), 
				СтруктураПодключения.БазаДанных);
			ПараметрыHTTP.Метод = "POST";
		Иначе
			ПараметрыHTTP.АдресРесурса = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(
				НСтр("ru = '%1/odata/standard.odata/Catalog_БанковскиеСчета(guid%2%3%2)'"), 
				СтруктураПодключения.БазаДанных, "'", Ref_Key);
			ПараметрыHTTP.Метод = "PATCH";
		КонецЕсли;
		
		СоздатьЗапрос(ПараметрыHTTP);
		ПараметрыHTTP.Метод = Неопределено;
		Если ПараметрыHTTP.КритическаяОшибка Тогда
			Возврат;
		ИначеЕсли ПараметрыHTTP.КодСостояния > 299 Тогда
			Продолжить;
		ИначеЕсли ПараметрыHTTP.КодСостояния = 200 ИЛИ ПараметрыHTTP.КодСостояния = 201 Тогда
			НаборДанных = РегистрыСведений.ИзмененныеОбъекты.СоздатьНаборЗаписей();
			НаборДанных.Отбор.Объект.Установить(Выборка.Объект);
			НаборДанных.Записать(Истина);
		КонецЕсли;
		
	КонецЦикла;
	
	Соединение = Неопределено;

	Если ИнтерактивныйРежим Тогда
		ТекстСообщения = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(НСтр("ru = 'Завершение обработки: %1'"), ТекущаяДатаСеанса());
		СообщениеТрассировки(ТекстСообщения, ИнтерактивныйРежим);
	КонецЕсли;
	
КонецПроцедуры

Код процедуры создания HTTP-запроса:

Процедура СоздатьЗапрос(ПараметрыHTTP)

	Попытка
	    Запрос = Новый HTTPЗапрос(ПараметрыHTTP.АдресРесурса, ПараметрыHTTP.ЗаголовокHTTP);
		Если ПараметрыHTTP.Метод = Неопределено Тогда
			ОтветОтСоединения = ПараметрыHTTP.Соединение.Получить(Запрос);
		Иначе
			Запрос.УстановитьТелоИзСтроки(ПараметрыHTTP.ТекстЗапроса);
			ОтветОтСоединения = ПараметрыHTTP.Соединение.ВызватьHTTPМетод(ПараметрыHTTP.Метод, Запрос);
		КонецЕсли;
		ПараметрыHTTP.КодСостояния = ОтветОтСоединения.КодСостояния;
	    ПараметрыHTTP.Ответ = СтрЗаменить(ОтветОтСоединения.ПолучитьТелоКакСтроку("UTF-8"), "odata.", "");
	Исключение
		ТекстСообщения = НСтр("ru = 'Ошибка соединения с WEB-сервером управленческой БД.'");
		СообщениеТрассировки(ТекстСообщения, ПараметрыHTTP.ИнтерактивныйРежим, УровеньЖурналаРегистрации.Ошибка);
		ПараметрыHTTP.Соединение = Неопределено;
		ПараметрыHTTP.КритическаяОшибка = Истина;
		Возврат;
	КонецПопытки;

	Если ПараметрыHTTP.КодСостояния > 299 Тогда
		ОбработатьОшибку(ПараметрыHTTP.Ответ, ПараметрыHTTP.КодСостояния, ПараметрыHTTP.ИнтерактивныйРежим, ПараметрыHTTP.ТекущийОбъект);
	КонецЕсли;
	
КонецПроцедуры

Процедуры трассировки и обработки ошибок:

Функция ОписаниеВнутреннегоКодаОшибкиOData(КодОшибки)
	
	Описание = Новый Структура(); 
	Описание.Вставить("Код0", "Возможность не поддерживается"); 
	Описание.Вставить("Код1", "Не удалось разобрать строку"); 
	Описание.Вставить("Код2", "Неверный формат запроса"); 
	Описание.Вставить("Код3", "Запрошенный тип представления не поддерживается"); 
	Описание.Вставить("Код4", "Неверное значение свойства"); 
	Описание.Вставить("Код5", "Остсутствует обязательное значение свойства"); 
	Описание.Вставить("Код6", "Неверный URL"); 
	Описание.Вставить("Код7", "Не хватает элемента ключа сущности"); 
	Описание.Вставить("Код8", "Тип сущности не найден"); 
	Описание.Вставить("Код9", "Экземпляр сущности не найден"); 
	Описание.Вставить("Код10","Запрошенное свойство не найдено"); 
	Описание.Вставить("Код11","Метод не найден"); 
	Описание.Вставить("Код12","Отсутствует обязательный аргумент метода"); 
	Описание.Вставить("Код13","Создание строк табличных частей напрямую не поддерживается"); 
	Описание.Вставить("Код14","Ошибка разбора опций запроса"); 
	Описание.Вставить("Код15","Сущность с таким ключом уже существует"); 
	Описание.Вставить("Код16","Не удалось присвоить свойство"); 
	Описание.Вставить("Код17","Объект не поддерживает режим загрузки данных"); 
	Описание.Вставить("Код18","Ошибка инициализации интерфейса OData: в объекте есть свойства с однаковыми именами"); 
	Описание.Вставить("Код19","Использованный HTTP-запрос запрещен в данном контексте"); 
	Описание.Вставить("Код20","Ошибка прав доступа"); 
	Описание.Вставить("Код21","Вызов нереализованной функции"); 
	Описание.Вставить("Код101","Недопустимое значение аргумента функции"); 

	Возврат ?(Описание.Свойство(КодОшибки),Описание[КодОшибки],"Неизвестная ошибка");
	
КонецФункции

Процедура ОбработатьОшибку(Ответ, КодСостояния, ИнтерактивныйРежим, ТекущийОбъект = Неопределено)

	Если Найти(Ответ, "<!DOCTYPE html") = 0 И Найти(Ответ, "<m:error xmlns") = 0 Тогда // json
		
		ЧтениеJSON = Новый ЧтениеJSON; 
		ЧтениеJSON.УстановитьСтроку(Ответ);
		СтруктураОтвета = ПрочитатьJSON(ЧтениеJSON);
		
		КодОшибки = СтрЗаменить(СтруктураОтвета.error.code, "-1", "101");	
		ОписаниеОшибки = ОписаниеВнутреннегоКодаОшибкиOData("Код"+КодОшибки);
		ЗначениеОшибки = СтруктураОтвета.error.message.value;
		
		ТекстСообщения = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(НСтр("ru = 'Ошибка запроса. Описание ошибки: %1 - %2 Значение ошибки: %3'"), 
			СтрЗаменить(КодОшибки, "101", "-1"), ОписаниеОшибки, ЗначениеОшибки);
		
	Иначе
			
		ТекстСообщения = СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(НСтр("ru = 'Ошибка сервера. Код ошибки: %1'"), КодСостояния);
			
	КонецЕсли;
	
	Если НЕ ТекущийОбъект = Неопределено Тогда
		ТекстСообщения = ТекстСообщения + Символы.ПС + СтроковыеФункцииКлиентСервер.ПодставитьПараметрыВСтроку(НСтр("ru = 'Текущий объект: %1 Тип: %2'"), ТекущийОбъект, ТипЗнч(ТекущийОбъект));
	КонецЕсли;
	
	СообщениеТрассировки(ТекстСообщения, ИнтерактивныйРежим, УровеньЖурналаРегистрации.Ошибка);

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

Процедура СообщениеТрассировки(ТекстСообщения, ИнтерактивныйРежим, УровеньЖР = Неопределено)

	Если ИнтерактивныйРежим Тогда
		ОбщегоНазначенияКлиентСервер.СообщитьПользователю(ТекстСообщения);
	Иначе
		УровеньЖР = ?(УровеньЖР=Неопределено, УровеньЖурналаРегистрации.Информация, УровеньЖР); 	
		ЗаписьЖурналаРегистрации(НСтр("ru='oData Выгрузка контрагентов и банковских счетов'"), УровеньЖР,
			ЭтотОбъект.Метаданные(),, ТекстСообщения);
	КонецЕсли;

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

Процедуру ОписаниеВнутреннегоКодаОшибкиOData сдернул откуда-то из просторов Интернет, к сожалению не помню автора, но спасибо выражаю.

В довершение добавлю, что на релизе платформы 8.3.10.2252 мне так и не удалось корректно записать через oData в приемнике запись независимого регистра сведений, перепробовал уйму вариантов, в т.ч. и через XML – стабильная ошибка 500, поэтому когда встала срочная задача сделать POST я реализовал через HTTP-сервис в приемнике. Если у кого-нибудь есть рабочие примеры - приведите плиз.

Для получения теоретического базиса и информации по публикации базы на web-сервере категорически рекомендуется прочесть:

https://its.1c.ru/db/v8311doc#bookmark:dev:TI000001358

https://its.1c.ru/db/v8311doc#bookmark:dev:TI000001426

//obrabotki1c.chavalah.ru/public/711302/

//obrabotki1c.chavalah.ru/public/565435/

Благодарю авторов данных статей, значительную часть моих познаний в данном вопросе я подчерпнул у них.

Код прилагаю в виде внешней обработки, с вопросами обращаемся)

91

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

Наименование Файл Версия Размер
Выгрузка контрагентов и банковских счетов
.epf 11,61Kb
20.03.18
6
.epf 11,61Kb 6 Скачать

См. также

Специальные предложения

Комментарии
Избранное Подписка Сортировка: Древо
1. fr13 21.03.18 08:33 Сейчас в теме
По мне так слишком сложно в реализации. Куда проще сделать все через SOAP и план обмена
2. timm00 106 21.03.18 09:36 Сейчас в теме
(1) Да Николай, SOAP проще. Но. SOAP требует наличия SOAP-сервисов на стороне клиента, и производительность обмена ниже. У меня например любой обмен не занимает более 1,5 секунд при условии что происходит инициализация сеанса. А получение данных - вообще чудо производительности, обходит COM в десятки раз.
А вот планы обмена я просто недолюбливаю, считайте это эксцентрикой)
3. gradi 3 21.03.18 09:44 Сейчас в теме
(2)
обходит COM в десятки раз

Это все хорошо, когда есть возможность опубликовать базу на веб-сервере. Без этого только СОМ.
5. timm00 106 21.03.18 10:14 Сейчас в теме
(3) Апач помогает если с лицензиями заморочка)
8. gradi 3 21.03.18 11:45 Сейчас в теме
9. kare 21 22.03.18 08:16 Сейчас в теме
(8)и с службой безопасности )
10. zarucheisky 22.03.18 17:30 Сейчас в теме
(2) Вы хоть "ИМХО, в моём случае" добавляйте, а то так категорично судить что тормоз/шустро :(
4. webresurs 158 21.03.18 09:47 Сейчас в теме
здорово!

Подскажите пож. в БП 3.0 через настройку OData включил доступ к документу платежное поручение и теперь надо в браузере получить документы за определенный период:

/odata/standard.odata/Document_ПлатежноеПоручение$format=json&$select=Number­,Date,Организация_Key,Контрагент,СуммаДокумента,НазначениеПлатежа,Комментарий,ДокументОснование_Type&$filter=Date(StartPeriod=datetime'2018-03-19T00:00:00',EndPeriod=datetime'2018-03-19T23:59:59')

выдает ошибку: не найдена , что не так подскажите?
6. timm00 106 21.03.18 10:28 Сейчас в теме
(4) Знак вопроса забываете)
/odata/standard.odata/Document_ПлатежноеПоручение?$format=json&$select=Number ,Date,Организация_Key,Контрагент,СуммаДокумента,НазначениеПлатежа,Комментарий,ДокументОснование_Type&$filter=Date(StartPeriod=datetime'2018-03-19T00:00:00',EndPeriod=datetime'2018-03-19T23:59:59')
13. webresurs 158 12.04.18 08:51 Сейчас в теме
(6) - ошибка
{
"odata.error": {
"code": "14",
"message": {
"lang": "ru",
"value": "Ошибка при разборе опции запроса $filter"
}
}
}
Показать
14. webresurs 158 12.04.18 09:02 Сейчас в теме
(6) воспользовался ссылкой из (12)

/odata/standard.odata/Document_ПлатежноеПоручение?allowedOnly=true&$select=Number,Date,Контрагент,СуммаДокумента,НазначениеПлатежа,Комментарий,ДокументОснование_Type&$filter=Date ge datetime'2018-04-02T00:00:00' and Date le datetime'2018-04-02T23:59:59'
16. timm00 106 12.04.18 12:28 Сейчас в теме
(14)
allowedOnly=true&
нужно убрать. Или добавить $
7. swimdog 583 21.03.18 10:58 Сейчас в теме
12. Bright Sun 23.03.18 13:32 Сейчас в теме
Мы сделали небольшой веб-сервис облегчающий генерацию OData-запросов по любой Конфигурации.
http://gen.bi-team.ru/GQ
Структуру метаданных можно передать как через файл ($metadata) так и через доп Обработку, которую можно запросить с ресурса http://bi-team.ru/
jONES1979; +1 Ответить
15. webresurs 158 12.04.18 09:03 Сейчас в теме
(12) - спасибо
- поделитесь обработкой с "gen.bi-team.ru/GQ " на infostar ?
Bizerber; +1 Ответить
18. androgin 03.05.18 02:57 Сейчас в теме
(12) Я, конечно извиняюсь, но ваша ссылка дает мне возможность почитать содержимое компа с установленной 1С ))))
Вам не приходило в голову, что нельзя посторонним загружать свои обработки в базу данных и выполнять серверный код из них?))
Никто не мешает мне прям сейчас сменить там пароль и заблокировать ваш комп )))))
Закройте "Все функции" )))
25. webester 28 03.05.18 19:35 Сейчас в теме
(18)Подозреваю у пользователя, от имени которого выполняется веб сервер или 1с(не знаю от чего имени выполняется код) скорее всего нет на это прав, не пароли менять, не еще какие либо непотребства вершить. Я полазил по машине, это скорее всего развернутая виртуалка, Хотя... судя по тому, что есть юзер2 в списке пользователей... Не надо меня только увольнять меня за код на коленке :) написал быстренько, некогда возиться, просто ради спортивного интереса
Прикрепленные файлы:
ПосмотретьНаФайлы.epf
32. androgin 03.05.18 21:07 Сейчас в теме
(25) "скорее всего нет на это прав" - это не смущает? ))
Я вот точно за свой сервер могу сказать у кого какие права)
33. webester 28 03.05.18 21:09 Сейчас в теме
(32) Конечно не смущает. Это не мой сервер. Я не знаю, есть там права или нет. Проверять лень. Да и вредить неохота.
17. androgin 03.05.18 01:47 Сейчас в теме
Выборка = Запрос.Выполнить().Выбрать();

Я бы за это уволил
19. zhuntovda 03.05.18 08:01 Сейчас в теме
(17)
Выборка = Запрос.Выполнить().Выбрать();


Просветите, почему?
20. Артано 641 03.05.18 09:39 Сейчас в теме
(19) Мусье педант, и не принял к сведению оговорку автора, что код писался на коленке за "полдня".
Увольнять за такое конечно не стоит, а вот делать замечание да

Лично меня, больше напрягли простыни методов, и мелкие сопутствующие ошибки я даже не заметил на фоне остального ужаса, так что ХЗ смысл придираться к отдельным запятым, если весь код плохо организован. Но судим мы здесь не о коде, а о методике, экспресс-реализацию которой нам любезно предложили в качестве лабораторного образца.
21. Bukaska 126 03.05.18 10:16 Сейчас в теме
(20) Чего то я тоже не догоню, когда это выборка стала вдруг такой нелюбимой? Или вопрос в другом?
22. Артано 641 03.05.18 10:19 Сейчас в теме
(21) Я полагаю, что комментатору за номером 17 не понравилось отсутствие промежуточной переменной типа РезультатЗапроса. По крайней мере мне тоже не понравилось бы, но своё отношение я высказал ранее
23. Bukaska 126 03.05.18 10:27 Сейчас в теме
(22)Ну я так и подумала, что либо промежуточная переменная, либо то, что в выборке можно было обойти результат не только напрямую.
30. androgin 03.05.18 21:03 Сейчас в теме
29. androgin 03.05.18 21:03 Сейчас в теме
31. androgin 03.05.18 21:05 Сейчас в теме
(20) Если уж и писать код, то его нужно хотя бы почитать после завершения.
Никто ведь не мешал сделать корректировки ))
Учитывая, что тут сидят критики и похлеще)
Оговорка "на коленке" тут не прокатит, по выше_озвученным причинам
26. androgin 03.05.18 20:51 Сейчас в теме
(19) Правильно так:
Если Запрос.Выполнить().Пустой() Тогда
Возврат;
КонецЕсли;
Зачем создавать выборку, если данных может не быть?
Если бы у вас в запросе был ЕСТЬNULL(), то я бы еще закрыл на это глаза.
1С за это снимает баллы на экзаменах!
А все минусующие сразу демонстрируют свои знания в 1С )))
27. webester 28 03.05.18 20:56 Сейчас в теме
(26)У вас увольняют за отсутсвие экономии полтакта процессора(или сколько занимает времени создание выборки)? Боюсь даже предположить, что бывает за не по стандарту оформленные комментарии. Или вдруг если отсуп забыл поставить. Просто сразу убивают наверное.
dg15000; Dementor; ser6702; +3 Ответить
34. androgin 04.05.18 01:31 Сейчас в теме
(27) Код должен быть функциональным и быстрым. И все эти "мелочи" всегда выливаются в производительность.
Каждый программист обязан думать о производительности своего кода.
С этим не поспоришь!
И поэтому ваши едкости - показатель вашей работы)
36. webester 28 04.05.18 04:30 Сейчас в теме
(34)
Каждый программист обязан думать о производительности своего кода.
Разумеется. Создание пустой выборки никак не влияет не на производительность, не на функциональность.

(34)
И все эти "мелочи" всегда выливаются в производительность.

Это не так. Миллионы строк кода которые выполняются просто при открытии формы списка или формы объекта в современных типовых влияют на производительность. Идите писателей типовых увольняйте. Но даже в этом случае создание пустых выборок или их отсутсвие никак бы не изменило ситуацию. Создание пустых выборок вообще никак и никогда не меняет ситуацию. а ваши едкости - показатель вашей личности, а не качество чьего-то кода. Какое-то раздувание щёк на ровном месте.
Dementor; Артано; +2 Ответить
35. Артано 641 04.05.18 03:54 Сейчас в теме
(26) Инициализация самой выборки практически бесплатна, выборка это просто объект который работает с результатом запроса, никаких данных в нем нет. Там конечно не полтакта, но не всегда различимое даже на уровне тысячных долей секунды время. Придирка и мера наказания неадекватны.
Как обычно в общем, самые злобные комментарии по несущественным поводам от тех кто не может увидеть серьезные проблемы и цепляется к мелочам. Это тоже многое демонстрирует, но уже из другой предметной области
43. androgin 04.05.18 12:42 Сейчас в теме
(35) за полтакта - у УЦ 1С. Доказывайте им, а не мне))))
44. androgin 04.05.18 12:44 Сейчас в теме
(35) ну и для особо одаренных:
С диска ИТС:
"Проверку того, что результат выполнения запроса не содержит строк следует выполнять с помощью метода Пустой. Поскольку на получение выборки из результата запроса (выгрузка его в таблицу значений) будет затрачиваться дополнительное время."
Докажите 1С, что они не правы!
52. webester 28 04.05.18 15:52 Сейчас в теме
Неплохо так бомбануло у народа от мимоходом брошенной фразы :) нет, что бы сказать ну погорячился, нет человек бросился доказывать, что он не верблюд. Я не поленился и скачал единственную поделку автора, открываем и что же видим:
https://monosnap.com/image/gSH6lPc1TNIrNeVwGq0wNS97z7RoBo.png
Что же вы особо одаренный (44) перед выборкой не проверили, вдруг результат запроса пустой? Чуть ли не единственный запрос на всю конфигурацию и сразу такой ляп. Вы уже пишете заявление или просто мимокрокодил?
53. androgin 04.05.18 17:09 Сейчас в теме
(52) О, да, Эта обработка была сделана, как раз в пример одного дяди (вроде вас), который усирался, что нельзя фоном выводить сообщения.
И код там в принципе его заимствован и не представляет интереса, о чем и было сказано там же))))
Наслаждайтесь )))
56. webester 28 04.05.18 18:40 Сейчас в теме
(53)
как раз в пример одного дяди (вроде вас)

Мы уже поняли, что вы один тут дартаньян
55. webester 28 04.05.18 18:26 Сейчас в теме
О, да, Эта обработка была сделана, как раз в пример одного дяди (вроде вас), который усирался, что нельзя фоном выводить сообщения.
Вообще наплевать, для чего или кого она сделана. Можно не оправдываться.
(52)
И код там в принципе его заимствован и не представляет интереса
Не не не так не пойдет: Тут в (31) человек явно говорит, что код должен быть написан сразу идеально
Никто ведь не мешал сделать корректировки ))
оговорки тут не катят по вышеозвученным причинам.(с)31
Наслаждайтесь )))
о да, уже :)
57. androgin 05.05.18 01:30 Сейчас в теме
(55) Мне не то ,что не свойственно оправдываться, но мне просто на#рать на ваши визги))
Вы все равно не можете сказать, что я не прав. Хоть умрите тут)
Пока существуют рекомендации 1С - ваши заметки тут просто лишняя писанина.
Далее: ваше упорство явно подпитывается вашим осознанием, что вы косяк оправдать не можете, и поэтому цепляетесь до каждого слова, что опять же делает вас смешным))
Выйдете из своей норки и признайтесь уже, что далеки от знаний 1С.
ps: и да, не мешало бы почитать ту статью с обработкой и взглянуть на ее срок)) Да и на свою писанину тогда уж)) зачем вам быть таким двуличным?
58. webester 28 05.05.18 04:15 Сейчас в теме
(57)
но мне просто на#рать на ваши визги))

Ну да, именно поэтому вы продолжаете писать. Полезли искать где была написана эта рекомендация. Вам все равно ага.
(57)
Пока существуют рекомендации 1С - ваши заметки тут просто лишняя писанина.

Рекомендации на то и рекомендации, что бы делать как лучше по возможности оценивая все возможные риски. А не фанатично исполнять каждую букву. Это мне кажется просто глупо. Еще вот не могу найти где, но абсолютно точно видел, в рекомендациях 1С следующее: "При проектировании приложения в вопросах производительности следует руководствоваться здравым смыслом. Очень часто разработчики в погоне за соблюдением стандартов, пишут абсолютно нечитаемый код". Даже в рекомендациях сказано, что это рекомендации а не требования закона.
(57)
Далее: ваше упорство явно подпитывается вашим осознанием, что вы косяк оправдать не можете, и поэтому цепляетесь до каждого слова,
Зачем мне оправдывать чужие косяки? А моего кода тут нет. Вам упорства тоже не занимать. И вот косяк, что вы погорячились в (17) (откуда и все и пошло) очевиден, но вы почему-то упорно его отрицаете.
что опять же делает вас смешным))
Я рад, что вы улыбаетесь, а не злитесь. (57)
Выйдете из своей норки и признайтесь уже, что далеки от знаний 1С.
Если вам станет легче, с удовольствием, но только, что же это изменит?
(57)
ps: и да, не мешало бы почитать ту статью с обработкой и взглянуть на ее срок))
Помним (31) оправданий быть не может :) вы уж извините. Какой-то злой гений который пишет код без ошибок и сразу по стандартам 1С, задал этот тренд.
(57)
Да и на свою писанину тогда уж)) зачем вам быть таким двуличным?
Я двуличный? Не я не предлагал увольнять за отсутствие экономии одной тысячной миллисекунды. И если вам не нравится мой код,тогда открывайте новый тред и пишите туда мои косяки поржем вместе. Еще можете сходить в мой бложек(я его правда уже давно не веду и забил на него, а гитахаб через пару лет, поменял обработку ссылок и теперь все линки ведут на самого себя, но статьи почитать все еще можно если не тыкать по ссылке а добавить "\" в конце) найти там еще больше лулзов и тыкнуть меня в них носом. Я буду рад почитать про это.
59. androgin 05.05.18 15:37 Сейчас в теме
(58) Мне правда не интересно с тролями спорить.
Суть одна: ни вы ни автор не правы)
Все остальное - ваша ущемленная гордость
63. Bassgood 822 10.11.18 20:49 Сейчас в теме
(44) Специально для Вас объясню о чем на самом деле идет речь в приведенной Вами рекомендации с диска ИТС:

В данном случае имеется ввиду получение данных из результата запроса либо выборкой (через ее метод "Следующий()"), либо выгрузкой в ТЗ (через метод "Выгрузить()" результата запроса), о чем четко написано в тексте рекомендации.
Инициализация объекта "Выборка" и получение через нее данных методом "Следующий" (именно о нем идет речь в рекомендации) - разные вещи!
1. "Выборка = Запрос.Выполнить().Выбрать();" - инициализация объекта, речь в рекомендации не об этом
2. "Выборка.Следующий()" - получение данных в объект выборки, именно об этом идет речь в рекомендации (не говоря уже о выгрузке в ТЗ)

Проверка наличия данных в результате запроса:
1. "Запрос.Выполнить().Пустой()" - верно
2. "Запрос.Выполнить().Выбрать().Следующий()" - неверно
3. "Запрос.Выполнить().Выгрузить().Количество() = 0" - неверно

А то что Вы не смогли объяснить это представителю УЦ 1С, а судя по всему не смогли этого сделать потому что сами не поняли сути рекомендации - так это говорит только о Вашей некомпетентности, именно поэтому и снимают балл на экзамене.
64. androgin 11.11.18 01:24 Сейчас в теме
(63)
Запрос.Выполнить().Выгрузить()

вот это уже затратно!
ни к чему выгружать в таблицу то, что может и не пригодиться в полном объеме.
мыслите шире, а не шаблонами.
Я смотрю у вас минимум практики
65. Bassgood 822 11.11.18 16:26 Сейчас в теме
(64) Выгрузку в ТЗ я привел Вам в качестве примера неверного использования проверки наличия данных в результате запроса, или Вы читали мой комментарий по диагонали, ровно также как и приведенную Вами рекомендацию с ИТС?
Я смотрю у вас минимум практики

Судя по тому, что Вы не понимаете сути рекомендации, которую сами же и приводите в качестве довода своей правоты, практики не хватает как раз именно Вам ;)
Свою практику я в свое время опубликовал на ИС, а ваших непревзойденных трудов я что-то здесь не вижу... может их по-просту и нет? ;)
37. Bukaska 126 04.05.18 09:22 Сейчас в теме
(26)Что -то мне кажется, что УЦ обычно как раз преподают именно тот вариант, за который вы бы уволили. Если это только не курсы спеца)))
45. androgin 04.05.18 12:45 Сейчас в теме
(37) Покреститесь, чтобы не казалось
39. Артано 641 04.05.18 10:07 Сейчас в теме
(26) И к слову о производительности. Ну допустим так. И запрос не пустой? Еще раз сделаете запрос выполнить? Ну и кого увольнять/убивать/насильничать? Была давным-давно такая реклама с хорошим слоганом: "иногда лучше жевать чем говорить".
Bukaska; Hamsik; +2 Ответить
42. androgin 04.05.18 12:41 Сейчас в теме
(39) вот в вашем случае как раз лучше жевать))
Сходите в 1С и сдайте экзамен. будет лучше и убедительней, чем ваши визги
60. rozaliya1606 07.05.18 10:57 Сейчас в теме
(26)
Приведенный вами также не корректен - приведет к выполнению запроса 2 раза,
это намного более грубый удар по производительности нежели создание пустой выборки,
если уж на то пошло следует объявить переменную и проверять в условии РезультатЗапроса.Пустой()
24. webester 28 03.05.18 17:29 Сейчас в теме
(17)Может есть хоть, что-то по существу, почему за это надо убивать?

Я конечно выгляжу совсем как дурак, но мне совершенно непонятно.
(22)Ну нет, промежуточной переменной. Почему это плохо?
Еще неплохо уволить тех, кто писал СП, там такие примеры Хранилище = Новый ХранилищеЗначения(Значение, Новый СжатиеДанных(9));
62. Bassgood 822 10.11.18 20:19 Сейчас в теме
(17) Судя по всем вашим комментариям и отношению к окружающим, могу с уверенностью сказать, что к руководящей должности Вас никто не допустит и под вашим началом работать никто не захочет, так что такая возможность Вам никогда не предоставится, а скорее наоборот - увольнять будут именно Вас ;)
p.s. Думаю аналогичного мнения о Вас придерживаются и ваши коллеги, если конечно они у Вас имеются
28. androgin 03.05.18 21:02 Сейчас в теме
Это зачем, если нигде не используется?
ЗаголовокHTTP2 = Новый Соответствие();
ЗаголовокHTTP2.Вставить("Content-Type", "application/json; charset=utf-8");

Это нужно вставить в первый заголовок: ЗаголовокHTTP.
Далее: вы в цикле носитесь в базу-приемник и проверяете там каждого контрагента.
Если в базе 1000 контрагенов? Точно уволил бы за это!
Что мешало хотя бы выгрузить все инн/кпп и разом проверить их там?
38. Hamsik 13 04.05.18 09:34 Сейчас в теме
(28) Вас в своё время уволили? К чему такая "токсичность" ? Может детская травма?
40. Артано 641 04.05.18 10:09 Сейчас в теме
(38) Это просто психологическая компенсация собственной некомпетентности. Пишешь говнокод, страдаешь от этого, но нахватался верхушек на курсах? Есть выход - зайди на форум и обгадь код придравшись к несущественной мелочи.
Hamsik; ser6702; +2 Ответить
47. Hamsik 13 04.05.18 12:46 Сейчас в теме
(41) Все же к оскорблениям переходить не стоит, я думаю правила форума к этому располагают, а в Вашем огромном таланте никто не сомневается.
49. androgin 04.05.18 12:47 Сейчас в теме
(47) ну так вот с себя и начните. А я пока ни слова оскорбления не сказал)
46. androgin 04.05.18 12:46 Сейчас в теме
(38) в мое время учили грамотно, чтобы не уволили. А вас видимо пора)))
48. Hamsik 13 04.05.18 12:46 Сейчас в теме
(46) Хорошо, видимо пора идти писать заявление, в чем провинился сударь ?
51. Hamsik 13 04.05.18 12:54 Сейчас в теме
(50) Надеюсь модераторы форума оценят ваши аргументированные доводы
54. androgin 04.05.18 17:10 Сейчас в теме
(51) Оценят, не сомневайтесь)
61. Dementor 338 09.05.18 12:39 Сейчас в теме
Отличная статья! И спасибо за упоминание моей заметки про чтение через oData. (вы же в курсе, что было продолжение про запись?). У меня в плане были еще парочка статей на данную тему для покрытия вопроса, но, к сожалению, участие в паре параллельных проектов забирает абсолютно все время. А ведь как раз хотел поэкспериментировать с регистрами сведений, накопления, бухгалтерии и расчета. А еще была задумка по работе с планом обмена (а-ля РИБ через веб). Может летом продолжу...

На злостных комментаторов не обращайте внимания. Я упомянутых проблем в коде не увидел ;-)
Если интересны рекомендации, то не нужно мучиться при наличии чисел со строковыми ключами в структурах - сразу применяйте соответствие. Но с точки зрения быстродействия лучше было написать через Если... ИначеЕсли... КонецЕсли. (переписывать не нужно)
Оставьте свое сообщение