Только представьте, что у вас есть рабочий образ Docker с реальным размером базового образа всего ~ 30 КБ, так что у вас почти не будет никаких накладных расходов. Давайте сделаем это в этой статье.
Как далеко мы можем зайти?
Таким образом, вы можете спросить, действительно ли возможно запустить ваше приложение на базовом образе 30 КБ. Короче говоря: «Да, это так!», Хотя, конечно, есть и недостаток.
Итак, давайте сначала проверим некоторые окончательные результаты. На следующем изображении вы можете увидеть три разных образа Docker. Все три изображения содержат одно и то же работающее приложение Go, простую программу Hello-World, ничего особенного.

pz/my-go-app-full-golang:1.15использовался как базовый образ → Вся среда выполнения Go + двоичные файлы, конечно, полный перебор. Здесь уже лучше было бы использовать альпийский или тонкий вариант. Мы не тестировали его в этом конкретном случае, но он должен уменьшить размер примерно на 90% или около того.pz/my-go-app-alpine-alpine:3.13.1был использован в качестве базового образа → Супер маленький дистрибутив Linux, содержащий только самое важное. Никакой дополнительной среды выполнения Go здесь нет, просто Linux.pz/my-go-app-scratch-scratchиспользовался в качестве базового образа → На самом деле это не совсем базовый образ, но мы говорим Docker, что действительно хотим начать с истинного нуля. Подробнее оscratchпозже в этой статье.
На следующем изображении вы можете увидеть файлы из корневой папки, в которые были встроены образы Docker. Как вы можете видеть, наше app, приложение Go, которое мы запускаем через образы Docker, имеет размер около 2 МБ. Поскольку размер нашего изображения, созданного с нуля, составляет всего 2,03 МБ, мы можем оценить накладные расходы примерно в 30 КБ для образа Docker по сравнению с реальным приложением. Довольно круто, правда?

Изображение `царапины '
«Можем ли мы использовать
FROM scratchдля всех видов приложений / языков?»
Теоретически да, практически никогда не должны. 😉
Но давайте начнем с того, о чем scratch изображение. Прежде всего, согласно описанию на Docker Hub, это образ, который наиболее полезен в контексте создания базовых образов или суперминимальных образов, содержащих только отдельные двоичные файлы.
Кроме того, начиная с Docker 1.5.0, команда FROM scratch не используется в Dockerfile и, как таковая, не создает дополнительный слой в образе. Несмотря на то, что образ scratch доступен в реестре Docker, его нельзя извлечь или запустить, и на него можно ссылаться только в Dockerfile.
«Хорошо, хорошо, я понял. Но могу ли я теперь запустить с ним свое приложение Node.Js / Python / любое другое? »
Длинный ответ: только если вы установите на нем Node.js / Python / что-то еще 😐
Довольно неудовлетворительно, правда? Верно, но на то есть причина. Как упоминалось ранее, изображение scratch на самом деле означает создание с нуля. Так что там уже абсолютно ничего нет. Ни оболочек, ни библиотек, ни системных файлов, ничего.
Поскольку scratch образ на самом деле ничего не содержит, вы также не сможете открыть bash в контейнере с помощью обычного docker exec -it CONTAINER /bin/bash. Так что во многих случаях изображение alpine, которое включает как минимум оболочку, может стоить дополнительных 5,5 МБ. 😉
Кроме того, такие языки, как JavaScript (Node.js) и Python, являются языками-интерпретаторами, которые предварительно не собираются в двоичные файлы, поэтому их невозможно запустить на scratch изображении. В случае JavaScript вам сначала нужно будет установить там Node.js, чтобы ваш код можно было интерпретировать во время выполнения. В случае с Node.js я хотел бы сослаться на другую мою статью Уменьшение размера образа Docker для Node.js на 90%!.
Фактический файл Dockerfile
«Хорошо, я понял, использование« царапины »создает супероптимизированный образ Docker, и решение использовать его должно быть осознанным ... Но я хочу его использовать, поэтому, пожалуйста, покажите мне код!»
Раз уж вы спросили, поехали. Отдельные шаги описаны непосредственно в Dockerfile:
Теперь давайте создадим и запустим этот Dockerfile. Имейте в виду, что требуется образец Go-приложения, использующего app.go в качестве точки входа. В качестве альтернативы вы можете проверить мой пример репозитория, содержащий приложение Go «Hello World» и указанное выше Dockerfile:
### Run into root application folder # Build application in current directory $ docker build -t pz/my-go-app-scratch . # Run built container once. # '--rm' indicates that the container should be removed aber run $ docker run --rm pz/my-go-app-scratch

Заключительные слова
Я надеюсь, что смогу дать вам небольшой рецепт, как докеризовать ваше приложение Go, а также дать несколько советов по оптимизации его размера. Имейте в виду, что начало с scratch может иметь свои подводные камни, и я обычно рекомендую использовать alpine в качестве базового образа, поскольку накладные расходы очень малы, и у вас есть, по крайней мере, возможность exec в ваш работающий контейнер.
Спасибо, что нашли время прочитать мою статью.
Если у вас есть какие-либо вопросы или дополнения, не стесняйтесь использовать раздел комментариев или напишите мне в LinkedIn или Twitter, чтобы связаться со мной 😊