Создание множественного дополнительного реквизита. Управление торговлей 11

20.03.18

Интеграция - Файловый обмен (TXT, XML, DBF), FTP

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

Здравствуйте, уважаемые читатели! 

Хочу поделиться своей реализацией множественного выбора дополнительного реквизита в Управлении торговлей 11 (проверено на 11.4.1.261) для последующей выгрузки его в интернет-магазин под управлением 1С битрикс. Для чего это потребовалось? В определенный момент менеджер интернет-магазина мне сказал: хочу увидеть весь ассортимент выбранного товара (условно назовем его Товар№1) красного, синего и зеленого цветов, как?. Сразу оговорюсь, что по ряду внутренних причин характеристики мы не используем, возможно, с ними будет совсем другая история, но поскольку данный вопрос возникает периодически, я решил написать эту статью. Так вот, в УТ цвет это у нас дополнительный реквизит и соответственно он может принимать только одно значение. На сайте это выглядит как выбор из списка, а требуется чтобы можно было отмечать галочкой несколько значений.

з.ы. это моя первая публикация (не только на ИС, но и вообще), не судите строго :)

Итак, начнем. Весь процесс доработки можно разделить на 3 этапа:

  1. Доработка механизма создания и вывода на форму дополнительных реквизитов.
  2. Доработка xsd схемы.
  3. Доработка выгрузки на сайт.

1. Доработка механизма создания и вывода на форму дополнительных реквизитов.

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

Чтобы получать ссылку на нужный элемент ПВХ, я добавил функцию в модуль УправлениеСвойствамиСлужебный

Функция ПолучитьУИДМножественногоСвойства() Экспорт
    Возврат "859484ef-7e0a-11e7-8111-3863bb43122b";
КонецФункции

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

Перед ним добавим следующий код:

лУИД = Новый УникальныйИдентификатор(ПолучитьУИДМножественногоСвойства());
МножественноеСвойство = ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.ПолучитьСсылку(лУИД);
ЭтоПервый = Истина;

А в теле цикла будем отлавливать наше свойство следующим образом:

Если Строка.Свойство = МножественноеСвойство Тогда
    Если ЭтоПервый Тогда
        ЭтоПервый = Ложь;
    Иначе 
        фКэшОписания = ОписаниеСвойства;
        ОписаниеСвойства = ОписаниеСвойств.Добавить();
        ЗаполнитьЗначенияСвойств(ОписаниеСвойства, фКэшОписания);
    КонецЕсли;
КонецЕсли;

В итоге должна получится следующая картина:

После этого переходим к созданию элементов на форме. Тут логика следующая, каждый дополнительный реквизит в своем наименовании имеет уникальный идентификатор и тем самым обеспечивается уникальность (простите за тавтологию) имен элементов формы. Поэтому нам необходимо пронумеровать наш реквизит в момент создания. За это отвечает процедура ЗаполнитьДополнительныеРеквизитыВФорме общего модуля УправлениеСвойствами.

Находим в ней строку

Для каждого ОписаниеСвойства Из ОписаниеСвойств Цикл

Перед началом этого цикла вставим счетчик, например:

СчСвойств = 1;

А в теле цикла, после строки

ОписаниеСвойства.ИмяУникальнаяЧасть = ...

добавим наш код:

Если СтрНайти(Строка(ОписаниеСвойства.Свойство.УникальныйИдентификатор()), УправлениеСвойствамиСлужебный.ПолучитьУИДМножественногоСвойства()) > 0 Тогда             
    ОписаниеСвойства.ИмяУникальнаяЧасть = ОписаниеСвойства.ИмяУникальнаяЧасть    +"_"+ Строка(СчСвойств);            
    СчСвойств = СчСвойств + 1;                                                  
КонецЕсли;

Получается такая картина:

Дальше, чтобы не заморачиваться с формой при обновлении, добавляем ее в расширение. Добавляем событие ПриСозданииНаСервере с типом вызова "После", в нем создаем кнопку для копирования и заполним технические реквизиты. На форму потребуется добавить 2 реквизита:

1. МножВыборИмя - тип строка, хранит имя дополнительного реквизита без индекса

2. СчСвойств - тип число, хранит текущий индекс дополнительного реквизита.

 
 Полный текст модуля формы в расширении

После этих действий у вас должно получиться что-то подобное:

Если нужно добавить кнопку удаления реквизитов, то, думаю, у вас не возникнет с этим больших проблем :)

2. Доработка xsd схемы.

Если вы не знакомы с этой темой, то в интернете полно информации с подробным описанием, расписывать детально тут не буду. Схема находится в плане обмена Б_ОбменССайтом в макете СхемаXSDОбмена. Сохраняем в файл, открываем и находим там строку

<xs:complexType name="ЗначенияСвойства">

после элемента "Значение" добавляем следующий код

<xs:element name="ЗначениеСвойства" minOccurs="0" maxOccurs="unbounded" >
                <xs:complexType>
                    <xs:sequence>
                        <xs:element name="Значение" type="tns:ЗначениеТип" maxOccurs="1" />
                    </xs:sequence>
                </xs:complexType>
            </xs:element>

В итоге должно получится следующее: 

Далее обновляем макет в плане обмена и сохраняем конфигурацию. Все, xsd схема готова.

3. Доработка выгрузки на сайт.

Итак, мы на финишной прямой. Еще чуточку усилий и все будет готово!

Открываем общий модуль Б_ОбменССайтомСерверВыгрузкаДанных, находим в нем процедуру ВыгрузитьСвойстваXDTO,

в ней ищем строку:

XDTOСвойство.Наименование	= Лев(ТекСвойство.Наименование, 250);

