gifts2017

Хранение и повторное использование текстов запросов.

Опубликовал Сергей Водаков (WaterSmith) в раздел Программирование - Практика программирования

В статье описан подход к хранению текстов запросов в конфигурации, с использованием макетов.
Основной целью описанного подхода является наведение порядка в конфигурации и обеспечение возможности простого повторного использования текстов запросов.

С появлением 1С версии 8.0, язык запросов получил закономерное развитие. Как известно, разработчики платформы ушли с пути “изобретения велосипеда”, и отказались от собственного механизма запросов с уникальным синтаксисом. Теперь язык запросов в 1С является, по сути, русским (ладно, билингвальным) диалектом SQL. А фирма 1С всячески рекомендует использовать запросы практически для любого извлечения данных.

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

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

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

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

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

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

Еще один способ, который имеет право на жизнь - создать обработку, выполняющую роль “библиотеки запросов”, и хранить общие запросы в ее макетах. Таких обработок может быть несколько, для лучшей организации и группировки текстов запросов. Также можно комбинировать: общий макет с общими для конфигурации запросами и, отдельно - обработки с запросами, относящимися к определенным подсистемам.

Далее, когда вам нужно выполнить какой-либо запрос, вы просто извлекаете текст нужного запроса конструкцией:

- для случая, когда запрос в макете объекта:

мОбъектЗапроса.Текст = ЭтотОбъект.ПолучитьМакет("ЗапросТаблицаСписокДатПериода").ПолучитьТекст();

- для случая, когда запрос в общем макете конфигурации:

мОбъектЗапроса.Текст = ПолучитьОбщийМакет("ЗапросТаблицаСписокДатПериода").ПолучитьТекст();

- для случая, когда запрос в макете специальной обработки:

мОбъектЗапроса.Текст = Обработки.ЗапросыПодсистемыСклад.ПолучитьМакет("ЗапросВыборкаОстаткиНоменклатуры").ПолучитьТекст();

Если вам нужно построить пакетный запрос, вы просто склеиваете его из разных макетов:

мОбъектЗапроса.Текст = мОбъектЗапроса.Текст +

ЭтотОбъект.ПолучитьМакет("ЗапросВыборкаОстаткиСырьяИГотовойПродукцииНаНачалоПериода").ПолучитьТекст();

Ну, думаю, идея понятна. Хотелось бы немного остановиться на присвоении имен макетам с запросами. Естественно, имена могут быть любыми, и если вы потомок Штирлица, или сотрудник КГБ, вы можете использовать имена типа “З1”, “З2” - смотрите как интересно, русская обфускация - бессмысленная и беспощадная - в действии! Враг точно будет в шоке. Но, для лучшего восприятия кода, я использую такую схему имени:

  1. Слово “Запрос - все макеты, содержащие тексты запросов, начинаются со слова “Запрос”, чтобы можно было отличить их от других макетов.

  2. Таблица” или “Выборка - после слова “Запрос” следует слово “Таблица” или “Выборка”. Слово “Таблица” означает, что запрос содержит команду “Поместить” и возвращает временную таблицу, “Выборка” - соответственно означает, что результат запроса нужно обрабатывать как обычно.

  3. ИмяВременнойТаблицы или Краткое описание выборки - Заканчивается имя макета именем временной таблицы, или кратким описанием содержимого выборки.

 Таким образом, имя макета приобретает, например, вид: "ЗапросТаблицаСписокДатПериода"; встретив его в коде, или увидев в дереве метаданных, мы поймем, что в этом макете содержится текст запроса, результат выполнения которого будет помещен во временную таблицу с именем “СписокДатПериода”.

Открыв этот макет на просмотр, мы увидим:

//Тип запроса: Самостоятельный универсальный

//Требования : Передача параметров ДатаНачалаПериода (Тип "Дата") и ДатаОкончанияПериода (Тип "Дата")

//Результат : Временные таблицы "СписокДатПериода" и "Цифры"

 

ВЫБРАТЬ 0 КАК Цифра ПОМЕСТИТЬ Цифры ОБЪЕДИНИТЬ

ВЫБРАТЬ 1 ОБЪЕДИНИТЬ

ВЫБРАТЬ 2 ОБЪЕДИНИТЬ

ВЫБРАТЬ 3 ОБЪЕДИНИТЬ

ВЫБРАТЬ 4 ОБЪЕДИНИТЬ

ВЫБРАТЬ 5 ОБЪЕДИНИТЬ

ВЫБРАТЬ 6 ОБЪЕДИНИТЬ

ВЫБРАТЬ 7 ОБЪЕДИНИТЬ

ВЫБРАТЬ 8 ОБЪЕДИНИТЬ

ВЫБРАТЬ 9;

 

////////////////////////////////////////////////////////////////////////////////

ВЫБРАТЬ

ДОБАВИТЬКДАТЕ(&ДатаНачалаПериода, ДЕНЬ, СписокДней.Дней) КАК Период

ПОМЕСТИТЬ СписокДатПериода

ИЗ

