создание инфраструктуры клиентских приложений

Какая ИТ-инфраструктура нужна для приложений будущего?

Надежные приложения будущего немыслимы без микросервисной архитектуры, гибкости облачных вычислений, сетей доставки контента (CDN) и мультиоблачного подхода. В этой статье мы остановимся на том, что и зачем есть в облаках в контексте приложений настоящего и будущего, и почему все большее значение в их построении приобретает свободное ПО (open source).

Свободное ПО

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

«В тени» мира лицензионных приложений всегда развивался свободный код, он же – свободное ПО, он же – открытое ПО, он же – open source. Его развивали и группы энтузиастов, и корпорации. Но долгое время открытые технологии вызывали скепсис у бизнеса, которому требовались поддерживаемые, протестированные решения. Считалось, что открытое ПО – незрелое, сложнее найти ИТ-специалистов, готовых с ним работать, и его сложнее поддерживать. До недавнего времени так оно и было, но сегодня это уже не так – свободное ПО вышло на новый уровень зрелости, достаточный даже для масштабных, высоконагруженных систем, а решения на его основе стали предлагать даже глобальные вендоры.

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

Одной из первых больших российских ИТ-компаний, сделавших ставку на широкое использование свободного кода при создании высоконагруженных сервисов, стала Mail.ru Group. Строго следуя этому подходу, облачную платформу Mail.ru Cloud Solutions (MCS) сделали на базе открытой облачной платформы OpenStack.

Микросервисная архитектура

Раньше приложения работали либо на физических серверах – серверное приложение, либо на пользовательских устройствах – клиентское. То есть, по сути, существовало два варианта приложения, каждое из которых было «прописано на конкретной железке» и находилось на ней целиком – это и есть т. н. «монолитная архитектура».

Появление облаков позволило разбивать каждое приложение на множество микросервисов — маленьких приложений, каждое из которых делает небольшой кусочек работы и передает его дальше, на другие микросервисы. В облаке можно разместить и «монолит», но если в его цепи операций возникает узкое место, приходится делать более мощным весь облачный сервер для приложения, усиливая даже те его части, которые не «тормозят». Обновление приложения тоже происходит целиком, а при его падении нужно «воскрешать» на другой виртуальной машине полностью всю систему. В микросервисной архитектуре можно избирательно, ситуативно и автоматически усиливать отдельные функции приложений, обновлять их по одному. А при падении отдельных микросервисов новые копии поднимаются быстро – просто в силу их небольшого размера. Поэтому микросервисный подход делает приложения гораздо более надежными, он более эффективно утилизирует вычислительные ресурсы.

В техническом отношении для микросервисной архитектуры на первый план выходят технологии контейнеризации и управления контейнерами – оркестрации.

Микросервис по своей сути – это небольшая программа, в которой реализована та или иная часть функциональности приложения. Но это не просто программа – она упакована в «контейнер». И не в единственном числе упакованная, сама по себе, а вместе с необходимым для ее работы окружением – операционной системой, библиотеками. Можно сказать, что это маленький, атомарный компьютер для запуска и работы одной программы. Контейнер можно разработать и протестировать в «контуре разработки», а потом легко переместить и развернуть в рабочей среде – виртуализированной или на оборудовании. Причем его можно запускать во многих экземплярах, которые усиливают общую производительность выполнения соответствующей задачи. В сочетании с автоматическим масштабированием каждый конкретный микросервис регулирует свою производительность и утилизирует облачные ресурсы на 100%. Docker – один из самых популярных «упаковщиков» или, на языке профи – «исполняемых сред контейнеров», но есть и другие – CoreOS, Intel Clear Containers, hyper.sh и пр.

Создавать сами контейнеры с микросервисами достаточно просто, как отмечают специалисты, – многие уже научились делать это самостоятельно. А вот дальше возникает задача оркестрации контейнеров, то есть управления ими в рамках единого кластера микросервисов приложения, и здесь самая популярная технология – Kubernetes. Но создать кластер микросервисов на базе Kubernetes, чтобы он был отказоустойчивым и легко управляемым, достаточно сложно, поскольку здесь требуется специальный опыт и знания. К счастью, готовый и настроенный кластер Kubernetes можно получить в виде облачного платформенного сервиса Kubernetes (Kubernetes as a Service). Сервис автоматизирует запуск кластеров микросервисов и управление ими. Посредством облачного Kubernetes заказчик может удобно запускать обновления, откатывать их обратно, если они оказались неудачными, управлять выделением ресурсов. А если понадобится помощь – эксперты MCS всегда поделятся своими знаниями. Площадками для этого становятся специально проводимые для клиентов мастерские (т.н. воркшопы, workshop), оперативные консультации в Telegram. Специалисты MCS помогают заказчику по всем направлениям: при аудите приложений, оценке возможности их переработки на микросервисную архитектуру и в процессе самой «переделки», при налаживании конвейера непрерывной разработки, тестирования и выкатывания обновлений – т.н. CI/CD.