это в цикле по коллекции тзнСвойств. После нее добавляем проверку. Если это наше свойство, то делаем его множественным.

Если СтрНайти(XDTOСвойство.Ид, УправлениеСвойствамиСлужебный.ПолучитьУИДМножественногоСвойства()) Тогда
	XDTOСвойство.Множественное = Истина;
КонецЕсли;

Далее нам нужно подкорректировать процедуру ВыгрузитьСвойстваНоменклатурыXDTO. Она не очень большая, поэтому приведу ее листинг с доработками. 

 
 Процедура ВыгрузитьСвойстваНоменклатурыXDTO

 

Вот и все, после этих манипуляций, xml код файла для битрикса должен выглядеть примерно так:

Битрикс такую структуру понимает и никаких действий со стороны сайта делать не требуется. Если вы все сделали правильно, то все должно работать.

p.s. 

Хочу поблагодарить Сергея Главатских за его идею копирования дополнительных реквизитов, а так же парней из ветки https://dev.1c-bitrix.ru, без них у меня бы ничего не получилось.

доработка обмен xml xsd битрикс множественный реквизит множественный выбор

См. также

SALE! 15%

Перенос данных 1C Файловый обмен (TXT, XML, DBF), FTP Системный администратор Программист Платформа 1С v8.3 1С:Розница 2 1С:Управление нашей фирмой 1.6 1С:Бухгалтерия 3.0 1С:Управление торговлей 11 1С:Комплексная автоматизация 2.х 1С:Управление нашей фирмой 3.0 1С:Розница 3.0 Россия Платные (руб)

Правила в универсальном формате обмена для ERP 2.5, КА 2.5, УТ 11.5, БП 3.0, Розница, УНФ, для последних версий конфигураций. Ссылки на другие конфигурации в описании публикации. Правила совместимы со всеми другими версиями конфигураций новыми и старыми, поддерживающими обмен и синхронизацию в формате EnterpriseData. Не требуется синхронного обновления правил после обновления другой конфигурации, участвующей в обмене. Типовой обмен через планы обмена кнопкой Синхронизация вручную или автоматически по расписанию, или вручную обработкой.

26280 руб.

12.06.2017    140922    793    295    

415

Перенос данных 1C Файловый обмен (TXT, XML, DBF), FTP Системный администратор Программист Платформа 1С v8.3 1С:Управление производственным предприятием 1С:Бухгалтерия 3.0 Россия Бухгалтерский учет Управленческий учет Платные (руб)

Перенос данных из 1С:Управление производственным предприятием 1.3 в 1С:Бухгалтерия предприятия 3.0 с помощью правил обмена. Переносятся остатки, документы (обороты за период), справочная информация. Правила проверены на конфигурациях УПП 1.3 (1.3.234.x) и БП 3.0 (3.0.161.x). Правила подходят для версии ПРОФ и КОРП.

35000 руб.

15.12.2021    23636    163    51    

121

SALE! 10%

Перенос данных 1C Файловый обмен (TXT, XML, DBF), FTP Программист Платформа 1С v8.3 1С:ERP Управление предприятием 2 1С:Бухгалтерия 3.0 1С:Управление торговлей 11 1С:Комплексная автоматизация 2.х Россия Платные (руб)

Перенос данных из ERP в БП 3 | из КА 2 в БП 3 | из УТ 11 в БП 3 | из ЕРП в БП 3 | Сэкономьте время - используйте готовое решение для перехода! | Перенос разработан в формате КД 2 (правила конвертации данных) | Переносятся все возможные виды документов, начальных остатков и нормативно-справочная информация| Можно опционально выгружать каждую пару "номенклатура+характеристика" как отдельную номенклатуру | Есть выгрузка настроек счетов учета и зарплатных данных из ERP / КА 2 | Можно проверить на вашем сервере перед покупкой

50722 45650 руб.

15.04.2019    71913    180    149    

122

SALE! 10%

Перенос данных 1C Файловый обмен (TXT, XML, DBF), FTP Системный администратор Программист Платформа 1С v8.3 1С:Комплексная автоматизация 1.х 1С:Управление производственным предприятием 1С:Бухгалтерия 3.0 Россия Бухгалтерский учет Платные (руб)

Перенос данных из 1С:Управление производственным предприятием 1.3 в 1С:Бухгалтерия предприятия 3.0 с помощью правил обмена | Можно выполнить переход с УПП на БП 3 или запускать выгрузку данных за выбранный период времени | Переносятся документы, начальные остатки и вся справочная информация | Есть фильтр по организации и множество других параметров выгрузки | Поддерживается несколько сценариев работы: как первичный полный перенос, так и перенос только новых документов | Перенос данных возможен в "1С: Бухгалтерия 3.0" версии ПРОФ, КОРП или базовую | Переход с "1С: УПП1.3" / "1С:КА 1.1" на "1С:БП3.0" с помощью правил конвертации будет максимально комфортным! | Можно бесплатно проверить перенос на вашем сервере!

43889 39500 руб.

25.02.2015    170900    302    256    

377

SALE! 10%

Перенос данных 1C Файловый обмен (TXT, XML, DBF), FTP Программист Платформа 1С v8.3 1С:ERP Управление предприятием 2 1С:Комплексная автоматизация 2.х 1С:Зарплата и Управление Персоналом 3.x Россия Бухгалтерский учет Управленческий учет Платные (руб)