(ВЫБРАТЬ

СотниТысяч.Цифра * 100000 + ДесяткиТысяч.Цифра * 10000 + Тысячи.Цифра * 1000 + Сотни.Цифра * 100 +

Десятки.Цифра * 10 + Единицы.Цифра КАК Дней

ИЗ

Цифры КАК СотниТысяч

ВНУТРЕННЕЕ СОЕДИНЕНИЕ Цифры КАК ДесяткиТысяч

ВНУТРЕННЕЕ СОЕДИНЕНИЕ Цифры КАК Тысячи

ВНУТРЕННЕЕ СОЕДИНЕНИЕ Цифры КАК Сотни

ВНУТРЕННЕЕ СОЕДИНЕНИЕ Цифры КАК Десятки

ВНУТРЕННЕЕ СОЕДИНЕНИЕ Цифры КАК Единицы

ПО (Единицы.ЦифраРАЗНОСТЬДАТ(&ДатаНачалаПериода, &ДатаОкончанияПериода, ДЕНЬ))

ПО (Десятки.Цифра * 10 РАЗНОСТЬДАТ(&ДатаНачалаПериода, &ДатаОкончанияПериода, ДЕНЬ))

ПО (Сотни.Цифра * 100 РАЗНОСТЬДАТ(&ДатаНачалаПериода, &ДатаОкончанияПериода, ДЕНЬ))

ПО (Тысячи.Цифра * 1000 РАЗНОСТЬДАТ(&ДатаНачалаПериода, &ДатаОкончанияПериода, ДЕНЬ))

ПО (ДесяткиТысяч.Цифра * 10000 РАЗНОСТЬДАТ(&ДатаНачалаПериода, &ДатаОкончанияПериода, ДЕНЬ))

ГДЕ

СотниТысяч.Цифра * 100000 + ДесяткиТысяч.Цифра * 10000 +

Тысячи.Цифра * 1000 + Сотни.Цифра * 100 + Десятки.Цифра * 10 +

Единицы.ЦифраРАЗНОСТЬДАТ(&ДатаНачалаПериода, &ДатаОкончанияПериода, ДЕНЬ)

) КАК СписокДней

;

Отсутствие вертикальных черточек и подсветка синтаксиса повышают восприятие. Копирование в консоль запросов, для отладки, и обратно - тоже упрощается.

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

Нужный запрос будет легко найти, даже просто взглянув на дерево метаданных. Знаете, бывает такое зудящее чувство: “Где-то я писал подобный запрос...”, - как в этом случае у вас продвигались поиски? Я, например, иногда все переписывал заново.

Код в модулях станет более лаконичным. Согласитесь, огромные блоки текста с запросами, прямо в коде, порой просто мешают охватить взглядом логику алгоритма. Убрав запросы с глаз долой, мы делаем код более наглядным.

Да, иногда для понимания кода нужно знать, что выдает запрос на выходе. Эту информацию лучше описать в комментарии, коротко и по-человечески, сразу перед получением текста из макета.

Можно развить идею и использовать в тексте макета шаблоны, подменяя их перед выполнением запроса. Мне самому пока такая мысль не нравится, я считаю, что лучше использовать два разных макета, - раз уж возникла нужда в разных запросах. Но кто мешает вам попробовать?

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

Скачать файлы

Наименование Файл Версия Размер Кол. Скачив.
Запросы в текстовых макетах.pdf
.pdf 317,54Kb
09.07.12
57
.pdf 317,54Kb 57 Скачать

См. также

Подписаться Добавить вознаграждение

Комментарии

1. Сергей Ожерельев (Поручик) 09.07.12 13:51
(0) И кой она нужна, статья в отдельном файле?
hulio; fishca; +2 Ответить 1
2. Сергей Водаков (WaterSmith) 09.07.12 13:58
Публикация статьи в отдельном файле позволяет мне, как автору, оценивать размеры аудитории (по количеству скачиваний). Так-же отделить комментарии тех, кто статью читал, от тех, кто пришел просто покомментировать (опять же, по отметке "файл скачал" напротив имени комментирующего.
Если же кто-то нуждается в стартмани, для скачивания именно этой статьи - могу перевести, с меня не убудет.
3. Сергей Рудаков (fishca) 09.07.12 14:33
(0) получите минус в карму за статью в отдельном файле.
denis_aka_wolf; kilokilo; xzorkiix; +3 1 Ответить
4. Геннадий Пустовалов (Gennadius09) 09.07.12 14:52
Идея здоровская, на мой взгляд. Плюс.
5. Юрий Былинкин (ardn) 09.07.12 15:57
Хотел бы прочитать статью
Стартмани не имею
6. Юрий Былинкин (ardn) 09.07.12 16:40
Спасибо.
Статья хорошая, мысль здравая.
Действительно, упорядочение текстов запросов колоссальное происходит. Так четче, строже конечно.
Однако есть моменты, из-за которых я скорее всего не перейду на такую систему:
1. Как это ни банально, но я привык оценивать свою работу в количестве строчек текста. Это не в организации такие порядки, я делаю это чисто для себя. Написание запроса - тоже работа, а так она выпадает из сделанного.
2. На 8.1 у меня нет подсветки синтаксиса в текстовом макете.
3. Конструктор запросов нельзя вызвать из макета.
7. Алексей Константинов (alexk-is) 09.07.12 17:03
(0) Если я скачаю файл, то с меня точно не убудет.
Но, качать статью почему-то не хочется...

Свободу слову!

Совершенно бесплатные и периодически обновляемые статьи здесь :)
rozhkovdmitriy; kilokilo; Hany; headMade; hulio; +5 Ответить
8. Ярослав Радкевич (WKBAPKA) 09.07.12 19:47
а мне скрины понравились... вот если бы пляжников заменить на могилки с крестами, прикольно б смотрелось )
9. Ярослав Радкевич (WKBAPKA) 09.07.12 19:56
но если честно, я не понял, для чего это нужно... это что то вроде унификации, вроде как понятно, для упрощения модуля, тоже вроде как понятно... но опять же, эти самые лоскутные запросы тогда как?
ну а с точки зрения чтения кода, да есть здравая идея
10. Сергей Силантьев (sils) 09.07.12 20:18
Статья здравая, не понял только про отчеты на СКД, как пользоваться конструкторами (например выходной формы), если запрос лежит в общем макете?
11. Сергей Водаков (WaterSmith) 09.07.12 20:30
(10) sils, А про СКД речь не шла. У СКД есть свое место, для хранения текста запроса, в источнике данных, и там ему и место.
12. Сергей Ожерельев (Поручик) 10.07.12 09:24
(2) Вот, у меня стартмани хоть ..ой жри, но тратить на скачивание почему-то жаба душит.
13. Сергей Ожерельев (Поручик) 10.07.12 09:25
(2) Но минус ставить не буду.
14. Сергей Водаков (WaterSmith) 10.07.12 09:50
(12) Поручик, Все 100% скачиваний я компенсировал, можете спросить в личку любого из скачавших. Компенсирую и вам.
15. Владимир (sinjevla) 10.07.12 13:58
Что за бред статья в отдельном файле. Минус за такое.
16. Анатолий Бритько (headMade) 10.07.12 14:01
Мне кажется тексты будет проще хранить (если есть такая необходимость) в модуле менеджера.
Не надо будет думать с наименованием текстов т.к. для каждого объекта можно будет посмотреть свои запросы
17. Сергей Водаков (WaterSmith) 10.07.12 14:04
(16) headMade, Так ведь фишка как раз в том, что у каждого запроса есть четкое, осмысленное имя. Это дисциплинирует.
И потом, сохраняя их в модуле менеджера, вы ведь тоже дадите им какие-то имена, разве нет?
18. Zigfridish (Bassgood) 10.07.12 15:31
(0), честно говоря, мне не жалко потратить один стартмани на скачивание статьи, НО мне лень скачивать, открывать и удалять файл статьи =)
Так-же отделить комментарии тех, кто статью читал, от тех, кто пришел просто покомментировать

