Что лучше: разделить разные компоненты стека по нескольким меньшим машинам или взять одну или две машины большего размера и разместить несколько компонентов на одной машине?
Я считаю, что если я начну с нескольких машин, будет легче масштабировать, увеличивая мощность каждой машины, когда это необходимо. Я все равно пока не готов к горизонтальному масштабированию.
У меня для начала бюджет 20 долларов в месяц.
Я выбрал DigitalOcean, потому что он выглядит гибким с их каплей 512 МБ, поэтому вот мои варианты:
1, 2, 3 or 4 Machines of 512MB
2 Machines of 1GB
1 Machine of 2GB
1 or 2 Machines of 512MB + 1 Machine of 1GB
Вот мой стек:
Nginx
+
Gunicorn with 3 workers (=4 processes, memory footprint: ~50MB/process)
+
3 or 4 RQ workers (memory footprint of each worker: ~50MB)
+
Redis as Cache (limit to 100MB to start)
+
Redis as DataStore (small size: it is not meant to store a lot of data, mainly used to store the queues for the workers)
+
PostgreSQL (not sure how much RAM I would need)
Главный недостаток, который я вижу при использовании нескольких небольших машин, заключается в том, что, поскольку ОС установлена на каждой машине, каждая машина имеет набор ресурсов, выделенных для ОС, которые «теряются» для приложения. Основное преимущество, которое я вижу, заключается в том, что его легче масштабировать по вертикали, поскольку каждую машину можно модернизировать отдельно.
Что было бы хорошим компромиссом?
Опция 1
512MB: Nginx, Gunicorn, Redis Cache
512MB: RQ Workers, Redis DataStore
1GB or 512MB: PostgreSQL
Я не уверен, стоит ли отдавать 1 ГБ только для PostgreSQL ... Может, стоит использовать дроплет на 512 МБ? Кроме того, мне интересно, не будет ли машина 512 МБ с Nginx, Gunicorn и кешем Redis слишком маленькой.
Так что я мог это сделать:
Вариант 2
1GB: Nginx, Gunicorn, Redis Cache
512MB: RQ Workers, Redis DataStore
512MB: PostgreSQL
Вариант 3 с использованием 2 машин большего размера
1GB: Nginx, Gunicorn, (RQ Workers), Redis Cache, (Redis DataStore)
1GB or 512MB: PostgreSQL, (RQ Workers here?), (Redis DataStore here?)
Один из способов распространения приложения на множество машин - запуск каждого уровня на отдельном оборудовании. Например, веб-сервер и сервер базы данных могут работать на одной машине или на разных машинах.
Выполнение того или другого не потребует серьезных изменений конструкции в программном стеке. В основном нужно следить за дополнительной задержкой связи, возникающей при ее разделении на разные машины. Если, например, у вас есть приложение, использующее множество запросов к базе данных для отображения веб-страницы, то большое количество циклов и обратно приведет к заметному замедлению работы вашего приложения. Но это то, на чем вы можете рассчитывать.
Объем масштабирования, который вы получаете от запуска разных слоев на разных машинах, невелик. Количество уровней в программном стеке имеет тенденцию расти медленнее, чем количество пользователей. Таким образом, вы просто не сможете масштабироваться с помощью одного этого подхода.
Однако разделение слоев на разном оборудовании может подготовить вас к масштабированию в другом направлении.
Если у вас есть один веб-сервер, обменивающийся данными с одним сервером базы данных, вас не сильно помешает настроить два веб-сервера, взаимодействующие с одним сервером базы данных. Другими словами, каждый уровень вашего программного стека можно масштабировать независимо.
Однако любой уровень, поддерживающий состояние, трудно масштабировать на большем количестве машин. В частности, база данных может оказаться самой сложной для масштабирования частью.
Что касается размера отдельных машин, я бы выбрал размер, обеспечивающий максимальную производительность за деньги. Будет размер, который будет оптимальным с этой точки зрения. Машины большего размера будут слишком дорогими, а машины меньшего размера не будут достаточно дешевыми.
Но также возникает вопрос, следует ли проектировать с учетом масштабируемости сейчас или позже. Вы можете потратить свое время на проектирование для масштабируемости, которая вам никогда не понадобится. С другой стороны, если вы не планируете масштабируемость на многих машинах, вы можете столкнуться с трудностями в поисках единственной машины, достаточно большой для размещения той части вашей системы, которую вы не можете распределить (база данных является вероятным кандидатом в качестве часть, нуждающаяся в одной гигантской машине в какой-то момент).
Это интересный вопрос, и последний пункт, сделанный @kasperd, является наиболее подходящим (так что +1 только за это). ИМО (и многие другие) - этот тип проблем хорош, но определенно не то, чем вы должны заниматься, если вы действительно не ожидаете роста - иначе вы тратите время и деньги. С учетом сказанного, вот несколько соображений и вариантов.
Фактически, в этот вопрос входит несколько вопросов, и главный из них - увеличивать или уменьшать масштаб (с учетом стоимости). Масштабирование обычно будет более ограниченным (и, возможно, будет немного более затратным, если вам нужна избыточность), чем масштабирование, и с разнообразием доступных опций PaaS масштабирование менее сложно, чем в прошлом, но при этом вам нужно посмотреть на цель приложения, которое вы доставляете, - сделать конкретный вывод о том, что лучше всего.
Digital Ocean в настоящее время не имеет функции автомасштабирования, поэтому, если вы предполагаете всплески спроса, вам придется вручную сделай это.
С точки зрения архитектуры, многие узкие места в системе будут связаны с базой данных, но это действительно зависит от того, насколько «управляемым данными» будет ваше приложение, поэтому, не зная, что именно представляет собой приложение, я не могу рекомендовать иметь более крупный экземпляр для вашей базы данных.
В некоторых отношениях управление несколькими небольшими экземплярами (исправление / обслуживание и т. Д.) Добавляет сложности, однако, если все уровни приложения разделены, это может потенциально во многих случаях упростить поиск узких мест (примечание: это также может сделать его более сложным). сложный, если это заканчивается проблемой производительности сети).
Мой последний совет - начать как можно с малого, поместить весь стек в один небольшой экземпляр и использовать такой инструмент, как Кузница чтобы управлять своим стеком, когда это необходимо. Ничто не мешает вам разделить уровни на более позднем этапе, масштабировать и отключить службы, которые вам не требуются в данном блоке (после разделения уровней).
Это дает вам гибкость при выборе вертикального или горизонтального масштабирования, если это необходимо, дает вам возможность легко разделять проблемы, и я полагаю, что самое главное, потому что у вас нет метрик для работы, поэтому вы эффективно работаете с неизвестным.