Перенос данных из ERP в ЗУП 3 | из КА 2 в ЗУП | Готовые правила конвертации данных (КД 2) для переноса остатков, документов с движениями и справочной информации 3 | Есть перенос начальной задолженности по зарплате и начальной штатной расстановки на выбранную дату | Обороты за прошлые годы (данные для расчета среднего) переносятся свернуто в документ "Перенос данных" | Есть фильтр по организациям | Документы за текущий период переносятся сразу с движениями, поэтому не потребуется делать перерасчеты | Перенос можно проверить перед покупкой, обращайтесь!

48278 43450 руб.

03.12.2020    36335    92    64    

88

Перенос данных 1C Файловый обмен (TXT, XML, DBF), FTP Системный администратор Программист Платформа 1С v8.3 Оперативный учет 1С:Управление торговлей 10 Россия Управленческий учет Платные (руб)

Перенос данных из 1С:Управление торговлей 10.3 в 1С:Управление торговлей 11.5 с помощью правил обмена. Переносятся остатки, документы (обороты за период), справочная информация. Правила проверены на конфигурациях УТ 10.3 (10.3.88.x) и УТ 11.5 (11.5.19.x).

35000 руб.

23.07.2020    50555    218    69    

177

Перенос данных 1C Файловый обмен (TXT, XML, DBF), FTP Системный администратор Программист Платформа 1С v8.3 Платформа 1C v8.2 1С:Комплексная автоматизация 1.х 1С:Управление торговлей 10 1С:Управление производственным предприятием Россия Платные (руб)

Регулярный обмен, выгрузка, перенос из КА 1.1, УПП 1.3, УТ 10.3 для обмена с любыми конфигурациями, поддерживающими обмен в формате EnterpriseData (КД3) - БП 3.0, ERP, КА 2, УТ 11, Розница 2, УНФ 1.6 и другими. Правила для старых и доработанных конфигураций не требуют синхронного обновления и совместимы с новыми и будущими конфигурациями. Обмен по расписанию, через папку, FTP, почту.

15300 руб.

18.02.2016    186615    587    509    

524

SALE! 10%

Перенос данных 1C Взаиморасчеты Оптовая торговля Логистика, склад и ТМЦ Файловый обмен (TXT, XML, DBF), FTP Системный администратор Программист Платформа 1С v8.3 1С:Управление торговлей 10 1С:ERP Управление предприятием 2 1С:Управление торговлей 11 1С:Комплексная автоматизация 2.х Россия Управленческий учет Платные (руб)

Можно проверить до покупки, оставьте заявку! Воспользовались более 268 компаний! Перенос данных из УТ 10.3 в УТ 11 | из УТ 10.3 в КА 2 | из УТ 10.3 в ERP. Предлагаем качественное и проверенное временем решение для перехода с УТ 10.3. Можно перенести начальные остатки, нормативно-справочную информацию и все возможные документы. При выгрузке можно установить отбор по периоду, организациям и складам. При выходе новых релизов конфигураций 1C оперативно выпускаем обновление переноса данных.

50722 45650 руб.

24.04.2015    194661    149    242    

279
Комментарии
Подписаться на ответы Инфостарт бот Сортировка: Древо развёрнутое
Свернуть все
1. EmpireSer 21.03.18 00:47 Сейчас в теме
По мне "ЗначениеСвойства" в XSD задан "не красиво". Можно было всё в одном месте указать:
<xs:element name="ЗначениеСвойства" type="tns:ЗначениеТип" minOccurs="0" maxOccurs="unbounded" />

Так же можно было доработать доп. реквизит так, что бы он просто принимал "СписокЗначений", а не делать копирование. По моему мнению это получилось "элегантнее".
shurik_shurik; +1 Ответить
2. bad_wag 51 21.03.18 11:06 Сейчас в теме
(1) В начале я так и пытался сделать, но для этого потребовалось дорабатывать поддержку списков значений доп реквизитами, а это, на мой взгляд, гораздо сложнее данной реализации
3. vis_tmp 32 11.05.18 18:15 Сейчас в теме
Спасибо, очень познавательно про множественные доп. реквизиты.
6. bad_wag 51 06.06.18 02:00 Сейчас в теме
4. mark_oilbass 05.06.18 14:07 Сейчас в теме
5. bad_wag 51 06.06.18 01:59 Сейчас в теме
9. itdvl 28 16.08.18 06:41 Сейчас в теме
(5) не понимаю как сделать кнопку удалить. Не подскажете?
7. mark_oilbass 04.07.18 15:39 Сейчас в теме
Коллеги, подскажите пожалуйста! как быть если множественных реквизитов несколько? Я в плане видов характеристик создал реквизит МножественныйРеквизит и с помощью него получаю все множественные доп свойства. Перед выгрузкой свойств формирую запрос результатом, которого является список всех множественных свойств и дальше делаю такие же проверки как в этой статье. Прикрепляю файл с кодом. Заработает ли такой код?
Прикрепленные файлы:
Код.txt
8. mark_oilbass 05.07.18 11:24 Сейчас в теме
10. EliWalles 27.05.19 10:02 Сейчас в теме
Возможно ли вынести функции в расширение и воспользоваться &Вместо("ЗаполнитьДополнительныеРеквизитыВФорме") такой конструкцией, что бы не менять конфигурацию, будет работать?
УИД - это в XML файле экспорта поле <Ид>?
11. bad_wag 51 27.05.19 13:41 Сейчас в теме
(10) Вынести в расширение можно, работать будет, но при обновлениях конфигурации надо будет следить за изменениями в этой функции. Про УИД сейчас не вспомню, можно посмотреть отладчиком или выгрузить в файл там уже глянуть
12. goodwill 20 02.07.19 15:40 Сейчас в теме
Большое спасибо за выложенный материал, очень помог.