Я думаю это можно определить по содержанию сообщений самих комментаторов...
19. Сергей Водаков (WaterSmith) 10.07.12 15:36
(18) Zigfridish, Отличный аргумент, в пользу размещения статьи в файле. Мне было бы неприятно осознавать, что я поощряю чью-то лень.
20. Яшин Антон (Anyxwar) 10.07.12 15:58
Согласен,нечего писать для лентяев которым даже нажать кнопку лень.А так же жаль жадных....
21. fhn iyg (zigomodo) 10.07.12 16:10
Легче создать папку и в ней текстовик с описанием когда,во сколько и какой запрос)
22. Сергей Водаков (WaterSmith) 10.07.12 16:33
(21) zigomodo, Легче чем что, простите? Можно поподробнее?
23. Сергей JesteR (JesteR) 10.07.12 16:50
Статью качать не стал, т.к. ИМХО:
Статья чтобы читать ее, а не качать )))
Вы как автор должны в первую очередь думать о тех для кого пишите, а не о себе.
Минус.
Збянтэжаны Саўка; Bassgood; +2 Ответить
24. Stamper (Stamper) 10.07.12 17:34
автору плюс за слог и особенно первое предложение :)
вот бы еще результат запроса повторно использовать -- вообще была бы красота
25. Сергей Водаков (WaterSmith) 10.07.12 17:46
(24) Stamper, А по поводу повторного использования результата запроса, это шутка такая? Временные таблицы еще никто не отменял.
26. Сергей Водаков (WaterSmith) 10.07.12 18:53
Я статью писал чтобы ее обсуждать, а не стартмани, в связи с чем открываю для свободного чтения. Желающие могут по прежнему скачать копию статьи в pdf.
ВНИМАНИЕ: в файле для скачки точно такая-же статья, чтобы потом не было вопросов.
27. Сергей JesteR (JesteR) 10.07.12 19:12
(26)Вот другое дело, сейчас с удовольствием прочту. Как бы теперь минус назад забрать :)
28. Сергей JesteR (JesteR) 10.07.12 19:13
(27)Все понял как минусик забрать :)
29. Евгений Мартыненков (JohnyDeath) 10.07.12 20:29
А можно все-таки услышать чем общий модуль не устроил? Мне кажется, вызывать ф-ии общего модуля куда симпатичнее.
30. Сергей Водаков (WaterSmith) 10.07.12 22:30
(29) JohnyDeath, Самое простое: запросы хранящиеся в общем модуле не видно в дереве метаданных.
Чем конкретно вам общий модуль симпатичнее? Назовите преимущества общего модуля, перед макетами. И еще, с удовольствием хотел бы услышать о недостатках размещения запросов в макетах. Я таковых пока не нашел.
31. Stamper (Stamper) 10.07.12 23:23
(25) WaterSmith, мы очевидно не поняли друг друга
в планировщике запросов СУБД, насколько мне известно, есть возможность кеширования результатов запроса для того, чтобы повторно не лезть за данными в БД
так вот я об этом
32. Сергей Водаков (WaterSmith) 10.07.12 23:29
(31) Stamper, Таки да, мы не поняли друг друга. И продолжаем не понимать. Насколько мне известно кэширование результатов запросов 1С осуществляет на уровне ядра. Так что тут можно обсуждать? Тем более не ясно, какое отношение это имеет к теме статьи.
33. Stamper (Stamper) 10.07.12 23:31
(32) WaterSmith, на уровне ядра, на уровне СУБД... на уровне еще черт знает чего. а весело бы было влиять на этот процесс
34. Сергей Водаков (WaterSmith) 10.07.12 23:33
(33) Stamper, Ну, тут на вкус и цвет - фломастеры разные. Многие вон с управляемыми блокировками, до сих пор разобраться не могут.
35. Stamper (Stamper) 10.07.12 23:35
(34) WaterSmith, ну вот та же проблема "черного ящика"
черт его знает, как оно работает и как протестировать
36. lootinn 11.07.12 04:00
(6) ardn,
2. На 8.1 у меня нет подсветки синтаксиса в текстовом макете.

