Трудности международных конфигураций.

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

Возьмем справочник единиц измерений. Для российских пользователей счет фактур единицы измерения должны показываться на русском (для проверяющих), а для иностранцев на их языке в отчетах.  Тоже с товарной номенклатурой.

У 1С есть в новых БСП подсистема «Мультиязычность»

Глава 3. Настройка и использование подсистем при разработке конфигурации :: Библиотека стандартных подсистем 3.1.10. Документация. Тестовая версия (1c.ru)

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

( КомментарийЯзык1, НаименованиеЯзык1, КомментарийЯзык2, НаименованиеЯзык2 )

а вывод представления в разных отчетах на разных языках через предопределенные процедуры


#Область ОбработчикиСобытий
Процедура ОбработкаПолученияПолейПредставления(Поля, СтандартнаяОбработка)
    МультиязычностьКлиентСервер.ОбработкаПолученияПолейПредставления(Поля, СтандартнаяОбработка);
КонецПроцедуры
Процедура ОбработкаПолученияПредставления(Данные, Представление, СтандартнаяОбработка)
    МультиязычностьКлиентСервер.ОбработкаПолученияПредставления(Данные, Представление, СтандартнаяОбработка);
КонецПроцедуры
Процедура ОбработкаПолученияДанныхВыбора(ДанныеВыбора, Параметры, СтандартнаяОбработка)
    МультиязычностьСервер.ОбработкаПолученияДанныхВыбора(ДанныеВыбора, Параметры, СтандартнаяОбработка, <Метаданные.ПланыВидовХарактеристик.ОбъектыАдресацииЗадач>);
КонецПроцедуры
#КонецОбласти

Эти предопределенные процедуры вызываются на каждую строку отчета или формы. Но код в них с моей точки зрения достаточно сложен. В более старых БСП ниже 3й версии этой подсистемы нет.

Простой способ возведения вавилонской башни.

Если стоит задача хранить переводы для представлений на разных языках, есть более простой выход.

  1. Создаете для нужных справочников реквизит АльтернативноеПредставление (не общий, у каждого справочника)

  2. Храните там строку , которая является аргументом для функции НСтр

  3. И создайте наиболее простые варианты процедур ОбработкаПолученияПредставления()

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

Вот как все выглядит

Главное в этих предопределенных процедурах использовать самые простые конструкции на уровне (процессор – память) без сложных обращений к СУБД . Ведь этот код будет вызываться на каждую строку в форме или отчете. Когда данные процедуры находятся в модуле менеджера, они вызываются автоматом для каждого отчета или формы, поэтому модификации отчетов и форм не требуется.

Процедура ОбработкаПолученияПредставления(Данные, Представление, СтандартнаяОбработка)

	СУУ_Представления.ОбработкаПолученияПредставленияСправочника(Данные, Представление, СтандартнаяОбработка);
	
КонецПроцедуры

Процедура ОбработкаПолученияПолейПредставления(Поля, СтандартнаяОбработка) 

    СУУ_Представления.ОбработкаПолученияПолейПредставленияСправочника(Поля, СтандартнаяОбработка);

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

Функция СформироватьАльтернативноеПредставлениеДокумента(Данные, Представление, СтандартнаяОбработка) Экспорт
	
	Попытка
		//Выводим представление если оно есть              
		Если ПустаяСтрока(Данные.СУУ_АльтернативноеПредставление) Тогда        
			Возврат Ложь;
		Иначе 	
			Представление = Данные.СУУ_АльтернативноеПредставление;
			СтандартнаяОбработка = Ложь; 
			Возврат Истина;
		КонецЕсли;
	Исключение 
		ЗаписьЖурналаРегистрации("Error", УровеньЖурналаРегистрации.Ошибка, , Данные.Ссылка, "There is an error "+ ОписаниеОшибки() +" during creating alternative representation for " + Представление);
		Возврат Ложь;
	КонецПопытки;
	
КонецФункции       

Процедура ОбработкаПолученияПредставленияСправочника(Данные, Представление, СтандартнаяОбработка) Экспорт   
	
	Если ЗначениеЗаполнено(Данные.СУУ_АльтернативноеПредставление) Тогда  
		СтандартнаяОбработка = Ложь;
		Попытка
			Представление = НСтр(Данные.СУУ_АльтернативноеПредставление);
		Исключение
			Представление = Данные.СУУ_АльтернативноеПредставление;
		КонецПопытки;
	КонецЕсли;
		
КонецПроцедуры

Возможно кто-то предложить еще более красивое решение, пишите на нашем канале. Лето будет жарким.

