Русский
Русский
English
Статистика
Реклама

Cloud

Стражи публичных облаков как мы внедряли анклавы Intel SGX для защиты чувствительных данных

14.01.2021 16:09:15 | Автор: admin
Как развеять предубеждения потенциальных пользователей относительно безопасности публичных облаков? На помощь приходит технология Intel Software Guard Extensions (Intel SGX). Рассказываем, как мы внедрили её в своём облаке и какие преимущества от нашего решения получила компания Aggregion.





Кратко об Intel SGX и его роли в облаке


Intel Software Guard Extensions (Intel SGX) набор инструкций ЦП, с помощью которых в адресном пространстве приложения создаются частные защищённые области (анклавы), где размещается код уровня пользователя. Технология обеспечивает конфиденциальность и целостность чувствительных данных. Путём изоляции в анклаве они получают дополнительную защиту как от несанкционированного внешнего доступа, в том числе со стороны провайдера облачных услуг, так и от внутренних угроз, включая атаки со стороны программного обеспечения привилегированного уровня.

Принципы работы. Для хранения кода и данных анклавов технология Intel SGX выделяет область памяти Processor Reserved Memory (PRM). ЦП защищает её от всех внешних обращений, в том числе от доступа со стороны ядра и гипервизора. В PRM содержится Enclave Page Cache (EPC), состоящий из блоков страниц объёмом 4 КиБ, при этом каждая страница должна принадлежать только одному анклаву, а их состояние фиксируется в Enclave Page Cache Metadata (EPCM) и контролируется ЦП.

Безопасность EPC обеспечивается за счёт Memory Encryption Engine (MEE), который генерирует ключи шифрования, хранящиеся в ЦП. Предполагается, что страницы могут быть расшифрованы только внутри физического ядра процессора.

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

Наш подход к внедрению Intel SGX


Чтобы в публичном облаке G-Core Labs появилась возможность выделять виртуальные машины с анклавами Intel SGX, нам пришлось пройти путь от компиляции патченного ядра KVM и QEMU до написания Python-скриптов в сервисах OpenStack Nova. Вычислительные узлы, которые планировалось использовать для выделения виртуальных машин повышенной безопасности, мы решили определить в отдельный агрегатор тип вычислительных ресурсов, требующий дополнительной настройки. На таких узлах было необходимо:

  • Включить поддержку Intel SGX на уровне BIOS.
  • Поставить патченные QEMU/KVM.

Изначально у нас не было понимания, как это должно работать и что в итоге мы должны прикрутить, чтобы получить ВМ нужной конфигурации. Разобраться с этим вопросом нам частично помогло руководство Intel для разработчиков. С его помощью мы узнали, как подготовить вычислительный узел для работы с SGX и какими дополнительными параметрами должен обладать конфигурационный XML-файл виртуальной машины. Здесь же мы нашли исчерпывающую информацию, как с помощью виртуализации KVM сделать гостевую машину с использованием Intel SGX. Чтобы убедиться, что мы смогли обеспечить поддержку данной технологии, мы использовали два способа:

  • Проверили секцию /dev/sgx/virt_epc в файле /proc/$PID/smaps:

    [root@compute-sgx ~]# grep -A22 epc /proc/$PID/smaps7f797affe000-7f797b7fe000 rw-s 00000000 00:97 57466526/dev/sgx/virt_epcSize:               8192 kBKernelPageSize:        4 kBMMUPageSize:           4 kBRss:                   0 kBPss:                   0 kBShared_Clean:          0 kBShared_Dirty:          0 kBPrivate_Clean:         0 kBPrivate_Dirty:         0 kBReferenced:            0 kBAnonymous:             0 kBLazyFree:              0 kBAnonHugePages:         0 kBShmemPmdMapped:        0 kBFilePmdMapped:         0 kBShared_Hugetlb:        0 kBPrivate_Hugetlb:       0 kBSwap:                  0 kBSwapPss:               0 kBLocked:                0 kBTHPeligible:0VmFlags: rd wr sh mr mw me ms pf io dc dd hg
    
  • И воспользовались данным shell-скриптом, предварительно поставив SGX-драйвер (все действия осуществлялись внутри ВМ):

    [root@sgx-vm ~]# cat check_sgx.sh#!/bin/bashMETRICS="sgx_nr_total_epc_pages \    sgx_nr_free_pages \    sgx_nr_low_pages \    sgx_nr_high_pages \    sgx_nr_marked_old \    sgx_nr_evicted \    sgx_nr_alloc_pages \    "MODPATH="/sys/module/isgx/parameters/"for metric in $METRICS ; do    echo "$metric= `cat $MODPATH/$metric`"done[root@sgx-vm ~]# curl -fsSL https://raw.githubusercontent.com/scontain/SH/master/install_sgx_driver.sh | bash -s - install -p metrics -p page0[root@sgx-vm ~]# ./check_sgx.shsgx_nr_total_epc_pages= 2048sgx_nr_free_pages= 2048sgx_nr_low_pages= 32sgx_nr_high_pages= 64sgx_nr_marked_old= 0sgx_nr_evicted= 0sgx_nr_alloc_pages= 0
    

    Стоит учитывать, что, если одна страница занимает 4 КиБ, то для 2048 страниц требуется 8 МиБ (2048 x 4 = 8192).

Трудности разработки и их преодоление


Отсутствие какой-либо технической документации по интеграции Intel SGX в OpenStack было нашей основной трудностью на момент внедрения. Поиск привел нас к статье проекта SecureCloud, где был представлен способ управления виртуальными машинами с анклавами SGX.

Найденная информация помогла понять, над чем именно нам предстоит работать. В результате мы сформировали следующие задачи:

  1. Добиться от сервиса OpenStack Nova генерации XML-файла с дополнительными параметрами для виртуальных машин с поддержкой Intel SGX.
  2. Написать фильтр планировщика OpenStack Nova с целью определения доступной памяти для анклавов на вычислительных узлах и осуществления некоторых других проверок.

Их выполнения было достаточно для интеграции Intel SGX в наше публичное облако.

Кроме того, мы дописали сбор статистики с учетом EPC:

# openstack usage showUsage from 2020-11-04 to 2020-12-03 on project a968da75bcab4943a7beb4009b8ccb4a:+---------------+--------------+| Field         | Value        |+---------------+--------------+| CPU Hours     | 47157.6      || Disk GB-Hours | 251328.19    || EPC MB-Hours  | 26880.02     || RAM MB-Hours  | 117222622.62 || Servers       | 23           |+---------------+--------------+


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



Научившись выделять виртуальные машины с поддержкой Intel SGX, мы использовали платформу SCONE компании Scontain, чтобы обеспечить возможность безопасного запуска контейнеризированных приложений в случае угроз со стороны привилегированного программного обеспечения. При использовании данного решения для прозрачной защиты файловых систем в средах Docker, Kubernetes и Rancher достаточно наличия процессора Intel с поддержкой SGX и драйвера Linux SGX.

Запуск каждого из контейнеров возможен лишь при наличии файла конфигурации, создаваемого клиентским расширением платформы SCONE. В нём содержатся ключи шифрования, аргументы приложения и переменные среды. Файлы, сетевой трафик и стандартные потоки ввода/вывода (stdin/stdout) прозрачно зашифрованы и недоступны даже для пользователей с правами root.
Платформа SCONE оснащена встроенной службой аттестации и конфигурации, проверяющей приложения на соответствие принятой политике безопасности. Она генерирует приватные ключи и сертификаты, которые должны быть доступны только в пределах анклава. Конфиденциальность и целостность данных в процессе их передачи обеспечиваются криптографическим протоколом TLS.

С помощью драйвера SGX для каждого анклава в виртуальном адресном пространстве резервируется до 64 ГБ памяти. Платформа SCONE поддерживает языки программирования C/C++/C#/Rust/Go/Python/Java. За счёт специального компилятора исходный код автоматически (без необходимости дополнительных модификаций) подготавливается к использованию совместно с Intel SGX.

Кейс Aggregion


Завершив все необходимые работы по интеграции Intel SGX, мы подключили к нашему публичному облаку платформу управления распределёнными данными компании Aggregion.

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

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

Принципы безопасной работы на платформе Aggregion. В контуре каждого поставщика чувствительные данные изолируются в анклавы Intel SGX, которые фактически представляют собой чёрные ящики: что происходит внутри, недоступно никому, в том числе и провайдеру облачной инфраструктуры. Проверка первоначального состояния анклава и возможности его использования для хранения конфиденциальной информации осуществляется за счёт удалённой аттестации, когда MrEnclave определяет хеш-значение.

Потенциальная польза для клиентов. Комбинирование баз данных нескольких поставщиков позволяет повысить эффективность совместных рекламных кампаний. При выделении целевой аудитории по заданным параметрам мэтчинг (сопоставление) сегментов выполняется непосредственно внутри контейнеров с поддержкой анклавов Intel SGX. За пределы выводится только конечный результат: например, численность пользователей, соответствующих выбранным атрибутам. Аналогичным образом оценивается эффективность проведенных кампаний: в анклавы выгружаются данные о рекламных показах и совершённых продажах для вычисления прироста покупок целевой группы относительно контрольной, который и выдаётся наружу для дальнейшего использования.



Выводы


Мы понимаем, что Intel SGX не является панацеей по защите данных и можно найти ряд статей, порицающих эту технологию, в том числе и на Хабре. Периодически появляются сообщения об атаках, способных извлечь конфиденциальные данные из анклавов: так, в 2018 году бреши в SGX пробили Meltdown и Spectre, в 2020 году SGAxe и CrossTalk. В свою очередь компания Intel устраняет выявленные уязвимости с помощью обновлений микрокода процессоров.

Почему же мы всё-таки решили внедрить данную технологию? Мы видим в применении Intel SGX возможность сократить потенциальную область кибератак за счёт создания дополнительного контура защиты облачной инфраструктуры G-Core Labs наряду с уже задействованными технологиями информационной безопасности и тем самым повысить доверие наших пользователей к хранению и обработке конфиденциальных данных. Надеемся, что в будущем нам ещё предстоит поделиться с вами успешными клиентскими кейсами, хотя и не берёмся утверждать, что наши статьи не будут основаны на историях обнаружения и устранения новых уязвимостей. А пока предлагаем вам поделиться своими методами по защите чувствительных данных в комментариях.
Подробнее..

Парадокс доверия облачным решениям три сценария, в которых ключи шифрования хранятся не в облаке

16.03.2021 18:09:12 | Автор: admin

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

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

Сценарий 1. Данные, которые лучше не хранить в облаке

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

В каждой сфере и в каждой компании есть данные, которые попадают в эту категорию. Например, в одной международной организации действуют очень строгие правила в отношении хранения ключей. Чтобы использовать для этого облачные платформы, ей необходимо получать специальное разрешение. Другая организация руководствуется собственным вариантом стандарта PCI DSS. Кроме того, у нее есть внутренние требования по управлению главными ключами с помощью аппаратного модуля безопасности в соответствии со стандартом FIPS 140-2 (уровень 3).

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

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

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

Сценарий 2. Требования местного законодательства и проблемы, связанные с ними

С развитием облачных технологий порядок их использования во многом зависит от требований законодательства в тех или иных странах. В этом сценарии организация хочет использовать облачную платформу из другой страны, но ее не устраивает, что у поставщика услуг будут ключи шифрования для всех данных. Если в том же облаке будут обрабатываться незашифрованные данные, поставщик услуг получит доступ и к ним. Некоторые организации также не хотят хранить ключи на криптографических устройствах (например, аппаратных модулях безопасности), управляемых поставщиком услуг (физически или с помощью ПО). Они справедливо полагают, что такой подход не соответствует принципу Hold Your Own Key (HYOK).

Проблемы могут быть связаны как с требованиями законодательства, так и с описанными выше причинами. Кроме того, регулирующие органы ЕС, России, Японии, Индии, Бразилии и других стран постоянно принимают новые акты, запрещающие хранить незашифрованные данные и/или ключи шифрования за рубежом. В качестве примеров можно привести отраслевые стандарты (например, TISAX в Европе), которые указывают или подразумевают, что у поставщика облачных услуг ни при каких обстоятельствах не может быть доступа к данным, а во многих случаях и к ключам шифрования. Однакопредварительные результаты опросауказывают на то, что возможны варианты, когда ключи шифрования находятся только у клиента (в то время как зашифрованные данные могут храниться за рубежом).

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

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

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

Сценарий 3. Централизованное управление ключами шифрования

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

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

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

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

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

Дальнейшие действия

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

  • Прочитайтеэту статьюоб управлении ключами шифрования в облаке.

  • Оцените риски для данных с учетом уязвимостей, нормативных требований, отношений между странами ит.д.

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

Ознакомьтесь ссервисамиотGoogle Cloud EKM (External Key Manager) и партнеров (Ionic, Fortanix, Thales ит.д.), которые позволяют перенести управление ключами из облака в локальную среду.


Напоминаем что при первой регистрации в Google Cloud: вам доступны бонусы на сумму 300 долларов США, а более 20 бесплатных продуктов доступны всегда. Подробнее поспециальной ссылке.

А так же выражаем благодарность за помощь в подготовке материала коллегам: Антон Чувакин, Иль Сон Ли,Звиад Кардава

Подробнее..

Как мы добавляли CPU флаги Intel SGX в libvirt

22.04.2021 14:23:53 | Автор: admin
С момента публикации статьи о внедрении Intel SGX в наше публичное облако прошло несколько месяцев. За это время решение было существенно доработано. В основном улучшения касаются устранения мелких багов и доработок для нашего же удобства.



Есть, однако, один момент, о котором хотелось бы рассказать подробнее.



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

Первые попытки


Ещё раз повторим формулировку задачи: нам требовалось передать параметры поддержки SGX в конфигурационный XML-файл виртуальной машины. Когда мы только начинали эту задачу решать, в OpenStack и libvirt поддержки SGX не было, соответственно, передать их в XML виртуальной машины нативно было невозможно.

Сначала мы попытались решить эту проблему путем добавления блока Qemu command-line в скрипт подключение к гипервизору через libvirt, как это описано в руководстве Intel для разработчиков:

<qemu:commandline>     <qemu:arg value='-cpu'/>     <qemu:arg value='host,+sgx,+sgxlc'/>     <qemu:arg value='-object'/>     <qemu:arg value='memory-backend-epc,id=mem1,size=''' + epc + '''M,prealloc'/>     <qemu:arg value='-sgx-epc'/>     <qemu:arg value='id=epc1,memdev=mem1'/></qemu:commandline>

Но после этого у виртуальной машины добавилась вторая процессорная опция:

[root@compute-sgx ~] cat /proc/$PID/cmdline |xargs -0 printf "%s\n" |awk '/cpu/ { getline x; print $0 RS x; }'-cpuSkylake-Client-IBRS-cpuhost,+sgx,+sgxlc

Первая опция задавалась штатно, а вторая была непосредственно нами добавлена в блоке Qemu command-line. Это приводило к неудобству при выборе модели эмуляции процессора: какую бы из моделей процессоров мы ни подставляли в cpu_model в конфигурационном файле вычислительного узла Nova, в виртуальной машине мы видели отображение хостового процессора.

Как решить эту проблему?

В поисках ответа мы сначала пробовали экспериментировать со строкой <qemu:arg value='host,+sgx,+sgxlc'/> и пытаться передать в неё модель процессора, но это не отменяло дублирование этой опции после запуска ВМ. Тогда было решено задействовать libvirt для присвоения флагов CPU и управлять ими через конфигурационный файл Novы вычислительного узла с помощью параметра cpu_model_extra_flags.

Задача оказалась сложнее, чем мы предполагали: нам потребовалось изучить инструкцию Intel IA-32 CPUID, а также найти информацию о нужных регистрах и битах в документации Intel об SGX.

Дальнейший поиск: углубляемся в libvirt


В документации для разработчиков сервиса Nova указано, что маппинг CPU флагов должен поддерживаться самим libvirtом.

Мы нашли файл, в котором описываются все флаги CPU это x86_features.xml (актуален с версии libvirt 4.7.0). Ознакомившись с этим файлом, предположили (как выяснилось потом, ошибочно), что нам нужно лишь получить hex-адреса необходимых регистров в 7-м листе с помощью утилиты cpuid. Из документации Intel мы узнали, в каких регистрах вызываются нужные нам инструкции: sgx находится в EBX регистре, а sgxlc в ECX.

[root@compute-sgx ~] cpuid -l 7 -1 |grep SGX      SGX: Software Guard Extensions supported = true      SGX_LC: SGX launch config supported      = true[root@compute-sgx ~] cpuid -l 7 -1 -rCPU:   0x00000007 0x00: eax=0x00000000 ebx=0x029c6fbf ecx=0x40000000 edx=0xbc000600

После добавления флагов sgx и sgxlc со значениями, полученными с помощью утилиты cpuid, мы получили следующее сообщение об ошибке:

error : x86Compute:1952 : out of memory

Сообщение, прямо говоря, не очень информативное. Чтобы хоть как-то понять, в чём проблема, мы завели issue в gitlabe libvirta. Разработчики libvirta заметили, что выводится неверная ошибка и исправили ее, указав на то, что libvirt не может найти нужную инструкцию, которую мы вызываем и предположили, где мы можем ошибаться. Но понять, что именно нам нужно было указывать, чтобы ошибки не было, нам так и не удалось.

Пришлось зарыться в источники и изучать, это заняло много времени. Разобраться удалось лишь после изучения кода в модифицированном Qemu от Intel:

    [FEAT_7_0_EBX] = {        .type = CPUID_FEATURE_WORD,        .feat_names = {            "fsgsbase", "tsc-adjust", "sgx", "bmi1",            "hle", "avx2", NULL, "smep",            "bmi2", "erms", "invpcid", "rtm",            NULL, NULL, "mpx", NULL,            "avx512f", "avx512dq", "rdseed", "adx",            "smap", "avx512ifma", "pcommit", "clflushopt",            "clwb", "intel-pt", "avx512pf", "avx512er",            "avx512cd", "sha-ni", "avx512bw", "avx512vl",        },        .cpuid = {            .eax = 7,            .needs_ecx = true, .ecx = 0,            .reg = R_EBX,        },        .tcg_features = TCG_7_0_EBX_FEATURES,    },    [FEAT_7_0_ECX] = {        .type = CPUID_FEATURE_WORD,        .feat_names = {            NULL, "avx512vbmi", "umip", "pku",            NULL /* ospke */, "waitpkg", "avx512vbmi2", NULL,            "gfni", "vaes", "vpclmulqdq", "avx512vnni",            "avx512bitalg", NULL, "avx512-vpopcntdq", NULL,            "la57", NULL, NULL, NULL,            NULL, NULL, "rdpid", NULL,            NULL, "cldemote", NULL, "movdiri",            "movdir64b", NULL, "sgxlc", NULL,        },        .cpuid = {            .eax = 7,            .needs_ecx = true, .ecx = 0,            .reg = R_ECX,        },

Из приведенного листинга видно, что в блоках .feat_names побитово (от 0 до 31) перечисляются инструкции из EBX/ECX-регистров 7-го листа; если инструкция не поддерживается Qemu или этот бит зарезервирован, то он заполняется значением NULL. Благодаря этому примеру мы сделали такое предположение: возможно, нужно указывать не hex-адрес необходимого регистра в libvirt, а конкретно бит этой инструкции. Проще это понять, ознакомившись с таблицей из Википедии. Слева указан бит и три регистра. Находим в ней нашу инструкцию sgx. В таблице она указана под вторым битом в регистре EBX:



Далее сверяем расположение этой инструкции в коде Qemu. Как мы видим, она указана третьей в списке feat_names, но это потому, что нумерация битов начинается от 0:

    [FEAT_7_0_EBX] = {        .type = CPUID_FEATURE_WORD,        .feat_names = {            "fsgsbase", "tsc-adjust", "sgx", "bmi1",

Можно посмотреть другие инструкции в этой таблице и убедиться при подсчете от 0, что они находятся под своим битом в приведенном листинге. Например: fsgsbase идет под 0 битом регистра EBX, и он указан в этом списке первым.

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

Мы стали более подробно разбираться в архитектуре 32-битных процессоров и увидели, что в таких процессорах имеются листы, которые содержат основные 4 регистра: EAX, EBX, ECX, EDX. Каждый из этих регистров содержит по 32 бита, отведенных под определенный набор инструкций CPU. Бит является степенью двойки и чаще всего может передаваться программе в hex-формате, как это сделано в libvirt.

Для лучшего понимания, рассмотрим еще пример c флагом вложенной виртуализации VMX из файла x86_features.xml, используемый libvirtом:

<feature name= 'vmx'>
<cpuid eax_in='0x01' ecx='0x00000020'/> # 25 = 3210 = 2016
</feature>

Обращение к этой инструкции осуществляется в 1-м листе к регистру ECX под 5 битом и убедиться в этом можно посмотрев таблицу Feature Information в Википедии.

Разобравшись с этим и сформировав понимание, как в итоге добавляются флаги в libvirt, мы решили добавить и другие флаги SGX (помимо основных: sgx и sgxlc), которые имелись в модифицированном Qemu:

[root@compute-sgx ~] /usr/libexec/qemu-kvm -cpu help |xargs printf '%s\n' |grep sgxsgxsgx-debugsgx-exinfosgx-ksssgx-mode64sgx-provisionkeysgx-tokenkeysgx1sgx2sgxlc

Некоторые из этих флагов являются уже не инструкциями, а атрибутами структуры управления данными анклавов (SECS); подробнее об этом можно прочитать в документации Intel. В ней мы нашли, что необходимый нам набор атрибутов SGX находится в листе 0x12 в подлисте 1:

[root@compute-sgx ~] cpuid -l 0x12 -s 1 -1CPU:   SGX attributes (0x12/1):      ECREATE SECS.ATTRIBUTES valid bit mask = 0x000000000000001f0000000000000036



На скриншоте таблицы 38-3 можно найти необходимые нам биты атрибутов, которые мы укажем позже в качестве флагов в libvirt: sgx-debug, sgx-mode64, sgx-provisionkey, sgx-tokenkey. Они находятся под битами 1, 2, 4 и 5.

Так же мы поняли из ответа в нашем issue: libvirt имеет макрос проверки флагов на предмет их поддержки непосредственно процессором вычислительного узла. Это означает то, что недостаточно указать в документе x86_features.xml необходимые листы, биты и регистры, если сам libvirt не поддерживает лист набора инструкций. Но к нашему счастью выяснилось, что в коде libvirta имеется возможность работы с этим листом:

/* Leaf 0x12: SGX capability enumeration * * Sub leaves 0 and 1 is supported if ebx[2] from leaf 0x7 (SGX) is set. * Sub leaves n >= 2 are valid as long as eax[3:0] != 0. */static intcpuidSetLeaf12(virCPUDataPtr data,               virCPUx86DataItemPtr subLeaf0){    virCPUx86DataItem item = CPUID(.eax_in = 0x7);    virCPUx86CPUIDPtr cpuid = &item.data.cpuid;    virCPUx86DataItemPtr leaf7;    if (!(leaf7 = virCPUx86DataGet(&data->data.x86, &item)) ||        !(leaf7->data.cpuid.ebx & (1 << 2)))        return 0;    if (virCPUx86DataAdd(data, subLeaf0) < 0)        return -1;    cpuid->eax_in = 0x12;    cpuid->ecx_in = 1;    cpuidCall(cpuid);    if (virCPUx86DataAdd(data, &item) < 0)        return -1;    cpuid->ecx_in = 2;    cpuidCall(cpuid);    while (cpuid->eax & 0xf) {        if (virCPUx86DataAdd(data, &item) < 0)            return -1;        cpuid->ecx_in++;        cpuidCall(cpuid);    }    return 0;}

Из этого листинга видно, что при обращении к 2-му биту EBX регистра 7-го листа (т.е. к инструкции SGX), libvirt может задействовать лист 0x12 для проверки имеющихся атрибутов в подлистах 0, 1 и 2.

Заключение


После проделанного исследования мы поняли, как правильно дополнить файл x86_features.xml. Мы перевели необходимые биты в hex-формат и вот что у нас получилось:

  <!-- SGX features -->  <feature name='sgx'>    <cpuid eax_in='0x07' ecx_in='0x00' ebx='0x00000004'/>  </feature>  <feature name='sgxlc'>    <cpuid eax_in='0x07' ecx_in='0x00' ecx='0x40000000'/>  </feature>  <feature name='sgx1'>    <cpuid eax_in='0x12' ecx_in='0x00' eax='0x00000001'/>  </feature>  <feature name='sgx-debug'>    <cpuid eax_in='0x12' ecx_in='0x01' eax='0x00000002'/>  </feature>  <feature name='sgx-mode64'>    <cpuid eax_in='0x12' ecx_in='0x01' eax='0x00000004'/>  </feature>  <feature name='sgx-provisionkey'>    <cpuid eax_in='0x12' ecx_in='0x01' eax='0x00000010'/>  </feature>  <feature name='sgx-tokenkey'>    <cpuid eax_in='0x12' ecx_in='0x01' eax='0x00000020'/>  </feature>

Теперь для передачи этих флагов виртуальной машине мы можем указать их в конфигурационном файле Nova с помощью cpu_model_extra_flags:

[root@compute-sgx nova] grep cpu_mode nova.confcpu_mode = customcpu_model = Skylake-Client-IBRScpu_model_extra_flags = sgx,sgxlc,sgx1,sgx-provisionkey,sgx-tokenkey,sgx-debug,sgx-mode64[root@compute-sgx ~] cat /proc/$PID/cmdline |xargs -0 printf "%s\n" |awk '/cpu/ { getline x; print $0 RS x; }'-cpuSkylake-Client-IBRS,sgx=on,sgx-mode64=on,sgx-provisionkey=on,sgx-tokenkey=on,sgx1=on,sgxlc=on

Проделав сложный путь, мы научились добавлять в libvirt поддержку флагов SGX. Это нам помогло решить проблему дублирования процессорных опций в XML-файле виртуальной машины. Полученный опыт мы будем использовать и в дальнейшей работе: если в процессорах Intel или AMD появится новый набор инструкций, мы сможем их аналогичным образом добавить в libvirt. Знакомство с инструкцией CPUID так же будет нам полезно при написании своих собственных решений.

Если у вас есть вопросы добро пожаловать в комментарии, постараемся ответить. А если у вас есть, что дополнить тем более пишите, будем очень признательны.
Подробнее..

Создать кластер за 120 секунд открытый курс по Managed Kubernetes

18.05.2021 12:12:57 | Автор: admin


Учебный центр Слёрм и Selectel совместными усилиями создали курс по Managed Kubernetes, доступ к урокам предоставляется бесплатно.

Спикеры курса познакомят с Managed Kubernetes Selectel и научат работать с кластерами.
Покажут популярные кейсы использования, разберут мультизональный кластер и расскажут, как рассчитать стоимость проекта.

По окончании курса вы сможете решать главную задачу организация контейнерной инфраструктуры.

Кому подойдёт курс


  • Администраторам, готовым приобрести практический опыт использования Kubernetes.
  • Инженерам, оптимизирующим затраты на рутинные задачи по разворачиванию и поддержке кластеров Kubernetes.
  • Разработчикам, желающим получать контейнерную инфраструктуру быстрее.

Спикеры


Марсель Ибраев, Chief Technology Officer, Слёрм
Инженер с 8-летним стажем,
Certified Kubernetes Administrator,
Внедрения Kubernetes для клиентов Southbridge.

Алексей Богданов, Product manager, Selectel Managed Kubernetes
Развиваю системы и людей больше трёх лет;
Работаю над продуктами Selectel: Managed Kubernetes, Serverless, CRaaS, API Gateway и MQaaS;
Рассказываю на вебинарах о Managed Kubernetes.

Формат курса


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

Во вводном модуле курса каждый студент получит промокод на 3 000 рублей для выполнения практических заданий в сервисе Managed Kubernetes Selectel.

Программа


Тема 1: Вводный модуль

  • О Selectel, курсе и промокоде

Тема 2: Знакомство с Managed Kubernetes Selectel

  • Managed Kubernetes VS bare-metal Kubernetes
  • Особенности и возможности Managed Kubernetes Selectel

Тема 3: Развёртывание своего кластера через Managed Kubernetes

  • Создание кластера из личного кабинета
  • Создание кластера через Terraform
  • Создание кластера через API Selectel

Практика: развернуть кластер одним из трёх изученных способов, настроить управление кластером через Kubectl со своего локального компьютера.

Тема 4: Практические кейсы по использованию Managed Kubernetes

  • Подключение сетевых дисков
  • Работа с сетевыми абстракциями
  • Настройки безопасности
  • Регламентные работы
  • Кастомизация кластера
  • Мониторинг и логирование
  • Настройка пользователей и конфига kubectl
  • Taint, Labels
  • Добавление кастомных зон в CoreDNS

Практика: Поднять отказоустойчивый кластер с 3 мастер-нодами и 3 воркер-нодами и 2 нодами с ролью ингресс в разных зонах. Установить ингресс-контроллер через Helm, настроить его согласно best practices.
Создать кластер Manager PostgreSQL и настроить взаимодействие кластера Kubernetes и кластера PostgreSQL.
Установить в кластер Kubernetes приложение RabbitMQ. Запустить его в 3 реплики, настроить персистентное хранение данных с помощью PV/PVC.

Тема 5: Мультизональный кластер Kubernetes

  • Создание мультизонального кластера Kubernetes в панели управления.

Тема 6: Поиск неисправностей и дебаг

  • Разберём способы поиска причин неисправностей и их устранения.

Тема 7: Ценовая политика

  • Как рассчитать стоимость проекта?


Managed Kubernetes Selectel


Kubernetes это система оркестрации контейнеров. Managed Kubernetes от Selectel упрощает процесс развёртывания, масштабирования и обслуживания контейнерной инфраструктуры. Обновлением версий, сертификатов, безопасностью и работоспособностью Control Plane Kubernetes занимается Selectel.

Сервис работает на базе Облачной платформы Selectel и использует её ресурсы для рабочих нод кластера: серверы, балансировщики, сети, диски.

В Managed Kubernetes можно управлять кластерами с помощью панели управления, Terraform или API сервиса. Создать кластер в Managed Kubernetes Selectel за две минуты реальность.

Начать учиться


Доступ откроется после регистрации автоматически: slurm.club/3tT7c2Q
Подробнее..

Перевод Введение в паттерн распределенной трассировки

25.01.2021 02:06:31 | Автор: admin

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

При работе с крупномасштабной системой очень важно следить за ключевыми показателями этой системы, работоспособностью приложений и достаточным объемом данных, чтобы иметь возможность быстро отслеживать и устранять проблемы. Пребывание в ОБЛАЧНОЙ среде, такой как AWS, Google Cloud, Azure, еще больше усугубляет проблему и затрудняет обнаружение, устранение и локализацию проблем из-за динамического характера инфраструктуры (вертикальное масштабирование, временные машины, динамические IP-адреса и т. д.).

Базис наблюдаемости:

  • Метрики - метрики приложений, метрики хоста/системы, метрики сети и т. д.

  • Логи (журналы) - логи приложений и поддерживающей инфраструктуры

  • Трейсы (трассировки) - отслеживание прохождения запроса через распределенную систему

В этой статье я сосредоточусь на двух аспектах наблюдаемости: логах (только сгенерированных приложением) и трейсах.

Логи

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

Splunk

Datadog

Logstash

Fluentd

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

Кореляция логов между микросервисами

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

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

Рисунок 1. Централизованное логирование.Рисунок 1. Централизованное логирование.

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

Рисунок 2: Конфигурация и образец лога Log4J2Рисунок 2: Конфигурация и образец лога Log4J2Рисунок 3: Фильтры запросов по UUID или UserIdРисунок 3: Фильтры запросов по UUID или UserId

Трассировка

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

  1. Путь запроса через распределенную систему.

  2. Задержка запроса при каждой пересылке/вызове (например, от одного сервиса к другому).

Ниже приведен пример трассировки для запроса, взаимодействующего с двумя микросервисами (сервисом-аукционом рекламы и сервисом-интегратором рекламы).

Рисунок 4. ТрассировкаРисунок 4. Трассировка

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

Составляющие трейса

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

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

Корреляция логов и трейсов

В итоге мы можем фильтровать логи по userId или другому уникальному идентификатору (например, сгенерированному UUID) и можем отслеживать по трейсам производительность/поведение отдельного запроса. Было бы неплохо, если бы мы могли связать это воедино и иметь возможность сопоставлять логи и трейсы для конкретного запроса!!

Наличие такой корреляции между логами и запросами позволяет:

  1. Сопоставлять метрики производительности напрямую с логами.

  2. Направлять в систему специальный запрос для устранения неполадок.

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

Реализация распределенной трассировки с помощью корреляции логов и трейсов

ПОДХОД #1: Инструментация с помощью сторонних решений, таких как DATADOG

Ссылка: DataDog APM

При таком подходе мы инструментируем сервисы в распределенных системах с DataDog APM (application performance monitors - системы мониторинга производительности приложений). Datadog выполняет 100%-ную трассировку запросов, а также может собирать логи, создаваемые вашими приложениями.

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

Рисунок 6: Инструментация приложения с DataDogРисунок 6: Инструментация приложения с DataDogРисунок 7: Корреляция логов и трейсов в DataDogРисунок 7: Корреляция логов и трейсов в DataDog

ПОДХОД #2: ZIPKINS, CLOUD-SLEUTH СО SPRING BOOT

Ссылка:

Zipkins, Cloud Sleuth

Преимущества:

  1. Полная интеграция в SPRING boot

  2. Простота в использовании

  3. Трейсы можно визуализировать с помощью пользовательского интерфейса Zipkins.

  4. Поддерживает стандарты OpenTracing через внешние библиотеки.

  5. Поддерживает корреляцию логов через контексты Log4j2 MDC.

Недостатки:

  1. Нет решения для автоматического сбора логов, связанных с трейсами. Нам придется самостоятельно отправлять логи в ElasticSearch и выполнять поиск, используя идентификаторы трейсов, сгенерированные cloud-sleuth (как заголовок X-B3-TraceId).

Дизайн:

Рисунок 8: Zipkins, Cloud Sleuth и Spring Boot.Рисунок 8: Zipkins, Cloud Sleuth и Spring Boot.

ПОДХОД #3: AMAZON XRAY

Ссылка: AmazonXRAY

Преимущества:

  1. Нативно поддерживает все ресурсы AWS, что очень хорошо, если ваши распределенные сервисы развернуты и работают в AWS

  2. Балансировщики нагрузки AWS автоматически генерируют идентификаторы (REQUEST ID) для каждого входящего запроса, что освобождает приложение от этой заботы. (Ссылка: https://docs.aws.amazon.com/elasticloadbalancing/latest/application/load-balancer-request-tracing.html)

  3. Позволяет выполнять трассировку на всем пути от шлюза API до балансировщика нагрузки, сервиса и других зависимых ресурсов AWS.

  4. Реализует корреляцию логов с помощью логов в CLOUDWATCH logs

Недостатки:

  1. Cloudwatch log может стать очень дорогими при большом объеме логов

ПОДХОД #4: JAGER

Ссылка: Jager

Преимущества:

  1. Поддерживает opentracing по умолчанию

  2. Имеет библиотеки, которые работают со Spring

  3. Поддерживает Jager Agent, который можно установить в качестве средства распространения трейсов и логов.

Недостатки:

С точки зрения обслуживания и настройки инфраструктуры достаточно сложен.

ЗАКЛЮЧЕНИЕ

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


Перевод статьи подготовлен в преддверии старта курса "Архитектура и шаблоны проектирования". Узнать подробнее о курсе.


ЗАБРАТЬ СКИДКУ

Подробнее..

Перевод Spring Cloud и Spring Boot. Часть 1 использование Eureka Server

26.01.2021 20:09:19 | Автор: admin

Будущих студентов курса Разработчик на Spring Framework и всех желающих приглашаем на открытый онлайн-урок по теме Введение в облака, создание кластера в Mongo DB Atlas018. Участники вместе с преподавателем-экспертом поговорят о видах облаков и настроят бесплатный Mongo DB кластер для своих проектов.

А сейчас делимся с вами традиционным переводом статьи.


В этой статье мы поговорим о том, как установить и настроить службу обнаружения (service discovery) для Java-микросервисов.

Что такое Eureka Server?

Eureka Server это service discovery (обнаружение сервисов) для ваших микросервисов. Клиентские приложения могут самостоятельно регистрироваться в нем, а другие микросервисы могут обращаться к Eureka Server для поиска необходимых им микросервисов.

Eureka Server также известен как Discovery Server и содержит такую информацию как IP-адрес и порт микросервиса.

Для создания приложения с Eureka Server необходимо в pom.xml добавить указанную ниже зависимость.

<dependency>  <groupId>org.springframework.cloud</groupId>  <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId></dependency>

Запускаем Eureka Server

Перейдите на https://start.spring.io и создайте шаблон проекта. Укажите метаданные, такие как Group, Artifact, и добавьте указанные ниже зависимости / модули. Нажмите "Generate Project" и загрузите проект в zip-файле. Далее разархивируйте его и импортируйте в IDE как Maven-проект.

  • Eureka Server

  • Web

  • Actuator

Проверьте, что pom.xml выглядит следующим образом:

<?xml version="1.0" encoding="UTF-8"?><project xmlns="http://personeltest.ru/away/maven.apache.org/POM/4.0.0" xmlns:xsi="http://personeltest.ru/away/www.w3.org/2001/XMLSchema-instance"        xsi:schemaLocation="http://personeltest.ru/away/maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">   <modelVersion>4.0.0</modelVersion>   <parent>       <groupId>org.springframework.boot</groupId>       <artifactId>spring-boot-starter-parent</artifactId>       <version>2.0.7.RELEASE</version>       <relativePath/> <!-- lookup parent from repository -->   </parent>   <groupId>com.example.eureka.server</groupId>   <artifactId>eureka-server</artifactId>   <version>0.0.1-SNAPSHOT</version>   <name>eureka-server</name>   <description>Demo project for Spring Boot</description>   <properties>       <java.version>1.8</java.version>       <spring-cloud.version>Finchley.SR2</spring-cloud.version>   </properties>   <dependencies>       <dependency>           <groupId>org.springframework.boot</groupId>           <artifactId>spring-boot-starter-actuator</artifactId>       </dependency>       <dependency>           <groupId>org.springframework.boot</groupId>           <artifactId>spring-boot-starter-web</artifactId>       </dependency>       <dependency>           <groupId>org.springframework.cloud</groupId>           <artifactId>spring-cloud-starter-netflix-eureka-server</artifactId>       </dependency>       <dependency>           <groupId>org.springframework.boot</groupId>           <artifactId>spring-boot-starter-test</artifactId>           <scope>test</scope>       </dependency>   </dependencies>   <dependencyManagement>       <dependencies>           <dependency>               <groupId>org.springframework.cloud</groupId>               <artifactId>spring-cloud-dependencies</artifactId>               <version>${spring-cloud.version}</version>               <type>pom</type>               <scope>import</scope>           </dependency>       </dependencies>   </dependencyManagement>   <build>       <plugins>           <plugin>               <groupId>org.springframework.boot</groupId>               <artifactId>spring-boot-maven-plugin</artifactId>           </plugin>       </plugins>   </build></project>

Теперь откройте файл EurekaServerApplication.java и добавьте для класса аннотацию @EnableEurekaServer, как показано ниже.

package com.example.eureka.server.eurekaserver;import org.springframework.boot.SpringApplication;import org.springframework.boot.autoconfigure.SpringBootApplication;import org.springframework.cloud.netflix.eureka.server.EnableEurekaServer;@SpringBootApplication@EnableEurekaServerpublic class EurekaServerApplication {  public static void main(String[] args) {     SpringApplication.run(EurekaServerApplication.class, args);  }}

Добавьте в application.properties, расположенный в src/main/resources, следующие параметры.

spring.application.name=eureka-serverserver.port=8761eureka.client.register-with-eureka=falseeureka.client.fetch-registry=false
  • spring.application.name уникальное имя для вашего приложения.

  • server.port порт, на котором будет запущено ваше приложение, мы будем использовать порт по умолчанию (8761).

  • eureka.client.register-with-eureka определяет, регистрируется ли сервис как клиент на Eureka Server.

  • eureka.client.fetch-registry получать или нет информацию о зарегистрированных клиентах.

Запустите сервер Eureka как Java-приложение и перейдите по адресу http://localhost:8761/

Вы увидите, что Eureka Server запущен и работает, но в нем еще нет зарегистрированных приложений.

Регистрация клиентского приложения в Eureka Server

Перейдите на https://start.spring.io и создайте шаблон проекта. Укажите метаданные, такие как Group, Artifact, и добавьте указанные ниже зависимости / модули. Нажмите "Generate Project" и загрузите проект в zip-файле. Далее разархивируйте его и импортируйте в IDE как Maven-проект.

  • DevTools

  • Actuator

  • Discovery Client

Проверьте, что ваш pom.xml выглядит следующим образом:

<?xml version="1.0" encoding="UTF-8"?><project xmlns="http://personeltest.ru/away/maven.apache.org/POM/4.0.0" xmlns:xsi="http://personeltest.ru/away/www.w3.org/2001/XMLSchema-instance"      xsi:schemaLocation="http://personeltest.ru/away/maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">  <modelVersion>4.0.0</modelVersion>  <parent>     <groupId>org.springframework.boot</groupId>     <artifactId>spring-boot-starter-parent</artifactId>     <version>2.0.7.RELEASE</version>     <relativePath/> <!-- lookup parent from repository -->  </parent>  <groupId>com.example.eureka.client</groupId>  <artifactId>EurekaClientApplication</artifactId>  <version>0.0.1-SNAPSHOT</version>  <name>EurekaClientApplication</name>  <description>Demo project for Spring Boot</description>   <properties>     <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>     <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>     <java.version>1.8</java.version>     <spring-cloud.version>Finchley.SR2</spring-cloud.version>  </properties>   <dependencies>     <dependency>        <groupId>org.springframework.boot</groupId>        <artifactId>spring-boot-starter-web</artifactId>     </dependency>     <dependency>        <groupId>org.springframework.boot</groupId>        <artifactId>spring-boot-starter-actuator</artifactId>     </dependency>     <dependency>        <groupId>org.springframework.boot</groupId>        <artifactId>spring-boot-devtools</artifactId>        <scope>runtime</scope>     </dependency>     <dependency>        <groupId>org.springframework.boot</groupId>        <artifactId>spring-boot-starter-test</artifactId>        <scope>test</scope>     </dependency>     <dependency>        <groupId>org.springframework.cloud</groupId>        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>     </dependency>  </dependencies>   <dependencyManagement>     <dependencies>        <dependency>           <groupId>org.springframework.cloud</groupId>           <artifactId>spring-cloud-dependencies</artifactId>           <version>${spring-cloud.version}</version>           <type>pom</type>           <scope>import</scope>        </dependency>     </dependencies>  </dependencyManagement>  <build>     <plugins>        <plugin>           <groupId>org.springframework.boot</groupId>           <artifactId>spring-boot-maven-plugin</artifactId>        </plugin>     </plugins>  </build></project>

Откройте файл EurekaClientApplication.java и добавьте для класса аннотацию @EnableDiscoveryClient, как показано ниже.

package com.example.eureka.client.application;import org.springframework.boot.SpringApplication;import org.springframework.boot.autoconfigure.SpringBootApplication;import org.springframework.cloud.client.discovery.EnableDiscoveryClient;@SpringBootApplication@EnableDiscoveryClientpublic class EurekaClientApplication {  public static void main(String[] args) {     SpringApplication.run(EurekaClientApplication.class, args);  }}

Добавление REST-контроллера

Создайте класс HelloWorldController в пакете com.example.eureka.client.application и добавьте GET-метод в этом классе.

package com.example.eureka.client.application;import org.springframework.web.bind.annotation.GetMapping;import org.springframework.web.bind.annotation.PathVariable;import org.springframework.web.bind.annotation.RestController;@RestControllerpublic class HelloWorldController {   @GetMapping("/hello-worlds/{name}")   public String getHelloWorld(@PathVariable String name) {       return "Hello World " + name;   }}

В application.properties, расположенный в src/main/resources, добавьте следующие параметры.

spring.application.name=eureka-client-serviceserver.port=8081eureka.client.service-url.defaultZone=http://localhost:8761/eureka/

Параметр eureka.client.service-url.defaultZone определяет адрес Eureka Server, чтобы клиентское приложение могло там зарегистрироваться.

Запуск клиентского приложения

Перед запуском приложения необходимо убедиться, что Eureka Server запущен и работает. Запустите нашего клиента как Java-приложение и перейдите в Eureka Server по адресу http://localhost:8761/. На этот раз вы должны увидеть, что наше клиентское приложение зарегистрировалось на Eureka Server.

Теперь вы знаете как использовать Eureka Server для своих микросервисов. В следующей статье посмотрим на распределенную трассировку (Distributed Tracing) для Spring Boot-микросервисов.


Узнать подробнее о курсе Разработчик на Spring Framework.

Записаться на открытый онлайн-урок по теме
Введение в облака, создание кластера в Mongo DB Atlas018.

Подробнее..

Тривиальная и неправильная облачная компиляция

28.01.2021 00:21:03 | Автор: admin


Введение


Данная статья не история успеха, а скорее руководство как не надо делать. Весной 2020 для поддержания спортивного тонуса участвовал в студенческом хакатоне (спойлер: заняли 2-е место). Удивительно, но задача из полуфинала оказалась более интересной и сложной чем финальная. Как вы поняли, о ней и своём решении расскажу под катом.


Задача


Данный кейс был предложен Deutsche Bank в направлении WEB-разработка.
Необходимо было разработать онлайн-редактор для проекта Алгосимулятор тестового стенда для проверки работы алгоритмов электронной торговли на языке Java. Каждый алгоритм реализуется в виде наследника класса AbstractTradingAlgorythm.


AbstractTradingAlgorythm.java
public abstract class AbstractTradingAlgorithm {    abstract void handleTicker(Ticker ticker) throws Exception;    public void receiveTick(String tick) throws Exception {        handleTicker(Ticker.parse(tick));    }    static class Ticker {        String pair;        double price;       static Ticker parse(String tick) {           Ticker ticker = new Ticker();           String[] tickerSplit = tick.split(",");           ticker.pair = tickerSplit[0];           ticker.price = Double.valueOf(tickerSplit[1]);           return ticker;       }    }}

Сам же редактор во время работы говорит тебе три вещи:


  1. Наследуешь ли ты правильный класс
  2. Будут ли ошибки на этапе компиляции
  3. Успешен ли тестовый прогон алгоритма. В данном случае подразумевается, что "В результате вызова new <ClassName>().receiveTick(RUBHGD,100.1) отсутствуют runtime exceptions".


Ну окей, скелет веб-сервиса через spring накидать дело на 5-10 минут. Пункт 1 работа для регулярных выражений, поэтому даже думать об этом сейчас не буду. Для пункта 2 можно конечно написать синтаксический анализатор, но зачем, когда это уже сделали за меня. Может и пункт 3 получится сделать, использовав наработки по пункту 2. В общем, дело за малым, уместить в один метод, ну например, компиляцию исходного кода программы на Java, переданного в контроллер строкой.


Решение


Здесь и начинается самое интересное. Забегая вперёд, как сделали другие ребята: установили на машину джаву, отдавали команды на ось и грепали stdout. Конечно, это более универсальный метод, но во-первых, нам сказали слово Java, а во-вторых...



у каждого свой путь.


Естественно, Java окружение устанавливать и настраивать всё же придётся. Правда компилировать и исполнять код мы будем не в терминале, а, как бы это ни звучало, в коде. Начиная с 6 версии, в Java SE присутствует пакет javax.tools, добавленный в стандартный API для компиляции исходного кода Java.
Теперь привычные понятия такие, как файлы с исходным кодом, параметры компилятора, каталоги с выходными файлами, сообщения компилятора, превратились в абстракции, используемые при работе с интерфейсом JavaCompiler, через реализации которого ведётся основная работа с задачами компиляции. Подробней о нём можно прочитать в официальной документации. Главное, что оттуда сейчас перейдёт моментально в текст статьи, это класс JavaSourceFromString. Дело в том, что, по умолчанию, исходный код загружается из файловой системы. В нашем же случае исходный код будет приходить строкой извне.


JavaSourceFromString.java
import javax.tools.SimpleJavaFileObject;import java.net.URI;public class JavaSourceFromString extends SimpleJavaFileObject {    final String code;    public JavaSourceFromString(String name, String code) {        super(URI.create("string:///" + name.replace('.', '/') + Kind.SOURCE.extension), Kind.SOURCE);        this.code = code;    }    @Override    public CharSequence getCharContent(boolean ignoreEncodingErrors) {        return code;    }}

Далее, в принципе уже ничего сложного нет. Получаем строку, имя класса и преобразуем их в объект JavaFileObject. Этот объект передаём в компилятор, компилируем и собираем вывод, который и возвращаем на клиент.
Сделаем класс Validator, в котором инкапсулируем процесс компиляции и тестового прогона некоторого исходника.


public class Validator {    private JavaSourceFromString sourceObject;    public Validator(String className, String source) {        sourceObject = new JavaSourceFromString(className, source);    }}

Далее добавим компиляцию.


public class Validator {    ...    public List<Diagnostic<? extends JavaFileObject>> compile() {        // получаем компилятор, установленный в системе        var compiler = ToolProvider.getSystemJavaCompiler();        // компилируем        var compilationUnits = Collections.singletonList(sourceObject);        var diagnostics = new DiagnosticCollector<JavaFileObject>();        compiler.getTask(null, null, diagnostics, null, null, compilationUnits).call();        // возворащаем диагностику        return diagnostics.getDiagnostics();    }}

Пользоваться этим можно как-то так.


public void MyMethod() {        var className = "TradeAlgo";        var sourceString = "public class TradeAlgo extends AbstractTradingAlgorithm{\n" +                "@Override\n" +                "    void handleTicker(Ticker ticker) throws Exception {\n" +                "       System.out.println(\"TradeAlgo::handleTicker\");\n" +                "    }\n" +                "}\n";        var validator = new Validator(className, sourceString);        for (var message : validator.compile()) {            System.out.println(message);        }    }

При этом, если компиляция прошла успешно, то возвращённый методом compile список будет пуст. Что интересно? А вот что.

На приведённом изображении вы можете видеть директорию проекта после завершения выполнения программы, во время выполнения которой была осуществлена компиляция. Красным прямоугольником обведены .class файлы, сгенерированные компилятором. Куда их девать, и как это чистить, не знаю жду в комментариях. Но что это значит? Что скомпилированные классы присоединяются в runtime, и там их можно использовать. А значит, следующий пункт задачи решается тривиально с помощью средств рефлексии.
Создадим вспомогательный POJO для хранения результата прогона.


TestResult.java
public class TestResult {    private boolean success;    private String comment;    public TestResult(boolean success, String comment) {        this.success = success;        this.comment = comment;    }    public boolean success() {        return success;    }    public String getComment() {        return comment;    }}

Теперь модифицируем класс Validator с учётом новых обстоятельств.


public class Validator {    ...    private String className;    private boolean compiled = false;    public Validator(String className, String source) {        this.className = className;        ...    }    ...    public TestResult testRun(String arg) {        var result = new TestResult(false, "Failed to compile");        if (compiled) {            try {                // загружаем класс                var classLoader = URLClassLoader.newInstance(new URL[]{new File("").toURI().toURL()});                var c = Class.forName(className, true, classLoader);                // создаём объект класса                var constructor = c.getConstructor();                var instance = constructor.newInstance();                // выполняем целевой метод                c.getDeclaredMethod("receiveTick", String.class).invoke(instance, arg);                result = new TestResult(true, "Success");            } catch (IllegalAccessException | InvocationTargetException | NoSuchMethodException | ClassNotFoundException | RuntimeException | MalformedURLException | InstantiationException e) {                var sw = new StringWriter();                e.printStackTrace(new PrintWriter(sw));                result = new TestResult(false, sw.toString());            }        }        return result;    }}

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


public void MyMethod() {        ...        var result = validator.testRun("RUBHGD,100.1");        System.out.println(result.success() + " " + result.getComment());    }

Вставить этот код в реализацию API контроллера задача нетрудная, поэтому подробности её решения можно опустить.


Какие проблемы?


  1. Ещё раз напомню про кучу .class файлов.


  2. Поскольку опять же идёт работа с компиляцией некоторых классов, есть риск отказа в записи любого непредвиденного .class файла.


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



Поэтому делать в точности как я не надо)


P.S. Ссылка на гитхаб с исходным кодом из статьи.

Подробнее..

О мифологии миграции монолита в облака

23.04.2021 12:19:27 | Автор: admin

Около десяти лет назад микросервисы получили первое признание. (Однако есть альтернативное мнение, что микросервисам уже пятнадцать лет). С тех пор масса фирм воспользовалась услугами облачных провайдеров и перенесла свои сервисы к ним. А некоторые из них даже успели разочароваться в облачных технологиях и вернулись к традиционной схеме монолита (или почти к ней, см. например [TB]).

Эта статья - не попытка уговорить вас на перенос вашего монолита в облако или отговорить от этого. Это попытка развеять возможно сидящие глубоко в вашем сознании необоснованные опасения или ожидания (другими словами - мифы и заблуждения) по поводу такого переноса.

Но вначале нам необходимо договориться о том, что же это такое - монолит.

Развивая идею из публикации [SN], я предлагаю ввести пять частичных метрик для измерения монолитности той или иной программной системы:

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

  2. Монолитность исполняемых артефактов. Это количество исполняемых артефактов. Например, это может быть количество ваших JAR-файлов. При этом иногда, в зависимости от особенностей вашей системы, вместо собственно JAR-файлов следует считать папку с основным JAR-файлом и вспомогательными файлами используемых библиотек и конфигураций.

  3. Монолитность времени исполнения (run time). Один исполняемый артефакт может использоваться у вас многократно (параллельно), с балансировкой каким-либо балансёром или диспетчером.

  4. Монолитность хранения данных. Эта величина измеряется количеством разных систем хранения ваших данных. Хранит ваше приложение данные в одной базе данных или в нескольких? Если система использует файловую систему в качестве хранилища данных - в скольки файлах и папках она это делает?

  5. Функциональная монолитность. В отличии от предыдущих величин, которые вычисляются более или менее однозначно, вычислить эту величину часто бывает очень трудно. Более того, разные специалисты при её вычислении могут прийти к разным результатам. Для её вычисления необходимо проанализировать входные и выходные интерфейсы приложения, его функциональность, и решить, на сколько независимых процессов можно было бы (не вдаваясь в детали текущей реализации) разбить основную функциональность приложения.

Таким образом, монолитность вашего приложения можно грубо оценить с помощью описанных пяти положительных целочисленных величин с минимальным значением 1.

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

Ну а теперь, вооруженные этим определением монолитности, перейдём к описанию типичных мифов по поводу переноса монолита в облако.

Миф 1: Всё или ничего

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

На самом деле это не так. Архитектурный паттерн, известный под именами Призма( см. [PR]), схожий с Canary deployments[CD] и A/B Testing, позволяет разрабатывать новые микросервисы постепенно, независимо от основного приложения и сбоку от него. Идея паттерна показана на рисунке внизу.

Паттерн "Призма"Паттерн "Призма"

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

Если ваша система общается с внешним миром с помощью HTTP-протокола, оба треугольника могут быть реализованы в виде одного простого proxy-сервера. Различные Service Mesh инструменты типа Istio предоставляю такую возможность на уровне конфигурации.

Первая (красная) призма направляет все входные данные на монолит, дублируя при этом данные интересные заново имплементированному сервису и посылая дублированные данные на него. Вторая призма перехватывает выходные данные вашего монолита, дублирует результаты запланированного к замещению сервиса и посылает дубликаты на сравнение в Comparator. Ну а Comparator сравнивает результаты нового варианта с результатами монолита.

Таким образом, монолит работает как и раньше (синие элементы на рисунке).

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

Миф 2: Просто расщепим на части и докенизируем

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

Нередко миграция монолита в облако представляется как простое расщепление монолита на несколько частей и перенос каждой части сначала в Docker/Kubernetes, а возможно потом - в одну из облачных сред типа AWS или Azure.

Увы, в большинстве случае так просто решить проблему не получается.

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

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

  1. Финансы (например, Data Warehouse)

  2. Reports

  3. Рекламации

  4. Ручные обрывы процессов в определённых ситуациях

  5. Коррекция неверных данных

  6. Evaluation (Периодическая оценка ситуации)

  7. Настройка системы

  8. Audit

  9. Workarounds

Способы удовлетворения потребностей этих групп должны быть учтены при подготовке плана миграции.

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

Расщепление монолита на части означает, как правило, не только замену API общения компонент монолита между собой, но и смену парадигмы их коммуникации. На практике это оборачивается переходом на event driven механизм коммуникации.

Не вдаваясь в детали, отметим пунктиром, над чем в этом случае следует подумать и что постараться сделать:

  1. Использование паттерна SAGA (см. [SA])при реализации распределённых транзакций.

  2. Использование паттерна QCRS (см. [QC])при работе с распределёнными данными.

  3. Использование идемпотентных функций (см. [IF]), позволяющих при возникновении проблем просто вызывать их заново без опасения за состояние сохранённых данных).

Миф 3: Переносить надо только функциональность, всё остальное предоставит провайдер

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

Реальность облачной жизни иная. По крайней мере, следующие проблемы вам наверняка придётся решать самостоятельно:

  1. Мониторинг

  2. Аудит

  3. Desaster Recovery

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


Миф 4: Облачные сервисы очень дёшевы

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

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

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

Практика показывает, что со временем центр тяжести перемещается на оплату именно этих, а не базовых сервисов.

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

Поэтому, мигрируя свои сервисы в облако, надо постоянно помнить о vendor lock-in и проектировать облачную архитектуру так, чтобы при необходимости иметь возможность сменить провайдера.

Миф 5: Микросервисы должны быть маленькими

То, что микросервисы должны быть маленькими, явствует из самого их названия, не правда ли? Поэтому при миграции в облака монолит надо разбить на большое число маленьких частей, разве не так? Примеры ландшафтов со многими сотнями и даже тысячами микросервисов, как например в банке Monzo ( см. [MB]), вроде бы также говорят в пользу такого подхода.

И опять, - в жизни всё сложнее. Излишнее измельчение сервисов может привести к слишком большому количеству интерфейсов между ними, сложности их обновления, проблемам при обновлении базовых библиотек и т.д. и т.п.

К счастью, отрасль уже накопила достаточное понимание проблемы и выработала конструктивные рекомендации по вопросу расщепления монолита на микросервисы. Детали вы найдёте в работах [HS], [ST], [HS1]. Здесь же короткий перечень основных критериев, когда такое расщепление возможно стоит делать:

  1. Выделять в отдельный сервис функциональность с объективно повышенной вероятностью ошибок в run time.

  2. Реализовывать компоненты с заведомо разным жизненным циклом в разных сервисах.

  3. Разделять на сервисы компоненты с заведомо разными ожидаемыми частотами внесения изменений и обновлений.

  4. Выделять в отдельный сервис функциональность, требующую повышенной скалируемости.

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

А иногда различные микросервисы появляются на свет просто из-за организационных причин (необходимость реализовать их разными командами).

Миф 6: Затраты на миграцию монолита непредсказуемы

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

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

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

Миф 7: Раз все так делают, значит так можно

Сервис мега-провайдера типа AWS или Azure отличается низкой латентностью, высокой надёжностью и доступностью по всему миру за счёт их собственных Data Centers. Неудивительно, что многие фирмы и государственные службы пользуются их услугами.

При этом использующие эти сервисы фирмы на вопрос о соблюдении правил защиты данных потребителей нередко отвечают: Ну если все так делают, значит это легально.

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

Увы, это не соответствует действительности.Все мега-провайдеры соблюдают законы США, в том числе - CLOUD Act [CA], позволяющий американским службам без судебного решения потребовать от провайдера любые данные. А это противоречит многим национальным и европейским законам о защите данных их граждан.

Но это в теории, на практике-то ничего неприятного не происходит?, возможно спросите вы. Нет, происходит. Например, в Германии уже рассматривались случаи наложения штрафов на образовательные учреждения и отдельных преподавателей за использование облачных продуктов типа Microsoft Office 365, Zoom и т.п.( см. [ MO]). В апреле 2021 года немецкая служба защиты приватных данных (Datenschutz-Aufsichtsbehrde) потребовала от многочисленных немецких фирм обоснования хранения данных у американских облачных провайдеров в связи с решением Европейского Суда по вопросу соглашения Privacy Shield (см. [DF]).

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

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

Что же касается американских спецслужб - я очень советую вспомнить про Сноудена, а ещё лучше прочитать (если не читали) его книгу [ES]. Лично меня в ней поразили две вещи.

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

Вторым поразившим меня в этой книге был эпизод с вербовкой абсолютно невиновного молодого человека, который в будущем мог занять в иерархии своей страны интересующую спецслужбы позицию. Сноуден в деталях рассказывает о попытках подставить этого человека под судебную ответственность. Знание некоторых деталей его биографии, его привязанностей и слабостей им в этом очень помогло. Собственно, в этом нет ничего нового. Мы все много раз видели это в кино про КГБ, ЦРУ и т.д. Но воспоминания Сноудена как участника операции показывают, что это всё не выдумки. Как мы видим, спецслужбы иногда охотятся и за абсолютно невиновными людьми. Хотите вы с вашим сервисом в этом участвовать (осознанно или неосознанно), особенно, если этого можно не делать?

Наверное нет. Так что же делать?

Самое главное - будьте честны перед своими пользователями. Перед тем как доверить вам свои данные, человек должен осознать, чем он рискуют. Расскажите ему (ей) об этом, перед тем как начать сотрудничество.

Постарайтесь сами обойтись без излишних приватных данных. Возможно, ваш бизнес может обойтись без обратной связи с некоторыми категориями пользователей через Email или телефон. Если ваш бизнес ориентирован на профессионалов, вы можете поддерживать в учётных записях (accounts) только логин, пароль и серию контрольных вопросов.

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

Ну и как самый крайний вариант - не используйте специализированные фичи мега-провайдеров, а используйте решения на базе открытых решений типа Docker/Kubernetes/Kafka, что позволит вам при необходимости развернуть бизнес в облаках локальных провайдеров интересующей вас страны.

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

Вместо заключения

Изложенное в этой статье не претендует на роль истины в последней инстанции. Процесс миграции монолитов в облака находится в полном разгаре. Накопленный опыт миграции неплохо обобщён и осмыслен в книге [MM].

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

Ссылки и литература

CA

CLOUD Act

https://en.wikipedia.org/wiki/CLOUD_Act

CD

Canary deployments

https://octopus.com/docs/deployments/patterns/canary-deployments

DF

Deutsche Firmen in der Datenschutzfalle Behrden intensivieren Ermittlungen wegen US-Cloud-Nutzung

https://www.xing-news.com/reader/news/articles/3938440?cce=em5e0cbb4d.%3AtgdwSkqSkgtEqcgH83anAB&link_position=digest&newsletter_id=74341&toolbar=true&xng_share_origin=email

DH

Datenschutzverste im Homeschooling und Bugelder

https://digitalcourage.de/blog/2020/datenschutzverstoesse-im-homeschooling-und-bussgelder

EK

EuGH kippt Rechtsgrundlage fr Datentransfers in die USA

https://www.handelsblatt.com/politik/international/privacy-shield-abkommen-eugh-kippt-rechtsgrundlage-fuer-datentransfers-in-die-usa/26009730.html?ticket=ST-1251974-6dlleMe6cOkufQQeue3s-ap1

ES

Edward Snowden. Permanent Record

Macmillan; Airport- edition (17 Sept. 2019). ISBN-13: 978-1529035667

HS

How small should Microservices be

https://medium.com/@ggonchar/deciding-on-size-of-microservices-dbb2a8d8f7e5

HS1

How Small Should Microservices Be?

https://stackoverflow.com/questions/56509701/how-small-a-micro-service-should-be

IF

Pattern: Idempotent Consumer

https://microservices.io/patterns/communication-style/idempotent-consumer.html

MB

Modern Banking in 1500 Microservices

https://www.infoq.com/presentations/monzo-microservices/?utm_source=email&utm_medium=architecture-design&utm_campaign=newsletter&utm_content=09222020

MM

Sam Newman. Monolith to Microservices: Evolutionary Patterns to Transform Your Monolith (English Edition) 1

ORelly. ISBN 13: 978-1492047841

MO

Microsoft Office 365: Die Grnde fr das Nein der Datenschtzer

https://www.heise.de/news/Microsoft-Office-365-Die-Gruende-fuer-das-Nein-der-Datenschuetzer-4919847.html

NI

The NIST Definition of Cloud Computing

https://nvlpubs.nist.gov/nistpubs/Legacy/SP/nistspecialpublication800-145.pdf

PR

Prizma switch technology

https://www.semanticscholar.org/paper/Prizma-switch-technology-Engbersen/f49764456f1668ab082d17c1f0c7f8b104835ebb

QC

Pattern: Command Query Responsibility Segregation (CQRS)

https://microservices.io/patterns/data/cqrs.html

SA

Pattern: Saga

https://microservices.io/patterns/data/saga.html

SM

6 Strategies for Migrating Applications to the Cloud

https://aws.amazon.com/de/blogs/enterprise-strategy/6-strategies-for-migrating-applications-to-the-cloud/

SN

Sam Newman: Migrating Monoliths to Microservices With Decomposition and Incremental Changes.

The InfoQ eMag/ Issue #91 /February 2021. Re-examining Microservices After the First Decade

ST

Should that be a Microservice? Keep These Six Factors in Mind

https://tanzu.vmware.com/content/blog/should-that-be-a-microservice-keep-these-six-factors-in-mind

TB

Thomas Betts. To Microservices and Back Again - Why Segment Went Back to a Monolith.

The InfoQ eMag/ Issue #91 /February 2021. Re-examining Microservices After the First Decade

Иллюстрации автора.

Подробнее..

Облачные Gateway API зачем нужны подобные сервисы и чем они отличаются у разных платформ

19.05.2021 16:06:46 | Автор: admin

Добро пожаловать в современный интернет, где большая часть взаимодействия приходится на интерфейсы прикладного программирования API. На API держится цифровой бизнес: с ними стало возможным предоставлять и получать услуги через приложения и подключённые к Сети устройства. Платёжные системы? Работают через API. Интерактивная карта, показывающая, как добраться от метро до офиса? Снова API. Даже бэкенд строится на API.

Похоже, мы окружены значит, придётся разбираться. Что такое API, на Хабре уже рассказывали, а я предлагаю рассмотреть поподробнее реализацию API Gateway на облачных платформах.

Зачем вообще нужны Gateway API

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

Представьте себе: у вас есть интернет-магазин по продаже реплик молота Тора. Для удобства пользователя имеется как сайт под десктоп и мобильные устройства, так и приложения для Android и iPhone, которые взаимодействуют с сервером через REST API.

Чтобы на странице товара отображались верные данные, нам нужно обратиться к нескольким службам: в одной учитывается наличие молота, в другой записаны материал, вес и длина ручки, в третьей сохраняются отзывы клиентов, а цена вообще указана в четвёртой. API Gateway позволяет обойтись одним запросом.

API Gateway выполняет множество задач: принимает, обрабатывает и распределяет запросы, контролирует трафик, осуществляет мониторинг и контроль доступа.

В микросервисной архитектуре паттерн API Gateway появился в качестве службы, обеспечивающей единую точку входа для веб-приложений и API, эдакой серверной части для клиентской части. В чём польза именно для микросервисов?

Например возможность повторного использования компонентов, упрощение бэкенда приложения, обеспечение доступа к статическим веб-страницам и документам, удобная проверка авторизации и подбор оптимального для каждого типа клиента API как это делает Netflix API Gateway.

Что такое облачные API Gateway

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

Классический API Gateway представляет собой шлюз между пользователями и любым количеством сервисов (API), выполняющий функцию обратного прокси, как Nginx и HAProxy. В то же время облачная версия API Gateway уже полноценный сервис для разработчиков, который простым в исполнении не назовёшь.

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

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

Как облачные API Gateway облегчают жизнь

Итак, в разработке всё чаще применяются облачные технологии и закономерно возникает вопрос об облачных шлюзах API, их особенностях и преимуществах. Стоит ли их применять или лучше как-нибудь по старинке?

Для чего разработчики вообще выбирают облачные API Gateway?

  • Чтобы сократить время разработки API Gateway создаётся в несколько кликов, а интеграция с облачными сервисами выбранной платформы занимает пару минут.

  • Чтобы обеспечить минимальную задержку ответа на запрос об этом позаботится система автоматического масштабирования.

  • Чтобы лучше контролировать трафик к примеру, с помощью ограничения нагрузки на количество запросов в секунду для каждого HTTPметода. А при необходимости можно сформировать кеш с настраиваемыми ключами и указанием жизненного срока в секундах.

  • Чтобы отлаживать API встроенными средствами меньше головной боли.

  • Чтобы генерировать клиентские SDK.

  • Чтобы одновременно использовать нескольких версий одного API, а также управлять стадиями выпуска от альфы до релиза.

  • Чтобы контролировать доступ к API и управлять его жизненным циклом от создания до публикации.

  • Чтобы уведомление приходило от сервиса, а не от разозлённого клиента, если что-то идёт не так.

  • Чтобы настраивать авторизацию удобным методом с помощью средств Lambda или токенов OAuth.

  • Чтобы отслеживать показатели к примеру, количество запросов, задержку вызова и количество ошибок на удобной панели мониторинга с визуальным интерфейсом.

  • Чтобы платить только за количество запросов в месяц или пользоваться сервисами бесплатно, если не выходить за рамки определённой цифры.

Как используют облачные API Gateway

Виртуальная доска

Простое приложение, состоящее из двух конечных точек POST для записи сообщений и GET для извлечения трёх последних сообщений. Реализовано с помощью AWS Gateway, AWS DynamoDB, AWS Serverless Application Model и Lambda.

Голосовой сервиc

Рецепт сервиса записи к врачу и регистрации в поликлинике, разработанный коммуникационной платформой Voximplant и Yandex.Cloud.

Бот для телеграма

Запуск бота на Python внутри одного из облачных сервисов, а именно Yandex.Cloud.

Трекер пульсометрии

Один из вариантов решения для сбора данных пульсовой оксиметрии для нескольких пользователей, отслеживания этих данных и обмена ими. Фронт написан на VueJS, бэкенд реализован с применением Amazon API Gateway.

Статический сайт в облаке

Пошаговая инструкция по деплою статического сайта в облако, прикрутке к нему сертификата Lets Encrypt, домена второго уровня и настройке API-шлюза в системе Yandex.Cloud.

Блог

И снова приложение на микросервисах реализация клиентской части на VueJS, взаимодействие настроено через REST API и gRPC, а в качестве базы данных используется MongoDB.

Реализация на разных облачных платформах

Сервис API Gateway предлагают несколько облачных платформ и все они предоставляют более-менее схожий пакет услуг. Так в чём же разница?

Azure API Management

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

Amazon API Gateway

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

Документация включает подробные инструкции от развёртывания RESTful API при создании бессерверного веб-приложения до работы с HTTP API, поэтому не придётся искать примеры по всей Сети, чтобы разобраться.

Особенности:

  • Создание API RESTful при помощи API HTTP или API REST.

  • Интерфейсы API WebSocket для разработки приложений, которым требуется двусторонняя связь в режиме реального времени.

  • Частная интеграция с AWS ELB и AWS Cloud Map.

  • Ключи API для сторонних разработчиков.

  • Генерирование клиентских SDK на многих языках, включая JavaScript, iOS и Android.

  • Внедрение подписи четвёртой версии для API REST и API WebSocket при авторизации и проверке запросов API к другим сервисам AWS API Gateway.

  • Авторизация с помощью AWS Lambda.

  • Amazon API Gateway можно пользоваться бесплатно целый год пока ваши потребности не превышают один миллион вызовов API, полученных для API REST, один миллион вызовов API, полученных для API HTTP, и один миллион сообщений и 750 000 минут подключения для API WebSocket в месяц.

  • Обучение с помощью пошаговых учебных пособий, а также доступ к более чем 500 бесплатным онлайн-курсам.

Oracle API Gateway

Сервис Oracle API Gateway стал доступен любому пользователю в конце 2019 года и уже пытается активно конкурировать с Amazon API Gateway. Получится ли у него отвоевать хотя бы часть аудитории у AWS, нам только предстоит увидеть а сравнивать всегда интереснее на собственном опыте. Почитать про создание своего Gateway API можно вот в этой статье.

Особенности платформы:

  • RESTful API в комбинации с Oracle Functions, а также возможностями Kubernetes и Compute.

  • Каждая служба в облачной инфраструктуре Oracle интегрируется с IAM для аутентификации и авторизации (консоль, SDK или CLI и REST API).

  • Интеграция с системой управления доступом Oracle Cloud Infrastructure.

  • Бесплатный период длительностью в тридцать дней, чтобы опробовать возможности широкого спектра сервисов Oracle Cloud, в том числе к Databases, Analytics, Compute, Container Engine for Kubernetes и т. д.

  • Платформа Oracle Cloud позиционирует себя как более экономичное решение, чем AWS, и в качестве примера упоминает, что соотношение цены и производительности в 2 раза выше, а стоимость исходящей пропускной способности составляет только 1/4 от стоимости у AWS.

Google API Gateway

Сервис перешёл на стадию публичного бета-тестирования 18 сентября 2020 года, так что пока о нём известно довольно мало и тем интереснее пронаблюдать за его развитием.Сейчас Google API Gateway позволяет управлять API других сервисов облачной платформы Cloud Functions, Cloud Run, App Enginе, Compute Engine и Google Kubernetes Engine. Настроить работу с Cloud Run, к примеру, можно всего за несколько минут.

Особенности:

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

  • До 2 миллионов запросов в месяц бесплатно.

  • Наличие пробной версии. Google Cloud предоставляет виртуальный кредит в размере 300 долларов, который необходимо потратить в течение последующих трёх месяцев. После окончания бесплатного периода оплата не начинает взиматься автоматически на платный тариф необходимо перейти вручную.

SberCloud API Gateway

SberCloud API Gateway использует наработки Huawei, а информации об особенностях применении в Сети можно найти немного, но здесь вам поможет Хабр: после недавнего хакатона один из участников рассказал о впечатлениях от SberCloud и сравнил функциональность с более известным AWS.

Особенности:

  • Доступ к облачным продуктам для физических лиц возможен только с помощью входа/регистрации через Сбер ID.

  • Управление квотами и регулирование запросов пользователей.

  • Встроенный инструмент отладки.

  • Визуализированная панель мониторинга API.

  • Создание каналов VPC для доступа к бэкенд-сервисам в сети VPC и управления нагрузкой путём отправки API-запросов на различные серверы.

  • Цифровая подпись, которая вступает в силу только после привязки к API.

  • Никакой минимальной или предварительной платы оплачивается только фактическое использование.

  • Возможность монетизации API.

Yandex API Gateway

23 сентября 2020 года к четырём сервисам платформы Yandex.Cloud прибавились ещё два Yandex API Gateway и база данных Yandex Database в режиме Serverless.

Yandex API Gateway интегрирован с другими сервисами платформы, благодаря чему возможна отправка HTTP-запросов с помощью функций Yandex Cloud Functions, доступ к статическим данным осуществляется Yandex Object Storage напрямую из хранилища, а запуск произвольных HTTP-сервисов в облаке возможен с помощью Yandex Managed Service for Kubernetes. Так что спектр применения широк к примеру, внутри облака можно запустить приложение на Express.js.

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

Особенности:

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

  • Поддержка OpenAPI 3.0.

  • Обработка запросов только по протоколу HTTPS. Сервис автоматически перенаправляет все запросы к API-шлюзам по протоколу HTTP на их HTTPS-версии.

  • Интеграция с системой управления доменами сервиса Certificate Manager. Для обеспечения TLS-соединения используется привязанный к домену сертификат.

  • Система квот и лимитов. Максимальный размер спецификации 3,5 МБ. Количество API-шлюзов в одном облаке 10, но, в отличие от максимального размера спецификации, меняется по запросу в техническую поддержку.

Тарификация по количеству запросов к созданным API-шлюзам и исходящему трафику. При этом запросы к API-шлюзам до 100 000 запросов в месяц не тарифицируются. Как, кстати, и входящий трафик, а также передача данных между сервисами Yandex.Cloud. Больше подробностей можно узнать в сообществе Serverless в Telegram:Yandex Serverless Ecosystem. Мы регулярно встречаемся в виртуальном пространстве и похоже созревает потребность в очной встрече.

Подробнее..

Перевод Argo CD готов к труду и обороне в Kubernetes

26.02.2021 20:18:58 | Автор: admin

Привет, Хабр. В рамках курса Инфраструктурная платформа на основе Kubernetes подготовили для вас перевод полезного материала.

Также приглашаем на открытый вебинар Работа с NoSQL базами в k8s (на примере Apache Cassandra). На вебинаре участники вместе с экспертом рассмотрят плюсы и минусы запуска Apache Cassandra в k8s: насколько такой вариант установки готов к продакшену, и какие подводные камни имеются.


В этой статье мы рассмотрим несколько вопросов касательно Argo CD: что это такое, зачем его используют, как его развернуть (в Kubernetes), как его использовать для реализации непрерывного развертывания (continuous deployment), как настроить SSO с помощью GitHub и разрешений и т. д.

Что такое Argo CD и GitOps

Argo CD это декларативный GitOps-инструмент непрерывной доставки (continuous delivery) для Kubernetes.

Но что же такое GitOps?

Официальное определение гласит, что GitOps это способ реализации непрерывного развертывания (continuous deployment) облачных приложений. Он фокусируется на создании ориентированного на разработчиков опыта эксплуатации инфраструктуры с использованием инструментов, с которыми разработчики уже знакомы, включая Git и Continuous Deployment.

Официальное определение не вдается в подробности, не так ли? Возможно, вы не так часто слышали об этой концепции, но, скорее всего, вы уже использовали ее: вы определяете свои K8s ресурсы в YAML или с помощью Helm-диаграммы, вы используете Git в качестве единого источника истины (single source of truth), вы запускаете одни автоматизированные CI задачи для деплоя в продакшн, когда ваша ветвь master изменена, и вы запускаете другие задачи по пул реквесту для деплоя на стейджи.

Почему GitOps

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

Развертывание (деплой) приложений и управление жизненным циклом должны быть:

  • автоматизированными

  • проверяемыми

  • простыми для понимания

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

В этом и заключается концепция GitOps и то, почему он хорош.

Почему Argo CD

Можно ли достичь вышеупомянутых преимуществ GitOps, используя любые другие инструменты CI/CD? Скорее всего, да. Например, вы можете использовать старый добрый Jenkins, определить разные задачи для разных ветвей, после чего задачи будут следить за Git-репозиториями или использовать хуки для реакции на события, а в конвейере вы можете выполнить несколько git clone и helm install. Нет ничего плохого в Jenkins, на что я указывал в моей предыдущей статье о CI: Введение в CI: сравнение 17 основных инструментов CI или Как выбрать лучшее CI в 2020 году.

Если вы не читали ее, я рекомендую вам сделать это, чтобы лучше понять, что мы ищем при выборе инструмента.

По сути, Argo CD упрощает все, о чем я упоминал выше: легко настраивать, легко развертывать, почти без особых напрягов, так что вы можете сосредоточиться на более важных вещах, а не возиться с инструментом, просто чтобы понять, как его использовать и настраивать.

Все еще неубедительно

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

Это часть фонда Cloud Native Computing Foundation (CNCF).

Он активно поддерживается и постоянно улучшается. Посмотрите количество на коммитов:

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

  • первый релиз v0.1.0 состоялся в марте 2018 года (относительно новый проект)

  • v1.0.0 зарелижен в мае 2019 (быстро развивается)

  • на момент написания статьи имеет версию v1.7.8 (ноябрь 2020, развивается очень быстро)

  • 4,3 тыс. звезд в репозитории Argo CD (еще больше на других репозиториях того же проекта)

  • 60 открытых PR и 500 открытых задач на сегодняшний день (очень даже неплохо, это означает, что сообщество активно занимается им и постоянно исправляет и придумывает запросы на новый функционал)

Он также упоминается в техническом радаре CNCF:

Он все еще находится на стадии ОЦЕНКА (ASSESS), что означает, что члены CNCF протестировали его, и он показался многообещающим. Он рекомендован к рассмотрению, когда вы сталкиваетесь с конкретной потребностью в подобной технологии в вашем проекте.

Радар является инициативой CNCF End User Community. Это группа из более чем 140 ведущих компаний и стартапов, которые регулярно встречаются для обсуждения проблем и передовых методов внедрения облачных технологий. Если вам лень разбираться, какой инструмент использовать, или если вы чувствуете себя неуверенно в отношении новых вещей, которые вы еще не пробовали, довольно безопасно выбрать один из вариантов, которые предлагает радар, потому что многие крупные компании уже протестировали его за вас, множество из имен которых вы уже слышали. Если это подходит им, есть большая вероятность, что и вам это понравится.

Развертывание

Окей, приступим к практике. У вас должен быть запущен кластер K8s, потому что мы собираемся делать это внутри k8s.

kubectl create namespace argocdkubectl apply -n argocd -f \https://raw.githubusercontent.com/argoproj/argo-cd/stable/manifests/install.yaml 

Один YAML, чтоб править всеми.

После развертывания у вас будет несколько запущенных подов и сервисов. Примеры:

Pods:argocd-application-controller-6b47c9bd78-kp6djargocd-dex-server-7b6d8776d8-knsxxargocd-redis-99fb49846-l466kargocd-repo-server-b664bd94b-bmtwrargocd-server-768879948c-sx875Services:argocd-dex-serverargocd-metricsargocd-redisargocd-repo-serverargocd-serverargocd-server-metrics

Комментарии по доступу к сервису и ingress:

Обратите внимание, что в развертывании по умолчанию сервис работает как тип Cluster IP, и ingress по умолчанию нет. Поэтому, если вы хотите получить доступ к сервису, вам нужно будет либо выполнить переадресацию портов, либо изменить тип сервиса на балансировщик нагрузки, либо создать ingress.

Если вы делаете это в производственном кластере, например в EKS в AWS, скорее всего, вы хотите использовать ingress и, вероятно, у вас уже есть ingress-контроллер. Вход для Argo CD здесь немного сложен, потому что на порту 443 он имеет как HTTPS (для веб-интерфейса консоли), так и GRPC для вызовов API командной строки. Если вы используете EKS, например, с ingress-контроллером Nginx, скорее всего, вы уже выполнили завершение TLS там, поэтому вам может потребоваться несколько ingress-объектов и хостов, один для протокола HTTP, другой для GRPC. Подробнее смотрите здесь.

Установка CLI

Для Mac это всего лишь одна команда:

brew install argocd

Инициализация

После установки изначальный пароль совпадает с именем пода сервера. Мы можем войти в систему:

argocd login  (переадресация портов, служба балансировки нагрузки, ingress - на ваш выбор)

и изменить пароль:

argocd account update-password

Вы также можете войти в консоль пользовательского интерфейса со своим юзернеймом и паролем, чтобы прочувствовать:

Страница входа в пользовательский интерфейс Argo CD

Добавление кластеров

Вы можете управлять сразу несколькими кластерами внутри Argo CD, например, у вас могут быть разные кластеры для разных сред, таких как dev, test, staging, production или что-то еще.

По умолчанию кластер, в котором развернут Argo CD, уже настроен с помощью Argo CD:

Вы также можете увидеть список кластеров с помощью интерфейса командной строки:

argocd cluster list

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

argocd cluster add CONTEXTNAMECONTEXTNAME- имя kube контекста в вашей локальной конфигурации.

Helloworld-пример развертывания

Теперь мы можем попробовать создать приложение на Argo CD.

Версия TL;DR или версия Мне не нравится UI в этом разделе это одна команда:

argocd app create helloworld --repo https://github.com/ironcore864/go-hello-http.git --path helm --sync-policy automatic --dest-server https://kubernetes.default.svc --dest-namespace default --values values.yaml --values values.dev.yaml

Эта CLI-команда создаст приложение, развернет его и синхронизирует. Чтобы продемонстрировать простоту Argo CD, я буду делать то же самое в пользовательском интерфейсе, а именно:

Нажмите кнопку NEW APP в консоли пользовательского интерфейса:

Затем вам нужно ввести несколько параметров для задачи, например:

  • Application Name: имя этого приложения. Здесь я назову его просто helloworld

  • Project: вы можете выбрать default. Project (проект) это концепция внутри Argo CD, в рамках которой вы можете создать несколько приложений и связать каждое приложение с проектом

  • Sync policy: вы можете выбрать между Manual и Automatic (что даст вам настоящий GitOps). Здесь я выберу Automatic (обратите внимание, что здесь в пользовательском интерфейсе значение по умолчанию Manual).

Нажмите SYNC POLICY и выберите Automatic

Затем мы перейдем к SOURCE части. Нам нужно указать URL-адрес git. Я собираюсь использовать пример, расположенный по адресу. Если вы перейдете в этот репозиторий, вы обнаружите, что там нет ничего, кроме простого Golang приложения с папкой с именем helm, которая представляет собой диаграмму для развертывания с несколькими файлами значений.

После того, как вы ввели URL-адрес git-репозитория, кликните часть PATH, и вы обнаружите, что Argo CD уже автоматически обнаружил, что у нас есть папка helm в этом репозитории, которая содержит вещи, которые могут нас заинтересовать:

Кликните Path и выберите имя папки helm в раскрывающемся меню.

Итак, здесь мы просто кликаем раздел Path и выбираем папку helm.

Стоит отметить, что Argo CD поддерживает несколько инструментов для развертывания. Сам Argo CD не предвзят; он позволяет использовать собственный YAML k8s, или kustomize, или helm. Например, если файлы в Path представляют собой схему управления, Argo CD знает, что нужно запустить установку Helm; но если это просто файлы YAML k8s, Argo CD знает, что вместо этого нужно запустить kubectl apply. Умно, не правда ли?

В разделе Destination нам нужно выбрать, в каком кластере Kubernetes развернуть это приложение (выбор из раскрывающегося списка) и в каком пространстве имен (введите текст).

Щелкните URL-адрес кластера, выберите кластер для развертывания и введите пространство имен.

Поскольку в этом примере в нашей папке helm есть диаграмма, Argo CD автоматически загружает новый раздел с именем Helm, чтобы попросить вас выбрать, какой файл значений, который нужно применить:

Кликните раздел VALUES FILES, и вы можете выбрать один или несколько файлов из списка, который выбирается из Path, настроенного ранее.

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

Здесь мы указали два файл со значениями, один по умолчанию, другой для dev стейджа, и в нем есть значения, которые переопределяют значения, определенные по умолчанию.

После нажатия кнопки Create Argo CD синхронизирует (sync) статус, определенный в git-репозитории, и если текущее состояние не совпадает с тем, что определено в git, Argo CD синхронизирует его и переведет состояние в то же, что определено в git. Через некоторое время вы увидите, что приложение синхронизировано, и какие компоненты развернуты:

Приложение синхронизированоПриложение синхронизированоПодробное представление приложенияПодробное представление приложения

В этом примере у нас есть развертывание, в котором развернут только 1 под (значения из values.dev.yaml переопределяет 3 пода по умолчанию, определенные в файле values.yaml), и сервис, раскрывающий развертывание. Теперь, если мы перейдем к целевому кластеру и проверим, он действительно уже развернут:

Приложение действительно развернуто, без шутокПриложение действительно развернуто, без шуток

Это демонстрирует весь процесс, в котором вы создаете приложение и развертываете его. Весь процесс занимает около 1 минуты, без написания bash-скриптов для cd в какую-либо папку, а затем для установки helm, или, что еще хуже, если у вас нет подходящего образа с helm, необходимости его собрать или найти.

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

GitHub SSO

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

После установки Argo CD имеет одного встроенного администратора, который имеет полный доступ к системе. Рекомендуется использовать пользователя с правами администратора только для изначальной настройки, а затем переключиться на локальных пользователей или настроить SSO-интеграцию.

Вы можете создать локального пользователя в Argo CD, но вы, вероятно, захотите настроить SSO.

Argo CD включает и поставляет Dex как часть установочного комплекта с целью делегирования аутентификации внешнему поставщику идентификации. Поддерживаются несколько типов поставщиков идентификации (OIDC, SAML, LDAP, GitHub и т. Д.). Для настройки единого входа (SSO) на Argo CD необходимо отредактировать файл конфигурации argocd-cm с настройками Dex-коннектора. После регистрации нового OAuth приложения в git вы можете отредактировать configmap argocd-cm, чтобы добавить следующие значения:

data:  url: https://argocd.example.com  dex.config: |    connectors:      # GitHub example      - type: github        id: github        name: GitHub        config:          clientID: aabbccddeeff00112233          clientSecret: $dex.github.clientSecret          orgs:          - name: your-github-org      # GitHub enterprise example      - type: github        id: acme-github        name: Acme GitHub        config:          hostName: github.acme.com          clientID: abcdefghijklmnopqrst          clientSecret: $dex.acme.clientSecret          orgs:          - name: your-github-org

После сохранения изменения должны вступить в силу автоматически, и у вас будет GitHub SSO уже для всей вашей команды.

GitHub SSO (здесь в примере корпоративный git)GitHub SSO (здесь в примере корпоративный git)

Если вы запустите GitHub SSO с новым пользователем, входящим в систему, он не увидит список кластеров или только что созданное приложение это из-за функций RBAC, позволяющих ограничивать доступ к ресурсам Argo CD. После того, как мы уже включили SSO, мы можем настроить RBAC, создав следующую configmap argocd-rbac-cm:

apiVersion: v1kind: ConfigMapmetadata:  name: argocd-rbac-cm  namespace: argocddata:  policy.default: role:readonly  policy.csv: |    p, role:org-admin, applications, *, */*, allow    p, role:org-admin, clusters, get, *, allow    p, role:org-admin, repositories, get, *, allow    p, role:org-admin, repositories, create, *, allow    p, role:org-admin, repositories, update, *, allow    p, role:org-admin, repositories, delete, *, allow    g, your-github-org:your-team, role:org-admin

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

Заключение

Установка, инициализация, управление (кластер, SSO, пользователь, RBAC), использование (создание приложения, развертывание) довольно просты. Я настоятельно рекомендую вам попробовать, в любом случае это займет у вас не больше часа. И я гарантирую, что вам понравится его простота и то, что он может вам принести.


Узнать подробнее о курсе Инфраструктурная платформа на основе Kubernetes.

Смотреть открытый вебинар Работа с NoSQL базами в k8s (на примере Apache Cassandra).

Подробнее..

Как готовить Helm правильно несколько полезных рецептов

16.05.2021 18:12:28 | Автор: admin
(источник фото -https://unsplash.com/photos/XWNbUhUINB8(источник фото -https://unsplash.com/photos/XWNbUhUINB8

Когда-то давно, когда ножей не знали,х@#$ говядину рубили... ой нет, это другая сказка, простите. Вот, правильная эта. Когда-то давно, деды сказывают, для обновления сервиса в среде инженерам приходилось самим писать скрипты для деплоймента, а некоторые даже запускали их сами из консоли, руками. Были даже причудливые инструменты вроде ClusterSSH, чтобы делать сеанс одновременной игры на всех нодах кластера.

Но тотальная контейнеризация, ввод в обиход универсального понятия "workload", и оркестризация привели к появлению Kubernetes, на котором сейчас работает примерно 3/4 мировых production сред.

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

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

Поэтому Helm стал де-факто стандартом в автоматизированных деплойментах Kubernetes, добавляя новые интересные возможности, которые идут гораздо дальше простой альтернативы выполнению kubectl apply -f ...

Ниже мы расссмотрим несколько примеров того, что можно получить от Helm по сравнению с простой командой kubectl apply, с чем разработчик сталкивается в реальной жизни. Мы покажем, как организовать доставку новых версий сервисов в разные среды, описывая параметры так, что не требуется копипастных повторений, которые ведут к ошибкам. Мы также увидим несколько других полезных приёмов - для удобного управления секретами и организации надёжных пайплайнов.

Итак, напомним, что Helm в принципе может делать три основные вещи:

  • сделать дескрипторы по шаблонам

  • накатить дескрипторы на кластер

  • использовать репозитории charts - взять шаблоны дескрипторов из центральной среды

В данном тексте мы фокусируемся на первых двух моментах, шаблонах и состоянии кластера, не затрагивая репозитории.

Шаблонизатор Helm работает примерно так:

Другими словами, Helm берёт исходники:

  • файлы, текстовые и бинарные

  • шаблоны .yaml

  • значения из одного или нескольких .yaml файлов, и, возможно, командной строки

и производит файлы .yaml для того, чтобы применить их на кластер Kubernetes.

При этом файлы вставляются в Secrets и ConfigMaps, а значения занимают свои места в шаблонах.

Получившиеся шаблоны можно скормить в кластер непосредственно через kubectl, или же (что открывает новые возможности) наложить их через Helm. Helm имеет встроенные средства управления состоянием кластера - несколько последних сделанных деплойментов сохраняются в отдельном Secret, что даёт возможность полного и точного отката при ошибке - то есть обеспечивает атомарность операции и целостность кластера.

Рассмотрим некоторые полезные техники Helm для решения типичных задач, с которыми девопс инженер сталкивается за пределами простого, понятного, нежно-розового мира hello world:

  • управление конфигурацией множества сред

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

  • повышение стабильности пайплайнов

Конфигурация множества сред

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

Другие тестовые среды предназначены, например, для приёмочного тестирования реальными пользователями (по уровню ответственности не Production - но весьма похожие). Такие среды обычно используются несколькими командами, поэтому все ожидают от них стабильности.

Production-среды имеют общие моменты, характерные для production, например реальный секретный ключ для платёжной системы. Но, тем не менее, могут различаться в других аспектах: например по региону, среда для "канареечных" релизов для тестов на малой группе, или по регионам. Или же может быть несколько production сред для каждого клиента или их группы, если ваш сервис больше похож на SaaS.

12 заповедей

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

Однако в скрижалях с 12 заповедями не сообщается подробностей - как именно передать эти значения в среды прозрачным, безопасным и контролируемым образом и где все это хранить. Особенно когда вам нужно поддерживать много сред, похожих по одним аспектам, но разных по другим. И как быть с некоторыми значениями конфигурации, которые лучше держать в секрете? Чтобы успешно справиться со всей этой сложностью с помощью Helm, необходимо внести некоторые улучшения в стандартную компоновку chart.

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

Код с конфигурацией - как мясное с молочным? Код с конфигурацией - как мясное с молочным?

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

Каждый новый билд порождает неизменяемые (immutable) контейнер(ы) с кодом, и Helm chart, который можно применить для любой среды - от локального docker-desktop до production кластера в AWS.

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

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

Следовательно:

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

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

  • а ещё больше мы не хотим ничего копипастить - это ведёт к визуальному мусору, глупым ошибкам, повышению затрат на поддержку - поэтому

    • каждое значение конфигурации и/или файл должны храниться в одном и только в одном месте,

    • если значения или файлы различаются в зависимости от среды, в каждой среде сохраняются только отличающиеся части,

    • добавление файла в конфигурацию должно требовать именно этого - добавление файла: никаких изменений в пицот других yaml-ов!

Мы будем хранить конфигурации всех наших сред в диаграмме Helm как часть chart.

Пример ниже, дополнительные каталоги выделены (+).

/env             // (+) значения для сред /<chart-name>    // chart    /files         // (+) конфигурационные файлы и их шаблоны     /templates     // шаблоны Helm   Chart.yaml     // заглавный файл chart  values.yaml    // значения по умолчанию

Файлы со значениями для сред

Давайте посмотрим подробнее на структуру ваших сред.

Допустим у вас есть два типа, TEST и PROD для тестовых и продакшен сред, соответственно. тип TEST делится на две разновидности -STABLE и -PR (пул реквест, нестабильная среда), а для типа PROD у вас разновидности это регионы, EU и US.

Получается примерно такая структура для /env (значения для сред) и /files (файлы конфигурации):

/env                  TEST.yaml            // общие значения для всех тестовых сред  TEST-PR.yaml         // только для PR/нестабильной  TEST-STABLE.yaml     // только для стабильной     PROD.yaml            // общие значения для всех продакшен сред  PROD-EU.yaml         // продакшен EU     PROD-US.yaml         // продакшен US /files                     /TEST                // общие файлы для всех тестовых сред  /TEST-PR             // ...  /TEST-STABLE         // ...    /PROD                // общие файоы для всех продакшен сред   /PROD-EU             // ...  /PROD-US             // ...  /shared              // файлы общие для всех средvalues.yaml             // значения общие для всех сред

Теперь посмотрим что внутри /files - текстовые и бинарные файлы конфигурации.

.../PROD    /binary    /text/PROD-EU    /binary    /text .../shared    /binary    /text    /secret-text

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

Не все типы файлов представлены на всех уровнях, но всему есть причина, давайте подробнее рассмотрим.

1. Мы предполагаем что секретные файлы только текстовые а не бинарные. Почему? Потому что так проще. Секретный двоичный файл (например .p12 сертификат) становится несекретным, если зашифровать его секретным ключом с достаточной (скажем 120+ бит) энтропией - и можно хранить его просто в гите, даже если он размеров в несколько (десятков) килобайт. С точки зрения безопасности - это просто рандомный набор битов. А вот ключ, отпирающий этот бинарник, мы будем хранить в строгом секрете - как и все другие-остальные пароли.

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

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

  • среда - разновидность (TEST-STABLE.yaml)

  • среда - тип (TEST.yaml)

  • общие значения (values.yaml)

Helm позволяет это сделать, указав файлы со значениями как последовательность опций --values:

helm upgrade --install <chart> path/to/<chart> --strict \     --values env/<env>.yaml --values env/<env>-<flavour>.yaml

В .yaml-файлах разновидности и типа среды содержатся атрибуты, например TEST-STABLE.yaml среди прочего содержит:

envFlavour: STABLE

а TEST.yaml содержит

envClass: TEST

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

Один ConfigMap и один Secret для всех файлов

Смотрим внимательно - вот одна, единая конфигурация для одного единственного ConfigMap и одного Secret, куда поместятся все ваши файлы. Бинарные файлы и текстовые несекретные файлы пойдут в ConfigMap, а секретные текстовые файлы в Secret.

# это нужно для вложенных range{{- $self := . -}} # список директорий, откуда берутся файлы - среда-разновидность, среда-тип и потом общие файлы из shared{{ $sources := (list "shared" .Values.envClass (printf "%s-%s" .Values.envFlavour .Values.envClass ) }}apiVersion: v1kind: ConfigMapmetadata:  name: myapp# вставить несекретные текстовые файлы как шаблоныdata:{{ range $env := $sources }}{{ range $path, $bytes := $self.Files.Glob (printf "files/%s/text/*" $env) }}  {{ base $path }}: {{ tpl ($self.Files.Get $path) $ | quote }}{{ end }}{{ end }}# вставить двоичные файлыbinaryData:{{ range $env := $sources }}{{ range $path, $bytes := $self.Files.Glob (printf "files/%s/binary/*" $env) }}  {{ base $path }}: {{ $self.Files.Get $path | b64enc | quote }}{{ end }}{{ end }}---apiVersion: v1kind: Secretmetadata:  name: myapp  labels:type: Opaquedata:# вставить секретные текстовые файлы как шаблоны{{ range $env := $sources }}{{ range $path, $bytes := $self.Files.Glob (printf "files/%s/secret-text/*" $env) }}  {{ base $path }}: {{ tpl ($self.Files.Get $path) $ | b64enc | quote }}{{ end }}{{ end }}

И это всё что нужно! Ничего не надо менять, если добавляется новый файл. Как только файл оказывается в нужном месте, он будет автоматически найден и добавлен в дескриптор, никаких изменений не требуется.

Тотальная шаблонизация

Имеющие опыт с Helm, возможно, задаются вопросом, к чему все эти хитрые танцы, если у Helm уже есть набор функций для ConfigMaps и Secrets?

А вот почему. Заметили маленькую функцию tpl, применяемую на каждый файл? Правильно, именно поэтому она нужна, чтобы каждый текстовый файл обрабатывался как отдельный шаблон - вы можете вставлять ссылки на значения как {{ .Values.myValue }}в любое место ваших текстовых файлов конфигурации.

Шаблон может использоваться для любого типа конфигурации, .properties, yaml, HOCON, например:

akka {  persistence {    cassandra {        keyspace = {{ .Values.cassandra.keyspace | quote }}        table = "{{ .Values.cassandra.tablePrefix }}messages"

Коварные кавычки

Кавычки в значении могут оказаться как лишними, так и наоборот, в зависимости от формата файла.

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

databasePassword: {{ .Values.databasePassword | quote }}

Для других значений, например в файле .properties, кавычки наоборот, вредны, поэтому их можно убрать вот так:

param/username={{ .Values.username | trimAll "\"" }}

Проецируемые тома (projected volumes)

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

Для этого в Kubernetes удачно завезли projected volumes - проецируемые тома, которые можно собирать из нескольких ConfigMaps и Secrets.

volumes:  - name: properties    projected:      defaultMode: 0640      sources:        - configMap:            name: myapp        - secret:            name: myapp

Очень просто смонтировать такой "сборный" том в директорию/confвашего приложения.

Линтер

Не вредно бывает запускать линтер для проверки chart на вменяемость, чтобы при ошибке пайплайн падал не в момент деплоймента, а существенно раньше.

У Helm есть для этого команды lint и template:

helm lint --debug path/to/<chart> --strict --values env/<env>.yaml \  --values env/<env>-<flavour>.yaml  helm template <chart> path/to/<chart> --strict --values env/<env>.yaml \  --values env/<env>-<flavour>.yaml

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

Но совершенству нет пределов (почти) - можно пойти ещё на шаг дальше и использовать yamllint для валидации yaml-дескрипторов. Это позволит отловить проблемы, которые иначе не получается ловить - например два файла с одним и тем же именем, которые оказались в PROD и PROD-EU, будут дважды вставлены в ConfigMap, что приведёт к ошибке при деплойменте.

Управление секретами

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

Обычно секретные значения хранятся в отдельном сервисе, типа Heroku Vault, Azure Vault, Google Cloud KMS и подобных. В Helm даже есть плагин для управления секретами,но в большинстве компаний управление секретами централизовано, и инженерам не позволено, да и не нужно, трогать секреты из production.

Когда пайплайн запускает обновление сервиса в подобной среде, то сам пайплайн имеет возможность считать секреты и вставить их в конфигурационные файлы. В большинстве случаев (Gitlab, Circle, Azure, ...) секреты становятся переменными среды, и всё что требуется - это вставить их в шаблон в самом начале.

Для этого мы добавим секцию в values.yaml

# secretsdatabase_username: "${UserNameSecret}"database_password: "${DatabasePasswordSecret}"

И в нашем пайплайне испольуемenvsubstили нечто похожее:

cat <chart>/values.yaml | envsubst > <chart>/values-injected.yamlmv <chart>/values-injected.yaml <chart>/values.yaml

Такой подход позволяет ссылаться на секреты просто как {{ .Value.xxx }} в любом шаблоне, вставляя их туда куда им положено быть.

Но полезно помнить, однако, что ничто автоматически не предотвратит ошибочное вставление секретного значения в несекретный текстовый файл.

Чтобы решить этот вопрос, можно ввести конвенцию называть секреты как XXXSecret, и добавить что-то типа такого:

EXPOSED_SECRETS=$(grep Secret <chart>/files | grep -v secret-files | wc -l)if [ $EXPOSED_SECRETS -gt 0 ]; then fail "Secrets are exposed"; fi

Это добавит уровень защиты против случайной потери секрета.

Атомарные обновления сред

Теперь последний раздел - как использовать Helm hooks для того, чтобы повысить надёжность ваших пайплайнов.

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

Это может показаться сложным - особенно если вы хотите реализовать это самостоятельно, вооружившись простым kubectl apply -f ... Но, к счастью, Helm многое делает "прямо из коробки".

Флаг --atomic

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

helm upgrade --install my-chart some/path/to/my-chart \    --atomic --debug --timeout 300s

Helm откатит обновление, если проверки проб health/readiness не дали положительного результата в указанный срок. Хорошо, но можно лучше.

Hooks

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

И разумеется, сигнализировать Helm откатить обновление, если тест не прошёл.

apiVersion: batch/v1kind: Jobmetadata:  name: myapp  labels:  annotations:     "helm.sh/hook": post-install,post-upgrade     "helm.sh/hook-delete-policy": before-hook-creation,hook-succeededspec:  template:    metadata:      name: myapp-smoke-test    spec:      restartPolicy: Never      containers:        - name: tests          image: test-image:           command: ['/bin/sh',                    '-c',                    '/test/run-test.sh']

Если вы используете--atomicфлаг и post-upgrade/post-install hook для тестов в пайплайне, вы можете со значительной долей уверенности считать пайплайн надёжным. Он будет иметь "зелёный" статус тогда, и только тогда, когда сервис был успешно обновлён, запущен и прошёл базовые тесты.

А если что-то пошло не так - Helm возвратит среду в то состояние, которое было до этого обновление, включая все конфигурации и дескрипторы.

Автоматически!

Заключение

Helm это бесплатный инструмент с открытым кодом для управления обновлениями сервисов и их конфигураций в кластерах Kubernetes.

Используя шаблоны и hooks, можно добиться того, что ваш continuous delivery плавен и надёжен настолько, что его практически никто не замечает.

***

Этот текст является авторским переводом, оригинал статьи этого же автора
https://jacum.medium.com/advanced-helm-practices-for-perfect-kubernetes-deployments-7fc4e00cc41c

Подробно об авторе - https://www.linkedin.com/in/tim-evdokimov/

Подробнее..

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

25.03.2021 22:22:00 | Автор: admin

В преддверии старта курса "Microservice Architecture" подготовили для вас традиционный перевод материала.


При проектировании и планировании новой архитектуры на основе (микро) сервисов бывают моменты, когда архитекторам приходится думать о стратегии развертывания и, следовательно, задаваться вопросом: Должны ли мы развернуть этот (микро) сервис как бессерверную функцию или лучше поместить его в контейнер? Или, быть может, лучше использовать выделенную виртуальную машину (VM)?

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

Кроме того, их модель оплаты по мере использования (pay per use) очень привлекательна, когда мы не уверены, какая нагрузка придется на наше приложение. Позже, когда сервис станет зрелым и нагрузка станет предсказуемой, может оказаться целесообразным перейти к более традиционной топологии развертывания, основанной на контейнерах или выделенных серверах.

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

Бессерверные функции

Бессерверные функции (Serverless Functions, также известные как FaaS, функция как сервис) - это блоки определенной логики, которые создаются и выполняются в ответ на заданные события, такие как HTTP-запросы или сообщения, полученные в топике Kafka. По завершении своего выполнения такие функции исчезают, по крайней мере, логически, и их стоимость возвращается к нулю.

FAAS реагирует на HTTP-запросы: множественное параллельное выполнение и модель pay per useFAAS реагирует на HTTP-запросы: множественное параллельное выполнение и модель pay per use

Все крупные общедоступные облака имеют FAAS предложения (AWS Lambda, Azure Functions, Google Functions, Oracle Cloud Functions). Кроме того FAAS также могут быть доступны в локальных вариациях с помощью таких фреймворков, как Apache OpenWhisk. У них есть некоторые ограничения с точки зрения ресурсов (например, для AWS максимум 10 ГБ памяти и 15 минут времени выполнения), но они могут покрыть многие варианты использования современных приложений.

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

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

Преимущества FaaS

Когда бессерверные функции простаивают, они ничего вам не стоят (модель Pay per use). Если бессерверная функция вызывается 10 клиентами одновременно, 10 ее инстансов запускаются почти одновременно (по крайней мере, в большинстве случаев). Полное предоставление инфраструктуры, управление, высокая доступность (по крайней мере, до определенного уровня) и масштабирование (от 0 до лимитов, определенных клиентом) полностью предоставляются командами специалистов, работающих за кулисами.

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

Таким образом, FaaS подразумевает два больших преимущества.

  • Эластичность на стероидах: масштабирование вверх и вниз по необходимости и оплата только за то, что используется.

  • Фокус на том, что отличает ваш бизнес: сконцентрируйте силы на разработке наиболее важных приложений, не тратя драгоценную энергию на сложные области, такие как современные инфраструктуры, которые FaaS предлагает вам в качестве товара.

Эластичность и затраты

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

Новый сервис должен быстро выходить на рынок с минимально возможными стартовыми вложениями и с самого начала должен быть хорошим сервисом.

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

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

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

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

Бессерверные функции могут СЭКОНОМИТЬ ВАМ МНОГО ДЕНЕГ, ровно также как и могут СТОИТЬ ВАМ БОЛЬШИХ ДЕНЕГ

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

Пример приложения. Рассмотрим приложение, которое получает 3.000.000 запросов в месяц. Обработка каждого запроса с помощью Lambda с 4 ГБ памяти занимает 500 мс (ЦП назначается автоматически в зависимости от памяти).

FaaS имеет модель pay per use, поэтому, независимо от кривой нагрузки (будь то пиковая или фиксированная), стоимость в месяц является фиксированной: 100,60 долларов США.

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

Сценарий с пиками нагрузки. Если для нагрузки характерны пиковые моменты, и мы хотим гарантировать постоянное хорошее время отклика для наших клиентов, нам необходимо определить размер инфраструктуры, чтобы выдерживать пиковую нагрузку. Если на пике у нас есть 10 одновременных запросов в секунду (что вполне возможно, если 3.000.000 запросов сосредоточены в определенные часы дня или в определенные дни, например, в конце месяца), вполне возможно, что нам понадобится виртуальная машина (AWS EC2) с 8 процессорами и 32 ГБ памяти, чтобы обеспечить ту же производительность, что и Lambda. В этом случае ежемесячная стоимость подскочит до 197,22 долларов США (можно сэкономить при заключении многолетнего контракта, но это снижает финансовую гибкость). Затраты увеличились почти вдвое. Эту разницу можно уменьшить путем динамического включения и выключения экземпляров EC2 в зависимости от нагрузки, но для этого требуется, чтобы нагрузка была предсказуемой, что увеличивает сложность и стоимость решения.

Сценарий с равномерной нагрузкой. Если нагрузка в основном равномерная, то дела обстоят совсем по другому. Если нет пиков, то мы можем легко выдержать нагрузку с помощью гораздо более дешевой машины. Вероятно, будет достаточно виртуальной машины с 2 процессорами и 8 МБ памяти, а ежемесячные затраты в этом случае составят 31,73 доллара США, что меньше трети стоимости Lambda.

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

Тут возникает вопрос: как мы можем достичь такой гибкости? Насколько это будет сложно?

Анатомия кодовой базы современного приложения

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

  • Логика приложения. Код (обычно написанный на таких языках, как Java, TypeScript или Go), который реализует то, что должно делать наше приложение

  • DevSecOps (CI/CD). Обычно это скрипты и файлы конфигурации, которые автоматизируют сборку, тестирование, проверки безопасности и развертывание приложения.

Логика приложения

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

  • Бизнес-логика. Код, который реализует поведение службы, выраженное в форме логических API (методов или функций), которые обычно ожидают некоторые данные, например, в формате JSON, в качестве входных и возвращают некоторые данные в качестве выходных. Этот код не зависит от технических механизмов, связанных с реальной средой, в которой он выполняется, будь то контейнер, бессерверная функция или сервер приложения. Находясь в контейнере, эти логические API могут быть вызваны чем-нибудь наподобие Spring Boot (если языком является Java), Express (с Node) или Gorilla (с Go). При вызове в бессерверной функции он будет использовать конкретный механизм FaaS, реализованный конкретным облачным провайдером.

  • Код, связанный с развертыванием. Код, который касается механики среды выполнения. Если необходимо поддерживать более одной модели развертывания, должны быть разные реализации этой части (но только этой части). В случае развертывания в контейнерах это та часть, где сосредоточены зависимости от аналогов Spring Boot, Express или Gorilla. В случае FaaS эта часть будет содержать код, реализующий механизмы, определенные конкретным облачным провайдером (функции AWS Lambda, Azure или Google Cloud, которые имеют собственные проприетарные библиотеки для вызова бизнес-логики).

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

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

  • Кода, связанный с развертыванием импортирует модули бизнес-логики

  • Бизнес-логика никогда не импортирует какие-либо модули/пакеты, которые зависят от конкретной среды выполнения.

Следуя этим двум простым правилам, мы максимизируем объем кода (бизнес-логики), пригодного для использования всеми моделями развертывания, и, следовательно, минимизируем стоимость перехода от одной модели к другой.

Невозможно абстрактно оценить относительные размеры частей бизнес-логики и кода, связанного с развертыванием. Но на примере, анализируя одну простую интерактивную игру, развертываемую как на AWS Lambda, так и на Google Application Engine, выясняется, что код, связанный с развертыванием, составляет 6% от кодовой базы (всего около 7 200 строк кода). Таким образом, 94% кодовой базы одинаковы, независимо от того, работает ли служба в Lambda или в контейнере.

DevSecOps (CI/CD)

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

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

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

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

Стремитесь изолировать то, что не зависит от модели развертывания, и максимизировать это

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

Разделение обязанностей между частями кодовой базы современного приложенияРазделение обязанностей между частями кодовой базы современного приложения

Заключение

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

Но со временем все может измениться. Нагрузки могут стать более стабильными и предсказуемыми, и в таких обстоятельствах модели FaaS могут оказаться намного дороже, чем более традиционные модели, основанные на выделенных ресурсах.

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

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


Узнать подробнее о курсе "Microservice Architecture".

Подробнее..

Управление инфраструктурой Open Telekom Cloud с помощью Ansible

06.05.2021 10:07:53 | Автор: admin

Open Telekom Cloud

В этой статье расскажу о нашем опыте работы над развитием инструментов управления инфраструктурой облачного сервиса Open Telekom Cloud, как мы столкнулись с особенностями этого облака, какие решения принимали и какие инструменты использовали.

Open Telekom Cloud международная публичная облачная платформа, основанная на OpenStack. Платформа идеально подходит для компаний или стартапов, которые работают с европейскими пользователями, чьи персональные данные должны храниться в пределах Евросоюза: сервис разработан Deutsche Telekom и соответствует стандартам защиты данных GDPR (Генеральный регламент о защите персональных данных) EC.

С чего все начиналось

Почти два года назад в поисках специалистов в Россию пришел проект Open Telekom Cloud. Требовалось много людей на автоматизированное тестирование и несколько человек в спецотряд под названием Ecosystems, требования были очень расплывчатые: Ну, надо знать Python и понимать, как работать с облачными сервисами

В то время, по удачному стечению обстоятельств, завершалось несколько проектов в Воронеже, и около 10 человек были готовы к взятию новых барьеров. Самых опытных из них отправили в команду Ecosystems, остальные отправились в QA.

Команда Ecosystems занималась API мониторингом, мониторингом сервисов, созданием модулей для Ansible, разработкой и поддержкой инструментов управления инфраструктурой Open Telekom Cloud. На данный момент она участвует еще и в разработке Terraform Provider, OpenStack SDK, OpenStack Ansible Collections. Во всех наших инструментах (OTC Extensions, Terraform Provider, Ansible Collections) мы стараемся максимально соответствовать OpenStack и переиспользовать существующие решения для него.

С самого начала с Open Telekom Cloud все оказалось довольно интересно. Разработка находится на стороне Huawei, декларировалось, что облако основано полностью на технологии OpenStack. Но Huawei внесли множество своих решений в сервисы. Многие из них были полностью написаны китайскими коллегами, были заметные отличия нашего API от OpenStack API.

Но тогда это нас не сильно волновало. Первой нашей задачей в Ecosystems было создание мониторингов, которые помогут определить качество работы тех или иных сервисов, в сложных сценариях. Например, использовать балансировщик нагрузки для хостов в разных AZ (availability zone), наблюдать за распределением запросов по каждому из хостов. Или следить за отказоустойчивостью того же балансировщика нагрузки в сценарии, когда один или несколько хостов за ним выключаются по тем или иным причинам.

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

Что ж, раз Terraform стал для нас критичным инструментом, мы отправились в репозиторий с провайдером и начали исправлять баги. В какой-то момент поддержка провайдера со стороны Huawei прекратилась, да и через некоторое время HashiCorp решили всех сторонних провайдеров убрать из своего репозитория.

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

С начала работы на проекте прошло примерно полгода, из-за провайдера объем работы вырос и стало понятно, что два человека со всем не справятся. Мы набрали в команду толковых ребят, и часть из них стала заниматься развитием и поддержкой Terraform провайдера, часть осталась на мониторингах.

Ansible и коллекции

Опустив некоторые детали, первоначально мониторинг работал примерно так:

Точкой входа был AWX, он вызывал плейбуки с ролью Terraform, результат выполнения Terraform снова передавался в Ansible, и далее выполнялись какие-то сценарии.

Кажется, что все отлично, есть базовый .tf модуль, который создает сетевую часть, и отдельные модули на каждый сценарий, .state всех модулей хранится в s3. Все удобно, работает как часы.

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

Был только Python и Ansible

Учитывая, что Open Telekom Cloud не является решением, на 100% совместимым с OpenStack, в нем присутствуют сервисы собственной разработки, например, RDS (Relational Database Service). С помощью Ansible мы не можем построить все необходимые нам ресурсы используя OpenStack SDK и ansible-collections-openstack, в таком виде, чтобы это было легко поддерживать.

Что ж, надо расширять возможности OpenStack SDK, адаптировать под наш проект и писать собственные коллекции. Для коллекций необходимо описание ресурсов, которых нет в OpenStack SDK, для таких ресурсов был создан проект OTC Extensions.

OTC Extensions

Этот проект дополняет и расширяет функции OpenStack SDK для работы с Open Telekom Cloud, так же если он установлен в качестве python package, в OpenStack Client добавляются дополнительные плагины для работы с облаком.

Взаимодействует с:

python-openstacksdk

python-openstackclient

Структура проекта близка к OpenStack SDK:

otcextensions/    sdk/        compute/            v2/                server.py                _proxy.py    tests/        unit/            sdk/                compute/                    v2/                        test_server.py

Все дополнительные ресурсы унаследованы от базового openstack.resource.Resource, или если мы хотим изменить существующий объект то нужно наследование от него базового класса этого объекта, например, если у openstack.compute.v2.server нет поддержки тэгов или они реализованы иначе:

class Server(server.Server):    def add_tag(self, session, tag):        """Adds a single tag to the resource."""    def remove_tag(self, session, tag):        """Removes a single tag from the specified server."""

И далее патчим Connection в методе load (otcextensions/sdk/__init__.py):

openstack.compute.v2.server.Server.add_tag = server.Server.add_tagopenstack.compute.v2.server.Server.remove_tag = server.Server.remove_tag

В итоге наш connection теперь будет работать с кастомными тегами.

Для нового ресурса:

otcextensions/    sdk/        elb/            v2/                elb_certificate.py                _proxy.py

В файле elb_certificate.py создаем класс, указываем его url, какие методы поддерживает, какие параметры принимает

class Certificate(resource.Resource):resources_key = 'certificates'base_path = ('/lbaas/certificates')# capabilitiesallow_create = Trueallow_fetch = Trueallow_commit = Trueallow_delete = Trueallow_list = True_query_mapping = resource.QueryParameters(    'id', 'name', 'description',    'type', 'domain', 'content',    'private_key', 'marker', 'limit',)# Properties#: Namename = resource.Body('name')#: Idid = resource.Body('id')#: Descriptiondescription = resource.Body('description')#: Certificate type.type = resource.Body('type')#: Domain name associated with the server certificate.domain = resource.Body('domain')#: Private key of the server certificate. *Type: string*private_key = resource.Body('private_key')#: Public key of the server certificate or CA certificate. *Type: string*content = resource.Body('certificate')#: Administrative status of the certificate.admin_state_up = resource.Body('admin_state_up')#: Creation timecreate_time = resource.Body('create_time')#: Specifies the project ID.project_id = resource.Body('tenant_id')#: Time when the certificate expires.expire_time = resource.Body('expire_time')#: Time when the certificate was updated.update_time = resource.Body('update_time')

Рядом обязательно должен быть файл _proxy.py, этот класс адаптер предоставляет интерфейс для работы с инстансом Connection, в нем мы описываем методы ресурса:

class Proxy(_proxy.Proxy):    skip_discovery = True    # ======== Certificate ========    def create_certificate(self, **attrs):        return self._create(_certificate.Certificate, **attrs)    def certificates(self, **query):        return self._list(_certificate.Certificate, **query)    def delete_certificate(self, certificate, ignore_missing=True):        return self._delete(_certificate.Certificate, certificate,                            ignore_missing=ignore_missing)    def get_certificate(self, certificate):        return self._get(_certificate.Certificate, certificate)    def update_certificate(self, certificate, **attrs):        return self._update(_certificate.Certificate, certificate, **attrs)    def find_certificate(self, name_or_id, ignore_missing=False):        return self._find(_certificate.Certificate, name_or_id,                          ignore_missing=ignore_missing)

В otcextensions/sdk/__init__.py eсть структура со всеми нестандартными ресурсами - OTC_SERVICES, добавляем наш ресурс по имени папки в которой он находится:

'elb': {    'service_type': 'elb',    'replace_system': True}

OTC_SERVICES так же в методе load, добавляются в Connection:

for (service_name, service) in OTC_SERVICES.items():    if service.get('replace_system', False):        if service['service_type'] in conn._proxies:            del conn._proxies[service['service_type']]    sd = _get_descriptor(service_name)    conn.add_service(sd)

На этом добавление сервиса завершено, мы можем его использовать через OpenStack SDK.

cfg = openstack.config.get_cloud_region(cloud=TEST_CLOUD_NAME)conn = connection.Connection(config=cfg)sdk.register_otc_extensions(conn)cert = conn.elb.create_certificate(    private_key=PRIVATE_KEY,    content=CERTIFICATE,    name=NAME )

Ansible collections

Окей, ресурсы теперь есть, осталось разобраться как их использовать, есть отличный вариант, создать коллекцию своих модулей и хранить ее в ansible-galaxy, по аналогии с ansible-collections-openstack создаем коллекцию ansible-collection-cloud, которая основана на OTC extensions.

Если модуль, который мы добавляем в коллекцию существует в OpenStack коллекции, то мы стараемся максимально обеспечить обратную совместимость, создавая единый интерфейс для модулей.

Делаем все по гайду (developing-collections):

ansible-collection-cloud/    plugins/        module_utils/            otc.py        modules/            elb_certificate.py            elb_certificate_info.py

В module_utils, храним базовый для всех модулей класс:

class OTCModule:    """Openstack Module is a base class for all Openstack Module classes.    The class has `run` function that should be overriden in child classes,    the provided methods include:    """

В нем создается инстанс Connection, и патчится через OTC extensions, чтобы мы могли использовать кастомные ресурсы.

Все модули делятся на два типа с постфиксом _info возвращают информацию о существующем ресурсе, без него создают/изменяют/удаляют ресурсы.

Например, lb_certificate_info:

from ansible_collections.opentelekomcloud.cloud.plugins.module_utils.otc import OTCModuleclass LoadBalancerCertificateInfoModule(OTCModule):    argument_spec = dict(        name=dict(required=False)    )    otce_min_version = '0.10.0'    def run(self):        data = []        if self.params['name']:            raw = self.conn.elb.find_certificate(name_or_id=self.params['name'], ignore_missing=True)            if raw:                dt = raw.to_dict()                dt.pop('location')                data.append(dt)        else:            for raw in self.conn.elb.certificates():                dt = raw.to_dict()                dt.pop('location')                data.append(dt)        self.exit_json(            changed=False,            elb_certificates=data        )def main():    module = LoadBalancerCertificateInfoModule()    module()if __name__ == '__main__':    main()

аналогично выполнен и lb_certificate.

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

Установка коллекций

Для начала работы необходимо установить коллекции в окружение, для примера используем venv (venv использовать необязательно, но такой подход имеет свои плюсы):

/$ cd ~~$ python3 -m venv ansiblevenv

Активируем окружение:

~$ source ansiblevenv/bin/activate(ansiblevenv) ~$

Установим OpenStack Client, otcextensions и wheel (необязательно):

(ansiblevenv) ~$ pip install wheel(ansiblevenv) ~$ pip install openstackclient(ansiblevenv) ~$ pip install otcextensions

Для работы с коллекциями далее необходимо установить их из Ansible-Galaxy (Ansible-Galaxy содержит множество свободно распространяемых ролей и коллекций, разрабатываемых сообществом). Дополнительно ставим OpenStack коллекцию для нативных ресурсов:

(ansiblevenv) $ ansible-galaxy collection install opentelekomcloud.cloud(ansiblevenv) $ ansible-galaxy collection install openstack.cloud

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

Авторизация

clouds.yaml

OpenStack client/sdk самостоятельно ищет файл для авторизации в следующих местах:

  1. system-wide (/etc/openstack/{clouds,secure}.yaml)

  2. Home directory / user space (~/.config/openstack/{clouds,secure}.yaml)

  3. Current directory (./{clouds,secure}.yaml)

clouds:  otc:    profile: otc    auth:      username: '<USER_NAME>'      password: '<PASSWORD>'      project_name: '<eu-de_project>'      # or project_id: '<123456_PROJECT_ID>'      user_domain_name: 'OTC00000000001000000xxx'      # or user_domain_id: '<123456_DOMAIN_ID>'    account_key: '<AK_VALUE>' # AK/SK pair for access to OBS    secret_key: '<SK_VALUE>'

После того, как файл создан, указываем переменной окружения OS_CLOUD имя конфигурации, в данном случае:

~$ export OS_CLOUD=otc

Имя может быть любым, и один файл может содержать множество конфигураций.

Чтобы проверить, что все сделано правильно, можно запустить любую команду OpenStack клиента:

~$ openstack server list

Если авторизация успешна, то мы получим список серверов:

Чтобы повысить безопасность, можно вынести чувствительную информацию из clouds.yaml. Рядом с файлом clouds.yaml создаем secure.yaml и помещаем туда все, что хотим скрыть:

clouds:  otc:    auth:      password: '<PASSWORD>'

Переменные окружения

Этот способ заключается в простом использовании переменных окружения, которые можно задавать вручную, либо создать файл, например, .ostackrc:

# .ostackrc fileexport OS_USERNAME="<USER_NAME>"export OS_USER_DOMAIN_NAME=<OTC00000000001000000XYZ>export OS_PASSWORD=<PASSWORD> # optionalexport OS_TENANT_NAME=eu-deexport OS_PROJECT_NAME=<eu-de_PROJECT_NAME>export OS_AUTH_URL=https://iam.eu-de.otc.t-systems.com:443/v3export NOVA_ENDPOINT_TYPE=publicURLexport OS_ENDPOINT_TYPE=publicURLexport CINDER_ENDPOINT_TYPE=publicURLexport OS_VOLUME_API_VERSION=2export OS_IDENTITY_API_VERSION=3export OS_IMAGE_API_VERSION=2

Создаем переменные:

~$ source .ostackrc

С авторизацией разобрались! Теперь можно полноценно использовать коллекции.

Использование коллекции

Как мы знаем в коллекции два типа модулей: с постфиксом info возвращают информацию о существующем ресурсе, без него создают/изменяют/удаляют ресурсы. Все модули вызываются по полному имени: opentelekom.cloud.*

Все info модули поддерживают поиск как по имени, так и по id ресурса, например:

- name: Get loadbalancer info  opentelekomcloud.cloud.loadbalancer_info:    name: "{{ lb_name_or_id }}"  register: result

Если передано имя ресурса, то в ответе вернется dict с параметрами ресурса, если имя не указано, то появится список всех доступных в проекте ресурсов. Не инфо модули также возвращают dict.

Пример сценария

Для примера использования коллекций создадим файл example.yaml и будем там описывать различные ресурсы. Создадим небольшую инфраструктуру: сеть, сервер и балансировщик нагрузки.

Для создания нативных ресурсов всегда используются OpenStack модули, например, сеть:

---- name: Create main network  openstack.cloud.network:    name: my_network  register: net- name: Getting info about external network  openstack.cloud.networks_info:    name: admin_external_net  register: ext_net- name: Create subnet  openstack.cloud.subnet:    name: my_subnet    network_name: "{{ net.network.name }}"    cidr: 192.168.0.0/16    dns_nameservers:          - 100.125.4.25          - 100.125.129.199  register: subnet- name: Create router  openstack.cloud.router:    name: "{{ public_router_scenario }}_router"    enable_snat: true    network: "{{ ext_net.openstack_networks[0].id }}"    interfaces:      - "{{ subnet.subnet.name }}"  register: router

Для сервера нам нужен ключ:

- name: Create key pair  openstack.cloud.keypair:    name: bastion_key_pair    public_key_file: "/tmp/keys/public.pub"  register: keypair

Создадим security group, откроем порты 80, 443 и 22 для ssh, также откроем icmp:

- name: Create security group  openstack.cloud.security_group:    name: bastion_secgroup    description: Allow external connections to ssh, http, https and icmp  register: sec_group- name: Add rules for tcp connection to the security group  openstack.cloud.security_group_rule:    security_group: "{{ sec_group.secgroup.name }}"    protocol: tcp    port_range_min: "{{ item }}"    port_range_max: "{{ item }}"    remote_ip_prefix: 0.0.0.0/0  loop:     - 22    - 80    - 443- name: Add a rule for icmp connection to the security group  openstack.cloud.security_group_rule:    security_group: "{{ secur_group.secgroup.name }}"    protocol: icmp    port_range_min: -1    port_range_max: -1    remote_ip_prefix: 0.0.0.0/0

Для подключения сервера к сети необходимо создать порт:

- name: Create a port for a bastion  openstack.cloud.port:    name: bastion_port    network: net.network.id    security_groups:      - "{{ sec_group.secgroup.name }}"     fixed_ips:       - ip_address: 192.168.200.10  register: port

Для создания сервера тоже используются нативные модули. Например, создадим bastion (это те хосты, которые принято использовать как jump для доступа в недоступные снаружи сети). Здесь также представлен пример инъекции команд при создании сервера через userdata:

- name: Getting information about a current image  openstack.cloud.image_info:    image: Standard_Debian_10_latest  register: image- name: Create a new instance  openstack.cloud.server:    state: present    name: bastion    flavor: s2.medium.2    key_name: bastion_key_pair    availability_zone: eu-de-01    security_groups:     - "{{ sec_group.secgroup.name }}"    timeout: 200    userdata: |      {%- raw -%}#!/usr/bin/env bash                 #setup ssh service config                 file=/etc/ssh/sshd_config                 cp -p $file $file.old &&                     while read key other; do                         case $key in                         GatewayPorts) other=yes ;;                         AllowTcpForwarding) other=yes ;;                         PubkeyAuthentication) other=yes ;;                         PermitTunnel) other=yes ;;                         esac                         echo "$key $other"                     done <$file.old > $file                 sudo service sshd restart                 mkdir -p /etc/sslcerts/live                 #generate Diffie-Hellman for TLS                 sudo openssl dhparam -out /etc/sslcerts/live/dhparams.pem 2048      {% endraw %}    nics:      - port-name: "{{ port.port.name }}"    boot_from_volume: true    volume_size: 5    image: "{{ image.openstack_image.id }}"    terminate_volume: true    delete_fip: true    auto_ip: true  register: bastion

Для динамической регистрации хоста используем add_host:

- name: Register nodes  add_host:    name: "{{ bastion.openstack.name }}"    groups: bastions    ansible_host: "{{ bastion.openstack.interface_ip }}"    ansible_ssh_user: linux    ansible_ssh_private_key_file: "/path/to/key"

После создания сервера можно проверить подключение:

- name: Wait for nodes to be up  hosts: bastions  gather_facts: no  tasks:    - name: Wait for nodes to be up      wait_for_connection:        timeout: 250

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

После того, как у нас создана сеть и есть хотя бы один сервер, мы можем создать loadbalancer:

- name: Create loadbalancer  opentelekomcloud.cloud.loadbalancer:    name: my_elastic_loadbalancer    state: present    vip_subnet: "{{ subnet.subet.id }}"    vip_address: 192.168.200.100    auto_public_ip: true  register: loadbalancer

Далее для loadbalancer создаем listener, если протокол https, то сразу можем создать сертификат:

- name: Create listener http  opentelekomcloud.cloud.lb_listener:    state: present    name: my_listener_http    protocol: http    protocol_port: 80    loadbalancer: "{{ loadbalancer.loadbalancer.id }}"  register: listener_http- name: Create Server certificate  opentelekomcloud.cloud.lb_certificate:    name: my_https_cetificate    content: "{{ some_https_certificate }}"    private_key: "{{ some_loadbalancer_https_key }}"  register: certificate- name: Create listener https  opentelekomcloud.cloud.lb_listener:    state: present    name: my_listener_https    protocol: terminated_https    protocol_port: 443    loadbalancer: "{{ loadbalancer.loadbalancer.id }}"    default_tls_container_ref: "{{certificate.elb_certificate.id }}"  register: listener_https

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

- name: Create lb pool http  opentelekomcloud.cloud.lb_pool:    state: present    name: my_pool_http    protocol: http    lb_algorithm: round_robin    listener: "{{ listener_http.listener.id }}"  register: lb_pool_http- name: Create lb pool https  opentelekomcloud.cloud.lb_pool:    state: present    name: my_pool_https    protocol: http    lb_algorithm: round_robin    listener: "{{ listener_https.listener.id }}"  register: lb_pool_https

Добавляем сервер в пул:

- name: Create members for a http pool in the load balancer  opentelekomcloud.cloud.lb_member:    state: present    name: my_member_http    pool: "{{ lb_pool_http.server_group.id }}"    address: 192.168.200.10    protocol_port: http    subnet: "{{ subnet.subet.id }}"  register: members_http- name: Create members for a https pool in the load balancer  opentelekomcloud.cloud.lb_member:    state: present    name: my_member_https    pool: "{{ lb_pool_https.server_group.id }}"    address: 192.168.200.10    protocol_port: http    subnet: "{{ subnet.subet.id }}"  register: members_https

И, наконец, добавим healthmonitor для каждого пула, чтобы наблюдать за статусом хостов:

- name: Enable health check for http members  opentelekomcloud.cloud.lb_healthmonitor:    state: present    name: http_healthcheck    pool: "{{ lb_pool_http.server_group.id }}"    delay: 1    max_retries: 2    monitor_timeout: 1    type: http- name: Enable health check for https members  opentelekomcloud.cloud.lb_healthmonitor:    state: present    name: https_healthcheck    pool: "{{ lb_pool_https.server_group.id }}"    delay: 1    max_retries: 2    monitor_timeout: 1    type: http

Если выполнять плейбук с verbosity, то в консоли мы увидим все параметры создаваемых ресурсов.

В результате на консоли можно увидеть наш сервер, балансировщик нагрузки и все остальные ресурсы:

Таким образом мы перевели инфраструктуру наших мониторингов полностью на Ansible.

Насколько мне известно, в России не одна компания пользуется услугами Huawei для создания собственных облачных сервисов, было бы интересно увидеть в комментариях, приходилось ли им решать подобные вопросы касаемо расширения ванильного OpenStack SDK и как они к этому подходили.

Весь код находится в публичном доступе и хранится на Github:

Если тема интересна, то буду рад поделиться своим опытом по работе с другими инструментами. Пишите в комментариях, готов ответить на ваши вопросы!

Подробнее..

Перевод Рекомендации по развертыванию Гибридного Облака (Hybrid Cloud) PostgreSQL

26.03.2021 18:19:00 | Автор: admin

Привет, хабровчане. В рамках набора в группу курса "PostgreSQL" подготовили для вас перевод материала.

Приглашаем также на открытый demo-урок на тему
Блокировки. На занятии вы узнаете, как работают блокировки; научитесь находить проблемные места в работе БД. Рассмотрим темы: блокировки объектов, блокировки строк, блокировки в памяти.


Гибридное Облако (Hybrid Cloud) это общий архитектурный дизайн в любой компании. Эта концепция сочетает в себе публичное облако, частное облако и даже локальные решения, что позволяет компаниям иметь гибкость в отношении того, где хранить и как использовать свои данные. Она также помогает при реализации среды высокой доступности (High Availability environment). Проблема заключается в том, что развертывание такой среды может быть сложной и трудоемкой задачей. В этом блоге мы увидим, что такое гибридное облако, рассмотрим некоторые соображения, которые необходимо принять во внимание, прежде чем использовать его, а также то, как развернуть эту среду с помощью ClusterControl.

Что такое Гибридное Облако?

Это топология, использующая сочетание частного и публичного облака, и даже локальных сервисов. Звучит похоже на мультиоблачную (Multi-Cloud) среду, но главное отличие заключается в том, что эта концепция относится к комбинациям публичного и частного, в которых может использоваться и локальное решение.

Вопросы в области применения баз данных гибридных облаков (Hybrid Cloud Databases Considerations)

Переход к гибридной среде (Hybrid Environment) отличается для каждой компании, так как у них есть свой уникальный набор данных, требований, ограничений и процессов, которые с ним связаны.

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

  • Совместимость: Убедитесь, что вы выбрали поставщика, который специализируется в вашей отрасли и знаком с особенностями требований, которые должны быть соблюдены, будь то HIPAA, FISMA, PCI, или любые другие правила, на которые подписывается ваша компания. В конечном счете, ваша стратегия управления базой данных должна определяться тем, какая архитектура будет наилучшим образом соответствовать потребностям вашего бизнеса и масштабу по мере вашего роста.

  • Рабочая нагрузка: Каждая база данных имеет различные рабочие нагрузки. Некоторые из них будут лучше работать в публичном облаке, другие в локальном варианте установки, а какие-то в частном облаке. Знание своей рабочей нагрузки необходимо для нахождения оптимального сочетания ваших баз данных.

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

Как разместить PostgreSQL в среде гибридного облака

Предположим, что у вас запущена инсталляция ClusterControl и вы уже создали два разных аккаунта Cloud Provider, или одну учетную запись, если вы используете публичное и частное облако в одном Cloud Provider, или если вы используете комбинацию облачных (Cloud) и локальных (On-prem) сред.

Подготовка вашей облачной среды

Во-первых, необходимо создать свою среду в основном облачном провайдере. В этом случае мы будем использовать AWS (Amazon Web Services) с 2 узлами PostgreSQL :

Убедитесь, что у вас есть SSH (Secure Shell) и PostgreSQL трафик, который разрешён с вашего сервера ClusterControl, посредством редактирования группы безопасности (Security Group):

Затем перейдите к следующему облачному провайдеру (Cloud Provider), или к Частным (Private) или Локальным (On-prem) серверам, и создайте, по крайней мере, одну виртуальную машину, которая будет резервным узлом.

И снова, убедитесь, что вы разрешаете SSH и PostgreSQL трафик с вашего сервера ClusterControl:

В этом случае мы разрешаем трафик без каких-либо ограничений по источнику, но это всего лишь пример и в реальной работе он не рекомендован.

Развертывание Кластера PostgreSQL

Зайдите на сервер ClusterControl и выберите опцию "Deploy (Развернуть)". Если у вас уже запущен экземпляр PostgreSQL, то вам нужно выбрать "Import Existing Server/Database (Импортировать Существующий Сервер/Базу данных)".

При выборе PostgreSQL, вы должны указать User (Пользователь), Key (Ключ) или Password (Пароль), а также порт для подключения по SSH к вашим узлам PostgreSQL. Вам также нужно имя вашего нового кластера и если вы хотите, ClusterControl установит и настроит для вас соответствующее программное обеспечение.

Пожалуйста, ознакомьтесь с пользовательскими требованиями ClusterControl для получения более подробной информации об этом этапе.

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

При добавлении ваших серверов вы можете ввести IP или имя хоста. На этом шаге также можно добавить узел, размещенный во вторичном облаке (Cloud Provider) или локально (on-prem), так как ClusterControl не имеет никаких ограничений по использованию сети, однако для большей ясности мы добавим его в следующем разделе. Единственным требованием здесь является наличие SSH-доступа к узлу.

На последнем шаге вы можете выбрать, будет ли ваша репликация Синхронной (Synchronous) или Асинхронной (Asynchronous).

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

Вы можете отслеживать статус процесса создания в мониторе активности ClusterControl.

После того, как задача будет выполнена, вы сможете увидеть ваш новый кластер PostgreSQL на главном экране ClusterControl.

Добавление удаленного узла ожидания (Remote Standby Node)

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

Перейдите к действиям кластера и выберите "Add Replication Slave (Добавить ведомое устройство репликации)":

Давайте используем опцию "Добавить новый ведомый узел репликации (Add new Replication slave)", так как мы предполагаем, что удаленный узел является новой установкой, если нет, то вы можете использовать опцию "Импортировать существующий ведомый узел репликации (Import existing Replication Slave)".

Здесь вам нужно только выбрать основной сервер (Primary server), ввести IP-адрес вашего нового резервного сервера и порт базы данных. Затем вы можете выбрать, если вы хотите, чтобы ClusterControl инсталлировал программное обеспечение, и должна ли репликация быть Синхронной (Synchronous) или Асинхронной (Asynchronous). Опять же, если вы добавляете узел в другом месте (другой облачный провайдер или локально установленный), вы должны использовать асинхронную репликацию, чтобы избежать проблем, связанных с производительностью сети.

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

Вы можете контролировать создание узла репликации в мониторе активности ClusterControl.

И проверьте свою окончательную топологию в разделе Topology View Section.

Заключение

Эти функции ClusterControl позволят вам быстро настроить репликацию в среде гибридного облака, между различными облачными провайдерами или даже между облачным провайдером и локальной (On-prem) средой для базы данных PostgreSQL (и других различных технологий), а также управлять настройкой простым и удобным способом. Обмен данными между облачными провайдерами или между Частным (Private) и Публичным (Public) облаками из соображений безопасности должен ограничивать трафик и использовать только известные источники, чтобы снизить риск несанкционированного доступа к вашей сети.


Узнать подробнее о курсе "PostgreSQL".

Смотреть вебинар Блокировки.

Подробнее..

Перевод Как я получил несколько сертификатов по облачным технологиям за 9 месяцев

10.02.2021 10:11:22 | Автор: admin

Айдар присоединился к EPAM Anywhere в качестве DevOps-инженера полтора года назад, и за это время прошел несколько программ сертификации, какое-то время был на бенче, сменил два проекта, а сейчас работает в двух проектных группах.

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

Простая мотивирующая история с полезными ссылками.

Почему облачные технологии?

Ты присоединился к EPAM Anywhere в качестве DevOps инженера. Почему ты решил развиваться в облачных технологиях?

Как и многие коллеги из моей области, я начал свою карьеру в ИТ в качестве системного администратора, а затем постепенно переходил к методологиям DevOps.

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

Когда я присоединился к EPAM Anywhere, у меня был небольшой опыт работы с облачными технологиями и несколько сертификатов в моем портфолио, с одной стороны, и сильное профессиональное стремление стать экспертом по облачным технологиям с другой.

Первые шаги в облаке

Первой платформой, которую я изучал, была Amazon Web Services. Это был основной поставщик облачных услуг на рынке в то время. Когда я начал работать с ним, я обнаружил, что моих практических навыков недостаточно для реализации даже несложных функций, поскольку мои знания были в основном теоретическими. Однако постепенно я повышал свои навыки, занимаясь крупными проектами. Мое правило не сдаваться и продолжать попытки, потому что построение карьеры в ИТ это всегда непрерывное обучение и сотрудничество.

Часть сертификатов ты получил самостоятельно, а остальные через EPAM Global Certification, верно?

Да, так и есть. Я предполагал, что один сертификат это всего лишь отправная точка длинного пути. Образование никогда не заканчивается, независимо от предмета. Все отрасли, особенно информационные технологии, развиваются; следовательно, каждый ИТ-специалист может постоянно расти и совершенствовать свои знания, чтобы соответствовать ожиданиям рынка и быть востребованным. Чем раньше вы это осознаете, тем лучше. Более опытные коллеги вдохновили меня двигаться дальше и уделять больше времени самообразованию.

В результате я прошел сертификацию AWS Cloud Practitioner и AWS Developer (Associate) до работы в EPAM, потом, будучи в EPAM, успешно сдал экзамен на AWS DevOps Engineer (Professional).

Помимо программы сертификации AWS, я принял участие в программе сертификации Microsoft Azure для сотрудников EPAM и прошел четыре сертификации: Azure Fundamentals; Azure Developer (Associate) и после небольшого перерыва архитектор решений Azure (Azure Solutions Architect Expert). Недавно я сертифицировался на Azure Data Scientist Associate.

От сертификатов AWS и Microsoft Azure до Google Cloud

Почему ты решил получить сертификат Google Cloud?

На то было несколько причин. У меня было желание попасть на проект с облачными технологиями и профессионально развиваться в этом стеке. Какое-то время я был на бенче и искал новые проекты, я просматривал открытые вакансии в EPAM и понял, что получить новую роль на проекте мне поможет опыт в облачных технологиях.

Затем я прочитал историю успеха о нашем коллеге, который получил ряд профессиональных сертификатов GCP, благодаря чему попал на новый интересный проект. Думаю, это послужило толчком для меня, я подал заявку на ещё одну сертификацию GCP и получил сертификат GCP Cloud Engineer (Associate).

Но это еще не конец истории. Поскольку я был на волне самообразования, я также решил изучить Kubernetes и, наконец, сдал экзамен на Kubernetes Application Developer (CKAD).

Сколько сертификатов сейчас в твоём портфолио?

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

Что, по-твоему, является самой сложной частью процесса сертификации и как с ней справиться?

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

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

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

В EPAM ещё есть возможность присоединиться к внутренним программам наставничества, которые предоставляют все необходимые ресурсы для подготовки к экзамену (учебные материалы, полезные ссылки и обзоры реальных случаев). Я бы также посоветовал присоединиться к дополнительным онлайн-сеансам под руководством наставников, чтобы получить более профессиональные идеи и советы.

Секреты успеха: ключевые принципы, которые помогут получить желаемые сертификаты

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

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

Также очень выгодно соответствовать ритму программы, в которой вы участвуете. Например, в одно время мне потребовалось 9 месяцев, чтобы завершить свои программы сертификации Azure, GCP и Kubernetes я сдавал экзамены каждые шесть недель.

Подводя итог, можно сказать, что успешная сдача сертификационного экзамена состоит из трех составляющих, независимо от предмета:

  • Мотивация, основанная на понимании преимуществ, которые сертификация даст для профессионального роста.

  • Продуманный стратегический план развития вашей карьеры на предстоящий период: 5 лет, 3 года, 1 год или меньше.

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

Например, на подготовку к экзамену по Azure было выделено всего 4 недели. Соответственно, я разделил свою рабочую неделю на часы, которые мог посвятить подготовке. Обычно у меня было два часа в день до и после работы над проектом плюс несколько часов в выходные. Иногда я даже учился в рабочее время, если у меня не было срочных задач.

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

Двигайтесь вперед и никогда не останавливайтесь на пути к своей мечте!

Подробнее..

Почему сертификация важна, как подготовиться и сдать экзамены AWS, Azure, GCP, etc

06.06.2021 14:21:06 | Автор: admin

Сразу с позитивного и очевидного

Сами по себе экзамены и сертификаты не несут в себе ничего отрицательного, негативные моменты будут рассмотрены ниже, начнем с позитивных и очевидных:

  • Сертификация подтверждает ваши технические знания (повышает "видимость" вашего CV для нового проекта/заказчика)

  • Позволяет двигаться в профессии, например от среднего уровня в "Professional" уровень

  • Подготовка к сертификации позволяет закрыть пробелы в знаниях

  • Позволяет выделить область необходимых знаний для разных ролей: Developer, DevOps, SysOps Administrator, разделить на "Middle/Associate", "Professional/Senior" уровень и определить "сколько" нужно изучать (см. рисунок ниже). Например вы работали работали с облаком на одном проекте 3 года, начали готовиться к AWS Certified Sysops Administrator и выяснилось, что для проекта знаний было достаточно и вы давно авторитет, а для сертификата среднего уровня нет (это может выручить при переходе на новый проект и избавить от ловушки "вечного мидла" если проект простой)

  • Показывает технологию с точки зрения производителя

  • На собеседованиях кандидаты с сертификатами, рассказывают более структурировано

  • Как результат, может помочь перейти на следующий уровень в карьере (например с Middle на Senior) и в некоторых случаях привлечет проекты

Негативное и позитивное использование сертификации

Негатив: "Я получил сертификат, сделайте мне x2 повышение" - если вы планируете повышать ЗП лучше обсудить этот момент и уточнить заранее, является ли ваша сертификация востребованной для компании или вашего отдела. Если вы получили один сертификат и тут же начали давить, что ЗП нужно увеличивать, вы просто встретите сопротивление.

Позитив: при подготовке к повышению лучше показать 2-3 или 3-4 достижения, в зависимости от позиции и требований. Сертификация облегчает этот процесс, например вы можете показать свою готовность к повышению представив несколько достижений:

  • я переписал код Terraform и деплоймент продукта теперь происходит на час быстрее

  • прошел ассесмент внутри компании по Английскому с A2+ на B1 или закончил курс

  • сдал экзамен и получил сертификат AWS Certified SysOps Administrator

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

Негатив: "получать сертификаты не имея реального опыта" - касается случаев, когда инженер начинает фанатично сдавать сертификат за сертификатом не применяя знания. Если вы сдали сразу 10 сертификатов Azure подряд, надо быть готовым отвечать на вопрос "зачем вы это сделали?", а главное уметь хорошо рассказывать про полученный опыт и что именно вы теперь умеете. В такой ситуации, знания полученные от первого сертификата улетучатся к десятому экзамену. К сожалению, результат такого подхода - инженер с большим количеством сертификатов который ничего не может сделать на проекте.

Позитив: Если вы готовитесь к новому проекту или только начинаете работу в профессии, полученные знания будут только плюсом. Лабораторные помогут получить базовый "боевой" опыт. Не следует стесняться рассказывать, что вы подготовились, успешно сдали экзамен и теперь умеете работать с определенными технологиями.

Негатив: "выпендреж и доминирование" - сертификация это один из пазлов большой мозаики вашего опыта, не стоит превращать это в культ.

Позитив: Для компании важно наличие сертифицированых специалистов, вы находитесь в отделе консалтинга по продукту или работаете как technology evangelist, тогда ваши достижения нужно "рекламировать" и сертификация в таком случае может сильно продвигать по карьерной лестнице.

Как готовиться к сертификации

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

  • пройти курс

  • прорешать все лабы (hands-on experience наиболее важен)

  • прорешать тесты

В процессе обучения ритм подготовки может меняться, возьмите паузу и отдохните когда закончите курс и лабораторные. Вернитесь к пройденному и постарайтесь проанализировать был ли материал понятен и сложилась ли картина. Если нет, лучше вернуться к курсу или лабораторным. В случае если теория улеглась и лабораторные работы все понятны нужно продолжать решать подготовительные тесты, они максимально приближены к реальному экзамену и показывают "сдан" тест или "провален". Таким образом можно оценивать готовность. Например, на ресурсе whizlabs около 7 тестов для экзамена "AWS Certified Solutions Architect", по 65 вопросов (вопросы повторяются). Когда тест завершается с результатом "PASS", все вопросы теста разобраны и понятны - вы готовы регистрироваться на официальный экзамен.

Ниже представлен roadmap для подготовки к сертификации "AWS Certified Solutions Architect". При подготовки к сертификатам Azure, Google Cloud или другим платформам можно использовать те же ресурсы. (Каждое облако предоставляет Free Tier - период бесплатного использования. Читайте внимательно правила Free Tier при регистрации и использовании, чтобы не потратить деньги или пишите вопросы в коменты).

"AWS Certified Solutions Architect" preparation roadmap:

  1. Тренинг: "A Cloud Guru: AWS Solutions Architect Associate" или курс на udemy (вы можете воспользоваться 7ми дневным бесплатным режимом на "A Cloud Guru". Внимательно следите за ценами и скидками, например ночью курсы udemy в 10 раз дешевле)

    https://acloudguru.com/course/aws-certified-solutions-architect-associate-saa-c02

    https://www.udemy.com/course/aws-certified-solutions-architect-associate-saa-c02/

  2. Лабораторные: в случае подготовки к AWS Solutions Architect, лабораторные идут в пакете к тесту на whizlabs.

    https://www.whizlabs.com/aws-solutions-architect-associate/

  3. Подготовительные тесты: AWS Certified Solutions Architect Associate - Practice Tests

    https://www.whizlabs.com/aws-solutions-architect-associate/

  4. Регистрация на экзамен (на момент написания статьи, сертификационный провайдер Pearson VUE позволяет сдавать экзамены AWS удаленно, из дома или офиса):

    https://aws.amazon.com/ru/certification/certified-solutions-architect-associate/

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

Подробнее..

Выбор оптимальной платформы для веб приложения

29.03.2021 10:21:19 | Автор: admin

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

Проблемы внедрения

Как уже упоминалось выше, запустить веб-приложение можно на разных платформах. Можно на собственных серверах компании, можно использовать Shared Hosting провайдеров, можно приобрести VPS/VDS хостинг, например, у DigitalOcean, а можно для размещения вашего веб-приложения использовать облачную инфраструктуру от интернет гигантов -Amazon Web Services (AWS), Google Cloud, Microsoft Azure и так далее. Существуют также и специально ориентированные на хостинг веб-приложений решения вроде Pantheon или WP Engine.

Множество возможных решений вызывает головную боль у новичка. Что выбрать? Что дешевле? Что надежнее? Где лучше техподдержка? Где больше возможностей и где лучше перспектива роста? Давайте рассмотрим плюсы и минусы каждого из вариантов.

Dedicated server

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

Shared Hosting

Если вы решили использовать Shared Hosting, то со стоимостью необходимых затрат наоборот, все хорошо. Это, пожалуй, самое дешевое решение. К тому же часто дополнительно вы получаете бесплатные доменные имена. Ваш сервер настроен и в общем-то не требует специальных технических знаний для использования. Все обслуживается и администрируется службой поддержки сервис провайдера. Но при этом вы крайне ограничены в добавлении и конфигурировании дополнительных возможностей для вашего проекта. Более того, производительность и стабильность вашего веб-приложения может серьезно пострадать из за внезапных и значительных потоков трафика ипотребления ресурсов сервера соседними сайтами и веб-приложениями. А таких прожорливых соседей у вас может быть несколько сотен! Оперативности технической поддержки при таком количестве клиентов скорее всего не следует ожидать. Кроме того, остро стоит вопрос безопасности shared hosting-а, ведь если хотя бы один из сайтов или веб-приложений будет взломан злоумышленниками, скорее всего они сумеют получить доступ и к ресурсам других проектов на этом сервере. По этим и другим причинам рынок shared hosting стагнирует в последние годы.

VPS Hosting

Одно из самых популярных решений. У многих на слуху компания DigitalOcean со своими популярными предложениями. Виртуальные приватные сервера дороже, чем Shared Hosting, на за эту разницу в цене вы получаете выделенные только для вас ресурсы на сервере, соседи по серверу не влияют на производительность вашего веб-приложения, конфигурируемость очень высокая поскольку вы имеете полный root доступ к вашей системе и тем самым имеете полное право навыполнение всех без исключения операций. Удобно вертикально масштабировать ваш VPS вручную и с даунтаймом. Достаточно остановить VPS, добавить ресурсов и снова запустить. С физическим сервером такое не пройдет. Но опять же, помимо достаточно ощутимой цены,тут требуется высокая квалификация и серьезные технические знания по управлению серверами. По сути, нужны специалисты такого же уровня, как и для управления физическими серверами, разница только в том, что нет проблем с hardware (не нужен план замен, закупок, монтажа и тому подобное), но инфраструктурно всё то же самое. Поэтому и для VPS hosting нужны высококвалифицированные администраторы.Чтобы сконфигурировать рабочее окружение для вашего веб-приложения и поддерживать его, вам потребуется немало времени.

Managed Hosting

Вариант хостинга, когда для вас запускают конкретное веб приложение, дают вам административный доступ в него, но непосредственное управление сервером осуществляется не вами. Таким образом, вы ограничены только вашим приложением. Управлять вы можете только тем, что оно позволяет делать в своих рамках. А поскольку таких как вы много на физическом сервере, то возникают все те же проблемы, которые характерны для Shared hosting -нестабильность объёма фактически доступных ресурсов, медленный ответ техподдержки и так далее.

Clouds

Давайте тут остановимся подробнее. Динамика роста популярности облачных решений в последние годы впечатляет. Аналитическая компания Gartner оценила объем мирового рынка публичных облачных сервисов в $242,7 млрд по итогам 2019 года. В 2021 году глобальный рынок внедрения облачных технологий превысит в общей сложности $306 млрд по данным той жеGartner. Решения на базе облачных технологий выбирают для себя компании и организации независимо от своего размера. Каждый находит в них для себя что-то свое, но общие преимущества облачных решений очевидны:

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

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

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

  • Исчезает необходимость в собственном штате системных администраторов для обслуживания серверного оборудования.

  • Нет больше необходимости заботиться о регулярных обновлениях используемых систем - облачный провайдер делает это за вас и как правило, совершенно незаметно для пользователей.

Но при всех преимуществах облачных технологий, в процессе их внедрения в работу компании, неизменно возникает проблема высокого порога вхождения. Она заключается в сложности выбора облачной архитектуры. Например, непросто выбрать подходящий для вашего проекта AWS stack, который обеспечивал бы все потребности и его стоимость не выходила бы за рамки бюджета. Вообще, если мы говорить об AWS, то его можно представить себе в виде некого конструктора, изкоторого вы можете сделать много разного - главное уметь это делать. Организацию хостинга веб-приложения с помощью AWS порой сравнивают со сборкой компьютера (по сравнению с покупкой готового - заказа хостинга у провайдера):EC2-это материнская плата и память. Онпозволяет запускать instance на базе образа операционной системы.EBS-это как диск. Вы можете сказать: сделай мне диск размером в 45 гигабайт и подключи его к такому-то instance (созданный "диск" будет называться volume). В результате в вашей системе появляется новое устройство, которое вы можете монтировать, форматировать и работать с ним. Все, что было записано на него, сохраняется независимо от жизни instance.S3-это как внешнее хранилище. Туда можно сохранять большие файлы и хранить их там вечно. А есть еще сервисы для логирования, мониторинга, баз данных, DNS и множество других. Как собрать из этого набора комплектующих именно тот "компьютер", или AWS stack, который обеспечит оптимальную работу вашего приложения и при этом не переплатить?Новичку в облачных технологиях непонятно, какую конкретно схему AWS stack использовать, какие выбрать сервисы и компоненты, как их соединять между собой. Оценить сложность выбора можно по вот этой схемеCNCF Cloud Native Landscape.

Усложняет задачу выбора и тот факт, что для использования AWS Cost Forecast или калькулятора для расчета расходов от пользователя требуются специфические знания и навыки. Кроме того, весьма сложно создать описания процессов, структуры и необходимых скриптов. Все это требует наличия высококвалифицированных специалистов, глубоко разбирающихся в облачных технологиях Amazon, Google или Microsoft.

В общем, главный минус хостинга в облаках - он сложный.

App-specificproviders

Если рассматривать услуги App-specific providers, которые рассчитаны в первую очередь на разработчиков, то широко известными примерами таких сервисов являются Google AppEngine, VMWare Pivotal Cloud Foundry, Heroku, Pantheon и другие. Такиесервисы представляют наборы готовых компонентов для создания приложений, а также фреймворки для управления платформой. В данном случае компонентами будут являться сервисы баз данных, репозитории, инструменты автоматизированного деплоя, мониторинга, среды тестирования и тому подобные сервисы.

Уровень входа в эти сервисы ниже, чем в облачные, но тем не менее, для развертывания хостинга вашего приложения на таких системах, какHeroku или Pantheon требуется написание специального манифеста,разрабатывать и отлаживать который для новичков очень непросто.Недостатки напоминают таковые у Managed hosting - ты имеешь только то, что тебе дают. При этом часто чего-то не додают, например, нужную конкретную версию компонента. Кроме того, неудобны ценовые планы - вы либоне помещаетесь в план, либо платите за большие ресурсы, чем потребляет ваш проект. В итоге часто получается так, что в процессе роста ваше приложение начинает обходиться слишком дорого, но так как вы уже адаптировали его для конкретного PaaS, перейти на какое-то другое решение вам уже сложно.Но при этом у App-specific providers нет проблемы выбора и соединения множества компонентов, как у AWS или других облачных провайдеров.

Предлагаемое решение

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

  • AWS account

  • GIT account

  • Ваше приложение должно быть докеризируемым, то есть иметь возможностьработать в докер контейнереи собираться через docker build.

Кастомизация и отличия от конкурентов

После развертывания приложения с помощью WSP,вы можете впоследствии кастомизировать его с помощью собственных terraform скриптов, например, или другими методами. При этом те внесенные кастомизации, которые не управляются из WSP, не будут потеряны после последующих развертываний новых версий приложения.Другим преимуществом WSP перед его основными конкурентами, продуктами Pantheon и Heroku, является то, что в них требуется предварительно написать манифест для развертываемого приложения, что требует высокой квалификации и глубокого знания продукта. При этом приложения у конкурентов будут работать только на их собственной инфрастуктуре, а в случае WSP приложения работают на инфраструктуре Amazon и будут продолжать работать на ней даже в случае отказа от дальнейшего использования WSP. В качестве минуса WSP, можно назвать необходимость отдельно оплачивать использование аккаунтов WSP и AWS, тогда как вPantheon и Heroku вы оплачиваете только их аккаунты.

Масштабируемость

В отличие от решений масштабируемости, которые предлагают сервис провайдеры,WSP предоставляет возможность использовать autoscaling, или, иначе говоря, горизонтальнуюмасштабируемость. Autoscaling легко настраивается в зависимости от потребностей работы вашего приложения. Учитывая, что вы платите только за фактически используемые ресурсы, autoscaling становится очень выгодным решением. Если нагрузка снижается, избыточные серверные мощности высвобождаются, соответственно вы платите меньше.

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

Наскриншоте нижехорошо видно, как просто это можно настроить:

Мониторинг и логи

Настройка систем мониторинга и логирования крайне нетривиальная задача в AWS. В WSP логирование с помощью ELK stack (Elasticsearch, Logstash, Kibana) и мониторинг с использованием Prometheus или Grafana настраиваются и подключаютсяпредельно просто. То есть, ониподключаются автоматически к каждому приложению,если при регистрацииAWS аккаунта к WSP было выбрано использование этой функциональности. В то же время вы всегда можете отключить мониторинг и логи, например, для экономии. И наоброт, включить их, когда они потребуются.

Так как мониторинг и логирование разворачиваются в AWS аккаунте, то они входит в стоимость AWS. Следовательно эти функции не исчезают даже если вы отказались от использования WSP.

Управление затратами

WSP в процессе развертывания приложения производит детальную разбивку затрат, что позволяет вам сделать точный прогноз по расходам за облачные сервисы, используемые вашим приложением. Эту сформированную разбивку и остальные данные по управлению затратами вы можете посмотреть вAWS Cost Explorer. Там можно увидеть затраты по временным периодам (в день, в месяц, в год) и по сервисам.

Технические домены с сертификатами

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

Автоматическое развертывание баз данных в Amazon RDS

WSP может автоматически разворачивать экземпляр базы данных типа PostgreSQL, MySQL или MariaDB для вашего приложения в Amazon RDS. Это настраивается непосредственно в "Environment settings" вашго приложения:

Zero downtime

Если в процессе работы с вашим приложением WSP производит развертывание новой версии приложения или откат на предыдущую версию, сессия работы переключается с текущей на новую версию приложения совершенно незаметно для вас. Реализован полный Zero Downtime для таких случаев.

One more thing!

  • Lift&Shift. Особенное внимание в разработке и концепции WSP уделяется тому, что вам совершенно не нужно как-то адаптировать и переделывать ваше приложение для его работы в облаке. С помощью WSP оно будет работать без каких то дополнительных усилий для его адаптации.

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

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

  • Все используемые в продукте компоненты стандартные. Эти компоненты- признанный мировой стандарт индустрии, имеют открытый исходный код и бесплатны.Никакие проприетарные компоненты не используются. Например, для pipeline в WSP используется Tekton.

  • Все секретные данные, такие, например, как пароли, логины и т.д. шифруются.

  • Поддерживается непрерывное развертывание (Continuous Deployment (CD)). То есть, платформа может автоматически собирать и разворачивать приложение по коммиту в GIT репозитории.

  • В настоящее время в качестве поддержки концепции "Infrastructure as a code" WSP может считывать параметры приложения из специальных файлов из git-репозитория, то есть кроме задания параметров приложения из UI возможно задавать параметры в файле.

Планы дальнейшего развития

В настоящее время WSP работает только с облачной инфрастуктурой Amazon. В дальнейшем планируется расширить этот список облачными сервисами Google, Microsoft Azure и DigitalOcean. Для тех потребителей, кто использует инфрастуктуру на базе Kubernetes также планируется поддержка.

Другим интересным путем развития WSP видится использование готовых докер образов приложений непосредственно с DockerHub.

Заключение

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

Проект находится еще в очень ранней стадии развития. Фаза активной разработки продолжается. В настоящее время команда Pleskуже использует WSP для наших собственных сервисов. Если вы хотите попробовать WSP, посмотреть, подходит ли он для вас, повлиять на развитие проекта путём обратной связи, поделиться вашими сценариями использования - welcome to closed alpha. Присоединиться можноздесь.

Подробнее..

Переход с Azure на GCP, с ASP.NET MVC на ASP.NET Core 3.1

26.01.2021 20:09:19 | Автор: admin

Автор: Андрей Жуков, .NET Team Leader, DataArt

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

Задача, поставленная заказчиком: Azure -> GCP

Заказчик решил перейти из одного облака (Azure) в другое (Google Cloud Platform). В некотором отдаленном будущем вообще планировалось перевести серверную часть на Node.js и развивать систему силами команды full-stack typescript-разработчиков. На момент моего входа в проект там существовала пара ASP.NET MVC приложений, которым решили продлить жизнь. Их мне и предстояло перенести в GCP.

Начальная состояние, факторы, мешающие сразу перейти на GCP

Первоначально имелось два ASP.NET MVC-приложения, которые взаимодействовали с одной общей MS SQL базой данных. Они были развернуты на Azure App Services.

Первое приложение назовем его Web Portal имело пользовательский интерфейс, построенный на базе Razor, TypeScript, JavaScript, Knockout и Bootstrap. С этими клиентскими технологиями никаких проблем не предвиделось. Зато серверная часть приложения использовала несколько сервисов, специфичных для Azure: Azure Service Bus, Azure Blobs, Azure Tables storage, Azure Queue storage. С ними предстояло что-то делать, т. к. в GCP ни один из них не поддерживается. Кроме того, приложение использовало Azure Cache for Redis. Для обработки длительных запросов была задействована служба Azure WebJob, задачи которой передавались через Azure Service Bus. По словам программиста, занимавшегося поддержкой, фоновые задачи могли выполняться до получаса.

Изначально архитектура Web Portal в нашем проекте выглядела такИзначально архитектура Web Portal в нашем проекте выглядела так

Azure WebJobs тоже предстояло чем-то заменить. Архитектура с очередью заданий для длительных вычислений не единственное среди возможных решений можно использовать специализированные библиотеки для фоновых задач, например, Hangfire, или обратиться к IHostedService от Microsoft.

Второе приложение назовем его Web API представляло собой ASP.NET WEB API. Оно использовало только MS SQL базы данных. Вернее, в конфигурационном файле были ссылки на несколько баз данных, в реальности же приложение обращалось только к одной их них. Но об этом нюансе мне только предстояло узнать.

Оба приложения были в работающем, но плохом состоянии: отсутствовала архитектура как таковая, было много старого неиспользуемого кода, не соблюдались принципы построения ASP.NET MVC приложений и т. д. Заказчик и сам признавал низкое качество кода, а человек, изначально написавший приложения, уже несколько лет не работал в компании. Был дан зеленый свет любым изменениям и новым решениям.

Итак, нужно было перевести ASP.NET MVC приложения на ASP.NET Core 3.1, перевести WebJob c .NET Framework на .NET Core, чтобы можно было разворачивать их под Linux. Использовать Windows на GCP возможно, но не целесообразно. Надо было избавиться от сервисов, специфичных для Azure, заменить чем-то Azure WebJob, решить, как будем развертывать приложения в GCP, т. е. выбрать альтернативу Azure App Services. Требовалось добавить поддержку Docker. При этом неплохо было бы внести хоть какую-то архитектуру и поправить качество кода.

Общие принципы и соображения

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

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

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

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

При замене сервисов Azure можно либо подобрать альтернативный GCP-сервис, либо выбрать cloud-agnostic-решение. Выбор сервисов в этом проекте и его обоснование в каждом случае мы рассмотрим отдельно.

План работ

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

  1. Web Portal c ASP.NET MVC на ASP.NET Core

    1.1. Анализ кода и зависимостей Web Portal от сервисов Azure и сторонних библиотек, оценка необходимого времени.

    1.2. Перевод Web Portal на .NET Core.

    1.3. Рефакторинг с целью устранения основных проблем.

    1.4. Merge изменений Web Portal из основной ветки репозитория, сделанных параллельно другими разработчиками.

    1.5. Докеризация Web Portal.

    1.6. Тестирование Web Portal, устранение ошибок и развертывание новой версии на Azure.

  2. Web API c ASP.NET MVC на ASP.NET Core

    2.1. Написание E2E автоматических тестов для Web API.

    2.2. Анализ кода и зависимостей Web API от сервисов Azure и сторонних библиотек, оценка необходимого времени.

    2.3. Удаление неиспользуемого исходного кода из Web API.

    2.4. Перевод Web API на .NET Core.

    2.5. Рефакторинг Web API с целью устранения основных проблем.

    2.6. Merge изменений Web API из основной ветки репозитория, сделанных параллельно другими разработчиками.

    2.7. Докеризация Web API.

    2.8. Тестирование Web API, устранение ошибок и развертывание новой версии на Azure.

  3. Устранение зависимостей от Azure

    3.1. Устранение зависимостей Web Portal от Azure.

  4. Развертывание в GCP

    4.1. Развертывание Web Portal в тестовой среде в GCP.

    4.2. Тестирование Web Portal и устранение возможных ошибок.

    4.3. Миграция базы данных для тестовой среды.

    4.4. Развертывание Web API в тестовой среде в GCP.

    4.5. Тестирование Web API и устранение возможных ошибок.

    4.6. Миграция базы данных для prod-среды.

    4.7. Развертывание Web Portal и Web API в prod GCP.

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

.NET Framework -> .NET Core

Перед началом переноса кода я нашел статью о миграции .Net Framework на .Net Core от Microsoft и далее ссылку на миграцию ASP.NET на ASP.NET Core.

С миграцией не-Web-проектов все обстояло относительно просто:

  • преобразование формата хранения NuGet-пакетов с помощью Visual Studio 2019;

  • адаптирование списка этих пакетов и их версий;

  • переход с App.config в XML на settings.json и замена всех имеющихся обращений к конфигурационным значениям на новый синтаксис.

Некоторые версии NuGet-пакетов Azure SDK претерпели изменения, повлекшие несовместимость. В большинстве случаев удалось найти не всегда самую новую, зато поддерживаемую кодом .NET Core версию, которая не требовала бы изменений в логике старого программного кода. Исключением стали пакеты для работы с Azure Service Bus и WebJobs SDK. Пришлось с Azure Service Bus перейти на бинарную сериализацию, а WebJob перевести на новую, обратно несовместимую версию SDK.

C миграцией ASP.NET MVC на ASP.NET Core дело обстояло намного сложнее. Все перечисленные выше действия нужно было проделать и для Web-проектов. Но начинать пришлось с нового ASP.NET Core проекта, куда мы перенесли код старого проекта. Структура ASP.NET Core проекта сильно отличается от предшественника, многие стандартные классы ASP.NET MVC претерпели изменения. Ниже я привожу список того, что изменили мы, и большая его часть будет актуальна для любого перехода с ASP.NET MVC на ASP.NET Core.

  1. Создание нового проекта ASP.NET Core и перенос в него основного кода из старого ASP.NET MVC проекта.

  2. Корректировка зависимостей проекта от внешних библиотек (в нашем случае это были только NuGet-пакеты, соображения по поводу версий библиотек см. выше).

  3. Замена Web.config на appsettings.json и все связанные с этим изменения в коде.

  4. Внедрение стандартного механизма Dependency injection от .NET Core вместо любой его альтернативы, использовавшейся в Asp.NET MVC проекте.

  5. Использование StaticFiles middleware для всех корневых папок статических файлов: изображений, шрифтов, JavaScript-скриптов, CSS-стилей и т. д.

app.UseStaticFiles(); // wwwrootapp.UseStaticFiles(new StaticFileOptions   {     FileProvider = new PhysicalFileProvider(         Path.Combine(Directory.GetCurrentDirectory(), "Scripts")),     RequestPath = "/Scripts"});

Можно перенести все статические файлы в wwwroot.

6. Переход к использованию bundleconfig.json для всех JavaScript и CSS-бандлов вместо старых механизмов. Изменение синтаксиса подключения JavaScript и CSS:

<link rel="stylesheet" href="~/bundles/Content.css" asp-append-version="true" /><script src="~/bundles/modernizr.js" asp-append-version="true"></script>

Чтобы директива asp-append-version="true" работала корректно, бандлы (bundles) должны находиться в корне, т. е. в папке wwwroot (смотри здесь).

Для отладки бандлов я использовал адаптированную версию хелпера отсюда.

7. Изменение механизма обработки UnhadledExceptions: в ASP.NET Core реализована его поддержка, остается с ней разобраться и использовать вместо того, что применялось в проекте раньше.

8. Логирование: я адаптировал старые механизмы логирования для использования стандартных в ASP.NET Core и внедрил Serilog. Последнее опционально, но, по-моему, сделать это стоит для получения гибкого structured logging c огромным количеством вариантов хранения логов.

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

10. Routing: в старом проекте использовался механизм, основанный на templates, его надо было чуть-чуть подправить.

11. JSON-сериализация: В ASP.NET Core по умолчанию используется библиотека System.Text.Json вместо Newtonsoft.Json. Microsoft утверждает, что она работает быстрее предшественницы, однако, в отличие от последней, она не поддерживает многое из того, что Newtonsoft.Json умела делать из коробки безо всякого участия программиста. Хорошо, что есть возможность переключиться обратно на Newtonsoft.Json. Именно это я и сделал, когда выяснил, что большая часть сериализации в Web API была сломана, и вернуть ее в рабочее состояние с помощью новой библиотеки, если и возможно, очень непросто. Подробнее об использовании Newtonsoft.Json можно прочитать здесь.

12. В старом проекте использовался Typescript 2.3. С его подключением пришлось повозиться, потребовалось установить Node.js, подобрать правильную версию пакета Microsoft.TypeScript.MSBuild, добавить и настроить tsconfig.json, поправить файл определений (Definitions) для библиотеки Knockout, кое-где добавить директивы //@ts-ignore.

13. Код для принудительной поддержки HTTPS включается автоматически при включении этой опции в визарде проекта. Старый код, использующий пользовательский атрибут HttpsOnly, был при этом убран.

14. Все низкоуровневые действия, такие как получение параметров из body запроса, URL запроса, HTTP Headers и HttpContext потребовали изменений, т. к. API для доступа к ним претерпел изменения по сравнению с ASP.NET MVC. Работы было бы заметно меньше, если бы в старом проекте чаще использовались стандартные binding механизмы через параметры экшенов (Actions) и контроллеров (Controllers).

15. Был добавлен Swagger c помощью библиотеки Swashbuckle.AspNetCore.Swagger.

16. Нестандартный механизм Authentication потребовал рефакторинга для приведения его к стандартному виду.

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

Что делать со специфичными сервисами Azure?

После перехода на ASP.NET Core предстояло избавиться от Azure-сервисов. Можно было либо подобрать решения, которые не зависят от облачной платформы, либо найти что-то подходящее из списка GCP. Благо у многих сервисов есть прямые альтернативы у других облачных провайдеров.

Azure Service Bus мы по настоятельной рекомендации заказчика решили заменить на Redis Pub/Sub. Это достаточно простой инструмент, не настолько мощный и гибкий как, например, RabbitMQ. Но для нашего простого сценария его хватало, а в пользу такого выбора говорило то, что Redis в проекте уже использовался. Время подтвердило решение было правильным. Логика работы с очередью была абстрагирована и выделена в два класса, один из которых реализует отправку произвольного объекта, другой получает сообщения и передает их на обработку. На выделение этих объектов ушло всего несколько часов, а если сам Redis Pub/Sub вдруг потребуется заменить, то и это будет очень просто.

Azure Blobs были заменены на GCP Blobs. Решение очевидное, но все-таки различие в функциональности сервисов нашлось: GCP Blobs не поддерживает добавление данных в конец существующего блоба. В нашем проекте такой блоб использовался для создания подобия логов в формате CSV. На платформе Google мы решили записывать эту информацию в Google Cloud operations suite, ранее известный как Stackdriver.

Хранилище Azure Table Storage использовалось для записи логов приложения и доступа к ним из Web Portal. Для этого существовал логгер, написанный самостоятельно. Мы решили привести этот процесс в соответствие с практиками от Microsoft, т. е. использовать их интерфейс ILogger. Кроме того, была внедрена библиотека для структурного логирования Serilog. В GCP логирование настроили в Stackdriver.

Какое-то время проект должен был параллельно работать и на GCP, и на Azure. Поэтому вся функциональность, зависящая от платформы, была выделена в отдельные классы, реализующие общие интерфейсы: IBlobService, IRequestLogger, ILogReader. Абстрагирование логирования было достигнуто автоматически за счет использования библиотеки Serilog. Но для того, чтобы показывать логи в Web Portal, как это делалось в старом приложении, понадобилось адаптировать порядок записей в Azure Table Storage, реализуя свой Serilog.Sinks.AzureTableStorage.KeyGenerator.IKeyGenerator. В GCP для чтения логов изGoogle Cloud operations были созданы Log Router Sinks, передающие данные в BigQuery, откуда приложение и получало их.

Что делать с Azure WebJobs?

Сервис Azure WebJobs доступен только для Azure App Services on Windows. По сути он представляет собой консольное приложение, использующее специальный Azure WebJobs SDK. Зависимость от этого SDK я убрал. Приложение осталось постоянно работающим консольным и следует похожей логике:

static async Task Main(string[] args){.   var builder = new HostBuilder();  ...              var host = builder.Build();  using (host)  {     await host.RunAsync();  }...}

За всю работу отвечает зарегистрированный с помощью Dependency Injection класс

public class RedisPubSubMessageProcessor : Microsoft.Extensions.Hosting.IHostedService{...public async Task StartAsync(CancellationToken cancellationToken)...public async Task StopAsync(CancellationToken cancellationToken)...}

Это стандартный для .NET Core механизм. Несмотря на отсутствие зависимости от Azure WebJob SDK, это консольное приложение успешно работает как Azure WebJob. Оно также без проблем работает в Linux Docker-контейнере под управлением Kubernetes, о чем речь в статье пойдет позже.

Рефакторинг по дороге

Архитектура и код приложения были далеки от идеала. В ходе многих шагов постепенно производились небольшие изменения кода, который они затрагивали. Были и специально запланированные этапы рефакторинга, согласованные и оцененные вместе с заказчиком. На этих этапах мы устраняли проблемы с аутентификацией и авторизацией, переводили их на практики от Microsoft. Был отдельный этап по внесению некой архитектуры, выделению слоев, устранению ненужных зависимостей. Работа с Web API началась с этапа удаления неиспользуемого кода. При замене многих Azure-сервисов на первом этапе производилось определение интерфейсов, выделение данных зависимостей в отдельные классы.

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

Docker

С поддержкой Docker все сложилось довольно гладко. Dockerfile можно легко добавить с помощью Visual Studio. Я добавил их для всех проектов, соответствующих приложениям, для Web Portal, Web API, WebJob (который в дальнейшем превратился просто в консольное приложение). Эти стандартные Dockerfile от Microsoft не претерпели особенных изменений и заработали из коробки за единственным исключением пришлось в Dockerfile для Web Portal добавить команды для установки Node.js. Этого требует build контейнер для работы с TypeScript.

RUN apt-get update && \apt-get -y install curl gnupg && \curl -sL https://deb.nodesource.com/setup_12.x  | bash - && \apt-get -y install nodejs

Azure App Services -> GKE

Нет единственно правильного решения для развертывания .NET Core-приложений в GCP, вы всегда можете выбрать из нескольких опций:

  • App Engine Flex.

  • Kubernetes Engine.

  • Compute Engine.

В нашем случае я остановился на Google Kubernetes Engine (GKE). Причем к этому моменту у нас уже были контейнеризованные приложения (Linux). GKE, оказалось, пожалуй, наиболее гибким из трех представленных выше решений. Оно позволяет разделять ресурсы кластера между несколькими приложениями, как в нашем случае. В принципе для выбора одного из трех вариантов можно воспользоваться блок-схемой по этой сслыке.

Выше описаны все решения по используемым сервисам GCP, кроме MS SQL Server, который мы заменили на Cloud SQL от Google.

Архитектура нашей системы после миграции в GCPАрхитектура нашей системы после миграции в GCP

Тестирование

Web Portal тестировался вручную, после каждого этапа я сам проводил простенький Smoke-тест. Это было обусловлено наличием пользовательского интерфейса. Если по завершении очередного этапа, новый кусок кода выпускался в Prod, к его тестированию подключались другие пользователи, в частности, Product Owner. Но выделенных QA-специалистов, в проекте, к сожалению, не было. Разумеется, все выявленные ошибки исправлялись до начала очередного этапа. Позднее был добавлен простой Puppeteer-тест, который исполнял сценарий загрузки одного из двух типов отчетов с какими-то параметрами и сравнивал полученный отчет с эталонным. Тест был интегрирован в CICD. Добавить какие-то юнит-тесты было проблематично по причине отсутствия какой-либо архитектуры.

Первым этапом миграции Web API, наоборот, было написание тестов. Для это использовался Postman, затем эти тесты вызывались в CICD с помощью Newman. Еще раньше к старому коду была добавлена интеграция со Swagger, который помог сформировать начальный список адресов методов и попробовать многие из них. Одним из следующих шагов было определение актуального перечня операций. Для этого использовались логи IIS (Internet Information Services), которые были доступны за полтора месяца. Для многих актуальных методов перечня было создано несколько тестов с разными параметрами. Тесты, приводящие к изменению данных в базе, были выделены в отдельную Postman-коллекцию и не запускались на общих средах выполнения. Разумеется, все это было параметризовано, чтобы можно было запускать и на Staging, и на Prod, и на Dev.

Тестирование позволило нам убедиться, что продукт после миграции сохранил стабильность. Конечно, идеальным вариантов было бы покрыть всю функциональность автоматизированными тестами. Поэтому в случае с Web API несмотря на гораздо большие усилия, затраченные в самом начале, миграция, поиск и исправление ошибок затем проходили гораздо легче.

Azure MS SQL -> GCP Managed MS SQL

Миграция MS SQL из Managed Azure в GCP Cloud SQL оказалась не такой простой задачей, как представлялось вначале. Основных причин тому оказался несколько:

  • Очень большой размер базы данных (Azure портал показал: Database data storage /

    Used space 181GB).

  • Наличие зависимостей от внешних таблиц.

  • Отсутствие общего формата для экспорта из Azure и импорта в GCP Cloud SQL.

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

Перед началом миграции нужно удалить все ссылки на внешние таблицы и базы данных, иначе миграция будет неудачной. Azure SQL поддерживает экспорт только в формат bacpac, более компактный по сравнению со стандартным backup форматом. В нашем случае вышло 6 Гб в bacpac против 154 Гб в backup. Но GCP Cloud позволят импортировать только backup, поэтому нам потребовалась конвертация, сделать которую удалось лишь посредством восстановления в локальную MS SQL из bacpac и создания backup уже из нее. Для этих операций потребовалось установить последнюю версию Microsoft SQL Server Management Studio, причем локальный сервер MS SQL Server был версией ниже. Немало операций заняли по многу часов, некоторые и вовсе длились по несколько дней. Рекомендую увеличить квоту Azure SQL перед импортом и сделать копию prod базы, чтобы импортировать из нее. Где-то нам потребовалось передавать файл между облаками, чтобы ускорить загрузку на локальную машину. Мы также добавили SSD-диск на 1 Тб специально под файлы базы данных.

Задачи на будущее

При переходе с Azure App Services на GCP Kubernetes мы потеряли CICD, Feature Branch deployments, Blue/Green deployment. На Kubernetes все это несколько сложнее и требует иной реализации, но наверняка делается посредством все тех же Github Actions. В новом облаке следуем концепции Iac (Infrastructure-as-Code) вместе с Pulumi.

От старого приложения нам достались низкая производительность и слишком продолжительное время запросов к базе данных. Устранение этих проблем среди приоритетов на ближайшее будущее.

Подробнее..

Как быстро и безболезненно сдать экзамен по Salesforce?

26.04.2021 20:23:29 | Автор: admin

Иван Левицкий, Salesforce разработчик, DataArt

Привет! Меня зовут Иван, как Salesforce разработчик я успел поработать уже в нескольких аутсорсинговых и аутстаффинговых компаниях, в локальных и распределенных командах, с клиентами из разных стран и индустрий. Соответственно, и потребности у заказчиков различались: одним инфраструктура Salesforce была нужна для внутренних систем, другим для работы с клиентами, третьим для разработки ISV-решений. С июля 2017 года моего первого знакомства с Salesforce я получил девять сертификатов, дважды экзамены мне приходилось пересдавать.

В этой статье я немного расскажу о самом Salesforce, но в основном речь в ней пойдет непосредственно о сертификатах и экзаменах: подготовке и сдаче.

О Salesforce

Logo historyLogo history

Немного о самом Salesforce, на случай если вы им предметно еще не интересовались. Это компания и одновременно ее ключевой продукт мировой лидер в области CRM. Но это не все, в Salesforce позиционируют себя как первый Cloud based CRM Solution и очень любят вспоминать термин No Software (даже используют в номере своего телефона 1-800-NO-SOFTWARE). А продукт с самого начала был задуман как SaaS Software as a Service облачная система, очень гибкая в плане настройки, масштабирования и расширения. Salesforce предлагает множество готовых решений для различных областей бизнеса: Sales Cloud, Service Cloud, Experience Cloud (Ex Community Cloud), CPQ, Force.com sites, Marketing B2B (Pardot), B2C clouds и это далеко не полный список.

Даже если вам не приходилось работать с инфраструктурой Salesforce, о новостях компании вы время от времени наверняка слышите: она в разное время поглотила таких IT-гигантов как Slack, Heroku и Tableau, не считая множества игроков поменьше, но также с серьезными именами. Кстати, Salesforce как компанию несколько раз признавали лучшим работодателем США, и на поддержку сообщества клиентов и Salesforce специалистов она тоже тратит значительные ресурсы. Короче говоря Salesforce экосистема в полном смысле слова.

Компании, купелнные Salesforce до 2020 годаКомпании, купелнные Salesforce до 2020 года

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

Для чего вообще нужна сертификация?

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

Насколько мне известно, сертификаты высоко ценятся среди:

Project Managerов Project Management Professional Certification (PMP);

Cyber Security специалистов: OSCP, OSCE, CISSP, SANS;

Salesforce специалистов.

Даже у бизнес-аналитиков мнения на этот счет уже значительно расходятся.

Что дает Salesforce сертификация?

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

Зачем это нужно Salesforce?

1. Сертификация обеспечивает ему дополнительный доход: допуск к экзамену стоит $ 200 или $ 400 (их очень много и предназначены они для людей разного профессионального уровня). Пересдача обойдется в $ 100 или $ 200, соответственно. Также есть возможность стать Salesforce CTA (Certified Technical Architect) всего за $ 6000 ($ 3000 за пересдачу). Тем не менее, речь здесь идет скорее о самоокупаемости самой системы сертификации, которая требует значительных ресурсов, в том числе человеческих.

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

Для чего это компании, в которой вы работаете?

Если вы работаете в продуктовой компании, ваш работодатель вряд ли заинтересован в том, чтобы вы получали сертификаты Salesforce. Если он, конечно, не занимается разработкой расширения функционала самой системы так называемых ISV.

Зато если ваша компания предоставляет услуги аутсорсинга или аутстаффинга, сертификация сотрудников становится для нее приоритетной.

Почему это так важно?

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

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

Для чего это лично вам?

1. Ваши сертификаты привязаны персонально к вам, а не к компании.

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

3. Исходя из вышесказанного, сертификаты пригодятся вам при пересмотре компенсации или будущем трудоустройстве. Тем более, клиенты аутсорсинговых компаний могут требовать их наличия, а сертифицированные Salesforce разработчики всегда в дефиците.

Я уже молчу о возможности потешить свое эго, распечатав и повесив сертификаты на видном месте. Что вы, лично я так никогда не делал! Но в целом система ачивок, бейджей и титулов в Salesforce настроена здорово, и участвовать в настолько геймифицированном процессе приятно.

С чего начать?

Начинать однозначно стоит с регистрации бесплатной Dev org. Здесь вы будете экспериментировать с Salesforce.

Далее нужно ознакомиться со списком всех специальностей, работающих с Salesforce, и выбрать для себя наиболее подходящую. Так называемый Career Path вы можете посмотреть здесь.

Salesforce Certification Paths

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

Для большинства специальностей первым станет сертификат Salesforce Certified Administrator, хотя некоторые вначале сдают экзамен на право называться Salesforce Certified Platform App Builder. Последний включает в себя более обширный набор навыков, и подготовка занимает немного больше времени. Но в целом сертификаты Administrator и App Builder заметно пересекаются, поэтому лучше сдавать их почти одновременно, чтобы не повторять теорию лишний раз.

Очень часто наличие сертификата Salesforce Certified Administrator обязательное условие для допуска к другим экзаменам. Прежде всего тем, которые предназначены для консультантов. Для администраторов и Marketing Cloud Email специалистов Salesforce предусматривает пробные экзамены стоимостью $20. Их успешная сдача не гарантирует успешного прохождения реального испытания, зато помогает выявить собственные слабые стороны, а если таких не находится укрепляет уверенность в себе.

Как подготовиться к Salesforce экзамену?

1. Выбрав сертификат, на который хотите сдавать, убедитесь, что у вас соблюдены все условия допуска к нему. Некоторые сертификаты таких условий не имеют, но проверить стоит в любом случае.

Сделать это можно при регистрации на экзамен на сайте Webassesor.

2. Не менее важный момент настрой. Причем не на победу: вы должны быть морально готовы к неудаче, особенно если это ваш первый опыт Salesforce экзамена. Сдать его с первой попытки не удается очень многим, так что это не трагедия, а скорее норма. Это не экзамен в школе, институте или университете: в любом случае вас не уволят и даже ругать никто не станет.

Немного успокоительного пересдача обойдется дешевле. Еще $ 40 скидки сможете получить, посетив вебинары серии Certification Days. Больше информации здесь, только учтите, что скидки не суммируются.

3. Составьте план подготовки к экзамену. Занятиям рекомендует уделить не менее месяца, особенно, если речь о первом знакомстве с Salesforce.

4. Как только план готов, пора регистрироваться на экзамен. Без дедлайна ваши планы это просто планы. Даже если вы не успеете подготовиться к выбранному вами дню, за 72 часа до сдачи сможете перенести ее на более поздний срок бесплатно. Только не откладывайте решение на последний момент, иначе за изменение даты придется доплатить еще $ 75.

5. Действуйте.

Рекомендации по подготовке

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

Разделите весь процесс подготовки на пять этапов.

1-й этап (особенно важный, если у вас нет практического опыта) ознакомление с Trailhead, официальной платформой для изучения Salesforce. Начинать стоит с trailов, в названии которых есть словосочетания "Quick Start" или "Quick Look". В качестве самого первого рекомендую этот Trailhead: Quick Look (5 mins).

2-й этап знакомство с описанием экзамена. Его можно найти здесь: выберете роль и соответствующий экзамен.

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

4-й этап подготовка к экзамену по принципу 3-4-5. Не пытайтесь понять все и сразу, подходите к каждой теме итеративно. Представьте, что это обычный экзамен, только в роли экзаменатора на нем выступаете вы. Самостоятельно оценивайте свои знания по конкретным темам по шкале от 3 до 5. Будем оптимистами оценки 1 и 2 в расчет брать не будем.

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

5-й этап повторение. Обязательно пройдитесь по тому, что знаете хуже всего.

Бонусы:

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

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

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

Полезные ссылки:

https://quizlet.com/ просто вбейте в строку поиска нужный вам экзамен;

https://t.me/SalesforceA группа в Telegram, где бесплатно выкладывают обновленные дампы Salesforce экзаменов;

https://focusonforce.com/ здесь есть все: теория, практика и объяснения каждого ответа. Сайт платный, но он того стоит.

На экзамене

В тесте будет 65 вопросов, пять из которых не влияют на результат они здесь для обкатки. Засчитывать или не засчитывать ответы на них, скорее всего, начнут уже при следующем Salesforce релизе. Зачем вам это знать? Если вы очень беспокоитесь о некоторых ответах постарайтесь убедить себя, что они относятся как раз к такой пятерке пробных вопросов. Наверное, в будущем их формулировки откорректируют.

Без паники. Salesforce клиентоориентированная компания, а вам повезло выступать в роли ее клиента. Что бы ни произошло, любая спорная ситуация, скорее всего, разрешится в вашу пользу. У меня есть опыт довольно стрессовых сдач Salesforce экзаменов (выключили электричество, экзаменационная программа зависла), но в каждом случае мне шли навстречу.

Распределите отведенное вам время. Не зацикливайтесь на сложном вопросе, у вас таких еще 64. Отложите его на потом.

Если не знаете ответа постарайтесь найти его методом исключения. Или положитесь на интуицию: это не мистика. а всего лишь не систематизированные знания.

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

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

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

Послесловие

Как бы банально это ни звучало, всегда верьте в себя. Без поражений не почувствовать настоящего вкуса победы, если таким поражением оказался несданный экзамен по Salesforce победа не за горами.

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

Удачи на экзаменах!

Подробнее..

Архитектура любительского стримингового сервиса DOS игр

29.12.2020 22:09:15 | Автор: admin
Недавно я написал небольшую статью о стриминге DOS игр в браузере. Настало время сделать небольшой технический обзор. Проект ведется исключительно мной, поэтому я его позиционирую как любительский. Среди общедоступных технологий позволяющих сделать стриминг игр можно выделить только WebRTC на нём и построен мой сервис. Как вы уже наверное догадались он состоит из браузерной и серверной части.


Браузерная часть


Основной компонент сервиса WebRTC сервер Janus. Из коробки он предоставляет простое API для подключения к серверу, и поддержки WebRTC протокола. Поэтому, браузерная часть получилось максимально простой, в виде обертки поверх Janus API.

Серверная часть


На стороне сервера используются dosbox, ffmpeg и Janus. Все они собраны вместе в docker контейнер.

Текущая версия сервиса использует:

  • Последнюю версию dosbox
  • Последнюю версию ffmpeg, скомпилированную с поддержкой кодеков vp9 и opus
  • Последнюю версию janus с небольшими дополнениями (о них ниже)


Стриминг звука и видео


Когда docker стартует, супервизор запускает все три программы. Dosbox запускает игру и начинает непрерывно генерировать кадры и звуки. Эти данные перенаправляются в ffmpeg, который создает два RTP стрима (звук, видео). Плагин для стриминга Janus (стандартный компонент), слушает эти стримы и генерирует WebRTC данные для браузера.

{dosbox} --> {ffmpeg} --> {janus streaming plugin} --> {browser}


Поддержка клавиатуры


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

  • pipe kdown когда кнопка нажата
  • pipe kup когда кнопка отпущена


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

{browser} --> {janus data text channel} --> {pipe} --> {dosbox}


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

Инфраструктура


Сервис запущен на платформе Amazon. Для каждого клиента создается новая задача Fargate. После старта задача получает публичный IP, который отправляется в браузер. При получении IP браузер инициирует WebRTC соединение с Janus сервером. Когда dosbox заканчивает работу, задача Fargate автоматически останавливается. Технически нет никаких ограничений на количество одновременных игроков.

{browser} --> {+fargate} --> {ip} --> {browser}
...
{browser} --> {stop} --> {-fargate}


Вместо заключения


Получилось достаточно поверхностно,

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

Обзорная статья: DOS Cloud Gaming
Подробнее..

Категории

Последние комментарии

  • Имя: Макс
    24.08.2022 | 11:28
    Я разраб в IT компании, работаю на арбитражную команду. Мы работаем с приламы и сайтами, при работе замечаются постоянные баны и лаги. Пацаны посоветовали сервис по анализу исходного кода,https://app Подробнее..
  • Имя: 9055410337
    20.08.2022 | 17:41
    поможем пишите в телеграм Подробнее..
  • Имя: sabbat
    17.08.2022 | 20:42
    Охренеть.. это просто шикарная статья, феноменально круто. Большое спасибо за разбор! Надеюсь как-нибудь с тобой связаться для обсуждений чего-либо) Подробнее..
  • Имя: Мария
    09.08.2022 | 14:44
    Добрый день. Если обладаете такой информацией, то подскажите, пожалуйста, где можно найти много-много материала по Yggdrasil и его уязвимостях для написания диплома? Благодарю. Подробнее..
© 2006-2024, personeltest.ru