главное меню - текст - язык запросов, и подсветка появляется.
37. lootinn 11.07.12 04:23
(30) WaterSmith, о общем модуле все-таки можно использовать конструктор запроса. Или Вам всегда удобно писать запросы "от руки"? А открыть общий модуль и посмотреть в нем список функций времени много не займет.
И вот непонятно, чем этот подход поможет для "лоскутных" запросов.
38. aspirator 23 (aspirator23) 11.07.12 07:51
Знал об этом методе, но не использовал. Прочитал - понравилось.
Тут же зачесалось - полез в одну из своих обработок, где несколько таких больших запросов, перенес в макеты.
Понравилось. Текст кода сокращается - удобнее работать.
Недостатки:
-не воспользуешься конструктором запросов. Т.е. это нужно использовать в финальной части написания кода
-даже не замечание, а уточнение - крошечное время извлечение текста из макета занимает.
Но это скорее теоретический спор. Всего 0,0004 сек.
39. Евгений Мартыненков (JohnyDeath) 11.07.12 08:24
(30) А зачем они нужны в дереве метаданных? Если будет общий модуль, то подсказка даст тебе знать какие экспортные ф-ии есть в модуле.
40. Олег Сорокин (Oleg_nsk) 11.07.12 08:25
Обычно нужны не тексты запросов, а результат их выполнения, поэтому запросы нигде не храню, а использую функции общего модуля в которые передаются параметры. Скажу честно не понял смысл хранения текста запроса в макетах. Ну будет у меня дерево текстов и что? Зачем оно? Единственное рациональное зерно тут - это склеивание запросов, но создавать подобные структуры для таких редких случаев (ведь при этом еще количество, типы и порядок полей в склеиваемых запросах должно совпадать) трудозатратно. Что касается визуального восприятия, то его прекрасно видно в консоли запросов. Однако, все равно плюс. Люблю безумные идеи.
41. Олег Сорокин (Oleg_nsk) 11.07.12 08:28
И еще... Господа минусующие, имейте совесть. Понятно, конечно, что вы Боги 1с, но автор тратит свое время и делится своими идеями и разработками. Минуса как считаю надо ставить за совсем уж бесполезную порнографию.
42. Антон Рощин (wolfsoft) 11.07.12 08:35
Вообще не понял, чего все прицепились к скачиванию за мани? Не нравится - ставьте минуса support-у, это их идея - ввести мани, автор-то тут при чём?
43. Владимир Чаклин (vec435) 11.07.12 08:38
еще как вариант - хранить в табличном макете,где в 1 колонке-название , во 2 -описание, в 3 и далее -варианты текста.так можно и тексты кода хранить.преимущество - переносимость в виде mxl файла. а по поводу хранения результата - в 8.2 есть временноехранилище а адрес временногохранилища можно хранить в параметре сеанса
44. Юрий Былинкин (ardn) 11.07.12 08:56
(36) lootinn,
Спасибо.
Век живи, век учись
45. Сергей Рудаков (fishca) 11.07.12 09:15
(0) теперь статья выглядит гораздо лучше!
46. Игорь Юндин (kereo) 11.07.12 10:36
Идея не плохая, но не думаю что найдет себе применения. Минусы хранения запроса в макете конечно есть...
Над идеей использования одних и тех же запросов никогда не думал, но для сокращения кода писал функции ПолучитьТекстЗапроса*** (вместо звезд краткое название, в описании, если необходимо, краткое пояснение цели запроса и его содержимого, если необходимо, дайте ф-ции параметры для динамического изменения тескта в зависимости от параметров). Ну а для объединения всего этого счастья, сделайте обработку "БиблиотекаЗапросов" с экспортными ф-ми. Кстати по поводу ф-ции, такие же встречал в типовых конфигурациях. Вот и все...
47. Илья (i132) 11.07.12 10:56
:-) наверно первоначальная статья скрытая в отдельном файле илюстрировала удобство когда запрос прячется где-то в другом месте?
48. Zigfridish (Bassgood) 11.07.12 11:19
(0), не вижу в этом смысла, в функциях общего модуля хранить тексты запросов куда удобнее, как это реализовано в некоторых случаях в типовых конфигурациях.
49. Ak A (frc) 11.07.12 11:48
(42) wolfsoft,
Вообще не понял, чего все прицепились к скачиванию за мани?

прицепились не к скачиванию как таковому (на что вы пытаетесь перевести - дескать, механизм стармани придумал support, вот к нему и придирайтесь), а к тому, что у автора есть выбор - за выложить стартмани или без.
Он, почему-то, выложил сначала за стартмани.
Правда, потом исправился...
50. Ak A (frc) 11.07.12 11:51
(46) kereo,
Ну а для объединения всего этого счастья, сделайте обработку "БиблиотекаЗапросов" с экспортными ф-ми

сделать Библиотеку запросов - самый лучший и безпроигрышный вариант в рамках платформы 1С, и то - у него есть значительные минуса.
51. Ak A (frc) 11.07.12 12:01
(22) WaterSmith,
вы, и все остальные, здесь отписавшиеся "как замечательно", мало знакомые с 1с (вернее, с той безобразной структурой языка, что называется 1С) - не понимаете, что один увидел "о, макеты! о, текстовые! буду хранить и запросы!", другой - через ХранилищеЗначения, третий - через текстовые файлы и т.д., в результате, следующий за ними программист увидит набор
ЭтотОбъект.ПолучитьМакет("ЗапросТаблицаСписокДатПериода").ПолучитьТекст();
ТекстЗапроса = ХранилищеЗапросТаблицаСписокДатПериода.Получить();
ТекстЗапроса = ЗапросТаблицаСписокДатПериодаТекст.ПрочитатьСтроку();

и т.д.
И что он разберет во всех этих жутких переплетениях? Что Макет - это не макет для ПФ вовсе, а текст запроса?
52. Сергей Водаков (WaterSmith) 11.07.12 12:20
(51) frc, Ну, я как раз заострил внимание на том, что очень важно ответственно подойти к именованию таких макетов. Практически все преимущества, описанного мною подхода заключаются в структурированных, "говорящих" именах.
Что касается хранилища значения, это вообще не в ту кассу, о хранилище речь шла исключительно в комментариях, к теме статьи отношения не имеющих. Там предлагалось сохранять готовую выборку (что на мой взгляд весьма спорно, нужно как-то заботиться об актуальности данных).
Насчет приведенного вами гипотетического винегрета из методик. Да, описанная вами ситуация кошмарна. Только вот использование в одном и том же коде переменных вида "А1, Б25, С6" и венгерской нотации, - ничуть не умаляет достоинств последней.
И напоследок, хотелось бы поинтересоваться, вы пишете: "вы, ....., мало знакомые с 1с .... - не понимаете", так вот, - что меня выдало? Что, для вас, послужило признаком моей "малознакомости"?
53. Евгений Мартыненков (JohnyDeath) 11.07.12 13:00
(52) WaterSmith,
Практически все преимущества, описанного мною подхода заключаются в структурированных, "говорящих" именах.