Kubernetes + виртуальная машина – это оптимально

Однако не все приложения можно поместить в контейнер – например, для баз данных это делать нерационально. И в этом случае компании предпочитают гибридную конфигурацию, в рамках которой используется и Kubernetes – для приложений, которые можно контейнеризовать, и виртуальные машины – на них работают другие системы. Например, на виртуальной машине можно запустить СУБД и предоставлять ее как сервис (DBaaS). В облаке MCS по этой модели предоставляются сервисы на основе СУБД PostgreSQL, Postgres Pro, Redis, ClickHouse, MongoDB, Arenadata DB.

Кроме того, совместное использование облачного Kubernetes и виртуальных машин позволяет правильно разграничивать права доступа пользователей к различным приложениям, а также удовлетворить запросы службы безопасности по обеспечению ИБ критичных информационных систем, требующих дополнительных мер по защите данных.

CDN-сервис – возможность быть рядом с пользователем

Задержка даже на долю секунды в оказании интернет-сервиса пользователю может быть критичной. Особенно значим этот параметр – время получения сервиса – для игр в реальном времени, стриминга различного медиа-контента. И даже на бизнес интернет-магазинов и сайтов заказа еды задержки тоже влияют: за проседание скорости поисковики «штрафуют» сайты в позиции поиска. Снизить временные задержки в предоставлении сервисов, свести их к минимуму помогают т.н. сети доставки контента или Content Delivery System, CDN. И это тоже важная опция, на которую нужно обращать внимание при выборе облачного провайдера, если бизнес чувствителен к падению скорости раздачи контента.

создание инфраструктуры клиентских приложений. 186. создание инфраструктуры клиентских приложений фото. создание инфраструктуры клиентских приложений-186. картинка создание инфраструктуры клиентских приложений. картинка 186.

MCS предлагает доставку контента как сервис на базе сети CDN-серверов. Он создан в партнерстве с «Мегафоном» и в сотрудничестве с 700 провайдерами контента и операторами связи. Сеть представлена во всех регионах мира – в 34 городах, включает порядка 400 ЦОД. Техническая поддержка оказывается в режиме 24/7. В рамках CDN-сервиса система сама в автоматическом режиме выбирает оптимальный маршрут доставки контента, гарантирует доступность содержимого при любой нагрузке, ускоряет загрузку сайта, снижает количество отказов, повышает конверсию, то есть долю посетителей сайта, ставших клиентами.

Мультиоблако

Мультиоблако – это когда облако заказчика включает в себя более одной облачной платформы разных провайдеров, которые отличаются друг от друга на технологическом уровне. Таким образом, критичный признак мультиоблака, в отличие от гибридной модели, – технологическая гетерогенность облачных платформ.

Приложение, чтобы оно могло работать в мультиоблаке, обязательно должно иметь микросервисную архитектуру и быть автомасштабируемым. Именно для этого предназначены технологии Docker и Kubernetes – последний реализует большую часть того, что нужно для мультиоблака, позволяет установить и отмасштабировать приложение из единой панели управления сразу в двух или более облаках – например, и на Amazon, и на MCS.

Какие задачи можно решать посредством мультиоблака? Первое назначение – снижение рисков привязанности к одному вендору (vendor lock), упрощение смены провайдера в случае необходимости. Например – перестал устраивать уровень обслуживания (SLA), технические возможности платформы. Или провайдер вдруг резко поднял оплату вычислительных мощностей. Или, что бывает чаще, изменился профиль использования трафика, при котором его стоимость становится критичным моментом. Вторая важная задача мультиоблака, отчасти связанная с первой, – обеспечение практически 100% гарантии доступа к сервису, защита от выхода из строя одной из облачных платформ. И третье назначение – возможность сэкономить, выбрав для разных сервисов наиболее подходящих по цене провайдеров. Это усложняет администрирование, но тоже возможно.

