На стороне источника (БП) реализован веб-сервис UploadUsers и метод Upload().
Для передачи данных реализован XDTO-пакет следующей структуры:
Написана функция для метода Upload(). Код приведен ниже:
Функция Upload()
УстановитьПривилегированныйРежим(Истина);
Запрос = Новый Запрос;
Запрос.Текст=
"ВЫБРАТЬ РАЗРЕШЕННЫЕ
| РаботникиОрганизацийСрезПоследних.Физлицо,
| МАКСИМУМ(РаботникиОрганизацийСрезПоследних.Период) КАК Период,
| РаботникиОрганизацийСрезПоследних.ПричинаИзмененияСостояния,
| РаботникиОрганизацийСрезПоследних.ПодразделениеОрганизации,
| РаботникиОрганизацийСрезПоследних.Должность
|ПОМЕСТИТЬ втПриемы
|ИЗ
| РегистрСведений.РаботникиОрганизаций.СрезПоследних(
| &ДатаАктуальности,
| Организация = &Организация
| И ПричинаИзмененияСостояния В (&сзСостояния)) КАК РаботникиОрганизацийСрезПоследних
|
|СГРУППИРОВАТЬ ПО
| РаботникиОрганизацийСрезПоследних.Физлицо,
| РаботникиОрганизацийСрезПоследних.ПричинаИзмененияСостояния,
| РаботникиОрганизацийСрезПоследних.ПодразделениеОрганизации,
| РаботникиОрганизацийСрезПоследних.Должность
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| РаботникиОрганизацийСрезПоследних.Физлицо,
| МАКСИМУМ(РаботникиОрганизацийСрезПоследних.Период) КАК Период,
| РаботникиОрганизацийСрезПоследних.ПричинаИзмененияСостояния
|ПОМЕСТИТЬ втУволенные
|ИЗ
| РегистрСведений.РаботникиОрганизаций.СрезПоследних(
| &ДатаАктуальности,
| Организация = &Организация
| И ПричинаИзмененияСостояния = &парамУвольнение) КАК РаботникиОрганизацийСрезПоследних
|
|СГРУППИРОВАТЬ ПО
| РаботникиОрганизацийСрезПоследних.Физлицо,
| РаботникиОрганизацийСрезПоследних.ПричинаИзмененияСостояния
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| втПриемы.Физлицо,
| втПриемы.ПричинаИзмененияСостояния КАК Принят,
| втУволенные.ПричинаИзмененияСостояния КАК Уволен,
| втПриемы.ПодразделениеОрганизации,
| втПриемы.Должность
|ПОМЕСТИТЬ втПредРаботники
|ИЗ
| втПриемы КАК втПриемы
| ЛЕВОЕ СОЕДИНЕНИЕ втУволенные КАК втУволенные
| ПО втПриемы.Физлицо = втУволенные.Физлицо
| И втПриемы.Период < втУволенные.Период
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| втПредРаботники.Физлицо,
| втПредРаботники.ПодразделениеОрганизации,
| втПредРаботники.Должность
|ПОМЕСТИТЬ втРаботающие
|ИЗ
| втПредРаботники КАК втПредРаботники
|ГДЕ
| втПредРаботники.Уволен ЕСТЬ NULL
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ
| КонтактнаяИнформация.Объект,
| КонтактнаяИнформация.Тип,
| КонтактнаяИнформация.Вид,
| КонтактнаяИнформация.Представление
|ПОМЕСТИТЬ втДоменныеУчетныеЗаписи
|ИЗ
| РегистрСведений.КонтактнаяИнформация КАК КонтактнаяИнформация
|ГДЕ
| КонтактнаяИнформация.Тип = &Тип
| И КонтактнаяИнформация.Вид = &Вид
|;
|
|////////////////////////////////////////////////////////////////////////////////
|ВЫБРАТЬ РАЗРЕШЕННЫЕ
| втРаботающие.Физлицо,
| втРаботающие.ПодразделениеОрганизации,
| ЕСТЬNULL(втРаботающие.Должность, """") КАК Должность,
| ЕСТЬNULL(втРаботающие.ПодразделениеОрганизации.Родитель, """") КАК ПодразделениеОрганизацииРодитель,
| ЕСТЬNULL(втДоменныеУчетныеЗаписи.Представление, """") КАК ДомменнаяУчетнаяЗапись
|ИЗ
| втРаботающие КАК втРаботающие
| ЛЕВОЕ СОЕДИНЕНИЕ втДоменныеУчетныеЗаписи КАК втДоменныеУчетныеЗаписи
| ПО втРаботающие.Физлицо = втДоменныеУчетныеЗаписи.Объект
|
|УПОРЯДОЧИТЬ ПО
| втРаботающие.Физлицо.Наименование";
Запрос.УстановитьПараметр("Организация", Справочники.Организации.НайтиПоКоду("000000001"));
Запрос.УстановитьПараметр("ДатаАктуальности", ТекущаяДата());
Запрос.УстановитьПараметр("Тип", Перечисления.ТипыКонтактнойИнформации.Другое);
Запрос.УстановитьПараметр("Вид", Справочники.ВидыКонтактнойИнформации.НайтиПоКоду("KR0000007"));
сзСостояния = Новый СписокЗначений;
сзСостояния.Добавить(Перечисления.ПричиныИзмененияСостояния.ПриемНаРаботу);
сзСостояния.Добавить(Перечисления.ПричиныИзмененияСостояния.Перемещение);
Запрос.УстановитьПараметр("сзСостояния", сзСостояния);
Запрос.УстановитьПараметр("парамУвольнение", Перечисления.ПричиныИзмененияСостояния.Увольнение);
тзРез = Запрос.Выполнить().Выгрузить();
Если тзРез.Количество()>0 тогда
МассивПользователейТип = ФабрикаXDTO.Тип("http://www.company.kz/ws/users", "UserList");
ПользовательТип = ФабрикаXDTO.Тип("http://www.company.kz/ws/users", "User");
UserList = ФабрикаXDTO.Создать(МассивПользователейТип);
Для каждого стр из тзРез Цикл
User = ФабрикаXDTO.Создать(ПользовательТип);
User.FIO = стр.ФизЛицо.Наименование;
User.unit_name = стр.ПодразделениеОрганизации.Наименование;
User.unit_id = стр.ПодразделениеОрганизации.Код;
User.upunit_name = стр.ПодразделениеОрганизацииРодитель.Наименование;
User.upunit_id = стр.ПодразделениеОрганизацииРодитель.Код;
User.user_id = стр.ФизЛицо.Код;
User.user_post = стр.Должность.Наименование;
User.dclogin = стр.ДомменнаяУчетнаяЗапись;
UserList.User.Добавить(User);
КонецЦикла;
Возврат UserList;
КонецЕсли;
УстановитьПривилегированныйРежим(Ложь);
КонецФункции
На стороне приемника (ДО) запускается внешняя обработка, которая получает данные от веб-сервиса и создает в ДО подразделения, пользователи, должности. Код обработки приведен ниже:
&НаСервере
Процедура НачатьСинхронизациюНаСервере()
//подключаемся к веб-сервису
всОпред = Новый WSОпределения(Объект.СтрокаПодключенияКВебСервису,Объект.Пользователь,Объект.Пароль,,,);
всПрокси = Новый WSПрокси(всОпред, "http://www.company.kz/ws/users", "UploadUsers", "UploadUsersSoap",,,);
всПрокси.Пользователь=Объект.Пользователь;
всПрокси.Пароль=Объект.Пароль;
//вызываем метод веб-сервиса
Значение = всПрокси.Upload();
//создаем таблицу значений, в которую выгрузим данные
ТЗПользователей = Новый ТаблицаЗначений;
ТЗПользователей.Колонки.Добавить("ФИО");
ТЗПользователей.Колонки.Добавить("ДоменнаяУчетнаяЗапись");
ТЗПользователей.Колонки.Добавить("Подразделение");
ТЗПользователей.Колонки.Добавить("ВышестоящееПодразделение");
ТЗПользователей.Колонки.Добавить("Должность");
ТЗПользователей.Колонки.Добавить("КодСотрудника");
ТЗПользователей.Колонки.Добавить("КодПодразделения");
ТЗПользователей.Колонки.Добавить("КодВышестоящееПодразделение");
Для каждого стр из Значение.User цикл
НоваяСтрока = ТЗПользователей.Добавить();
НоваяСтрока.ФИО = стр.FIO;
НоваяСтрока.ДоменнаяУчетнаяЗапись = стр.dclogin;
НоваяСтрока.Подразделение = стр.unit_name;
НоваяСтрока.ВышестоящееПодразделение = стр.upunit_name;
НоваяСтрока.Должность = стр.user_post;
НоваяСтрока.КодСотрудника = стр.user_id;
НоваяСтрока.КодПодразделения = стр.unit_id;
НоваяСтрока.КодВышестоящееПодразделение = стр.upunit_id;
КонецЦикла;
Для каждого стрТЗ из ТЗПользователей цикл
//ищем подразделение вместе с вышестоящим
ИскПодразделение = НайтиИлиСоздатьПодразделение(стрТЗ.КодПодразделения,стрТЗ.Подразделение,стрТЗ.КодВышестоящееПодразделение,стрТЗ.ВышестоящееПодразделение);
//ищем пользователя
ИскСотрудник = НайтиПользователя(стрТЗ.КодСотрудника);
Если ИскСотрудник=Неопределено тогда
ОбъектПользователь = Справочники.Пользователи.СоздатьЭлемент();
//заполняем дополнительный реквизит "КодСотрудника" кодом из источника
НовСтрока = ОбъектПользователь.ДополнительныеРеквизиты.Добавить();
НовСтрока.Свойство = ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.НайтиПоНаименованию("КодСотрудника");
НовСтрока.Значение = стрТЗ.КодСотрудника;
НовСтрока.ТекстоваяСтрока = стрТЗ.КодСотрудника;
Иначе ОбъектПользователь = ИскСотрудник.ПолучитьОбъект();
КонецЕсли;
ОбъектПользователь.Наименование = стрТЗ.ФИО;
ОбъектПользователь.Подразделение = ИскПодразделение.Ссылка;
ОбъектПользователь.КодЯзыка = "ru";
ОбъектПользователь.ПредставлениеВДокументах = стрТЗ.ФИО;
ОбъектПользователь.ПредставлениеВПереписке = стрТЗ.ФИО;
ОбъектПользователь.ПредставлениеВПерепискеСРангом = стрТЗ.ФИО;
//создаем пользователя информационной базы отправляя структуру параметров через дополнительные свойства
//процедуры сами сделают связь с элементом справочника "Пользователи" и пользователем ИБ через уникальный идентификатор
ОписаниеПользователяИБ = Новый Структура;
ОписаниеПользователяИБ.Вставить("Действие", "Записать");
ОписаниеПользователяИБ.Вставить("Имя", стрТЗ.ФИО);
ОписаниеПользователяИБ.Вставить("ПолноеИмя", стрТЗ.ФИО);
ОписаниеПользователяИБ.Вставить("АутентификацияОС", Истина);
ОписаниеПользователяИБ.Вставить("ПоказыватьВСпискеВыбора", Истина);
ОписаниеПользователяИБ.Вставить("ПользовательОС", стрТЗ.ДоменнаяУчетнаяЗапись);
ОписаниеПользователяИБ.Вставить("АутентификацияСтандартная", Ложь);
ОбъектПользователь.ДополнительныеСвойства.Вставить("ОписаниеПользователяИБ", ОписаниеПользователяИБ);
ОбъектПользователь.Записать();
//записываем доп сведения по пользователю, чтобы в карточке пользователя отображались
НаборЗаписей = РегистрыСведений.СведенияОПользователяхДокументооборот.СоздатьНаборЗаписей();
НаборЗаписей.Отбор.Пользователь.Установить(ОбъектПользователь.Ссылка);
НаборЗаписей.Прочитать();
НаборЗаписей.Записать();
Запись = НаборЗаписей.Добавить();
Запись.Пользователь = ОбъектПользователь.Ссылка;
Запись.Подразделение = ИскПодразделение.Ссылка;
Запись.Должность = ?(ПустаяСтрока(стрТЗ.Должность),"", НайтиИлиСоздатьДолжность(стрТЗ.Должность));
Запись.ГрафикРаботы = Справочники.ГрафикиРаботы.НайтиПоНаименованию("Пятидневка");
НаборЗаписей.Записать();
КонецЦикла;
КонецПроцедуры
&НаСервере
Функция НайтиИлиСоздатьДолжность(НаименованиеДолжности)
ИскДолжность = Справочники.Должности.НайтиПоНаименованию(НаименованиеДолжности, Истина);
Если ИскДолжность=Справочники.Должности.ПустаяСсылка() тогда
ДолжноситьОбъект = Справочники.Должности.СоздатьЭлемент();
ДолжноситьОбъект.Наименование = НаименованиеДолжности;
ДолжноситьОбъект.Записать();
ИскДолжносить = ДолжноситьОбъект.Ссылка;
КонецЕсли;
Возврат ИскДолжность.Ссылка;
КонецФункции
&НаСервере
Функция НайтиИлиСоздатьПодразделение(КодПодразделения,Подразделение,КодВышестоящееПодразделение,ВышестоящееПодразделение)
//сперва изем вышестоящее подразделение, если нет то создаем
Запрос = новый Запрос;
Запрос.Текст=
"ВЫБРАТЬ
| СтруктураПредприятияДополнительныеРеквизиты.Ссылка
|ИЗ
| Справочник.СтруктураПредприятия.ДополнительныеРеквизиты КАК СтруктураПредприятияДополнительныеРеквизиты
|ГДЕ
| СтруктураПредприятияДополнительныеРеквизиты.Свойство = &Свойство
| И СтруктураПредприятияДополнительныеРеквизиты.Значение = &Значение";
Запрос.УстановитьПараметр("Свойство", ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.НайтиПоНаименованию("ВнешнийКод"));
Запрос.УстановитьПараметр("Значение", КодВышестоящееПодразделение);
тзВышПод = Запрос.Выполнить().Выгрузить();
Если тзВышПод.Количество()>0 тогда
ВышПод = тзВышПод[0].Ссылка.ПолучитьОбъект();
Иначе ВышПод = Справочники.СтруктураПредприятия.СоздатьЭлемент();
ВышПод.Наименование = ВышестоящееПодразделение;
НовСтрока = ВышПод.ДополнительныеРеквизиты.Добавить();
НовСтрока.Свойство = ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.НайтиПоНаименованию("ВнешнийКод");
НовСтрока.Значение = КодВышестоящееПодразделение;
НовСтрока.ТекстоваяСтрока = КодВышестоящееПодразделение;
ВышПод.Записать();
КонецЕсли;
//теперь ищем само подразделение
Запрос = новый Запрос;
Запрос.Текст=
"ВЫБРАТЬ
| СтруктураПредприятияДополнительныеРеквизиты.Ссылка
|ИЗ
| Справочник.СтруктураПредприятия.ДополнительныеРеквизиты КАК СтруктураПредприятияДополнительныеРеквизиты
|ГДЕ
| СтруктураПредприятияДополнительныеРеквизиты.Свойство = &Свойство
| И СтруктураПредприятияДополнительныеРеквизиты.Значение = &Значение";
Запрос.УстановитьПараметр("Свойство", ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.НайтиПоНаименованию("ВнешнийКод"));
Запрос.УстановитьПараметр("Значение", КодПодразделения);
тзПод = Запрос.Выполнить().Выгрузить();
Если тзПод.Количество()>0 тогда
Под = тзПод[0].Ссылка.ПолучитьОбъект();
Иначе Под = Справочники.СтруктураПредприятия.СоздатьЭлемент();
Под.Наименование = Подразделение;
НовСтрока = Под.ДополнительныеРеквизиты.Добавить();
НовСтрока.Свойство = ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.НайтиПоНаименованию("ВнешнийКод");
НовСтрока.Значение = КодПодразделения;
НовСтрока.ТекстоваяСтрока = КодПодразделения;
Под.Записать();
КонецЕсли;
Под.Родитель = ВышПод.Ссылка;
Под.Записать();
Возврат Под.Ссылка;
КонецФункции
&НаСервере
Функция НайтиПользователя(КодСотрудника)
ИскПользователь = Неопределено;
Запрос = Новый Запрос;
Запрос.Текст=
"ВЫБРАТЬ
| ПользователиДополнительныеРеквизиты.Ссылка
|ИЗ
| Справочник.Пользователи.ДополнительныеРеквизиты КАК ПользователиДополнительныеРеквизиты
|ГДЕ
| ПользователиДополнительныеРеквизиты.Свойство = &Свойство
| И ПользователиДополнительныеРеквизиты.Значение = &Значение";
Запрос.УстановитьПараметр("Свойство",ПланыВидовХарактеристик.ДополнительныеРеквизитыИСведения.НайтиПоНаименованию("КодСотрудника"));
Запрос.УстановитьПараметр("Значение",КодСотрудника);
тзРез = Запрос.Выполнить().Выгрузить();
Если тзРез.Количество()>0 тогда
ИскПользователь = тзРез[0].Ссылка;
КонецЕсли;
Возврат ИскПользователь;
КонецФункции
&НаКлиенте
Процедура НачатьСинхронизацию(Команда)
НачатьСинхронизациюНаСервере();
КонецПроцедуры
Можете скачать архив со схемой XDTO-пакета и обработкой "Синхронизация пользователей".
В итоге получаем выстроенную структуру предприятия, пользователей и авторизацию через ОС. Затем, опубликовав базу Документооборот на веб-сервере, получаем работающую систему ДО.