В общем модуле нельзя сделать "говорящие" имена ф-ий? Я поддерживаю frc
54. Ak A (frc) 11.07.12 13:21
(52) WaterSmith,
о хранилище речь шла исключительно в комментариях

я написал именно как пример - а что еще можно при думать для хранения текста запроса.
Именно для иллюстрации:
Насчет приведенного вами гипотетического винегрета из методик

, а не в связи с проскочившим в комменатриях ХранилищеЗначений.
так вот, - что меня выдало?

радость от открытия "применения механизма 1С" для своих нужд, для чего, на самом деле, нужна реализация минимум на уровне платформы :)
Все остальное - лишь измудрости на радость новичкам, малоподходящие для широкого использования.
Так что если не хотите - не обижайтесь на мое замечание :)
55. Сергей Водаков (WaterSmith) 11.07.12 13:25
(53) JohnyDeath, Конечно же можно. Видите ли, при объективной оценке методологии, решения, некой сущности, наличие альтернатив, само по себе, не может рассматриваться как недостаток.
1. Можно использовать говорящие имена макетов.
2. Можно создать общий модуль с говорящими именами функций.
Это два решения одной и той же задачи. Общий модуль - первое что пришло мне в голову, но я не стал останавливаться на этом решении, и подумал дальше.
Общий модуль, хорош для общих, универсальных запросов, которые могут использоваться в контексте различных объектов. При необходимости привязать "коллекцию запросов" к определенному объекту, мы будем вынуждены использовать модуль менеджера (или модуль объекта, как вы считаете?). А в этом модуле могут уже присутствовать другие процедуры и функции. Можно выделить в модуле, ограниченную комментарием секцию: //КОЛЛЕКЦИЯ ЗАПРОСОВ

Но мне, по прежнему, не ясно чем такой подход лучше описанного мною?

P.S. Прошу обратить внимание, я тут не делаю революций, и ничего никому не доказываю. Вся эта дискуссия имеет под собой одну цель: выявить слабые стороны метода. Пока я таких не вижу.
56. Ak A (frc) 11.07.12 13:27
(53) JohnyDeath,
WaterSmith боится, что общие модули тогда превратятся в гигантскую простыню, навроде глобальника в 7.7, где ничего нельзя будет найти :))
Но забывает, что и выгрузить объекты в 1С - пока нельзя (кричат, что сделают в 8.3 выгрузку объектов в XML - но сомнительно, что это не будет очередная "полувыгрузка недообъектов"), равно как и макеты вместе с этими объектами.
Т.е. и с этой точки зрения ценность хранения в макетах - стремится к нулю...
57. Ak A (frc) 11.07.12 13:30
(55) WaterSmith,
Общий модуль, хорош для общих, универсальных запросов, которые могут использоваться в контексте различных объектов.

а зачем в макете харнить уникальный запрос, который больше нигде не будет использоваться? А если используется - хотя бы в рамках одного объекта, много раз, так это уже "универсальный" запрос.
Говоря об "общие модули - для русских многообъектных запросов", вы забываете, что в 1С даже внутри объекта сложно получить связь между модулем менеджера и модулем объекта, модулем объекта и модулем формы - не используя общие модули для увязки.
58. Сергей Водаков (WaterSmith) 11.07.12 13:33
(57) frc, Давайте на минуточку отвлечемся от общих модулей. Для простоты представим, что хранение текстов запросов в общих модулях, ничем не хуже, будем считать что в общих модулях тоже удобно.
Вопрос то в другом: Чем плохо в макетах?
59. Ak A (frc) 11.07.12 13:42
(58) WaterSmith,
Вопрос то в другом: Чем плохо в макетах?

хотя бы тем, что запросы "размазаны" по разным объектам, причем таким, которые даже и не создавались изначально для хранения текстов запросов, а для хранения печатных макетов.
1с тоже использует макеты для хранения двоичных данных ("нам это удобно") - а удобно ли пользоваться этим, если неизвестно что там хранится, и даже посмотреть ничего нельзя? Потому как механизм создавался только для хранения макетов в различных редактируемых видах.
60. Ak A (frc) 11.07.12 13:46
(58) WaterSmith,
т.е. 1С - хранит в макетах Макеты и двоичные данные (которые вообще неизвестно что содержат - макеты ли, запросы ли, письма МинФина ли...), вы теперь еще и запросы там храните.
Через некотрое время - будут и формы хранить. Потом - данные документов.
И что - вся конфигурация "съедет" в один объект - "Макет"?
Ваш подход изначально неверен, на что я и указываю Вам.
Да, может пользоваться, но - при долгосрочной перспективе неверен. Т.е. имеет долгосрочные изъяны.
61. Сергей Водаков (WaterSmith) 11.07.12 14:04
(60) frc, Не сочтите за переход на личности, но у вас паранойя, вы не доверяете своему инструменту, вот цитирую вас:
"кричат, что сделают в 8.3 выгрузку объектов в XML - но сомнительно, что это не будет очередная "полувыгрузка недообъектов"
....
а удобно ли пользоваться этим, если неизвестно что там хранится, и даже посмотреть ничего нельзя?
....
двоичные данные (которые вообще неизвестно что содержат - макеты ли, запросы ли, письма МинФина ли...)"

Рассматривать макеты, исключительно как средство создания печатных форм, это ретроградство. Вы правда считаете, что разработчики 1С придумали такое многообразие:
- Табличный документ
- Текстовый документ
- Двоичные данные
- Active документ
- HTML документ
...
Исключительно для создания печатных форм?