Есть у мультиоблака и отдельные недостатки, в их числе – невозможность использовать те или иные проприетарные сервисы облачных провайдеров. Например, СУБД DinamoDB от AWS – реплику этой базы данных у другого провайдера создать не получится. Выход из ситуации – отказ от использования такого рода сервисов в пользу базовых IaaS и PaaS-сервисов.

В рамках мультиоблачной стратегии MCS предоставляет клиентам инструментарий для единого управления развертыванием, управлением, мониторингом, масштабированием приложений, работающих в федеративных кластерах Kubernetes. Оказывают специалисты MCS и услуги консалтинга на этапе построения мультиоблачной стратегии бизнеса, а также в ходе эксплуатации. MCS реализовано решение для автоматического развертывания федеративных кластеров Kubernetes одновременно на мощностях AWS и MCS. Работает проект с Acronis, позволяющий создавать бэкапы в другом облачном плече. Кроме того, MCS предоставляет сервисы, позволяющие осуществлять мультиоблачное восстановление данных после сбоя (Disaster Recovery).

Более простой вариант мультиоблака (в нестрогом смысле) создают для выполнения требований закона 152-ФЗ и других правил использования персональных данных на том или ином локальном рынке. Здесь объединение облаков разных вендоров реализуется проще: часть данных хранится и обрабатывается в одном облаке, часть — в другом. Например, международная компания работает одновременно и в Западной Европе, и в России. В этом случае встречается вариант, когда мультиоблако базируется на платформах AWS и MCS: на Amazon обслуживаются европейские пользователи сервисов, на облаке MCS – российские. Примером таких компаний может быть «Битрикс24».

Уже сегодня, как свидетельствуют эксперты, наблюдается возросший спрос на мультиоблако со стороны банковской и других отраслей экономики – количество конкурсов на создание гетерогенных облачных платформ растет с прошлого года. Один из существенных факторов, способствующих этому, – слияния и поглощения, когда возникает гетерогенная ИТ-инфраструктура, которую требуется поддерживать. Мультиоблачную стратегию будут использовать и российские поставщики SaaS-сервисов, которым необходимо гарантировать доступность почти на 100%-м уровне, что невозможно реализовать на базе монооблака.

Будущее ИТ-инфраструктуры

Каждая из технологий для современных приложений «прокачивает» их в разных аспектах. Микросервисная архитектура, которая технически реализуется на контейнерах под управлением Kubernetes, берет на себя надежность, простоту обновлений приложений и даже оптимизацию расходов на облачную инфраструктуру – за счет 100% утилизации ресурсов. CDN улучшает опыт пользователей и помогает обойти конкурентов в поиске. Использование свободного ПО и мультиоблака направлены на устойчивость и безопасность бизнеса, обеспечение его независимости от отдельных вендоров приложений и провайдеров облаков.

Источник

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

Сразу оговоримся, что в этой публикации мы не будем затрагивать вопросы подходов к созданию полномасштабных приложений для Web, подразумевающих наличие крупной кодовой базы, заставляющей функционировать её серверную часть. Как-то исторически сложилось так, что клиентская часть подобных приложений, как правило, реализуется на JavaScript и производных от него языках и фреймворках, а серверная – уж на чём придётся. В конце концов, не столь уж это и важно – главное, чтобы соответствующая программная среда была поднята на сервере и реализованный в ней код спокойно выполнял свою задачу.

Вместе с тем со временем всё чаще стала возникать потребность в написании монолитных – как правило, простых и непритязательных веб-приложений, не требующих для работы серверной части. Естественно, с широким распространением HTML5 подобные приложения начали обретать весьма богатый функционал, однако. Однако же не все разработчики были готовы смириться с существующим положением вещей, когда все доступные им решения, по сути, имели своим краеугольным камнем всё тот же пресловутый JavaScript.

В конце концов, многие, что называется, “с младых ногтей” привыкли к другому подходу к проектированию и созданию приложений широкого профиля. Это, в первую очередь, различные RAD-среды, среди которых в нашей стране наибольшей популярностью (по крайней мере, в академической среде), всегда пользовалась Delphi. Натянул пару кнопок на форму, прописал нужные обработчики событий на привычном языке Pascal – красота. Чего ещё можно желать, в особенности если вы сосредоточены на реализации каких-то нужных вам алгоритмов, а интерфейс для вас не играет такой уж принципиальной роли?

