Сервис запроса/ответа, детские вопросы по архитектуре

MiksIr

miksir@home:~$
Есть некий сервис отправки чего-то куда-то и получение ответа.
Стадии такие: принять запрос, сериализовать (например, в XML) со служебными полями, отправить, получить ответ, десериализовать, дать ответ.

Как бы это архитектурно сделать красиво. Допустим, объект-сервис Connector, который делает запрос принимает в себя объект сериализатора Serialize, объект запроса Request и отдает объект ответа Response. Или я уже на этой стадии ушел в оверинжиниринг?

Если работаем с Response - как эти объекты создаются? Инжектировать в Connector фабрику ResponseFabric и спрашивать ее "дай Response" передав необходимые для инициализации данные? Ну и про Request то же самое.

И Serialize тогда куда прицепить - к коннектору (брать из Request данные и сериализовать) или к запросу/ответу (Connector будет спрашивать getSerialized)?
 
Последнее редактирование:

MiksIr

miksir@home:~$
Да... уже раз сто исправляю, какая-то дурная привычка, понять не могу откуда ;)
 

fixxxer

К.О.
Партнер клуба
Наверное, потому что много слов, которые заканчиваются на -nce. Я раньше тоже так ошибался.

По теме - а что это? Если какой-то xml-rpc, то непонятно, к чему ему такая гибкость - это его внутреннее дело, как устроен транспорт.
 

MiksIr

miksir@home:~$
Ограничиться одним объектом с request($data)? Получается очень тяжелый класс. И сериализация, и дополнительные запросы на установку сессии (аутентификация), и анализ ответов, причем и ошибок уровня транспорта, и ошибок уровня приложения. Как бы разные слои, хочется их разделить.
 

AnrDaemon

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

fixxxer

К.О.
Партнер клуба
Ограничиться одним объектом с request($data)?
Снаружи - да. Внутри - с точки зрения внешнего апи не должно быть разницы, а с точки зрения внутренней архитектуры - побил бы по принципу "как удобнее писать юнит тесты".

Вот недавно делал реализацию jsonrpc2-сервера для laravel, в принципе наверное твое близко, только наоборот. Там, конечно, по-хорошему надо сделать framework agnostic и отдельный адаптер, но чот лень. =)
 

MiksIr

miksir@home:~$
Ну да, наружу торчит Api->request, который внутри уже через инжектированную фабрику создает Request, и передает его в коннектор. Тот в ответ выдает Response. Можно обойтись, наверное, без Request/Response, там мало чего внутри. По сути Request добавляет в запрос пару констант, а Response типа для isError(). А сериализатор инжектируется уже в коннектор.
 

WMix

герр M:)ller
Партнер клуба
не, типо покушал, потрудился и остатки жизнедеятельности оставил. исключительная ситуация, между прочим.
 

grigori

( ͡° ͜ʖ ͡°)
Команда форума
Перечитал 3 раза и не смог понять задачу.
>принять запрос, сериализовать (например, в XML) со служебными полями, отправить, получить ответ, десериализовать, дать ответ.
Пишется библиотека для генерации исходящего запроса или входящего или обоих?
Если запрос сначала принимаем, то куда его затем надо отправлять?
 

MiksIr

miksir@home:~$
Ну под "принять" имеется ввиду вызов метода. Т.е. чисто на отправку запроса на удаленный сервис и получение ответа работа. С нюансом, что еще понятие сессии (аутентификация и использование полученного ID). Ну и с учетом, что там SOAP с одним методом и одним строковым параметром - который является XML-ем с запросом.
 

AnrDaemon

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

Тугай

Новичок
Посмотри, как сделано в .Net Framworke. System.Net HttpWebRequest и HttpWebResponse.
То что ты называешь Connector - это контекст запроса (аутентификация и использование полученного ID, ...). Там не Connector принимает в себя Serialize и Request, а Request принимает в себя Serialize и Connector (StreamingContext).

Запрос выполняется с данными в контексте.
 

grigori

( ͡° ͜ʖ ͡°)
Команда форума
@Тугай, то ж в .Net, им надо сделать API для всех случаев жизни, а @MiksIr -- для одного сервиса и одного приложения.

Я бы шел по Бритве Оккама: сначала просто сделал Адаптер, который принимает DTO.
Сессию лучше оставить в Адаптере. DTO будет гарантировать валидность данных и работа с ними будет простой.
Если выходит "очень тяжелый класс. И сериализация, и дополнительные запросы на установку сессии" - выделяю Кодек, причем, здесь я бы DI сделал как опцию только для тестов.
 

Тугай

Новичок
@grigori, твой вариант похож на то, что в .Net, (Адаптер это Request, DTO - Serialize, а кодек - Context). Та же архитектура.

"объект-сервис Connector, который делает запрос принимает в себя объект сериализатора Serialize, объект запроса Request ..." - так называть нельзя, сразу каша какая-то в голове.
Connector делает запрос, Connector принимает объект запроса Request. Два раза слово "запрос" и за каждым совсем разные вещи.
 

Тугай

Новичок
Еще так можно "как в tcp/ip" - прикладной уровень, уровень протокола, уровень транспорта.
 
Последнее редактирование:

MiksIr

miksir@home:~$
Посмотри, как сделано в .Net Framworke. System.Net HttpWebRequest и HttpWebResponse.
То что ты называешь Connector - это контекст запроса (аутентификация и использование полученного ID, ...). Там не Connector принимает в себя Serialize и Request, а Request принимает в себя Serialize и Connector (StreamingContext).

Запрос выполняется с данными в контексте.
Боюсь что буду долго в .net разбираться ;) Конкретно по tcp кто ходит, Request? А StreamingContext - это DTO или что? Кто кого вызывает.
 
Сверху