Пожалуйста назовите мне, объективные "долгосрочные изъяны". В каком именно случае текст запроса, хранящийся в текстовом макете повлияет на работу системы:
- будет недоступен и его невозможно будет выполнить
- повлияет на быстродействие системы
- повлияет на стабильность базы данных
Или же укажите на ситуации в которых обслуживание такого кода потребует больших трудозатрат, чем обслуживание кода созданного с классическим подходом.
63. Саўка Збянтэжаны (Збянтэжаны Саўка) 11.07.12 17:04
(26) WaterSmith, это замечание надо вынести в саму статью
64. Саўка Збянтэжаны (Збянтэжаны Саўка) 11.07.12 17:12
(61) WaterSmith, имхо, если забыл где и что лежит, и нужно найти "иголку в стоге сена", то плохо искать, ибо я обычно ищу текст только в модулях, а если еще и в макетах, то время поиска увеличивается на .?.
65. vladal (Vladal) 11.07.12 17:33
(1) Поручик, для качателей нужна.
66. Ak A (frc) 11.07.12 17:35
(61) WaterSmith,
вы не доверяете своему инструменту

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

да, считаю. Что только для макетов.
А иначе - было бы и место (и инструмент) для хранения запросов, и всяких-разных двоичных данных, и просомторщики всего и вся, что может хранится, и т.д.
А пока - Макеты созданы для макетов, макеты там прекрасно смотрятся, редактируются и используются.
В отличие от всего другого, что там пытаются хранить.
повлияет на стабильность базы данных

в 1С на это вообще может повлиять все, что угодно - вплоть до космического излучения.
будет недоступен и его невозможно будет выполнить

а что - разработчики где-то обмолвились, что "нет, никогда, макеты для запросов - самое то"?
повлияет на быстродействие системы

ну Вы забыли еще сравнится с "использованием различных СУБД", с "восстановлением последовательности", с "расчетом себестоимости" и т.д.
Я уже назвал Вам недостатки, которые для Вас - видимо, достоинства.
Попробуйте через текстовые файлы хранить и подключать запросы. Тоже найдете массу "привлекательного" :))
67. Антон Рощин (wolfsoft) 11.07.12 17:37
(49) Так его ж право, как выкладывать - за мани или без, как говорится, не хочешь - не качай ;) Некоторые вообще всякую хрень за деньги выкладывают - продают - и ничего, не минусуют.
68. Ak A (frc) 11.07.12 17:54
(67) wolfsoft,
к статьям это не относится.
Статьи - это не обработки, и искусственно создавать "скачки" на статьи есть нехорошо.
69. Сергей Водаков (WaterSmith) 11.07.12 18:13
(64) Збянтэжаны Саўка, Вот это аргумент. Действительно, скорость поиска может упасть. Например, я замерял скорость поиска заведомо отсутствующего текста в модулях конфигурации УПП, поиск занял 25 секунд, при поиске в модулях и макетах - 45 секунд, при поиске только в макетах - 26 секунд. Понятно, что результаты сильно зависят от количества объектов в конфигурации. Насколько это существенно, смотрите сами. На мой взгляд, вполне приемлемо.
70. Zigfridish (Bassgood) 12.07.12 01:14
(66) frc, макеты бывает полезно использовать еще не только для печатных форм, но также и для хранения каких-либо таблиц или данных в виде табличного или текстового документов, с помощью которых в коде можно циклом заполнить таблицу значений или еще какую структуру... это я так, к слову =)
BorisMor; +1 Ответить
71. Александра Афанасьева (Ava_1c) 12.07.12 12:24
Предлагаю пойти дальше: от процедур и функций отказаться, их текст выносить в макеты и в коде вместо вызова подпрограммы писать "Выполнить (...)".
Упорядочивать - так упорядочивать, что уж..
Хорошим тоном будет вызвать в таких местах функцию, которая вернет текст запроса, но вместо этого, запрос просто копируется, или же вообще переписывается из модуля в модуль.
Слабо верю, что разработчик, который практикует "копи-паст запросов" станет заморачиваться с созданием макетов и следить за корректностью их имен..
А ежели и так все "многоразовое" выносится в отдельные функции - зачем делать лишние телодвижения с созданием макетов? "Правила именования" соблюдай, и будет тебе счастье.
72. Сергей Водаков (WaterSmith) 12.07.12 13:52
(71) Ava_1c, Я уже говорил, что на мой взгляд, наличие альтернативных решений, само по себе не является недостатком. А применяя в споре метод "доведения до абсурда", конечно можно создать видимость, что вы спор выиграли, только к конструктивности это не имеет никакого отношения.
Получается примерно так:
я говорю, - а давайте будем носки класть в нижний ящик, отдельно от трусов. - А вы мне отвечаете, - да чего уж там, давай и трусы класть в нижний, и куртки.
73. Александра Афанасьева (Ava_1c) 12.07.12 14:42
(72) Альтернатива - это бесспорно хорошо.
Например, гвоздь можно забить молотком. А в качестве альтернативы - можно микроскопом. Я ж не спорю, можно.
Но ИМХО, инструменты лучше все-таки использовать по их прямому назначению.

Да, к сожалению в 1с неделимая единица, которая отображается в дереве конфигурации - это общий модуль/макет/форма. Детализации до уровня подпрограмм и, тем более, запросов - увы, нет.

По предложенному варианту лично я вижу
минусы: (их уже перечисляли)
  • Тратим лишние ресурсы на ПолучитьМакет() + ПолучитьТекст() + РеквизитФормыВЗначение("Объект") (для управляемых форм);
  • Из макета не открыть конструктор запроса;
  • Медленнее работает глобальный поиск.
плюсы:
  • Организация "правильного именования" (применимо везде и без макетов);
  • Возможность открыть текста запроса через дерево конфигурации (лично для меня бесполезно, т.к. бОльшая часть запросов - сложные, и их удобнее редактировать через конструктор. + всегда можно просто открыть общий модуль и точно также пробежаться по списку функций).