Хочу добавить от себя немного, Мне показалось не очень удачным определять множественный реквизит по GUID, в разных базах они разные и код получается не универсальным. Так же нет возможности добавить несколько множественных реквизитов. Для того что бы это исправить я добавил в ПланВидовХарактеристик.ДополнитеотныеРеквизитыИСведения новый реквизит МножественныйРеквизит

Изменения от первоначальной статьи следующие
1) Функция ПолучитьУИДМножественногоСвойства() не нужна
2) В модуле УправлениСвойствами

Если ОписаниеСвойства.Свойство.МножественныйРеквизит Тогда
	ОписаниеСвойства.ИмяУникальнаяЧасть = ОписаниеСвойства.ИмяУникальнаяЧасть    +"_"+ Строка(СчСвойств);            
	СчСвойств = СчСвойств + 1;                                                  
КонецЕсли;


3) УправлениеСвойствамиСлужебный


// < -- xs
СоответствиеСвойствЭтоПервый = Новый Соответствие;
// xs -- > 
	
// Заполнение значений свойств.
Для Каждого Строка Из ДополнительныеСвойстваОбъекта Цикл
	ОписаниеСвойства = ОписаниеСвойств.Найти(Строка.Свойство, "Свойство");
	Если ОписаниеСвойства <> Неопределено Тогда
		
		// < -- xs
		Если СоответствиеСвойствЭтоПервый.Получить(Строка.Свойство) = Неопределено Тогда
			СоответствиеСвойствЭтоПервый.Вставить(Строка.Свойство, Истина);
		КонецЕсли; 
		
		Если Строка.Свойство.МножественныйРеквизит Тогда
			
			Если СоответствиеСвойствЭтоПервый.Получить(Строка.Свойство) Тогда
				СоответствиеСвойствЭтоПервый.Вставить(Строка.Свойство, Ложь);
			Иначе 
				фКэшОписания = ОписаниеСвойства;
				ОписаниеСвойства = ОписаниеСвойств.Добавить();
				ЗаполнитьЗначенияСвойств(ОписаниеСвойства, фКэшОписания);
			КонецЕсли;
		КонецЕсли;
		// xs -- > 

		// Поддержка строк неограниченной длины.
		Если НЕ ЭтоДополнительноеСведение
		   И ИспользоватьНеограниченнуюСтроку(
		         ОписаниеСвойства.ТипЗначения, ОписаниеСвойства.МногострочноеПолеВвода)
		   И НЕ ПустаяСтрока(Строка.ТекстоваяСтрока) Тогда 
			
			ОписаниеСвойства.Значение = Строка.ТекстоваяСтрока;
		Иначе
			ОписаниеСвойства.Значение = Строка.Значение;
			КонецЕсли;
	КонецЕсли;
КонецЦикла;
Показать


4) Форма элемента справочника Номенклатура, так же добавил туда кнопку удаления реквизита.


&НаСервере
Процедура хот_ПриСозданииНаСервереПосле(Отказ, СтандартнаяОбработка)
	
	НоваяКоманда = ЭтаФорма.Команды.Добавить("СкопироватьСвойство");
	НоваяКоманда.Заголовок = "+";
	НоваяКоманда.Действие = "хот_СкопироватьСвойство";
	
	НоваяКоманда = ЭтаФорма.Команды.Добавить("УдалитьСвойство");
	НоваяКоманда.Заголовок = "-";
	НоваяКоманда.Действие = "хот_УдалитьСвойство"; 
	
	Для каждого стрДополнительногоРеквизита Из ЭтаФорма.Свойства_ОписаниеДополнительныхРеквизитов Цикл
		
		Если НЕ стрДополнительногоРеквизита.Свойство.МножественныйРеквизит Тогда
			Продолжить;
		КонецЕсли; 
			
		Если Элементы.Найти("КнопкаСкопироватьСвойство") = Неопределено Тогда
			НоваяКнопка = Элементы.Добавить("КнопкаСкопироватьСвойство", Тип("КнопкаФормы"),   Элементы.Найти("ГруппаДополнительныеРеквизитыКнопки"));
			НоваяКнопка.ИмяКоманды = "СкопироватьСвойство";
		КонецЕсли; 
		
	КонецЦикла; 
	
	спМножественныхСвойств = ПолучитьСписокМножественныхСвойств();
	Если спМножественныхСвойств.Количество() > 0 Тогда
		НоваяКнопка = Элементы.Добавить("КнопкаУдалитьСвойство", Тип("КнопкаФормы"), Элементы.Найти("ГруппаДополнительныеРеквизитыКнопки"));
		НоваяКнопка.ИмяКоманды = "УдалитьСвойство";
	КонецЕсли;
		
КонецПроцедуры

&НаСервере
Функция ПолучитьСписокМножественныхСвойств()
	
	спМножественныхСвойств = Новый СписокЗначений;
	
	вт_Свойства = ЭтаФорма.Свойства_ОписаниеДополнительныхРеквизитов.Выгрузить();
	вт_Свойства.Колонки.Добавить("Счетчик");
	вт_Свойства.ЗаполнитьЗначения(1, "Счетчик");
	вт_Свойства.Свернуть("Свойство", "Счетчик");
	
	Для Каждого стрСвойство из вт_Свойства Цикл 
		Если стрСвойство.Счетчик > 1 Тогда
			спМножественныхСвойств.Добавить(стрСвойство.Свойство);
		конецЕсли
	КонецЦикла;
	
	Возврат спМножественныхСвойств;
	
КонецФункции

