Всем доброго времени суток.
Подскажите пожалуйста как организовать импорт данных в 1с из фавйла csv.
Или направьте куда почитать.
Дальше я что-то туплю, не могу сдвинуться с мертвой точки.
Подскажите пожалуйста как организовать импорт данных в 1с из фавйла csv.
Или направьте куда почитать.
Процедура ПрайсИзcsv()
Перем ИмяПути,ИмяФайла;
ИмяФайла = "1";
ИмяПути="C:\";
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv",,) = 1 Тогда
ТекстДок = СоздатьОбъект("Текст");
КонецЕсли;
Дальше я что-то туплю, не могу сдвинуться с мертвой точки.
По теме из базы знаний
- Загрузка номенклатуры в справочник и документ из файла Excel и CSV, обновление цен и реквизитов (адаптируется под разные конфигурации 1С: 7.7)
- CSV парсинг на 1С8, допускающий включение кавычек и символа переноса строки в полях
- Экспорт документа "Ведомости на счета" из 1С в формат CSV файла/Импорт из CSV РайффайзенБанка. ЗУП 3.1
- Импортозамещение BI. Встраивание 1С:Аналитики в аналитический ландшафт компании
- Чтение csv файлов
Ответы
Подписаться на ответы
Инфостарт бот
Сортировка:
Древо развёрнутое
Свернуть все
Ну, если в память влезет, то ТекстДок.Открыть(ИмяПути + ИмяФайла);
А затем пройтись по строкам: Для НомСтроки = 1 По ТекстДок.КоличествоСтрок() Цикл Стр = ТекстДок.ПолучитьСтроку(НомСтроки); КонецЦикла;
А потом разобрать строку на составляющие и т.д.
А затем пройтись по строкам: Для НомСтроки = 1 По ТекстДок.КоличествоСтрок() Цикл Стр = ТекстДок.ПолучитьСтроку(НомСтроки); КонецЦикла;
А потом разобрать строку на составляющие и т.д.
Функция РазобратьСтроку(Стр)
СтрРазб = Стр;
Рзд = " ";
Сп = СоздатьОбъект("СписокЗначений");
Если Лев(СтрРазб,1) = Рзд Тогда
СтрРазб = Сред(СтрРазб, 2);
КонецЕсли;
Инд = Найти(СтрРазб, Рзд);
Пока Инд <> 0 Цикл
ТекСтр = Сред(СтрРазб, 1, Инд - 1);
Сп.ДобавитьЗначение(СокрЛП(ТекСтр));
СтрРазб = Сред(СтрРазб, Инд + 1);
Инд = Найти(СтрРазб, Рзд);
КонецЦикла;
для н = 1 по сп.размерсписка() Цикл
Сообщить(сп.получитьзначение(н));
КонецЦикла;
Возврат Сп;
КонецФункции
Процедура ПрайсИзcsv()
Перем ИмяПути,ИмяФайла;
ИмяФайла = "";
ИмяПути="";
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv",,) = 1 Тогда
ТекстДок = СоздатьОбъект("Текст");
КонецЕсли;
ТекстДок.Открыть(ИмяПути + ИмяФайла);
НомерИмпортированнойСтроки = 0;
Для НомСтроки = 1 По ТекстДок.КоличествоСтрок() Цикл
таб.новаястрока();
Стр = ТекстДок.ПолучитьСтроку(НомСтроки);
СЗ = РазобратьСтроку(Стр);
ТекСтрока = ТекстДок.ПолучитьСтроку(НомСтроки);
Спис = СоздатьОбъект("СписокЗначений");
Спис = РазобратьСтроку(ТекСтрока);
ЛеваяСтрока="";
//получаем данные...
Код = СокрЛП(Спис.ПолучитьЗначение(1,ЛеваяСтрока)); //число - это номер колонки в текстовом файле
Модель = СокрЛП(Спис.ПолучитьЗначение(2,ЛеваяСтрока));
Наименование = СокрЛП(Спис.ПолучитьЗначение(3,ЛеваяСтрока));
ТорговаяМарка = СокрЛП(Спис.ПолучитьЗначение(4,ЛеваяСтрока));
Сертификат3 = СокрЛП(Спис.ПолучитьЗначение(5,ЛеваяСтрока));
Кодф = СокрЛП(Спис.ПолучитьЗначение(6,ЛеваяСтрока));
Род = СокрЛП(Спис.ПолучитьЗначение(7,ЛеваяСтрока));
КолЕдиниц = СокрЛП(Спис.ПолучитьЗначение(8,ЛеваяСтрока));
РозничнаяЦена = Число(СокрЛП(Спис.ПолучитьЗначение(9,ЛеваяСтрока)));
Куренси1 = Число(СокрЛП(Спис.ПолучитьЗначение(10,ЛеваяСтрока)));
Валюта = СокрЛП(Спис.ПолучитьЗначение(11,ЛеваяСтрока));
КонецЦикла;
КонецПроцедуры
ПоказатьТак вот получилось, все работает.
А вот подскажите пожалуйста как мне так сделать что бы мне не только определенный csv который я сейчас делаю раскладывало, а так что бы любой csv беру и мне в таблицу его содержание выдает.
я так понимаю надо что-то типо функции разбиения столбцов и функцию заполнения таблицы по столбцам и строкам.
или универсальной такой разборки не сделать?
Нужно для функции разбиения определить параметр - символ разделителя, чтобы было более универсально... и достаточно, если не хочешь попробовать другие способы (см. в синтакс-помошнике: СтрЗаменить и ИзСтрокиСРазделителями).
В процедурке ПрайсИзcsv кусок кода:
переделать на:
А то не красиво получается.
В процедурке ПрайсИзcsv кусок кода:
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv",,) = 1 Тогда
ТекстДок = СоздатьОбъект("Текст");
КонецЕсли;
переделать на:
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv",,) <> 1 Тогда
Возврат;
КонецЕсли;
ТекстДок = СоздатьОбъект("Текст");
А то не красиво получается.
Вот что получилось, может будут ещё какие-то дополнения к коду.
Заранее спасибо
Заранее спасибо
Функция РазобратьСтроку(Стр) //Отделяет в строке столбцы
СтрРазб = Стр;
Рзд = " ";
Сп = СоздатьОбъект("СписокЗначений");
Если Лев(СтрРазб,1) = Рзд Тогда
СтрРазб = Сред(СтрРазб, 2);
КонецЕсли;
Инд = Найти(СтрРазб, Рзд);
Пока Инд <> 0 Цикл
ТекСтр = Сред(СтрРазб, 1, Инд - 1);
Сп.ДобавитьЗначение(СокрЛП(ТекСтр));
СтрРазб = Сред(СтрРазб, Инд + 1);
Инд = Найти(СтрРазб, Рзд);
КонецЦикла;
Возврат Сп;
КонецФункции
Процедура ПрайсИзcsv() //получает из *.csv или *.txt данные и раскладывает их
Перем ИмяПути,ИмяФайла;
ИмяФайла = "";
ИмяПути="";
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv",,) <> 1 Тогда
Возврат;
КонецЕсли;
ТекстДок = СоздатьОбъект("Текст");
ТекстДок.Открыть(ИмяПути + ИмяФайла);
НомерИмпортированнойСтроки = 0;
// ТЗ=СоздатьОбъект("ТаблицаЗначений");
Для НомСтроки = 1 По 1 Цикл //заполняет заголовки в таблице
Стр = ТекстДок.ПолучитьСтроку(НомСтроки);
СЗ = РазобратьСтроку(Стр);
ТекСтрока = ТекстДок.ПолучитьСтроку(НомСтроки);
Спис = СоздатьОбъект("СписокЗначений");
Спис = РазобратьСтроку(ТекСтрока);
ЛеваяСтрока="";
Для н = 1 по спис.размерсписка() Цикл
Тз.новаяколонка(СокрЛП(Спис.ПолучитьЗначение(н,ЛеваяСтрока)),,,СокрЛП(Спис.ПолучитьЗначение(н,ЛеваяСтрока)));
КонецЦикла;
КонецЦикла;
Для НомСтроки = 2 По ТекстДок.КоличествоСтрок() Цикл //pfgjkyztn nf,kbwe
Стр = ТекстДок.ПолучитьСтроку(НомСтроки);
СЗ = РазобратьСтроку(Стр);
ТекСтрока = ТекстДок.ПолучитьСтроку(НомСтроки);
Спис = СоздатьОбъект("СписокЗначений");
Спис = РазобратьСтроку(ТекСтрока);
ЛеваяСтрока="";
//получаем данные
Код = СокрЛП(Спис.ПолучитьЗначение(1,ЛеваяСтрока)); //число - это номер колонки в текстовом файле
Модель = СокрЛП(Спис.ПолучитьЗначение(2,ЛеваяСтрока));
Наименование = СокрЛП(Спис.ПолучитьЗначение(3,ЛеваяСтрока));
ТорговаяМарка = СокрЛП(Спис.ПолучитьЗначение(4,ЛеваяСтрока));
РегистрацНомер = СокрЛП(Спис.ПолучитьЗначение(5,ЛеваяСтрока));
ВнутКод = СокрЛП(Спис.ПолучитьЗначение(6,ЛеваяСтрока));
Род = СокрЛП(Спис.ПолучитьЗначение(7,ЛеваяСтрока));
КолЕдиниц = СокрЛП(Спис.ПолучитьЗначение(8,ЛеваяСтрока));
РозничнаяЦена = СокрЛП(Спис.ПолучитьЗначение(9,ЛеваяСтрока));
Куренси1 = СокрЛП(Спис.ПолучитьЗначение(10,ЛеваяСтрока));
Цена2 = СокрЛП(Спис.ПолучитьЗначение(11,ЛеваяСтрока));
Валюта2 = СокрЛП(Спис.ПолучитьЗначение(12,ЛеваяСтрока));
ТЗ.КоличествоКолонок(Макс(ТЗ.КоличествоКолонок(),Спис.РазмерСписка()));
НС=ТЗ.НоваяСтрока();
ТЗ.Заполнить(Спис,НС,НС);
КонецЦикла;
КонецПроцедуры
Показать
Вот обновленный код, значительно уменьшился)
Функция РазобратьСтроку(Стр) //Отделяет в строке столбцы
СтрРазб = Стр;
Рзд = " ";
Сп = СоздатьОбъект("СписокЗначений");
Если Лев(СтрРазб,1) = Рзд Тогда
СтрРазб = Сред(СтрРазб, 2);
КонецЕсли;
Инд = Найти(СтрРазб, Рзд);
Пока Инд <> 0 Цикл
ТекСтр = Сред(СтрРазб, 1, Инд - 1);
Сп.ДобавитьЗначение(СокрЛП(ТекСтр));
СтрРазб = Сред(СтрРазб, Инд + 1);
Инд = Найти(СтрРазб, Рзд);
КонецЦикла;
Возврат Сп;
КонецФункции
Процедура ПрайсИзcsv() //получает из *.csv или *.txt данные и раскладывает их
Перем ИмяПути,ИмяФайла;
ИмяФайла = "";
ИмяПути="";
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv",,) <> 1 Тогда
Возврат;
КонецЕсли;
ТекстДок = СоздатьОбъект("Текст");
ТекстДок.Открыть(ИмяПути + ИмяФайла);
НомерИмпортированнойСтроки = 0;
// ТЗ=СоздатьОбъект("ТаблицаЗначений");
Для НомСтроки = 1 По 1 Цикл //заполняет заголовки в таблице
Стр = ТекстДок.ПолучитьСтроку(НомСтроки);
СЗ = РазобратьСтроку(Стр);
ТекСтрока = ТекстДок.ПолучитьСтроку(НомСтроки);
Спис = СоздатьОбъект("СписокЗначений");
Спис = РазобратьСтроку(ТекСтрока);
ЛеваяСтрока="";
Для н = 1 по спис.размерсписка() Цикл
Тз.новаяколонка(СокрЛП(Спис.ПолучитьЗначение(н,ЛеваяСтрока)),,,СокрЛП(Спис.ПолучитьЗначение(н,ЛеваяСтрока)));
КонецЦикла;
КонецЦикла;
Для НомСтроки = 2 По ТекстДок.КоличествоСтрок() Цикл //заполняем таблицу значениями
Стр = ТекстДок.ПолучитьСтроку(НомСтроки);
СЗ = РазобратьСтроку(Стр);
ТекСтрока = ТекстДок.ПолучитьСтроку(НомСтроки);
Спис = СоздатьОбъект("СписокЗначений");
Спис = РазобратьСтроку(ТекСтрока);
//получаем данные
ТЗ.КоличествоКолонок(Макс(ТЗ.КоличествоКолонок(),Спис.РазмерСписка()));
НС=ТЗ.НоваяСтрока();
ТЗ.Заполнить(Спис,НС,НС);
КонецЦикла;
КонецПроцедуры
Показать
Спис = СоздатьОбъект("СписокЗначений");
Поставь перед циклом. Будет значительно быстрее. Если строк мало - то это незаметно, а вот если много...
Вообще старайся СоздатьОбъект() в циклы не ставить. Лучше один раз создай, а потом если необходимо просто очищай.
ЗЫ: В данном коде Спис = СоздатьОбъект("СписокЗначений"); вообще не нужно. У тебя и так функция РазобратьСтроку возвращает СписокЗначений
Поставь перед циклом. Будет значительно быстрее. Если строк мало - то это незаметно, а вот если много...
Вообще старайся СоздатьОбъект() в циклы не ставить. Лучше один раз создай, а потом если необходимо просто очищай.
ЗЫ: В данном коде Спис = СоздатьОбъект("СписокЗначений"); вообще не нужно. У тебя и так функция РазобратьСтроку возвращает СписокЗначений
А зачем все так сложно?
Берем 1С++
и все
Берем 1С++
и все
ЗагрузитьВнешнююКомпоненту("1cpp.dll");
ИмяФайла = "";
ИмяПути="";
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv",,) <> 1 Тогда
Возврат;
КонецЕсли;
ИТЗ=СоздатьОбъект("ИндексированнаяТаблица");
ИТЗ.ИзФайла(ИмяПути + ИмяФайла);
ИТЗ.ВыбратьСТроки();
ПОка ИТЗ.ПОлучитьСтроку()=1 Цикл
.. тута работаем с полями таблицы
КонецЦикла;
Показать
Правда, для 8.2)
Текст = Новый ЧтениеТекста(ПутьКФайлуЗагрузки);
ТЗ = Новый ТаблицаЗначений;
ПерваяСтрока = Истина;
Стр = Текст.ПрочитатьСтроку();
Пока Стр <> Неопределено Цикл // строки читаются до символа перевода строки
мсвСтрока = ОбщегоНазначения.РазложитьСтрокуВМассивПодстрок(Стр, ";");
Если ПерваяСтрока Тогда
Для каждого КолонкаМСВ Из мсвСтрока Цикл
ИмяКолонки = КолонкаМСВ;
ИмяКолонки = СтрЗаменить(ИмяКолонки, Символ(32), "");
ИмяКолонки = СтрЗаменить(ИмяКолонки, "(", "");
ИмяКолонки = СтрЗаменить(ИмяКолонки, ")", "");
КолонкаТЗ = ТЗ.Колонки.Добавить(ИмяКолонки);
КонецЦикла;
ПерваяСтрока = Ложь;
Иначе
строкаТЗ = ТЗ.Добавить();
ИндексКолонки = 0;
Для каждого Колонка Из ТЗ.Колонки Цикл
строкаТЗ[Колонка.Имя] = мсвСтрока[ИндексКолонки];
ИндексКолонки = ИндексКолонки + 1;
КонецЦикла;
КонецЕсли;
Стр = Текст.ПрочитатьСтроку();
КонецЦикла;
Показать
Универсальная загрузка/импорт из *.csv без 1с++
в таблицу значений с названиями колонок из файла.
тз.ВыбратьСтроку() можно удалить либо закомментировать (добавил для проверки результатов импорта).
в таблицу значений с названиями колонок из файла.
тз.ВыбратьСтроку() можно удалить либо закомментировать (добавил для проверки результатов импорта).
Перем сп;
Функция РазобратьСтроку(Стр)
Стр = СтрЗаменить(Стр,";""",";");
Стр = СтрЗаменить(Стр,""";",";");
Стр = """"+СтрЗаменить(Стр,";",""",""");
сп.УдалитьВсе();
сп.ИзСтрокиСРазделителями(Стр);
Возврат Сп;
КонецФункции
Процедура Сформировать()
Перем ИмяПути,ИмяФайла;
ИмяФайла = "";
ИмяПути="";
сп = СоздатьОбъект("СписокЗначений");
тз = СоздатьОбъект("ТаблицаЗначений");
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv|*.csv",,) <> 1 Тогда
Возврат;
КонецЕсли;
Т = СоздатьОбъект("Текст");
Т.Открыть(ИмяПути + ИмяФайла);
Для К = 1 По Т.КоличествоСтрок() Цикл
Если К > Т.КоличествоСтрок() Тогда Прервать; КонецЕсли;
Стр = Т.ПолучитьСтроку(К);
Если ПустоеЗначение(Стр) = 1 Тогда Продолжить; КонецЕсли;
сп = РазобратьСтроку(Стр);
Если К = 1 Тогда
//Создадим колонки
Для М=1 По сп.РазмерСписка() Цикл
тз.НоваяКолонка(сп.ПолучитьЗначение(М));
КонецЦикла;
Иначе
//Заполним таблицу
тз.НоваяСтрока();
Для М=1 По тз.КоличествоКолонок() Цикл
тз.УстановитьЗначение(тз.НомерСтроки,М,сп.ПолучитьЗначение(М));
КонецЦикла;
КонецЕсли;
КонецЦикла;
тз.ВыбратьСтроку();
//ДАЛЕЕ ОБРАБАТЫВАЕМ ТАБЛИЦУ ПО СВОЕМУ УСМОРТЕНИЮ
КонецПроцедуры
Показать
(17)
код совсем не рабочий, это для какой конфигурации?
Перем ИмяПути,ИмяФайла;
ИмяФайла = "";
ИмяПути="";
сп = СоздатьОбъект("СписокЗначений");
тз = СоздатьОбъект("ТаблицаЗначений");
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv|*.csv",,) <> 1 Тогда
Возврат;
КонецЕсли;
Т = СоздатьОбъект("Текст");
Т.Открыть(ИмяПути + ИмяФайла);
Для К = 1 По Т.КоличествоСтрок() Цикл
Если К > Т.КоличествоСтрок() Тогда Прервать; КонецЕсли;
Стр = Т.ПолучитьСтроку(К);
Если ПустоеЗначение(Стр) = 1 Тогда Продолжить; КонецЕсли;
сп = РазобратьСтроку(Стр);
Если К = 1 Тогда
//Создадим колонки
Для М=1 По сп.РазмерСписка() Цикл
тз.НоваяКолонка(сп.ПолучитьЗначение(М));
КонецЦикла;
Иначе
//Заполним таблицу
тз.НоваяСтрока();
Для М=1 По тз.КоличествоКолонок() Цикл
тз.УстановитьЗначение(тз.НомерСтроки,М,сп.ПолучитьЗначение(М));
КонецЦикла;
КонецЕсли;
КонецЦикла;
тз.ВыбратьСтроку();
//ДАЛЕЕ ОБРАБАТЫВАЕМ ТАБЛИЦУ ПО СВОЕМУ УСМОРТЕНИЮ
ПоказатьИмяФайла = "";
ИмяПути="";
сп = СоздатьОбъект("СписокЗначений");
тз = СоздатьОбъект("ТаблицаЗначений");
Если ФС.ВыбратьФайл(0,ИмяФайла, ИмяПути, "Открыть файл","*.csv|*.csv",,) <> 1 Тогда
Возврат;
КонецЕсли;
Т = СоздатьОбъект("Текст");
Т.Открыть(ИмяПути + ИмяФайла);
Для К = 1 По Т.КоличествоСтрок() Цикл
Если К > Т.КоличествоСтрок() Тогда Прервать; КонецЕсли;
Стр = Т.ПолучитьСтроку(К);
Если ПустоеЗначение(Стр) = 1 Тогда Продолжить; КонецЕсли;
сп = РазобратьСтроку(Стр);
Если К = 1 Тогда
//Создадим колонки
Для М=1 По сп.РазмерСписка() Цикл
тз.НоваяКолонка(сп.ПолучитьЗначение(М));
КонецЦикла;
Иначе
//Заполним таблицу
тз.НоваяСтрока();
Для М=1 По тз.КоличествоКолонок() Цикл
тз.УстановитьЗначение(тз.НомерСтроки,М,сп.ПолучитьЗначение(М));
КонецЦикла;
КонецЕсли;
КонецЦикла;
тз.ВыбратьСтроку();
//ДАЛЕЕ ОБРАБАТЫВАЕМ ТАБЛИЦУ ПО СВОЕМУ УСМОРТЕНИЮ
код совсем не рабочий, это для какой конфигурации?
Совсем не рабочий - это как вы решили? Если не умеет использовать, то дело не в коде.
Используйте универсальную загрузку:из этой статьи
Используйте универсальную загрузку:
Весь импорт через кнопку, с выбором файла
&НаСервере
Процедура ИмпортНаСервере(Результат,ДопПараметр) Экспорт
Если (Результат = Неопределено) Тогда
Иначе
ТекстДок=Новый ТекстовыйДокумент;
ТекстДок.Прочитать(Результат[0]);
Для Строка = 2 по ТекстДок.КоличествоСтрок() цикл
Текстрок=ТекстДок.ПолучитьСтроку(Строка);
СтрРазд = СтрРазделить(ТекСтрок, ";", Ложь);
Тип = Справочники.[НазваниеСправочника].СоздатьЭлемент();
Тип.Код = СтрРазд[0];
Тип.Наименование = СтрРазд[1];
Тип.Записать();
КонецЦикла;
Сообщить("Успешный импорт");
КонецЕсли;
КонецПроцедуры
&НаКлиенте
Процедура Импорт(Команда)
ОкноВыбора = новый ДиалогВыбораФайла(РежимДиалогаВыбораФайла.Открытие);
ОкноВыбора.Показать(Новый ОписаниеОповещения("ИмпортНаСервере",ЭтотОбъект));
КонецПроцедуры
Показать
Вариант кода для импорта данных из csv файла. Также через кнопку
&НаКлиенте
Процедура ИмпортДанных(Команда)
Диалог = Новый ДиалогВыбораФайла(РежимДиалогаВыбораФайла.Открытие);
Диалог.Заголовок = "Выберите файл csv";
Диалог.Фильтр = "Документ csv | *.csv";
Если Диалог.Выбрать() Тогда
ПрочитанныйФайл = Новый ТекстовыйДокумент;
ПрочитанныйФайл.Прочитать(Диалог.ПолноеИмяФайла);
ИмпортДанныхНаСервере(ПрочитанныйФайл);
Иначе
ПоказатьЗначение(, "Файл не выбран");
КонецЕсли
КонецПроцедуры
&НаСервере
Процедура ИмпортДанныхНаСервере(ПрочитанныйФайл)
Разделитель = ";";
Для НомерСтроки = 1 по ПрочитанныйФайл.КоличествоСтрок() Цикл
Строка = ПрочитанныйФайл.ПолучитьСтроку(НомерСтроки);
МассКол = СтрРазделить(Строка,Разделитель);
Элемент = Справочники.Сотрудники.СоздатьЭлемент();
Элемент.Наименование = МассКол[0];
Элемент.Записать();
КонецЦикла;
Сообщить("импорт завершен");
КонецПроцедуры
Показать
если сущности в erd диаграмме:
Объекты, Клиенты, Договора, Сотрудники, Выезд, Акты, Подключение к сигнализации, Отчисления, Город, Вид клиента и др
то диаграмма прецедентов:
Заключить договор охраны, Оформить подключение к сигнализации, Оформить факт срабатывания сигнализации, Оформить акт осмотра объекта, Отправить отчисления, Сформировать отчет.
Актеры: Сотрудники и клиенты
Объекты, Клиенты, Договора, Сотрудники, Выезд, Акты, Подключение к сигнализации, Отчисления, Город, Вид клиента и др
то диаграмма прецедентов:
Заключить договор охраны, Оформить подключение к сигнализации, Оформить факт срабатывания сигнализации, Оформить акт осмотра объекта, Отправить отчисления, Сформировать отчет.
Актеры: Сотрудники и клиенты
Для получения уведомлений об ответах подключите телеграм бот:
Инфостарт бот