Итого, в чем профит, откровенно говоря, не поняла. =(
Медленнее работает, неудобно программисту (сужу по себе).. Порядка тому, кто не задумывался об этом раньше, не добавит.
Креатив и "альтернатива" - да, вполне.
sergelemon; userGJ; tormozit; lootinn; servs; Bassgood; xzorkiix; +7 Ответить
74. Модератор раздела Артур Аюханов (artbear) 12.07.12 19:24
(0) Нежизнеспособно :( Попробуй поработать с полгодика по такой схеме, сам замучаешься :(
Теряется главные плюсы при кодировании - простой, четкий и быстрый доступ к нужным объектам кода, например, к тексту запроса.
одни из самых значительных затрат при кодировании - сопровождение кода. для нормального сопровождения код должен быть простым и легкочитаемым.
Упрятав код (текст запроса) в макет, мы затрудняем себе возможность чтения и повторного использования своего же кода.
хочешь юзать общие запросы - юзай или общие модули, или у конкретных объектов используй экспортные функции.
75. Anya Yakushina (Little-ann) 12.07.12 20:42
Статью прочитала до последней строчки, но скачивать файл желания не имею. Задумка, конечно, оригинальная, но вот на практике (сами ж говорите, что запросов очень и очень много) не очень удобна в использование. По мне по ходу удобнее запрос использовать, при прочтении кода легко восстанавливается логика работы, а так - лишние движения обеспечены. ИМХО))
76. Дмитрий (adamx) 12.07.12 23:40
Я немного не понял смысла... В маленькой конфе, когда этих макетов 10-15 еще можно по названию вспомнить запрос, но потом.... Представьте - весь ЗиУП или УТ построены на таких вот макетах. Там этих запросов - тысячи.... И вот вы разворачиваете дерево макетов. КАК В НЕМ НАЙТИ НУЖНЫЙ ЗАПРОС? Как его поправить? Без конструтора вероятность ошибки на порядок выше. Так же можно и в текстовые файлы выносить - тогда можно править запросы без пересохранения конфигурации... Но оно надо?
77. Сергей Водаков (WaterSmith) 13.07.12 00:22
Всем спасибо, я все понял, идея оказалась нежизнеспособной.
78. aspirator 23 (aspirator23) 13.07.12 07:26
(77) Не отчаивайся.
Во-первых если конфигурация находится на поддержке, а это чаще всего, все предложенные варианты малопригодны: снимать с поддержки не всегда удобно. В таких случаях "положить" большие запросы, особенно если их много в обработке, в макет обработки - самое оно.
Во-вторых плохое-хорошее решение, но это новый взгляд. Уже за это плюс. Не случайно много комментариев.
sergelemon; +1 Ответить 1
79. Семен Слепаков (sa1m0nn) 13.07.12 08:19
Про такой подход в типовых конфигурациях:
встретил подобное в 1С:Документооборот, справочник Условия маршрутизации. Только там не чисто текстовые запросы, а схемы СКД.
80. Сергей Водаков (WaterSmith) 13.07.12 09:10
(79) sa1m0nn, Ну, схемы СКД это один из видов макетов, больше их хранить негде, так-что не удивительно, что они размещены в макетах.
81. Семен Слепаков (sa1m0nn) 13.07.12 09:35
Я к тому, что подход такой же - для каждого вида документа свой запрос, там их много, все в своих макетах. СКД там для полиморфных настроек.
82. Alexey Osipov (alexey_1c) 16.07.12 10:00
Спасибо, очень интересно
83. Ak A (frc) 16.07.12 10:17
(81) sa1m0nn,
каких еще полиморфных настроек? Все схемы СКД хранятся в макетах.
В любой конфигурации.
(78) aspirator23,
снимать с поддержки не всегда удобно.

а макеты править - снимать не надо?
84. aspirator 23 (aspirator23) 16.07.12 11:28
(83) В конфигурации находящейся на поддержке, можно использовать предложеную технологию во внешних обработках, отчетах.
В таких конфигурациях внешних отчетов/обработок множество.
85. alex ivanov (newuserv82) 16.07.12 16:24
(84) aspirator23,
а для базовых конфигураций эту технологию во внешних обработках можно использовать ?
а для управляемых форм ?
86. aspirator 23 (aspirator23) 16.07.12 17:12
(85) Автор ответит. Для конфигураций находящихся на поддержке без изменения,
внешние обработки единственный способ решения задач пользователей.
Надеюсь я не слишком категоричен :) ?
87. Сергей Водаков (WaterSmith) 16.07.12 17:30
(85) newuserv82, Если доступен макет, то что мешает? Какие вы видите трудности?
(86) aspirator23, Никак не могу понять, почему все так бояться конфигураций на поддержке с возможностью изменения?
88. aspirator 23 (aspirator23) 16.07.12 17:45
(87) Кто ж спорит? Именно так как правило у всех и стоит.
Но в базовых конфигурациях и в маленьких фирмах, там где нет собственных программистов лучше не снимать с поддержки - иначе потом хлопоты для владельца базы данных могут расти как ком, если бездумно править конфигурацию.
89. rsb rsb (fibrsb) 17.07.12 09:42
Спасибо! Очень ценная информация
90. Сергей JesteR (JesteR) 18.07.12 11:06
Прочитал.
Не вижу плюсов переноса кусков запроса в макеты.
Я бы так делать не стал.
91. Hany (Hany) 19.07.12 16:36
Скорее не минусы, а неудобства (из-за непривычного подхода):

- обычно по второму разу написанный запрос красивее и оптимальней, т.к. на таблицы смотришь более зрелым взглядом, куда-то "исчезают" лишние соединения или заменяются на поля другой таблицы

- если в макете какой-то запрос нужно будет переделать, то придется думать о том, где он используется и как повлияют текущие изменения

- наглядность "чтения" такого запроса сомнительна. Не видно структуру таблицы, а только ее название...А что в ней - надо вспоминать или открывать разные макеты для того, чтобы вспомнить?

