How to choose between cache-aside, read-through, write-through, client-side, and distributed caching strategies Как мы уже упоминали в последнем пост, мы рады, что Пека Энберг решила написать И мы гордимся тем, что спонсируем три главы из него. Зачем скрывать данные? Целая книга о латентности Получить выдержку из книги Latency PDF Получить выдержку из книги Latency PDF Получить выдержку из книги Latency PDF Кроме того, Печка только что поделилась ключевыми отзывами из этой книги в (в настоящее время доступно по запросу) Мастеркласс по созданию приложений с низкой задержкой Давайте продолжим нашу Книга содержит выдержки из кешированной главы Пекки, перепечатанные здесь с разрешения издателя. Латентность * * в При добавлении кэширования к вашему приложению, вы должны сначала рассмотреть вашу стратегию кэширования, которая определяет, как происходит чтение и запись из кэша и основного хранилища резервных копий, таких как база данных или услуга. Другими словами, когда ваше приложение смотрит на значение из кэша, но значение не существует или истекло, стратегия кэширования устанавливает, является ли это ваше приложение или кэш, который получает значение из резервного хранилища.Как обычно, различные стратегии кэширования имеют различные компромиссы по задержке и сложности, так что давайте пойдем прямо в это. Cache-aside кэширование При ударе кэша задержка доступа к данным доминирует задержкой связи, которая обычно небольшая, так как вы можете получить кэш вблизи на кэш-сервере или даже в пространстве памяти приложения. Однако, когда есть пропущенный кэш, с кэш-сайтом кэширования, кэш является пассивным хранилищем, обновляемым приложением, то есть кэш только сообщает о пропущенном, и приложение отвечает за получение данных из резервного хранилища и обновление кэша. Рисунок 1 показывает пример кэширования на стороне кэша в действии.Приложение смотрит на значение из кэша с помощью ключа кэширования, который определяет данные, которые интересуют приложение. Если ключ существует в кэше, кэш возвращает значение, связанное с ключом, которое приложение может использовать. Однако, если ключ не существует или истек срок действия в кэше, у нас есть пропущенный кэш, который приложение должно обработать. Предположим, что вы кешируете информацию пользователя и используете идентификатор пользователя в качестве ключа поиска. В этом случае приложение выполняет запрос с помощью идентификатора пользователя, чтобы прочитать информацию пользователя из базы данных. Информация пользователя, возвращенная из базы данных, затем преобразуется в формат, который вы можете хранить в кэше. Затем кэш обновляется с идентификатором пользователя в качестве ключа кэша и информацией в качестве значения. Например, типичным способом выполнения этого типа кэша является преобразование информации пользователя, возвращенной из базы данных в JSON и хранение этой информации в кэше. Кэш-сайд популярен потому, что легко настроить кэш-сервер, такой как Redis, и использовать его для кэширования запросов базы данных и ответов на сервисы. С кэш-сайд кэширования, кэш-сервер пассивен и не нуждается в том, чтобы знать, какую базу данных вы используете или как результаты переносятся в кэш. Во многих случаях кеширование на стороне кеша является простым и эффективным способом уменьшения задержки приложений.Вы можете скрыть задержку доступа к базе данных, имея наиболее соответствующую информацию на кеш-сервере рядом с вашим приложением. Например, если у вас есть несколько одновременных читателей, которые ищут ключ в кэше, вам нужно координировать в своем приложении, как вы справляетесь с одновременными пропущениями кэша; в противном случае вы можете в конечном итоге иметь несколько доступов к базе данных и обновлений кэша, что может привести к последующим поискам кэша, возвращающим различные значения. Тем не менее, с кэш-сайд кэширования, вы теряете поддержку транзакций, потому что кэш и база данных не знают друг друга, и это ответственность приложения координировать обновления к данным. Наконец, кэш-сайд кэширования может иметь значительную задержку хвоста, потому что некоторые кэш-поиски испытывают задержку чтения базы данных на задержку кэша. Это означает, что, хотя в случае удара кэша, задержка доступа является быстрой, потому что она поступает от близлежащего кэш-сервера; кэш-поиски, которые испытывают задержку кэша, являются только такими быстрыми, как доступ к базе данных. Читать через кеширование Читательный кэш – это стратегия, при которой, в отличие от кэш-сайта, кэш является активным компонентом, когда отсутствует кэш. Когда есть кэш-память, кэш-память пытается автоматически прочитать значение для ключа из резервного магазина. Задержка аналогична кэш-сайту, хотя задержка получения резервного магазина от кэша до резервного магазина, а не от приложения к резервному магазину, которая может быть меньше, в зависимости от вашей архитектуры развертывания. Рисунок 2 показывает пример прочитанного кэша в действии. Приложение выполняет поиск кэша на ключе, и если есть пропущенный кэш, кэш выполняет прочтение в базу данных, чтобы получить значение для ключа. Кэш затем обновляет себя и возвращает значение в приложение. С точки зрения приложения пропущенный кэш прозрачен, потому что кэш всегда возвращает ключ, если он существует, независимо от того, был пропущен кэш или нет. Читательный кэш более сложен для реализации, потому что кэш должен иметь возможность читать резервный магазин, но он также должен преобразовывать результаты базы данных в формат для кэша. Например, если резервный магазин является сервером базы данных SQL, вам нужно преобразовать результаты запроса в JSON или аналогичный формат, чтобы хранить результаты в кэше. Однако, поскольку кэш координирует обновления, а база данных читается с помощью кэширования через чтение, он может предоставить транзакционные гарантии приложению и обеспечить последовательность при одновременных пропущениях кэша. Разумеется, такое же предупреждение о задержке хвоста применяется к кешам с прочтением, как и к кешам с прочтением. Исключение: как активные компоненты, кеши с прочтением могут лучше скрывать задержку, например, с кешированием с обновлением. Здесь кеш асинхронно обновляет кеш до истечения срока действия значений – следовательно, скрывая задержку доступа к базе данных от приложений полностью, когда значение находится в кеше. Писать через кэшинг В таких случаях кэш предоставляет интерфейс для обновления значения ключа, который приложение может призывать. В случае кэш-сайта кэш-сайта приложение является единственным, которое общается с резервным хранилищем и, следовательно, обновляет кэш. Однако с кэш-сайтом кэш-сайта есть два варианта для работы с кэш-сайтом: кэш-сайт и кэш-сайт. Письменный кэш – это стратегия, при которой обновление кэша распространяется немедленно в резервный магазин. Всякий раз, когда кэш обновляется, кэш синхронно обновляет резервный магазин с кешированной стоимостью. Латентность письма кэша доминирует по задержке письма в резервный магазин, что может быть значительным. Как показано на рисунке 3, приложение обновляет кэш с использованием интерфейса, предоставляемого кэшем с ключом и парой значений. Кэш обновляет свое состояние с новой стоимостью, обновляет базу данных с новой стоимостью и ждет, пока база данных не осуществит обновление, пока не признает обновление кэша в приложении. Письменное кеширование направлено на то, чтобы сохранить кеш и резервное хранилище в синхронизации. Однако, для нетранзакционных кеш, кеш и резервное хранилище могут быть синхронизированы при наличии ошибок. Например, если запись в кеш удается, но запись в резервное хранилище не удается, оба будут синхронизированы. Как и в случае с кэшем с прочтением, кэш с записью предполагает, что кэш может подключиться к базе данных и преобразовать значение кэша в запрос базы данных. Например, если вы кешируете данные пользователя, где идентификатор пользователя служит ключом, а документ JSON представляет ценность, кэш должен быть в состоянии преобразовать представление информации пользователя в JSON в обновление базы данных. При записывающемся кешировании наиболее простым решением часто является хранение JSON в базе данных. Основным недостатком записывающегося кеширования является задержка, связанная с обновлениями кэша, что по существу эквивалентно задержке комментирования базы данных. Написать позади caching Стратегия кэширования «запись» обновляет кэш немедленно, в отличие от кэширования «запись», которое отменяет обновления базы данных. Другими словами, при кэшировании «запись» кэш может принимать несколько обновлений перед обновлением резервного хранилища, как показано на рисунке 4, где кэш принимает три обновления кэша перед обновлением базы данных. Латентность записи кэша с записью ниже, чем при кэшировании с записью, потому что резервный магазин обновляется асинхронно. То есть кэш может распознать запись сразу же в приложении, что приводит к записи с низкой латентностью, а затем выполнить обновление кэша с записью на фоне. Однако недостаток кэша с записью заключается в том, что вы теряете поддержку транзакций, потому что кэш больше не может гарантировать, что кэш и база данных синхронизируются. Кроме того, кэш с записью может снизить долговечность, что является гарантией того, что вы не потеряете данные. Клиентская сторона caching Стратегия кэширования на стороне клиента означает наличие кэша на уровне клиента в вашем приложении.Хотя кэш-серверы, такие как Redis, используют кэширование в памяти, приложение должно общаться по сети, чтобы получить доступ к кэшу через протокол Redis. Если приложение является службой, работающей в центре данных, кэш-сервер отлично подходит для кэширования, потому что сетевое кругосветное путешествие в центре данных является быстрым, а сложность кэша находится в самом кэше. Тем не менее, задержка последней мили все еще может быть значительным фактором в пользовательском опыте на устройстве, поэтому кэширование на стороне клиента так прибыльно. При кэшировании на стороне клиента сочетание кэширования через чтение и за записью является оптимальным с точки зрения задержки, потому что как чтение, так и запись быстры.Конечно, ваш клиент обычно не сможет напрямую подключиться к базе данных, а вместо этого получает доступ к базе данных косвенно через прокси-сервер или сервер API. Кэширование на стороне клиента также затрудняет гарантию транзакций из-за слоев косвенного доступа к базе данных и задержки. Для многих приложений, которые нуждаются в кешировании на стороне клиента с низкой задержкой, локальный подход к репликации может быть более практичным. Но для простого кеширования с прочтением кеширование на стороне клиента может быть хорошим решением для достижения низкой задержки. Распределенный кеш До сих пор мы только обсуждали кеширование, как если бы существовал один экземпляр кеша. Например, вы используете кеш в приложении или один сервер Redis для кеширования запросов из базы данных PostgreSQL. Однако, вам часто нужны несколько копий данных, чтобы уменьшить географическую задержку в разных местах или масштабировать, чтобы вместить вашу нагрузку. С таким распределенным кешированием у вас есть многочисленные экземпляры кеша, которые работают независимо или в кластере кеша. С распределенным кешированием у вас есть много тех же осложнений и соображений, что и с обсуждаемыми в Главе 4 о репликации и Главе 5 о разделении. С распределенным кешированием вы не хотите помещать все кешированные данные на каждый экземпляр, но вместо этого у вас есть кешированные данные, разделенные между узлами. В целом, распределенный кэшинг является пересечением преимуществ и проблем кэширования, разделения и репликации, поэтому будьте осторожны, если вы идете с этим. * * в Чтобы продолжать читать, от ScyllaDB или . Скачать 3 главу Latency выдержку бесплатно Купить полную книгу Мэннинг О компании Cynthia Dunlop Синтия является старшим директором по стратегии контента в ScyllaDB. Она пишет о разработке программного обеспечения и инженерии качества более 20 лет.