При традиционном дизайне и проектировании веб-приложений всё совсем не так. Тут тебе бы неплохо помнить и все основные детали описаний различных тэгов HTML-разметки и атрибутов CSS-стили, и уметь сверстать всё это дело воедино, да ещё и “оживить” интерактивными сценариями, реализованными на JavaScript. Очевидно, что такой подход, ориентированный в первую очередь на дизайн, а не на саму разработку как таковую, вряд ли устроит нашего традиционного разработчика, воспитанного на классических алгоритмах и структурах данных, с возможным вкраплением зачатков объектно-ориентированного подхода. (Напоминаем, что речь идёт в первую очередь о разработчиках небольших приложений, где теоретически мог бы управиться и один человек.)

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

Надо сказать, что тенденции придать веб-разработке некоторые черты RAD-технологии (Rapidapplicationdevelopment, т.е. дословно “быстрой разработки приложений” – именно так принято именовать подход к разработке приложений, реализованный, в частности, в BorlandDelphi) существуют уже достаточно давно. Здесь нельзя не упомянуть хотя бы о DHTML (или Dynamic HTML) – подходе, так же позволяющем придавать некоторую интерактивность самим приложениям и, в частности, используемым в них элементам пользовательских веб-форм, – интерактивность, похожую на то, что мы можем видеть в Delphi, VisualBasic и прочих RAD-средах проектирования традиционных приложений.

DHTML-приложения подразумевали полноценную автономную браузерную реализацию, без какой-либо поддержки со стороны сервера – именно то, что сейчас известно как Richwebapplication (ранее –RichInternetapplications, RIA) и тесно соприкасающиеся с ними SPA (Single-page applications– одностраничные веб-приложения). Однако сама по себе технология DHTML так и не оправдала возложенных на неё надежд, и была вытеснена всё теми же альтернативными подходами, требующими установки автономных плагинов, – такими, как AdobeFlash или JavaServlet (позднее – JavaFX). В то же время она в числе прочих компонентов составила прочную основу, на которой базируется такой широко известный в веб-разработке подход, как AJAX (где уже широко задействуется и серверная часть).

Правда, такие приложения уместнее сравнивать скорее с создаваемыми посредством майкрософтовской технологии ASP.NET

Вспомним заодно уж и о Xojo – кросс-платформенной объектно-ориентированной среде программирования, основанной на языке REALbasic (своеобразном аналоге VisualBasic– почти как Lazarus по отношению к BorlandDelphi; правда, на сей раз речь идёт о коммерческом продукте). Она тоже в настоящий момент позволяет создавать код не только для Windows, macOS или Linux, но и напрямую для веба – используя для этого всё те же принципы проектирования RAD. Правда, такие приложения уместнее сравнивать скорее с создаваемыми посредством майкрософтовской технологии ASP.NET – в последних, конечно же, тоже широко используются принципы проектирования RAD, но тем не менее требуют для своего развёртывания веб-сервер.

Пусть другие теперь строят прогнозы, мы же лишь попытались дать краткий сравнительный обзор технологий для построения приложений, работающих прямо в браузере пользователя (что называется, “из коробки”) – как имеющих на данный момент скорее историческое значение, так и пока ещё актуальных.

Источник

Архитектура мобильного клиент-серверного приложения

создание инфраструктуры клиентских приложений. image loader. создание инфраструктуры клиентских приложений фото. создание инфраструктуры клиентских приложений-image loader. картинка создание инфраструктуры клиентских приложений. картинка image loader.
К добавлению внешнего сервера рано или поздно приходит любой сложный проект. Причины, при этом, бывают совершенно различные. Одни, загружают дополнительные сведения из сети, другие, синхронизируют данные между клиентскими устройствами, третьи- переносят логику выполнения приложения на сторону сервера. Как правило, к последним относятся большинство «деловых» приложений. По мере отхода от парадигмы «песочницы», в которой все действия выполняются только в рамках исходной системы, логика выполнения процессов переплетается, сплетается, завязывается узлами настолько, что становится трудно понять, что является исходной точкой входа в процесс приложения. В этом момент, на первое место выходит уже не функциональные свойства самого приложения, а его архитектура, и, как следствие, возможности к масштабированию.
Заложенный фундамент позволяет либо создать величественный архитектурный ансамбль, либо «накурнож» — избушку на куриных ножках, которая рассыпается от одного толчка «доброго молодца» коих, за время своего существования повидала видимо — невидимо, потому что, глядя на множественные строительные дефекты заказчик склонен менять не исходный проект, а команду строителей.
Планирование — ключ к успеху проекта, но, именно на него выделяется заказчиком минимальный объем времени. Строительные паттерны — туз в рукаве разработчика, который покрывает неблагоприятные комбинации где время — оказывается решающим фактором. Взятые за основу работающие решения позволяют сделать быстрый старт, чтоб перейти к задачам, кажущиеся заказчику наиболее актуальными (как-то покраска дымоходной трубы, на еще не возведенной крыше).
В этой статье я постараюсь изложить принцип построение масштабируемой системы для мобильных устройств, покрывающей 90-95% клиент-серверных приложений, и обеспечивающей максимальное отдаление от сакраментального «накурножа».