- если считаю, что написанный запрос стОит того, чтобы его запомнить, у меня есть всегда сохраняемый файл из консоли запросов, в котором названия запросов - "говорящие"

Плюсы:

+ незаурядный подход всегда вызывает уважение

+ если автор и правда нашел удобство в таком использовании, значит так оно и есть
92. Apextrofimov (trand) 20.07.12 22:28
Вообще-то в конфигурации Раруса "Альфа-Авто" у всех отчетов запросы хранятся в макетах. Так что хранение запросов в макетах уже существует лет 5 как минимум. В макетах же Рарус хранит и настройки отчетов по умолчанию: отборы, поля и т.д. Будет время и желание поглядите как реализовано у Раруса.
93. Роман Романов (romansun) 21.07.12 01:32
когда деревья были большие, а у восьмой версии 1с еще не было даже первой подверсии мы хранили запросы в справочнике :), и там же в справочнике их можно было и отладить (функционал Консоли Запросов) и т.д.

Запросы в справочнике - это весьма удобно, чуть что - тут же поправил и у пользователя уже другая выборка.

А еще к запросам можно было прикрутить настройку запроса - это подчинённый справочник. В настройке хранилась, к примеру, шапка и подвал какого-нить типового запроса. Т.е., к примеру, верхняя секция-обёртка "ВЫБРАТЬ" и нижняя "ГДЕ"... Или "ИТОГО ПО". Ну и т.п. Соответственно, пользователь в отчете просто выбирал нужную ему настройку - и получал свой необходимый отчет с нужными полями, отборами, итогами и пр. Более того, пользователь сам мог настраивать себе нужные ему настройки ))

А через пару лет вышла 8.1, в которой было появилась СКД :)

---

На сегодняшний день, имхо, имеет смысл хранить СКД в виде xml в справочнике, и на лету собирать типа, да, Универсальный Отчет.
94. г. Казань Рустем Гумеров (Rustig) 23.07.12 10:17
мне понравилось только замечание, что запросы можно-таки хранить в базе как ТекстовыйДокумент. очень удобно в ряде случаев.
95. Piter Antares (piterantares) 25.07.12 16:24
Автор предлагает способ ухода от задвоения текстов запросов.
Так как 1С не даёт классы и наследование - приходится извращаться, кто-то копипастит, даже когда можно функцию написать, а кто-то неприемлет "задвоение кода" даже в тексте запроса.
Идея хорошая! Тем кто любит писать функции отдельные в модулях - ничего не мешает при этом тексты запросов вынести в макеты, при этом, кстати, функции будут различаться в основном названием используемых макетов.
Как вариант - следующий шаг идеи - всегда из макета грузить текст запроса в поле на форме, а ещё следующий - изменение логики работы системы не перезапуская 1С, есть компании или периоды в компаниях, когда работа идёт 24х7 и плотная, а что-то есть желание поменять...
96. Сергей Старых (tormozit) 26.07.12 17:10
Мне кажется, что оптимальным решением для многократно используемых в программном коде запросов является их оформление в виде функции ПолучитьЗапрос<ИмяЗапроса>(<ИмяПараметраЗапроса1>=, <ИмяПараметраЗапроса2>=, ...). Там же можно задать и значения по умолчанию. Все такие функции разумно сложить в несколько общих модулей и возможно даже включить повторное использование возвращаемых значений.
Получать запрос например так
ЗапросРасчетаСебестоимости = ПолучитьЗапросРасчетСебестоимости(Подразделение, ГруппаНоменклатуры);
функция ПолучитьЗапросРасчетСебестоимости(Подразделение, ГруппаНоменклатуры) Экспорт
    Результат = Новый запрос("ВЫБРАТЬ ...");
    Результат.УстановитьПараметр("Подразделение", Подразделение);
    Результат.УстановитьПараметр("ГруппаНоменклатуры", ГруппаНоменклатуры);
    Возврат Результат;
конецфункции
...Показать Скрыть
97. Доржи Балбаров (Angeros) 27.07.12 04:10
Лично для меня очень сомнительно применять ваш метод на практике. Всеже отладку в консоли никто не отменял, а этот метод ее усложнит в разы. Для себя использую такой подход. Прямо в консоли создал несколько вкладок с запросами и назвал их понятным для себя образом. Далее нужно просто взять оттуда текст и подогнать его под задачку...
98. Петр Лунегов (pvlunegov) 27.12.12 07:56
Почитал обмен мнениями. очень интересно.
Я в сложных обработках с кучей запросов извращался с выделением часто встречающихся запросов в функции типа ПолучитьЗапрос<ИмяЗапроса>(<ИмяПараметраЗапроса1>=, <ИмяПараметраЗапроса2>=, ...).
На счет распространения этого принципа на всю конфигурацию...
На мой взгляд это нежизнеспособно, поскольку конфигурация пишется МНОЖЕСТВОМ программистов (любая средней сложности минимум 2-мя).
Вечером дома я еще занимаюсь программированием под Android.
в 1с ооочень нехватает объектно-ориентированного подхода в кодинге.
Это очень печально.
Достоинством объектно-ориентированного подхода в плане кодинга и ОБМЕНА кодом между программистами - это:
1). Другому программисту не обязательно разбирать чужой код
2). Другой программист может использовать лишь общий интерфейс объекта в своем коде, залазить внурть кода не надо.

Таким образом, такой подход можно вполне применять в 1с, но он !почему-то! НЕ ПРОДВИГАЕТСЯ 1с, хотя во внутреннем языке все инструменты для этого есть.

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

В общем, господа, 1с сильно ущемило программистов в правах, не реализовав то, что так нужно любому С++ программисту.

Давайте напишем 1с петицию с просьбой это сделать...
99. Максим Зудин (kasper076) 27.12.12 08:46
100. Сергей Водаков (WaterSmith) 27.12.12 11:33
(98) pvlunegov, Фирма 1С знает о таких пожеланиях, но, по неизвестным причинам, упорно этому сопротивляется.

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