&НаСервере
Функция ПолучитьСписокМножественныхСвойствВсе()
	
	спМножественныхСвойств = Новый СписокЗначений;
	
	Для каждого стрДополнительногоРеквизита Из ЭтаФорма.Свойства_ОписаниеДополнительныхРеквизитов Цикл
		
		Если НЕ спМножественныхСвойств.НайтиПоЗначению(стрДополнительногоРеквизита.Свойство) = Неопределено Тогда
			Продолжить;
		КонецЕсли; 
		
		Если стрДополнительногоРеквизита.Свойство.МножественныйРеквизит Тогда
			спМножественныхСвойств.Добавить(стрДополнительногоРеквизита.Свойство);
		КонецЕсли; 
		
	КонецЦикла;
	
	Возврат спМножественныхСвойств;
	
КонецФункции

&НаКлиенте
Процедура хот_СкопироватьСвойство()
	
	спМножественныхСвойств = ПолучитьСписокМножественныхСвойствВсе();
	
	Оповещение = Новый ОписаниеОповещения("хот_ПослеВыбораИзМеню", ЭтотОбъект);
	ПоказатьВыборИзМеню(Оповещение, спМножественныхСвойств, Элементы.КнопкаСкопироватьСвойство);
	
КонецПроцедуры

&НаКлиенте
Процедура хот_УдалитьСвойство()
	
	//Список свойств, для которых есть несколько значений
	спМножественныхСвойств = ПолучитьСписокМножественныхСвойств();
	
	спМножественныхСвойствВыбор = Новый СписокЗначений;
	Для каждого стрДополнительногоРеквизита Из ЭтаФорма.Свойства_ОписаниеДополнительныхРеквизитов Цикл
		
		Если спМножественныхСвойств.НайтиПоЗначению(стрДополнительногоРеквизита.Свойство) = Неопределено Тогда
			Продолжить;
		КонецЕсли; 
		
		спМножественныхСвойствВыбор.Добавить(стрДополнительногоРеквизита, СокрЛП(стрДополнительногоРеквизита.Свойство) + " " + СокрЛП(ЭтаФорма[стрДополнительногоРеквизита.ИмяРеквизитаЗначение]));
				
	КонецЦикла;
	
	Оповещение = Новый ОписаниеОповещения("хот_ПослеВыбораИзМенюУдалитьСвойство", ЭтотОбъект);
	ПоказатьВыборИзМеню(Оповещение, спМножественныхСвойствВыбор, Элементы.КнопкаУдалитьСвойство);
	
КонецПроцедуры

&НаКлиенте
Процедура хот_ПослеВыбораИзМеню(ВыбранныйЭлемент, Параметры) Экспорт
	Если НЕ ВыбранныйЭлемент = Неопределено Тогда
		хот_ДобавитьРеквизиты(ВыбранныйЭлемент.Значение)
	КонецЕсли;
КонецПроцедуры

&НаКлиенте
Процедура хот_ПослеВыбораИзМенюУдалитьСвойство(ВыбранныйЭлемент, Параметры) Экспорт
	Если НЕ ВыбранныйЭлемент = Неопределено Тогда
		УдалитьСвойство(ВыбранныйЭлемент.Значение.ИмяРеквизитаЗначение);
	КонецЕсли;
КонецПроцедуры

&НаСервере
Процедура УдалитьСвойство(ИмяРеквизитаЗначение)
	Элементы.Удалить(Элементы.Найти(ИмяРеквизитаЗначение));
	
	НайденныеСтроки = ЭтаФорма.Свойства_ОписаниеДополнительныхРеквизитов.НайтиСтроки(Новый Структура("ИмяРеквизитаЗначение", ИмяРеквизитаЗначение));
	Для Каждого стрСвойство Из НайденныеСтроки Цикл 
		ЭтаФорма.Свойства_ОписаниеДополнительныхРеквизитов.Удалить(стрСвойство);
	КонецЦикла;
	
Конецпроцедуры

&НаСервере
Процедура хот_ДобавитьРеквизиты(ДопРеквизит)
	
	ОписаниеТипа = Новый ОписаниеТипов("СправочникСсылка.ЗначенияСвойствОбъектов");
	Для каждого стрДополнительногоРеквизита Из ЭтаФорма.Свойства_ОписаниеДополнительныхРеквизитов Цикл
		Если стрДополнительногоРеквизита.Свойство = ДопРеквизит Тогда
			ОписаниеТипа = стрДополнительногоРеквизита.ТипЗначения;		
			Прервать;
		КонецЕсли; 
	КонецЦикла;
	
	ИмяРеквизита = СтандартныеПодсистемыСервер.ПреобразоватьСтрокуВДопустимоеНаименованиеКолонки("ДополнительныйРеквизит_" + Строка(Новый УникальныйИдентификатор));
	лСвойство = ДопРеквизит;
	
	лМассив = Новый Массив;
	лМассив.Добавить(Новый РеквизитФормы(ИмяРеквизита, ОписаниеТипа,,ДопРеквизит.Наименование, Истина));
	ИзменитьРеквизиты(лМассив);
	
	НовЭлемент = Элементы.Вставить(ИмяРеквизита, Тип("ПолеФормы"), Элементы.Найти("ГруппаДополнительныеРеквизиты"));
	НовЭлемент.ПутьКДанным = ИмяРеквизита;
	НовЭлемент.Вид = ВидПоляФормы.ПолеВвода;
	
	МассивПараметров = Новый Массив;
	МассивПараметров.Добавить(Новый ПараметрВыбора("Отбор.Владелец", лСвойство));
	
	Элементы[ИмяРеквизита].ПараметрыВыбора = Новый ФиксированныйМассив(МассивПараметров);
	
	ДобавитьСвойство(ЭтаФорма, ИмяРеквизита, лСвойство);
	