Пока занимался доработкой данной статьи, на хабре вышла аналогичная статья (http://habrahabr.ru/company/redmadrobot/blog/246551/). Не со всеми акцентами автора я согласен, но в целом, мое видение не противоречит и не пересекается с материалом изложенным там. Читатель же, сможет определить, какой из подходов более гибкий, и более актуальный.

создание инфраструктуры клиентских приложений. image loader. создание инфраструктуры клиентских приложений фото. создание инфраструктуры клиентских приложений-image loader. картинка создание инфраструктуры клиентских приложений. картинка image loader.

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

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

создание инфраструктуры клиентских приложений. image loader. создание инфраструктуры клиентских приложений фото. создание инфраструктуры клиентских приложений-image loader. картинка создание инфраструктуры клиентских приложений. картинка image loader.

Общая структура приложения

создание инфраструктуры клиентских приложений. image loader. создание инфраструктуры клиентских приложений фото. создание инфраструктуры клиентских приложений-image loader. картинка создание инфраструктуры клиентских приложений. картинка image loader.

Насколько работоспособное данное приложение? Думаю, что ни у кого нет сомнения, что используя Delphi или Visual Studio можно в момент решить эту задачу. Используя Xcode сделать это несколько сложнее, но тоже можно не сильно напрягаясь. Однако, вслед за появлением прототипа, начинают появляться вопросы масштабируемости. Становится очевидным, что для отображения графика необходимо хранить данные за предыдущий период. Не проблема, можно добавить хранилище данных внутрь формы графиков. Однако, данные могут приходить от разных провайдеров и в разных форматах. Кроме того, арифметические операции могут осуществляться с разными валютам, а значит, необходимо обеспечить их выбор. Делать такой выбор на форме графиков — несколько нелогично, хотя и возможно, однако, от таких настроек зависит что именно мы будем отображать на графике. Это означает, что если мы выносим дополнительные параметры в окно настроек, то нам придется как-то их передавать через главную форму в окно графиков. В этом случае логично будет сделать локальную переменную, в которой и хранить передаваемые параметры, и обеспечить доступ из одной форме к другой форме через главную форму. Ну и так далее. Цепочку рассуждений можно строить весьма долго, и сложность взаимодействий будет возрастать.

Конечно, данный подход требует больше усилий по программированию, и соотвественно, изначально предполагает больше времени. Однако, исходя из подзадач ясно, что во-первых, работу над ним легко распараллелить — в то время как один разработчик занят формированием ядра — другой, создает и отлаживает UI. Ядро может благополучно работать в рамках консоли, UI прощелкиваться в девайсе и, ко всему прочему, к обеим частям можно прикрутить независимые юнит-тесты. Другим несомненным достоинством является то, что второй подход значительно более масштабируем. В случае пересмотра функциональности проекта, любые изменения будут вносится многократно быстрее, потому что попросту не существует ограничительных рамок визуальных представлений. Сами визуальные формы (GUI) отображают необходимый минимум основанный на существующих в ядре задачах.

создание инфраструктуры клиентских приложений. image loader. создание инфраструктуры клиентских приложений фото. создание инфраструктуры клиентских приложений-image loader. картинка создание инфраструктуры клиентских приложений. картинка image loader.

GitHub содержит множество библиотек, позволяющих использовать REST соединения, для iOS, наиболее востребованной является AFNetworking.

REST опирается на использование GET, POST, PUT, HEAD, PATCH и DELETE запросов. Такой зоопарк называют RESTFul ( habrahabr.ru/post/144011 ) и, как правило, он применяется только тогда, когда пишется универсальный API для работы мобильных приложений, веб-сайтов, десктопов и космических станций в одной связке.
Подавляющее большинство приложений ограничивает систему команд двумя типами, GET и POST, хотя, достаточно только одного — POST.
GET запрос передается в виде строки, которую Вы используете в браузере, а параметры для запроса передаются разделенные знаками ‘&’. POST запрос так же использует «браузерную строку» но, параметры скрывает внутри невидимого тела сообщения. Последние два утверждения повергают в уныние тех, кто с запросами ранее не сталкивался, в действительности же, технология отработана настолько, что она совершенно прозрачна для разработчика, и не приходится вникать в такие нюансы.
Выше, было описано что отправляется серверу. А вот то, что приходит от сервера — куда интересней. Если Вы используете AFNetworking, то со стороны сервера Вы получите Как правило, iOS разработчики называют JSON- оном сериализированный словарь, но это не совсем так. Истинный JSON имеет чуть более сложный формат, но в чистом виде им практически никогда пользоваться не приходится. Однако, о том, что имеется отличие знать нужно — бывают нюансы.
Если Вы работаете с сервисом, установленным на Microsoft Windows Server, то вероятнее всего, там будет использован WCF. Однако, начиная с Windows Framework 4, имеется возможность для клиентов поддерживающих только REST протокол, сделать доступ совершенно прозрачно, декларативным образом. Вы даже сможете не тратить время на получении пояснений об API — документация о системе команд генерируется автоматически IIS (майкрософтовским веб-сервером).

Ниже приводится минимальный код, для реализации Network Layer при помощи AFNetworking 2 на Objective-C.

Этого вполне достаточно чтоб передавать сетевые GET и POST сообщения. В большинстве своем, Вам не потребуется больше корректировать эти файлы.

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

Класс унаследован от ClientBase. Код класса настолько просто, что нет необходимость даже приводить его целиком — он состоит их единообразного описания API:

Как говорится: «Ничего лишнего».

Network Cache Layer:
Данный слой кеширования задействуется для ускорения сетевого обмена между клиентом и сервером на уровне iOS SDK. Выбор ответов осуществляется стороной лежащей за пределами контроля системы, и не гарантирует снижение сетевого трафика, но ускоряет его. Доступа к данным или механизмам реализации нет ни со стороны приложения, ни со стороны системы. При этом используется SQLite хранилище.

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

Вызвать нужно из любого места приложения однократно. Например из стартового слоя.

*Время UTC — это время, когда команды была вызвана, а не когда ответ был возвращен серверу. Как правило, они совпадают, но поскольку у приложения может имеется механизм очереди запросов, то теоретически, между вызовом сбойной команды, и регистрацией записи сервером могут проходить месяцы.
Предполагается, что схемы JSON запросов предоставляют серверные разработчики после реализации новых команд API.

Каждая схема, как и каждая команда, обязана удовлетворять определенным оговоренным ранее критериям. В приведенном примере ответ сервера должен содержать два основных и одно опциональное поле.
«status» обязательное. Содержит идентификатор OK или ERROR (или код HTTP типа «200»).
«reason» обязательное Содержит текстовое описание причины ошибки, если она возникла. В противном случае — это поле пустое.
«data» опциональное. Содержит результат выполнения команды. В случае ошибки отсутствует.
Пример схемы:

Благодаря библиотеке разработанной Максимом Луниным сделать это стало очень просто. ( habrahabr.ru/post/180923 )

Код класса валидации приводится ниже

Network Items layer:
Именно на этот слое лежит ответственность за маппинг данных из JSON в десериализированное представление. Данный слой используется для описания классов, осуществляющих объектное или объектно-реляционное преобразование. В сети существует большое количество библиотек, осуществляющих объектно-релационные преобразования. Например JSON Model ( github.com/icanzilb/JSONModel ) или все та же библиотека Максима Лунина. Однако, не все так радужно. От проблем маппинга они не избавляют.

создание инфраструктуры клиентских приложений. image loader. создание инфраструктуры клиентских приложений фото. создание инфраструктуры клиентских приложений-image loader. картинка создание инфраструктуры клиентских приложений. картинка image loader.

В классе HttpCache по-мимо методов сохранения результатов запроса имеется еще один, интересный метод:

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

Путем еще одной небольшой модификации листинга 1 легко решается вопрос с очередями:

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

Проверка подключения к сети осуществляется с помощью классов AFNetworkReachabilityManager или Reachability от Apple ( developer.apple.com/library/ios/samplecode/Reachability/Introduction/Intro.html ) совместно с паттерном наблюдатель. Его устройство слишком примитивно, чтоб описывать в рамках статьи.
Однако, не все запросы должны быть отправлены в очередь. Некоторые из них могут не быть актуальными к моменту появления сети. Решить какие из команд дожны быть записаны в кеш очереди, а каки быть актуальны толко в момент вызова можно как на уровне слоя кеширования, так и на уровне слоя API.

В первом случае, в листинг 9, вместо вызова метода сохранения в очередь, необходимо вставить виртуальный метод, и унаследовать от класса ApiLayer унаследовать классы LocalCacheLayerWithQueue и LocalCacheLayerWithoutQueue. После чего в заданном виртуальном методе класса LocalCacheLayerWithQueue сделать вызов [HttpQueue request: endpoint: method:]

Во втором случае немного изменится вызов запроса из класса ApiLayer

В листинге 9 именно для такого случая предусмотрено условие if(queueAvailable).

Так же, отдельным вопросом является вопрос кеширования изображений. В общем-то, вопрос не сложный, и оттого, имеющий бесконечное количество реализаций. К примеру, библиотека SDWebImage делает это весьма успешно: ( github.com/rs/SDWebImage ).

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

Приведу пример асинхронной загрузки изображения из сети, с коррекцией ошибки MIME (к примеру, Amazon часто отдает неправильный MIME type, в результате чего, их же веб-сервер отправляет изображение, не как двоичный файл с картинкой, а как поток данных).

Метод может казаться весьма избыточным, но легко модифицируемым к конкретным нуждам разработчика. Из важных моментов следует отметить то, что в качестве ключа для кеширования используется хеш URL изображения. Практически невозможно чтоб при таком подходе случилась коллизия в рамках файловой системы устройства.
При каждом чтении файла из кеша, у него модифицируется дата доступа. Файлы которые не перечитываются долгое время можно спокойно удалить еще на старте приложения.

Когда речи идет о чтении файла из бандла приложения, имеется нюанс, который забывают разработчики: iOS SDK предоставляет нам такие методы как [UIImage imageNamed:] и [UIImage imageWithContentsOfFile:]. Использовать первый проще, но он существенно влияет на загруженность памяти — дело в том, что файл загруженный при помощи него, остается в памяти устройства, до тех пор, пока приложение не будет завершено. Если это файл, который имеет большой объем, то это может стать проблемой. Рекомендуется использовать второй метод, как можно чаще. Кроме того, полезно сделать небольшое усовершенствование в метод загрузки:

Теперь Вам не придется задаваться вопросом, в какой резолюции присутствует файл.

Workflows layer:
Все реализованные алгоритмы, которые не относятся к слоям ядра, и не представляют собой GUI должны быть вынесены в классы специфических последовательностей рабочих процессов. Каждый из этих процессов оформляется в своем стиле, и подключается к основной части приложения путем добавления ссылок на экземпляр соответствующего класса в GUI. В подавляющем большинстве случаев, все эти процессы являются не визуальными. Однако имеются некоторые исключения, например, когда необходимо осуществить длинную последовательность предопределенных кадров анимации, с заданными алгоритмами отображения
Вызывающий код должен иметь минимальные знания об этой функциональности. Все настройки flow должны быть инакапсулированы. Google в качестве примера приводит код для уведомления из сервера аналитики, и предлагает включить его в место, где событие возникает.

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

Существуют довольно развитые рабочие процессы, логика функционирования которых зависит от внутренного состояния. Такие процессы должны быть реализованы при помощи паттернов «Стратегия» или «Машина состояний». Как правило, совместно с паттерном «стратегия» используется паттерн «медиатор» который опосредует обращение к тому или иному алгоритму.
Один из часто используемых процессов — процесс авторизации пользователя — очевидный претендент на рефаторинг с использованием паттерна «машины состояний». При этом, именно на этом flow должна лежать ответственность за «автоматическую» авторизацию пользователя, а не рекурсивным образом вызываться из абстрактных слоев (Network Layer, или Validation Items).

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

Local storage:
Желание разработчиков находится в тренде новых технологий, порой, сталкивается со здравым смыслом, и, последний часто проигрывает. Одно из веяний моды было использование локального хранилища на основе CoreData. Некоторые разработчики настаивали, что его нужно использовать в как можно большем количестве проектов, не смотря на то, что даже сама Apple признавала, что есть определенные трудности.
Существует большое количество способов сохранение временных данных в постоянном хранилище устройства. Использование CoreData оправдано в том случае, когда нам необходимо хранить большое количество редко обновляемых данных. Однако, если в приложении имеется несколько сот записей, и ни постоянно обновляются скопом использование CoreData в этих целях неоправданно дорого. Таким образом, получается, что большую часть времени ресурсов устройство тратит на синхронизацию данных полученных из сети, с теми данными которые уже есть на устройстве, несмотря на то, что весь массив данных, будет обновлён во время следущей сессии.

Использование CoreData ( habrahabr.ru/post/191334 ), кроме того, требует также соблюдение определённых процедур, алгоритмов и архитектурных решений, что ограничивает нас в выборе стратегии разработки, а так же существенно осложняет механизмы отладки нашего приложения.

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

Локальное хранилище на основе файловой системы

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

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

Отрицательной стороной такого подхода считается, что это плохо влияет на производительность устройства, однако, изучение вопроса показывает, что объем таких данных не превышает 5Кбайт, данные загружаются в память мгновенно, единым блоком, и таким же образом освобождаются из памяти, сразу же после того, как в них отпадает необходимость, например, когда ViewController перестает существовать. В то же время чтение данных блоками (построчно) из базы данных SQL порождает большое количество объектов (на уровне выходящем за рамки контроля приложения), которые суммарно превышают указанный объем, к тому же, создают дополнительную нагрузку на процессор. Использование центрального хранилище оправдано тогда, когда данные должны сохраняться долгое время, на протяжении многих сессий работы приложения. При этом, данные из сети загружаются частично.

Локальное хранилище на основе CoreData.

CoreData не предоставляет возможности для использование сериализированных данных. Все данные должны быть подвергнуты объектно-реляционным преобразованиям, до их использования слоем локального хранилища. После получения данных от команды API profile, происходит передача данных в метод категории copyDataFromRemoteJSON, где из словаря извлекаются данные, а затем уже сохраняются в соответствующем управляемом объекте (потомокк класса NSManagedObject).
Вот пример того, как это происходит:

Еще лучшим подходом было бы, если бы callback из API мог бы возвращать валидизированные сериализированные данные, упакованные, к тому же, в управляемый объект.

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

При использовании библиотеки MagicalRecords возникает ситуация, когда для правильного функционирования приложения табличное представление должно быть частью UITableViewController, иначе становится затруднительным использование NSFetchController лежащий в основе загрузки данных CoreData. Таким образом, существует зависимость в использовании пользовательского интерфейса, от локального хранилища. Т. е. имплементация CoreData ограничивает в разработке UI.

Не смотря на высказанные возражения, использование CoreData может, действительно, потенциально увеличить производительность при возрастании объема данных, в том случае, если воспользоваться следующими альтернативами:

Альтернатива 1
Произвести нормализацию данных API сервера. Сервер должен возвращать не полный иерархический объект, с множеством вложенных сущностей, а множество мелких объектов, которые легко добавляются в базу данных.
В этом случае:
Загружаться будут небольшие порции свежих данных, что уменьши сетевой трафик.
Приложение сможет сделать запрос к серверу с идентификаторами объектов, чтоб сервер вернул список того, что необходимо удалить.
Отпадает необходимость в синхронизации получаемых данных для каждой загружаемой записи.

Заключение:
Статья получилась довольно длинной, и, сомневаюсь, что большинство читателей осилят ее до конца. По этой причине, часть, связанную с GUI я решил отсюда выкинуть. Во-первых, она относилась к построению пользовательского интерфейса через UITabbar, а во-вторых, в одной из скайп групп, состоялась весьма интересная дискуссия относительно использования широко известных паттернов MVC и MVVM. Излагать принципы построения интерфейса не имеет смысл без скурпулезного изложения существущих практик и подходов, которые заводят разработчиков в тупик. Но это тема большой еще одной многостраничной статьи. Здесь же, я постарался рассмотреть лишь вопросы, связанные с функционированием ядра приложения.
Если читатели проявят достаточный интерес к этой тематике, то в ближайшее время постараюсь выложить исходные классы, для использование в качестве шаблона приложения.

Источник

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *