Задача: реализовать метод API для создания элемента приложения "Входящее письмо" в ELMA365 (например, из 1С) с заполнением контекстных переменных типа Приложение и переменной типа "Файлы"-Несколько.
Вводные данные:
Контекст приложения "Входящие письма":
- Отправитель (sender) тип Приложение - "Контрагенты" - Один. Контрагенты - приложение в этом же разделе.
- Подписал (signatory) тип Приложение - "Контактные лица" - Один. Контактные лица - приложение в этом же разделе.
- Проект (project) тип Приложение - "Проекты" - Один. Проекты - приложение в этом же разделе.
- Ответственный (assignee) тип Пользователи-Один.
- Файлы (files) тип Файлы-Несколько.
Условия:
- Из сторонней системы передаётся массив файлов с двумя параметрами:
- название файла,
- содержимое файла в формате base64
Если массив не пустой, письмо создаётся с файлами.
- Для заполнения проекта в body передаётся строка "projectCode". По этому значению выполняется поиск Проекта по совпадению с переменной "kod1C" типа Строка. Если Проект не найден, письмо создаётся без проекта.
- Для заполнения Ответственного в body передаётся строка "assigneeFIO". По этому значению выполняется поиск Пользователя по совпадению с "__name". Если пользователь не найден, письмо создаётся без ответственного.
- Для заполнения Контрагента в body передаются строки name, fullname, inn, kod1C. По значению "inn" выполняется поиск контрагента. Если Контрагент не найден, создаётся новый Контрагент.
- Для заполнения Контактного лица в body передаются строки fio, position . По значению "fio" выполняется поиск Контактного лица по совпадению с "__name". Если Контактное лицо не найдено, создаётся новое.
Реализация:
Создаём свой модуль в разделе Администрирование-Модули.
В настройки модуля добавляем все приложения, которые нам понадобятся для создания Входящего письма:
Создаём метод API "incoming_letter_create" тип POST:
В методах API на вкладке Сценарии появится наш метод async function incoming_letter_create(req: FetchRequest): Promise<HttpResponse | void> {}
Перед его реализацией добавим метод конвертации строки base64 в тип ArrayBuffer:
Код:
//функция конвертации строки base64 в тип ArrayBuffer
function base64ab(base64: string): ArrayBuffer {
const binary_string = atob(base64);
const len = binary_string.length;
const bytes = new Uint8Array(len);
for (var i = 0; i < len; i++) { bytes[i] = binary_string.charCodeAt(i); }
return bytes.buffer;
}
Затем реализуем наш метод API incoming_letter_create . Весь код сценариев API модуля:
Код:
//функция конвертации строки base64 в тип ArrayBuffer
function base64ab(base64: string): ArrayBuffer {
const binary_string = atob(base64);
const len = binary_string.length;
const bytes = new Uint8Array(len);
for (var i = 0; i < len; i++) { bytes[i] = binary_string.charCodeAt(i); }
return bytes.buffer;
}
async function incoming_letter_create(req: FetchRequest): Promise<HttpResponse | void> {
const response = new HttpResponse()
const request = JSON.parse(req.body! as string)//получаем body
const letterName = request['name']
const assigneeFIO = request['assigneeFIO']
const projectCode = request['projectCode']
const contractorName = request['contractor']['name']
const contractorFullname = request['contractor']['fullname']
const contractorINN = request['contractor']['inn']
const contractorKod1C = request['contractor']['kod1C']
const cotactFIO = request['contact']['fio']
const cotactPosition = request['contact']['position']
const description = request['description']
const filesData = request['files']
let project = await Namespace.params.fields.project1c.app.search().where((f, g) => g.and(f.kod1C.eq(projectCode), f.__deletedAt.eq(null))).first()//ищем проект по полю kod1C
let assignee = await System.users.search().where((f, g) => g.and(f.__name.like(assigneeFIO), f.__deletedAt.eq(null))).first()//ищем Пользователя по ФИО
let contractor = await Namespace.params.fields.contractors.app.search().where((f, g) => g.and(f.inn.eq(contractorINN), f.__deletedAt.eq(null))).first()//ищем контрагента по ИНН
if (!contractor) {//если не нашли, создаём контрагента
contractor = Namespace.params.fields.contractors.app.create()
contractor.data.__name = contractorName
contractor.data.fullname = contractorFullname
contractor.data.inn = contractorINN
contractor.data.kod1c = contractorKod1C
await contractor.save()
}
let contact = await Namespace.params.fields.contacts.app.search().where((f, g) => g.and(f.__name.like(cotactFIO), f.__deletedAt.eq(null))).first()//ищем Контактное лицо по ФИО
if (!contact) {//если не нашли, создаём контакт
contact = Namespace.params.fields.contacts.app.create()
contact.data.__name = cotactFIO
contact.data.position = cotactPosition
contact.data.contractors = contractor
await contact.save()
}
let newIncomingletter = Namespace.params.fields.incoming_letter.app.create() //создаём входящее письмо
newIncomingletter.data.__name = letterName;//Тема
newIncomingletter.data.description = description;//описание
newIncomingletter.data.sender = contractor;//Отправитель
newIncomingletter.data.signatory = contact;//Подписал
if (project) {
newIncomingletter.data.project = project//проект
}
if (assignee) {
newIncomingletter.data.assignee = assignee//Ответственный
}
if (filesData)//если указан массив файлов
{
const filesArray: FileItem[] = []
for (let i in filesData) {//массив данных файлов
if (i) {
let fileName = filesData[i].fileName as string; //получаем название файла
let content = filesData[i].base64 as string;//получаем контент в base64
if (content) {
let abContent = base64ab(content)//вызываем метод конвертации base64 в ArrayBuffer
if (fileName && abContent) {
let file = await Namespace.params.fields.file.create(fileName, abContent)//создаём файл
filesArray.push(file)
}
}
}
}
newIncomingletter.data.files = filesArray;//заполняем переменную Файлы
}
await newIncomingletter.save()//сохраняем письмо
try {
const letterId = newIncomingletter.data.__id//получаем id созданного письма и возвращаем его в ответе сервера
response
.status(200)
.json({
msg: 'success',
letterId: letterId,
})
.set('Content-Type', 'application/json')
}
catch (e) {
response
.status(500)
.json({
msg: 'error: ' + e.message,
})
.set('Content-Type', 'application/json')
}
return response
}
Для использования метода нужно корректно заполнить body. Пример body можно посмотреть во вложениях к статье.