КонецПроцедуры

&НаСервереБезКонтекста
Процедура ДобавитьСвойство(лФорма, ИмяРеквизита, Свойство)

	лШаблон = лФорма.Свойства_ОписаниеДополнительныхРеквизитов.НайтиСтроки(Новый Структура("Свойство", Свойство));
	НовоеСвойство = лФорма.Свойства_ОписаниеДополнительныхРеквизитов.Добавить();
	
	Если лШаблон.Количество() > 0 Тогда
		ЗаполнитьЗначенияСвойств(НовоеСвойство, лШаблон[0]);
		НовоеСвойство.ИмяРеквизитаЗначение = ИмяРеквизита;
	КонецЕсли;
	
КонецПроцедуры


Показать


5) Модуль Б_ОбменССайтомСерверВыгрузкаДанных

Процедура ВыгрузитьСвойстваXDTO

// < -- xs
XDTOСвойство.Множественное = ТекСвойство.СвойствоНоменклатуры.МножественныйРеквизит;
// xs -- > 


Процедура ВыгрузитьСвойстваНоменклатурыXDTO


Процедура ВыгрузитьСвойстваНоменклатурыXDTO(ПараметрыОбмена, Владелец, ВладелецТип, ВыборкаНоменклатуры, МенеджерВременныхТаблиц);
	
	XDTOЗначенияСвойствТип 	= Б_ОбменССайтомСервер.ПолучениеТипОбъектаXDTO(ПараметрыОбмена,  "ЗначенияСвойств", Истина, ВладелецТип);
	XDTOЗначенияСвойстваТип = Б_ОбменССайтомСервер.ПолучениеТипОбъектаXDTO(ПараметрыОбмена,  "ЗначенияСвойства");
	
	// < -- xs
	XDTOЗначениеСвойства_МножТип = Б_ОбменССайтомСервер.ПолучениеТипОбъектаXDTO(ПараметрыОбмена,  "ЗначениеСвойства", Истина, XDTOЗначенияСвойстваТип);
	// xs -- > 
	
	Запрос = Новый Запрос;
	запрос.МенеджерВременныхТаблиц = МенеджерВременныхТаблиц;
	запрос.Текст =  "ВЫБРАТЬ *
	|ИЗ
	|	ВремЗначенияСвойствТовара КАК ВремЗначенияСвойствТовара
	|ГДЕ
	|	(ВремЗначенияСвойствТовара.Номенклатура = &Номенклатура	
	|И НЕ ВремЗначенияСвойствТовара.НеВыгружатьВСвойстваТоваров)";
	
	Запрос.УстановитьПараметр("Номенклатура", ВыборкаНоменклатуры.Номенклатура);
	Выборка = Запрос.Выполнить();
	
	Если НЕ Выборка.Пустой() тогда	
		ВыборкаСвойств = Выборка.Выбрать();
		XDTOЗначенияСвойств = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойствТип);
		
		// < -- xs
		XDTOЗначенияСвойства_Множ = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойстваТип);
		// xs -- > 
		
		Пока ВыборкаСвойств.Следующий() Цикл
			
			XDTOЗначенияСвойства = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойстваТип);
			
			XDTOЗначенияСвойства.Ид = XMLСтрока(ВыборкаСвойств.ИдентификаторСвойства);
			
			// < -- xs
			Если ВыборкаСвойств.Свойство.МножественныйРеквизит Тогда
				XDTOЗначениеСвойстваМнож = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначениеСвойства_МножТип);
				XDTOЗначениеСвойстваМнож.Значение = XMLСтрока(ВыборкаСвойств.ИдентификаторЗначения);
				
			    XDTOЗначенияСвойства_Множ.Ид = XMLСтрока(ВыборкаСвойств.ИдентификаторСвойства);
				XDTOЗначенияСвойства_Множ.ЗначениеСвойства.Добавить(XDTOЗначениеСвойстваМнож);
				XDTOЗначенияСвойства_Множ.Значение.Добавить(XMLСтрока(ВыборкаСвойств.ИдентификаторЗначения));
				Продолжить;
			КонецЕсли;
			// xs -- > 
			
			XDTOЗначенияСвойства.Значение.Добавить(XMLСтрока(ВыборкаСвойств.ИдентификаторЗначения));
			
			XDTOЗначенияСвойств.ЗначенияСвойства.Добавить(XDTOЗначенияСвойства);	
			
		КонецЦикла;
		
		// < -- xs	
		XDTOЗначенияСвойств.ЗначенияСвойства.Добавить(XDTOЗначенияСвойства_Множ);
		// xs -- >

		Владелец.ЗначенияСвойств = XDTOЗначенияСвойств;
	КонецЕсли;
	
КонецПроцедуры

Показать
Прикрепленные файлы:
2711640; nemec; Varozh; Buхter; bonya_by; chng; user1136006; +7 Ответить
13. bad_wag 51 02.07.19 18:09 Сейчас в теме
(12) Спасибо! Ну я решал свою задачу, по этому об универсальности не думал, но вы развернулись на широкую ногу! Хоть в типовую переноси :) Отличное дополнение
14. Djo82 11 04.07.19 15:17 Сейчас в теме
с кнопками не разобрался, если не сложно поясните подробнее
15. Djo82 11 04.07.19 16:51 Сейчас в теме
16. user1136006 07.08.19 11:54 Сейчас в теме
(12) Прекрасное решение, спасибо! Но обнаружил проблему: если было выбрано несколько значений, а потом меньшее количество - предыдущий выбор сохраняется. Наверное, надо каким-то образом очищать реквизиты во время загрузки, может быть проблема только у меня...
17. RSTR 07.09.19 13:16 Сейчас в теме
bad_wag, просьба-вопрос к вам. Можете ли вы сделать настройку данной доработки в нашей базе? Сделали всё по инструкции, в УТ множественный реквизит появился, но в файл обмена с Битриксом этот реквизит не попадает.. УТ (11.4.6.174), Битрикс 7.0.1.21
Сколько это будет стоить?
18. Djo82 11 31.01.20 19:33 Сейчас в теме
Статья помогла решить задачу. Спасибо!

Но не отработала процедура "ВыгрузитьСвойстваНоменклатурыXDTO" при условии, что присутствует несколько множественных свойств. Подсмотрел исходники от партнеров с Битрикс. Немного подправил процедуру и файл "СхемаXSDОбмена". Вдруг кому поможет.

Процедура ВыгрузитьСвойстваНоменклатурыXDTO(ПараметрыОбмена, Владелец, ВладелецТип, ВыборкаНоменклатуры, МенеджерВременныхТаблиц);
	
	XDTOЗначенияСвойствТип 	= Б_ОбменССайтомСервер.ПолучениеТипОбъектаXDTO(ПараметрыОбмена,  "ЗначенияСвойств", Истина, ВладелецТип);
	XDTOЗначенияСвойстваТип = Б_ОбменССайтомСервер.ПолучениеТипОбъектаXDTO(ПараметрыОбмена,  "ЗначенияСвойства");
	
	//++все отлично
	XDTOЗначенияСвойствМножТип   = Б_ОбменССайтомСервер.ПолучениеТипОбъектаXDTO(ПараметрыОбмена, "ЗначениеСвойства", Истина, XDTOЗначенияСвойстваТип);
	//все отлично++
	
	Запрос = Новый Запрос;
	запрос.МенеджерВременныхТаблиц = МенеджерВременныхТаблиц;
	запрос.Текст =  "ВЫБРАТЬ *
	|ИЗ
	|	ВремЗначенияСвойствТовара КАК ВремЗначенияСвойствТовара
	|ГДЕ
	|	(ВремЗначенияСвойствТовара.Номенклатура = &Номенклатура	
	|И НЕ ВремЗначенияСвойствТовара.НеВыгружатьВСвойстваТоваров)";
	
	Запрос.УстановитьПараметр("Номенклатура", ВыборкаНоменклатуры.Номенклатура);
	Выборка = Запрос.Выполнить();
	
	//Если НЕ Выборка.Пустой() тогда	
	//	ВыборкаСвойств = Выборка.Выбрать();
	//	XDTOЗначенияСвойств = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойствТип);
	//	
	//	Пока ВыборкаСвойств.Следующий() Цикл
	//		
	//		XDTOЗначенияСвойства = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойстваТип);
	//		
	//		XDTOЗначенияСвойства.Ид = XMLСтрока(ВыборкаСвойств.ИдентификаторСвойства);
	//		XDTOЗначенияСвойства.Значение.Добавить(XMLСтрока(ВыборкаСвойств.ИдентификаторЗначения));
	//		
	//		XDTOЗначенияСвойств.ЗначенияСвойства.Добавить(XDTOЗначенияСвойства);	
	//		
	//	КонецЦикла;
	//	Владелец.ЗначенияСвойств = XDTOЗначенияСвойств;
	//КонецЕсли;
	ТаблицаСвойств = Выборка.Выгрузить();
	
СвернутьТаблицуПодСписокЗначений(ТаблицаСвойств,"ИдентификаторСвойства","Значение");
	
	Если НЕ ТаблицаСвойств.Количество() = 0 Тогда
		XDTOЗначенияСвойств = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойствТип);
		Для Каждого ВыборкаСвойств из ТаблицаСвойств Цикл

				XDTOЗначенияСвойства = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойстваТип);
				
				XDTOЗначенияСвойства.Ид = XMLСтрока(ВыборкаСвойств.ИдентификаторСвойства);
				Если НЕ ВыборкаСвойств.БулевоЗначение тогда
					Если НЕ ТипЗнч(ВыборкаСвойств.Значение) = Тип("СписокЗначений") Тогда
						XDTOЗначенияСвойства.Значение.Добавить(XMLСтрока(ВыборкаСвойств.ИдентификаторЗначения));
					Иначе
						Для каждого Свойство из ВыборкаСвойств.Значение Цикл
							XDTOЗначенияМножСвойств = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначенияСвойствМножТип);
							XDTOЗначенияМножСвойств.Значение = XMLСтрока(Свойство.Значение);
							XDTOЗначенияСвойства.ЗначениеСвойства.Добавить(XDTOЗначенияМножСвойств);
						КонецЦикла;
					КонецЕсли;
				Иначе
					XDTOЗначенияСвойства.Значение.Добавить(Строка(ВыборкаСвойств.ИдентификаторЗначения));
				КонецЕсли;
				
				XDTOЗначенияСвойств.ЗначенияСвойства.Добавить(XDTOЗначенияСвойства);
				
		КонецЦикла;
		Владелец.ЗначенияСвойств = XDTOЗначенияСвойств;
	КонецЕсли;
КонецПроцедуры

