Чтение JSON документа и нахождение ссылочных документов

1. user1582372 07.04.23 10:08 Сейчас в теме
Добрый день, делаю обмен документа поступление и не встает номенклатура в табличной части по наименованию, по GUID не встает так как GUID разный. застрял на этом месте
ИначеЕсли ОбъектСтруктура.Свойство("NAME") Тогда


Функция ПолучитьЗначениеJSON(СтрJSON,СтруктураТипов,Значение,Позиция=1,Ключ="")
	Перем Кавычка;

	СоответствиеХМЛ           = СтруктураТипов.СоответствиеХМЛ;
	МассивТиповТекст          = СтруктураТипов.МассивТиповТекст;
	МассивОтсутствующихТипов  = СтруктураТипов.МассивОтсутствующихТипов;
	
	ЗначениеВСтроке="";
	Кавычек=0;
	Комментарий=Ложь;
	Строка=Ложь;

	Пока Позиция<=СтрДлина(СтрJSON) Цикл
		ХХ=Сред(СтрJSON,Позиция,2);
		Х=Лев(ХХ,1);
		Позиция=Позиция+1;

		Если Х>" " ИЛИ Строка Тогда //Отсекаем всякий хлам

			Если Комментарий Тогда
				//Это комментарий. Крутимся в цикле пока не встретится конец комментария
				Если ХХ="*/" Тогда
					//Комментарий закончился
					Комментарий=Ложь;
					Позиция=Позиция+1;
				КонецЕсли;

			ИначеЕсли Х="\" Тогда
				Позиция=Позиция+1;
				ХХ=ВРег(ХХ);
				Если ХХ="\""" Тогда ЗначениеВСтроке=ЗначениеВСтроке+""""
				ИначеЕсли ХХ="\\" Тогда ЗначениеВСтроке=ЗначениеВСтроке+"\"
				ИначеЕсли ХХ="\/" Тогда ЗначениеВСтроке=ЗначениеВСтроке+"/"
				ИначеЕсли ХХ="\:" Тогда ЗначениеВСтроке=ЗначениеВСтроке+":"
				ИначеЕсли ХХ="\," Тогда ЗначениеВСтроке=ЗначениеВСтроке+","
				ИначеЕсли ХХ="\B" Тогда ЗначениеВСтроке=ЗначениеВСтроке+Символ(8)
				ИначеЕсли ХХ="\F" Тогда ЗначениеВСтроке=ЗначениеВСтроке+Символы.ПФ //перевод формы (страницы)
				ИначеЕсли ХХ="\N" Тогда ЗначениеВСтроке=ЗначениеВСтроке+Символы.ПС //перевод строки
				ИначеЕсли ХХ="\R" Тогда ЗначениеВСтроке=ЗначениеВСтроке+Символы.ВК //возврат каретки
				ИначеЕсли ХХ="\T" Тогда ЗначениеВСтроке=ЗначениеВСтроке+Символы.ВТаб //символ вертикальной табуляции
				ИначеЕсли ХХ="\U" Тогда
					ЗначениеВСтроке=ЗначениеВСтроке+Символ(Hex2Число(Сред(СтрJSON,Позиция,4))); //шестнадцатиричное число
					Позиция=Позиция+4
				КонецЕсли;

			ИначеЕсли Строка Тогда
				//Если строка не закончилась - то пропускаем управляющие символы
				Если Х=Кавычка Тогда
					//Закончилась строка
					Строка=Ложь;
					Кавычек=Кавычек+1;
				Иначе
					ЗначениеВСтроке=ЗначениеВСтроке+Х;
				КонецЕсли;

			ИначеЕсли ХХ="/*" Тогда
				//Начался комментарий
				Комментарий=Истина;
				Позиция=Позиция+1;

			ИначеЕсли Найти("""'{}[]:,",Х)>0 Тогда
				Если Х="""" ИЛИ Х="'" Тогда
					//Началась строка
					//Строка - коллекция нуля или больше символов Unicode, заключенная в
					//двойные кавычки, используя "\" в качестве символа экранирования.
					//Символ представляется как односимвольная строка.
					//Похожий синтаксис используется в C и Java.
					Строка=Истина;
					Кавычка=Х;
					Кавычек=Кавычек+1;

				ИначеЕсли Х="{" Тогда
					//Начался объект
					//Объект - неупорядоченный набор пар ключ/значение.
					//Объект начинается с "{" и заканчивается "}".
					//Каждое имя сопровождается ":", пары ключ/значение разделяются ",".
					ОбъектСтруктура=Новый Структура;
					//Объект=Новый Структура;
					Пока Истина Цикл
						//Получим ключ и значение
						Ключ="";
						Режим=ПолучитьЗначениеJSON(СтрJSON,СтруктураТипов,Значение,Позиция,Ключ);
						//0 - есть значение и не конец объекта (запятая)
						//1 - есть значение и конец объекта
						//2 - нет значения и не конец объекта (запятая)
						//3 - нет значения и конец объекта
						Если Режим=0 Тогда
							ОбъектСтруктура.Вставить(Ключ,Значение);
						ИначеЕсли Режим=1 Тогда
							ОбъектСтруктура.Вставить(Ключ,Значение);
							Прервать
						ИначеЕсли Режим=3 Тогда
							Прервать
						КонецЕсли;
					КонецЦикла;
					Если ОбъектСтруктура.Свойство("UID") Тогда
						//Это простой ХМЛ тип
							Если МассивТиповТекст.Найти(ОбъектСтруктура.TYPE)<>Неопределено Тогда
							Значение = XMLЗначение(Тип(ОбъектСтруктура.TYPE),ОбъектСтруктура.UID);
							Иначе
							МассивОтсутствующихТипов.Добавить(ОбъектСтруктура.TYPE);
							Значение = ОбъектСтруктура.UID;
							КонецЕсли; 
				ИначеЕсли ОбъектСтруктура.Свойство("NAME") Тогда	
					 
					//Если Тип(ОбъектСтруктура.TYPE) = Тип("СправочникСсылка.Номенклатура") Тогда 
						//Сообщить(ОбъектСтруктура.NAME); 
						
						Если МассивТиповТекст.Найти(ОбъектСтруктура.TYPE)<>Неопределено Тогда
							Значение = XMLСтрока(ОбъектСтруктура.NAME);  // на этом моменте я застрял ОбъектСтруктура.NAME - тут приходит строка нужная мне;
						
						    							
				//Значение = XMLЗначение(Тип(ОбъектСтруктура.TYPE),XMLСтрока(ОбъектСтруктура.NAME)); --- тут выходит ошибка							
						Иначе
							МассивОтсутствующихТипов.Добавить(ОбъектСтруктура.TYPE);
							Значение = ОбъектСтруктура.NAME; 
						КонецЕсли;
						
					ИначеЕсли ОбъектСтруктура.Свойство("OBJECT") Тогда
							//Это объект
							Если ЗначениеЗаполнено(ОбъектСтруктура.Ссылка) И СоответствиеХМЛ.Получить(ТипЗнч(ОбъектСтруктура.Ссылка))<>Неопределено Тогда
								//Получаем объект
								ОбъектИБ = ОбъектСтруктура.Ссылка.ПолучитьОбъект();
								Если ОбъектИБ = Неопределено Тогда
									//Если объекта нет, то создать
									ОбъектИБ = Вычислить(ОбъектСтруктура.NEW); 
									ОбъектИБ.УстановитьСсылкуНового(ОбъектСтруктура.Ссылка);
								КонецЕсли; 
								
								//Проверим соответствие испльзования элементов для групп
								МетаданныеЗначения = ОбъектИБ.Метаданные();
								ЭтоГруппа = ОбъектСтруктура.Свойство("ЭтоГруппа") И ОбъектСтруктура.ЭтоГруппа = Истина;
								Для каждого Реквизит Из МетаданныеЗначения.Реквизиты Цикл
									Если ЭтоГруппа И Реквизит.Использование = Метаданные.СвойстваОбъектов.ИспользованиеРеквизита.ДляЭлемента Тогда
										ОбъектСтруктура.Удалить(Реквизит.Имя)
									КонецЕсли; 
								КонецЦикла; 
								//Проверить совпадение подчиненности справочников
								Если ОбъектСтруктура.Свойство("Владелец") И МетаданныеЗначения.Владельцы.Количество()=0 Тогда
									ОбъектСтруктура.Удалить("Владелец")
								КонецЕсли; 
								
								//Заполнить реквизиты
								ЗаполнитьЗначенияСвойств(ОбъектИБ,ОбъектСтруктура);
								//Определить ТЧ и попытаться заполнить
								Для каждого ТабличнаяЧасть Из МетаданныеЗначения.ТабличныеЧасти Цикл
									//Если ТЧ для групп не используется и наш объект группа, то пропустить ТЧ
									Если ЭтоГруппа И ТабличнаяЧасть.Использование = Метаданные.СвойстваОбъектов.ИспользованиеРеквизита.ДляЭлемента Тогда
										Продолжить;
									КонецЕсли; 
									//Если есть данные о ТЧ, то заполнить ТЧ, иначе очистить
									Если ОбъектСтруктура.Свойство(ТабличнаяЧасть.Имя) И ТипЗнч(ОбъектСтруктура[ТабличнаяЧасть.Имя]) = Тип("ТаблицаЗначений") Тогда
										ОбъектИБ[ТабличнаяЧасть.Имя].Загрузить(ОбъектСтруктура[ТабличнаяЧасть.Имя]);
									Иначе 
										ОбъектИБ[ТабличнаяЧасть.Имя].Очистить();
									КонецЕсли; 
								КонецЦикла;
								Если ОбъектСтруктура.Свойство("SAVE") И ОбъектСтруктура.SAVE = Истина Тогда
								    ОбъектИБ.ОбменДанными.Загрузка = Истина;
									Попытка
										ОбъектИБ.Записать();
										ТекстСообщения = "Записан объект """+ОбъектИБ+"""";
									Исключение
										ТекстСообщения = "Не удалось записать объект """+ОбъектИБ+"""";
									КонецПопытки; 
									Сообщение = Новый СообщениеПользователю;
									Сообщение.Текст = ТекстСообщения;
									Сообщение.КлючДанных = ОбъектСтруктура.Ссылка;
									Сообщение.Сообщить(); 
								КонецЕсли; 
								Значение = ОбъектИБ;
							Иначе
								Значение = ОбъектСтруктура.Ссылка;
							КонецЕсли; 
					ИначеЕсли ОбъектСтруктура.Свойство("TYPE") Тогда
						Если ОбъектСтруктура.TYPE = "ТаблицаЗначений" Тогда
							//Это таблица
							СтруктураТЗ = Новый Структура;
							ТаблицаРезультата = Новый ТаблицаЗначений;
							Для каждого Колонка Из ОбъектСтруктура.COLUMNS Цикл
								ТаблицаРезультата.Колонки.Добавить(Колонка.Ключ);
							КонецЦикла; 
							Для каждого СтрокаТаблицы Из ОбъектСтруктура.ROWS Цикл
								НоваяСтрока = ТаблицаРезультата.Добавить();
								ЗаполнитьЗначенияСвойств(НоваяСтрока,СтрокаТаблицы);
							КонецЦикла; 
							Значение= ТаблицаРезультата;
						Иначе
							//Сюда мы попадать не должны
							Сообщить("Тип не определен:"+ОбъектСтруктура.TYPE);
						КонецЕсли; 
					Иначе
						//Иначе это обычная структура
						Значение = ОбъектСтруктура;
					КонецЕсли; 
					Возврат 0
				ИначеЕсли Х="[" Тогда
					//Начался массив
					//Массив - упорядоченная коллекция значений.
					//Массив начинается с "[" и заканчивается "]".
					//Значения разделены ",".
					Массив=Новый Массив;
					Пока Истина Цикл
						Режим=ПолучитьЗначениеJSON(СтрJSON,СтруктураТипов,Значение,Позиция);
						//0 - есть значение и не конец массива (запятая)
						//1 - есть значение и конец массива
						//2 - нет значения и не конец массива (запятая)
						//3 - нет значения и конец массива
						Если Режим=0 Тогда
							Массив.Добавить(Значение);
						ИначеЕсли Режим=1 Тогда
							Массив.Добавить(Значение);
							Прервать
						ИначеЕсли Режим=3 Тогда
							Прервать
						КонецЕсли;
					КонецЦикла;
					Если Массив.Количество() > 0 И ТипЗнч(Массив[0])=Тип("Структура") Тогда
						//Если мы получили массив структур, то это таблица
						ТаблицаРезультата = Новый ТаблицаЗначений;
						Для каждого Колонка Из Массив[0] Цикл
							ТаблицаРезультата.Колонки.Добавить(Колонка.Ключ);
						КонецЦикла; 
						Для каждого СтрокаТаблицы Из Массив Цикл
						    НоваяСтрока = ТаблицаРезультата.Добавить();
							ЗаполнитьЗначенияСвойств(НоваяСтрока,СтрокаТаблицы);
						КонецЦикла; 
						Значение= ТаблицаРезультата;
					Иначе
						Значение=Массив;
					КонецЕсли; 
					Возврат 0
				ИначеЕсли Х="]" ИЛИ Х="}" Тогда
					//Закончился массив/объект
					Если ЗначениеВСтроке="" И Кавычек=0 Тогда
						Возврат 3 //нет значения и конец массива/объекта
					Иначе
						Значение=ПолучитьЗначениеИзСтроки(ЗначениеВСтроке,Кавычек);
						Возврат 1 //есть значение и конец массива/объекта
					КонецЕсли;
				ИначеЕсли Х=":" Тогда
					Ключ=ЗначениеВСтроке;
					Возврат ПолучитьЗначениеJSON(СтрJSON,СтруктураТипов,Значение,Позиция);

				Иначе
					// запятая
					Прервать
				КонецЕсли;

			Иначе
				ЗначениеВСтроке=ЗначениеВСтроке+Х;
			КонецЕсли;
		КонецЕсли;
	КонецЦикла;

	Если Кавычек>0 Тогда
		Значение=ЗначениеВКавычках(ЗначениеВСтроке);
	Иначе
		Если ЗначениеВСтроке="" Тогда
			Возврат 2
		Иначе
			Значение=ЗначениеБезКавычек(ЗначениеВСтроке)
		КонецЕсли;
	КонецЕсли;
	Возврат 0
КонецФункции
Показать
Ответы
Подписаться на ответы Инфостарт бот Сортировка: Древо развёрнутое
Свернуть все
2. laperuz 46 07.04.23 10:48 Сейчас в теме
Охренеть, самописный код разбора JSON.
А чем ПрочитатьJSON() не устраивает?
user1880116; vv2; +2 Ответить
3. user1880116 07.04.23 11:54 Сейчас в теме
(2) Что нашел, то и скопипастил, что непонятного =)
4. ImHunter 315 07.04.23 12:38 Сейчас в теме
(1) А в чем вопрос-то? Ну разный UUID в разных базах. И что?
5. user1582372 07.04.23 12:51 Сейчас в теме
(4) хочу вставить номенклатуру в табличной части по наименованию
6. user1880116 07.04.23 12:59 Сейчас в теме
(5) Какую из трех с одинаковым наименованием?
7. ImHunter 315 07.04.23 13:03 Сейчас в теме
(5) Похоже, что переписывать где-то тут:
                                    //Если есть данные о ТЧ, то заполнить ТЧ, иначе очистить
                                    Если ОбъектСтруктура.Свойство(ТабличнаяЧасть.Имя) И ТипЗнч(ОбъектСтруктура[ТабличнаяЧасть.Имя]) = Тип("ТаблицаЗначений") Тогда
                                        ОбъектИБ[ТабличнаяЧасть.Имя].Загрузить(ОбъектСтруктура[ТабличнаяЧасть.Имя]);

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

Для получения уведомлений об ответах подключите телеграм бот:
Инфостарт бот