Комментарии (9)


  1. kale
    17.05.2024 09:27
    +1

    Напрасно вы ссылку даете на документацию с ограниченным доступом. Читатели будут справедливо недовольны.


    1. 1CUnlimited Автор
      17.05.2024 09:27

      К сожалению 1С держит это на ИТС подписке, но это официальная документация. Те кто занимается 1С как правило имеют доступ иначе не скачаешь обновления. Для интересующихся пробный период на 7 дней* на количество емейлов :) всегда можно получить


  1. cherv81
    17.05.2024 09:27

    Из плюсов - представленное решение понятно, просто и решает поставленную задачу. Конечно, реализация получилась очень частная, например, непонятно, как реализовать представление по нескольким полям.

    Но сама реализация очень спорна с разных точек зрения. Например, заполнение поля "Альтернативное представление" для пользователя трудоёмко, правильно указать все эти ru, en и точки с запятыми в правильных местах - явно не задача пользователя. Напрашивается программное заполнение данного реквизита, чтобы форматирование происходило автоматически, но тогда поле не должно быть доступно в пользовательском режиме, а данные для его заполнения хранятся в нормальных полях "Английское наименование", "Российское наименование" и т.д. или в таблице соответствий Язык - Поле - Значение, например, Английский язык - Наименование товара - Метрические тонны.

    Заполнение пользователями, видимо, приводит и к не очень хорошему коду. Попытка - Исключение сразу режут глаза, но, как я понимаю, это позволяет обойти ошибки заполнения. Тем не менее, такой код точно не прошел бы код-ревью. Нужно изменить архитектуру и избавиться от методов написания кода "оберну всё в попытку", чем грешат многие, закрывая ошибки проектирования. Заменить попытки как минимум нужно на проверку того, что содержится в параметре Данные (содержится ли ключ с нужным полем) + проверка корректности форматной строки.


    1. 1CUnlimited Автор
      17.05.2024 09:27

      Нужно изменить архитектуру и избавиться от методов написания кода "оберну всё в попытку", чем грешат многие, закрывая ошибки проектирования. 

      Интерфейс для ввода как я отметил там есть. Но если кто-то заполнит альтернативное представление (через обработку) другим кривым способом или не заполнит. Да сработает

      Исключение Представление = Данные.СУУ_АльтернативноеПредставление; КонецПопытки;

      Это больше защита от дурака

      Не забывайте что эти стандартные обработчики срабатывают на каждую строку формы или отчета. Программа должна отрабатывать без ошибок в любом случае. Иначе получите 10500. Исключений на экран пользователя.


      1. cherv81
        17.05.2024 09:27

        Да, я понимаю, что это стандартные обработчики. И в них никогда в стандартных конфигурациях не используется конструкция Попытка - Исключение. Вы видели такие примеры в коде типовых конфигураций, например, в этих обработчики? Вообще, конструкция Попытка - Исключение нужна в работе, когда мы имеем дело с транзакциями, например, или вызовом внешних сервисов, когда мы не можем гарантировать, как поведет себя система в тех местах, которые мы не контролируем. Если есть текстовое поле, которое мы даём ввести пользователю, и мы не можем его ограничить, чтобы оно было введено корректно и вынуждены ловить Попыткой ошибки - значит, что мы спроектировали что-то не так. К сожалению, повторюсь, такие вещи часто встречаются и в тиражных решениях (в конфигурациях Альфа-Авто, например) - и все эти места очень режут глаз и говорят о недоработанности решения.


  1. 1CUnlimited Автор
    17.05.2024 09:27

     Например, заполнение поля "Альтернативное представление" для пользователя трудоёмко, правильно указать все эти ru, en и точки с запятыми в правильных местах - явно не задача пользователя.

    Там на скрине показана форма ввода пользователю формат строки соблюдать не нужно


    1. cherv81
      17.05.2024 09:27

      Хорошо. Тогда в каких случаях мы ожидаем, что функция НСтр не сработает?


      1. 1CUnlimited Автор
        17.05.2024 09:27

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

        Отвечу сразу на оба вопроса.

        Типовые конфигурации нельзя считать образцом кода, хотябы по тому что на нескольких терабайт они просто сдохнут. Скорее архитектура в них это антипаттерн, вот свежий пример. А я их могу много накидать

        Что делать, когда фоновые задания для печатных форм 1С тормозят? / Хабр (habr.com)

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

        Сколько точек зрения у  Архитектора в ИТ? / Хабр (habr.com)

        В данном случае - есть интерфейс ввода (кстати на общей форме) для ввода строки для Нстр , есть проверка на пустоту.

        Но код универсален - он применяется не только в единицах измерениях, но и в других объектах. И я понимаю что справочник могут создать обработкой импорта, кривым представлением представлением без ru en . На эти редкие случаи и ставится Попытка Исключение

        В целом у меня правило - любой код на каком то уровне оборачивается в Попытка Исключение . Либо идет запись в лог, либо обрабатывается разумным образом. Просто вылетающая программа это плохо - потом концов не найдешь.

        и вынуждены ловить Попыткой ошибки - значит, что мы спроектировали что-то не так.

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


        1. cherv81
          17.05.2024 09:27

          Что ж, если у Вас правило любой код заворачивать в Попытку - далее дискутировать бесполезно. Если интересно почитайте комментарии к статье https://infostart.ru/1c/articles/2053466/ и вообще литературу о таком подходе. И да, проблема большей частью не с производительностью кода в данном случае. И почему в загрузку обработкой нельзя добавить проверку - тоже не объясняете. А спроектировать правильно можно, это не иллюзия, было бы желание.