Процедура СвернутьТаблицуПодСписокЗначений(Таблица,ПолеДляАнализа,ПолеДляСвертки) Экспорт
	Если Ложь Тогда Таблица = Новый ТаблицаЗначений; КонецЕсли;
	СписокСвойств = Новый Соответствие;
	Для каждого Строка из Таблица Цикл
		НайденноеСвойство = СписокСвойств.Получить(Строка[ПолеДляАнализа]);
		Если НЕ НайденноеСвойство = неопределено Тогда
			Если НЕ ТипЗнч(НайденноеСвойство) = Тип("СписокЗначений") Тогда
				Список = Новый СписокЗначений;
				Список.Добавить(НайденноеСвойство);
				Список.Добавить(Строка[ПолеДляСвертки]);
				СписокСвойств.Вставить(Строка[ПолеДляАнализа], Список);
			Иначе
				НайденноеСвойство.Добавить(Строка[ПолеДляСвертки]);
			КонецЕсли;
		Иначе			
			СписокСвойств.Вставить(Строка[ПолеДляАнализа], Строка[ПолеДляСвертки]);
		КонецЕсли;
	КонецЦикла;
	КолонкиКопия = Таблица.ВыгрузитьКолонку("Значение");
	ОписаниеТипов = Новый ОписаниеТипов(Таблица.Колонки.Значение.ТипЗначения,"СписокЗначений");
	ШиринаКопия = Таблица.Колонки.Значение.Ширина;
	
	Таблица.Колонки.Удалить("Значение");
	Таблица.Колонки.Добавить("Значение",ОписаниеТипов,"Значение",ШиринаКопия);
	Таблица.ЗагрузитьКолонку(КолонкиКопия, "Значение");
	
	Для каждого Свойство из СписокСвойств Цикл
		Если ТипЗнч(Свойство.Значение) = Тип("СписокЗначений") Тогда
			НайденныеСтроки = Таблица.НайтиСтроки(Новый Структура(ПолеДляАнализа,Свойство.Ключ));
			Н = 0;
			Для Каждого Строка из НайденныеСтроки Цикл
				Н = Н + 1;
				Если Н = 1 Тогда
					Строка.Значение = Свойство.Значение;
				Иначе
					Таблица.Удалить(Строка);
				КонецЕсли;
			КонецЦикла;
		КонецЕсли;
	КонецЦикла;

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


Показать


Немного другой текст в "СхемаXSDОбмена"

<xs:complexType name="ЗначенияСвойства">
        <xs:sequence>
            <xs:element name="Ид" type="tns:ИдентификаторГлобальныйТип" />
            <xs:element name="Наименование" type="tns:НаименованиеТип" minOccurs="0" />
            <xs:element name="Значение" type="tns:ЗначениеТип" minOccurs="0" maxOccurs="unbounded" />
            <xs:element name="ЗначениеСвойства" minOccurs="0" maxOccurs="unbounded" >
                <xs:complexType>
                    <xs:sequence>
                        <xs:element name="Значение" type="tns:ЗначениеТип" maxOccurs="1" />
                    </xs:sequence>
				</xs:complexType>
            </xs:element>
        </xs:sequence>
    </xs:complexType>
Показать
19. user691380_bel4enkin 18.04.20 14:18 Сейчас в теме
А случайно никто не выкладывал подобное расширение под УТ11.4 чтобы не изучать все тонкости? Интересует множественный реквизит с выгрузкой на сайт Opencart
20. ArturShaibakov 09.02.21 20:47 Сейчас в теме
Для 1с Розница, редакция 2.3 (2.3.5.35), дальше первого пункта делать ничего не нужно, все работает.
21. user1375596 20.08.21 20:08 Сейчас в теме
вы уверены, что Битрикс умеет парсить такую конструкцию?

					<ЗначенияСвойства>
						<Ид>e94be4ad-fb60-11eb-80e2-c643fff9747c</Ид>
						<Значение>
							<Значение>f237f346-fb60-11eb-80e2-c643fff9747c</Значение>
							<Значение>f237f347-fb60-11eb-80e2-c643fff9747c</Значение>
							<ЗначенияСвойства>
								<Значение>f237f346-fb60-11eb-80e2-c643fff9747c</Значение>
							</ЗначенияСвойства>
							<ЗначенияСвойства>
								<Значение>f237f347-fb60-11eb-80e2-c643fff9747c</Значение>
							</ЗначенияСвойства>
						</Значение>
					</ЗначенияСвойства>
Показать



У меня БУС 21.400.300 не воспринимает такой массив.
22. user1375596 21.08.21 08:54 Сейчас в теме
23. sderzhu 10.11.22 16:30 Сейчас в теме
Если СтрНайти(XDTOЗначенияСвойства.Ид, УправлениеСвойствамиСлужебный.ПолучитьУИДМножественногоСвойства()) > 0 Тогда
				XDTOЗначениеСвойстваМнож = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначениеСвойства_МножТип);
				XDTOЗначениеСвойстваМнож.Значение = XMLСтрока(ВыборкаСвойств.ИдентификаторЗначения);
				
			    XDTOЗначенияСвойства_Множ.Ид = XMLСтрока(ВыборкаСвойств.ИдентификаторСвойства);
				XDTOЗначенияСвойства_Множ.ЗначениеСвойства.Добавить(XDTOЗначениеСвойстваМнож);
				//XDTOЗначенияСвойства_Множ.Значение.Добавить(XMLСтрока(ВыборкаСвойств.ИдентификаторЗначения));
				Продолжить;
			КонецЕсли;
Показать

Закоменченная строка не нужна - лишнее это...

И, кстати, если нужно полностью очистить множественное значение, нужно обязательно послать пустое значение:

XDTOЗначениеСвойстваМнож = ПараметрыОбмена.МояФабрикаXDTO.Создать(XDTOЗначениеСвойства_МножТип);
				XDTOЗначениеСвойстваМнож.Значение = XMLСтрока("");
24. Rustamilyok 08.10.24 13:36 Сейчас в теме
Что за модуль для выгрузки в битрикс дорабатывался?
Оставьте свое сообщение