Docker for Mac и Kubernetes


Начиная с версии 17.12 CE Edge, Docker for Mac поставляется вместе с Kubernetes. Теперь для создания локального Kubernetes кластера нет необходимости в использовании дополнительных инструментов, таких как Minikube. В качестве эксперимента, попробуем развернуть на кластере небольшой сервис и посмотрим, что из этого получится.

На момент написания статьи, у меня установлена самая последняя версия Docker for Mac - 18.02.0.

Docker For Mac

Для эксперимента, я написал простой генератор коротких ссылок на Go - brevity. Сервис разделен на 2 части: API для генерация коротких ссылок и их обработчик. Для хранения данных используется PostgreSQL.

Чтобы развернуть его и все необходимые зависимости, нам потребуется Helm - пакетный менеджер для Kubernetes, который заметно упрощает процесс развертывания и дальнейшей поддержки различных сервисов. Для его установки мы воспользуемся Homebrew:

$ brew install kubernetes-helm

После установки, нам нужно будет инициализировать Helm:

$ helm init

Если у вас настроен доступ к нескольких Kubernetes кластерам, то вам необходимо будет переключиться на локальный:

$ kubectl config use-context docker-for-desktop

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

$ helm install --name pg --namespace db --set postgresPassword=postgres,persistence.size=1Gi stable/postgresql

Helm позволяет переопределять значения по-умолчанию и тем самым настроить сервис под собственные нужды. Список сервисов, которые можно установить через Helm можно найти здесь - hub.kubeapps.com.

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

$ kubectl get pods -n db
NAME                            READY     STATUS                       RESTARTS   AGE
pg-postgresql-bbd4bbb5c-njkzs   0/1       CreateContainerConfigError   0          <invalid>

Сервис не запущен из-за ошибки. Чтобы узнать подробности, достаточно выполнить следующую команду:

$ kubectl describe pods -n db pg-postgresql-bbd4bbb5c-njkzs | tail -n 1
Warning  Failed                 <invalid> (x4 over 19s)  kubelet, docker-for-desktop  Error: lstat /Users/mgrachev/.docker/Volumes/pg-postgresql/pvc-588afa8b-0e90-11e8-8d22-025000000001: no such file or directory

Kubernetes не видит директорию, хотя она на самом деле есть. Оказалось, что Docker for Mac не понимает опцию subPath в конфигурации PostgreSQL для Kubernetes. В Minikube тоже была такая проблема, но её уже исправили.

Для решения этой проблемы, нам понадобится отредактировать Deployment для PostgreSQL:

$ kubectl edit deployment -n db pg-postgresql

И удалить следующую строчку:

subPath: postgresql-db

Теперь, если мы еще раз посмотрим на список запущенных подов, то увидим, что ошибок нет и сервис запущен:

$ kubectl get pods -n db
NAME                             READY     STATUS    RESTARTS   AGE
pg-postgresql-5c954c46c6-6bt2t   1/1       Running   0          26s

Далее, нам нужно создать БД для brevity. Сначала зайдем в контейнер:

$ kubectl exec -it -n db pg-postgresql-5c954c46c6-6bt2t bash

Внутри контейнера запускаем psql от имени пользователя postgres и создаем БД:

root@pg-postgresql-5c954c46c6-6bt2t:/# gosu postgres psql
postgres=# CREATE DATABASE brevity_production;

Чтобы наше приложение было доступно из кластера, нам понадобится Ingress Controller. Для этих целей отлично подойдет nginx:

$ helm install --name nginx stable/nginx-ingress

Переходим к установке brevity. Склонируем проект и запустим команду helm install, только в качестве аргумента передадим путь к заранее подготовленному чарту (пакеты в Helm называются чартами):

$ git clone https://github.com/mgrachev/brevity
$ cd brevity
$ helm install --name brevity ./helm

Проверяем, что все сервисы запущены:

$ kubectl get pods
NAME                                                   READY     STATUS    RESTARTS   AGE
brevity-brevity-778799dd4-zlb6g                        1/1       Running   0          1h
nginx-nginx-ingress-controller-c8cf56768-h4txk         1/1       Running   0          1h
nginx-nginx-ingress-default-backend-864c9484bf-rfdq4   1/1       Running   0          1h

Далее попробуем сгенерировать короткую ссылку, отправив POST запрос к API brevity:

$ curl -X "POST" "http://localhost/api/v1/shortlink" --data-urlencode "url=https://github.com/mgrachev"
{"shortlink":"http://localhost/MyAyEy"}

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

$ kubectl logs brevity-brevity-778799dd4-zlb6g
time="2018-02-19T09:31:03Z" level=info msg="HTTP Server started at port: 80"
time="2018-02-19T09:32:35Z" level=info msg="Successful returns a short link, short: http://localhost/MyAyEy, original: https://github.com/mgrachev"
time="2018-02-19T09:32:43Z" level=info msg="Redirect to https://github.com/mgrachev, using token: MyAyEy"

Как видно из логов, сервис успешно обработал короткую ссылку и перенаправил на страницу github.com/mgrachev. На этом можно закончить наш эксперимент.

В заключение скажу, что Docker for Mac с поддержкой Kubernetes меня порадовал. Достаточно в настройках поставить всего одну галочку и в твоем распоряжение будет полностью готовый к работе кластер с Kubernetes на борту. Из минусов отмечу, что это пока нестабильная версия и могут встречаться разного рода ошибки. Но даже сейчас, он вполне пригоден для локальной разработки и тестирования.

Similar posts

Update-informer v0.5.0

⭐️ Overview of key changes included in the new version

Dotenv-linter v3.1.0

⚡️ Overview of the key changes included in this release

GitHub Actions to guard your workflow

Automated code review with GitHub Actions 🐶

Dotenv-linter v3.0.0

⚡️Обзор ключевых изменений вошедших в новый релиз 🎉

Dotenv-linter: линтер .env файлов

⚡️Молниеносный инструмент для проверки .env файлов 🦀

Автоматическая проверка кода на Go

Обзор инструмента для автоматической проверки кода на Go.

Автоматическая проверка кода с помощью Vexor

Пошаговая инструкция, что для этого нужно сделать.

Управление зависимостями через Homebrew

Управление внешними зависимостями проекта c помощью Homebrew Bundle.

Класс Set и уникальные коллекции объектов

Рассмотрим решение одной задачи с использованием класса Set и DDD.

Настройка Passenger для работы с Action Cable

Решаем проблему работы WebSocket-сервера через Phusion Passenger.