Примечание.
Для доступа к этой странице требуется авторизация. Вы можете попробовать войти или изменить каталоги.
Для доступа к этой странице требуется авторизация. Вы можете попробовать изменить каталоги.
Azure Cosmos DB — быстрая и гибкая распределенная база данных, которая легко масштабируется с гарантированными уровнями задержки и пропускной способности. Для масштабирования базы данных с помощью Azure Cosmos DB не нужно вносить в архитектуру существенные изменения или писать сложный код. Для увеличения или уменьшения масштаба достаточно выполнить один вызов API. Дополнительные сведения см. в разделах о подготовке пропускной способности контейнера и о подготовке пропускной способности базы данных.
Так как для доступа к Azure Cosmos DB выполняются сетевые вызовы, вы можете выполнить оптимизации на стороне клиента, чтобы повысить производительность при работе с пакетом SDK .NET для SQL.
Если вы хотите повысить производительность базы данных, рассмотрите варианты, описанные в следующих разделах.
Рекомендации по размещению
Включение сборки мусора на стороне сервера
В некоторых случаях для оптимизации можно уменьшить частоту сборки мусора. В .NET установите для параметра gcServer значение true.
Масштабирование клиентской рабочей нагрузки
Если вы тестируете на высоком уровне пропускной способности или на скорости, превышающие 50 000 единиц запросов в секунду (ЕЗ/с), клиентское приложение может стать узким местом рабочей нагрузки, так как компьютер может завершить использование ЦП или сети. Если вы достигли этой точки, то можете повысить производительность Azure Cosmos DB, развернув клиентские приложения на нескольких серверах.
Замечание
Высокая загрузка ЦП может привести к увеличению задержки и исключений времени ожидания запроса.
Операции с метаданными
Не проверяйте, существует ли база данных или контейнер путем вызова Create...IfNotExistsAsync или Read...Async в критическом пути или перед выполнением операции с элементом. Проверка должна выполняться только при запуске приложения, если необходимо удалить их (в противном случае это не требуется). Эти операции метаданных создают дополнительную задержку от начала до конца, не имеют соглашения об уровне обслуживания и имеют свои собственные отдельные ограничения, которые масштабируются иначе, чем операции с данными.
Логирование и трассировка
В некоторых средах включено средство .NET DefaultTraceListener. DefaultTraceListener создает проблемы с производительностью в рабочих средах, что приводит к возникновению узких мест из-за высокой загрузки ЦП и большого числа операций ввода-вывода. Убедитесь, что средство DefaultTraceListener отключено для вашего приложения, удалив его из TraceListeners в продуктивных средах.
Версии SDK выше 3.23.0 автоматически удаляют его при обнаружении. С более старыми версиями ее можно удалить с помощью следующих команд:
if (!Debugger.IsAttached)
{
Type defaultTrace = Type.GetType("Microsoft.Azure.Cosmos.Core.Trace.DefaultTrace,Microsoft.Azure.Cosmos.Direct");
TraceSource traceSource = (TraceSource)defaultTrace.GetProperty("TraceSource").GetValue(null);
traceSource.Listeners.Remove("Default");
// Add your own trace listeners
}
Высокая доступность
Общие рекомендации по настройке высокой доступности в Azure Cosmos DB см. в статье "Высокий уровень доступности" в Azure Cosmos DB.
Помимо хорошей базовой настройки на платформе базы данных, существуют определенные методы, которые можно реализовать в самом пакете SDK для .NET, что может помочь в сценариях сбоя. Две важные стратегии — это стратегия доступности на основе порогового значения и разбиение цепи на уровне секции.
Стратегия доступности на основе порогового значения
Стратегия доступности на основе порогового значения может улучшить задержку на хвосте и общую доступность, отправляя параллельные запросы на чтение в вторичные регионы (как указано в ApplicationPreferredRegions) и принимая самый быстрый ответ. Такой подход может значительно снизить влияние региональных сбоев или условий высокой задержки на производительность приложения.
Пример конфигурации:
Это можно сделать с помощью CosmosClientBuilder:
CosmosClient client = new CosmosClientBuilder("connection string")
.WithApplicationPreferredRegions(
new List<string> { "East US", "East US 2", "West US" } )
.WithAvailabilityStrategy(
AvailabilityStrategy.CrossRegionHedgingStrategy(
threshold: TimeSpan.FromMilliseconds(500),
thresholdStep: TimeSpan.FromMilliseconds(100)
))
.Build();
Или путем настройки параметров и их добавления в CosmosClient:
CosmosClientOptions options = new CosmosClientOptions()
{
AvailabilityStrategy
= AvailabilityStrategy.CrossRegionHedgingStrategy(
threshold: TimeSpan.FromMilliseconds(500),
thresholdStep: TimeSpan.FromMilliseconds(100)
)
ApplicationPreferredRegions = new List<string>() { "East US", "East US 2", "West US"},
};
CosmosClient client = new CosmosClient(
accountEndpoint: "account endpoint",
authKeyOrResourceToken: "auth key or resource token",
clientOptions: options);
Принцип работы.
Первоначальный запрос: В момент времени T1 отправляется запрос на чтение в первичный регион (например, Восточный США). Пакет SDK ожидает ответа до 500 миллисекунд (значение
threshold).Второй запрос: Если ответа от основного региона в пределах 500 миллисекундах нет, параллельный запрос отправляется в следующий предпочтительный регион (например, восточная часть США 2).
Третий запрос: Если ни основной, ни дополнительный регион не отвечает в пределах 600 миллисекунда (500 мс + 100 мс,
thresholdStepзначение), пакет SDK отправляет другой параллельный запрос в третий предпочтительный регион (например, западная часть США).Самый быстрый ответ выигрывает: Независимо от того, какой регион отвечает первым, этот ответ принимается, а другие параллельные запросы игнорируются.
Замечание
Если первый предпочтительный регион возвращает непереносительный код состояния ошибки (например, документ не найден, ошибка авторизации или конфликт), сама операция завершается сбоем, так как стратегия доступности не имеет никакого преимущества в этом сценарии.
Автоматический выключатель на уровне раздела
Средство разбиения на уровне секций (PPCB) — это функция пакета SDK для .NET, которая повышает доступность и задержку путем отслеживания неработоспособных физических секций. Если этот параметр включен, он помогает направлять запросы в более устойчивые регионы, предотвращая каскадные сбои из-за региональных или специфических для секций проблем. Эта функция независима от функций автоматического переключения, запускаемых серверной частью, и контролируется через переменные среды.
Эта функция по умолчанию отключена, но включается автоматически, когда включена отказоустойчивость на уровне раздела.
Принцип работы
-
Обнаружение сбоев: При обнаружении определенных ошибок, таких как
503 Service Unavailable,408 Request Timeoutили маркеров отмены, пакет SDK подсчитывает последовательные сбои для секции. -
Активация переключения на резервный режим: После достижения заданного порога последовательных сбоев пакет SDK перенаправляет запросы для этого диапазона ключей секции в следующий предпочтительный регион, используя
GlobalPartitionEndpointManagerCore.TryMarkEndpointUnavailableForPartitionKeyRange. - Фоновое восстановление: Фоновая задача инициируется во время переключения на резерв, чтобы периодически переоценивать работоспособность неисправной секции, пытаясь подключиться ко всем четырем репликам. Когда система стабилизируется, SDK удаляет переопределение и возвращается в основную область.
Поведение по типу учетной записи
- Запись в один регион (один главный): Только запросы на чтение участвуют в логике отработки отказа PPCB.
- Запись в нескольких регионах (многоуровневая): Оба запроса на чтение и запись используют логику отработки отказа PPCB.
Параметры конфигурации
Используйте следующие переменные среды для настройки PPCB:
| Переменная среды | Description | По умолчанию |
|---|---|---|
AZURE_COSMOS_CIRCUIT_BREAKER_ENABLED |
Включает или отключает функцию PPCB. | false |
AZURE_COSMOS_PPCB_CONSECUTIVE_FAILURE_COUNT_FOR_READS |
Последовательные сбои чтения для инициации отказоустойчивости. | 10 |
AZURE_COSMOS_PPCB_CONSECUTIVE_FAILURE_COUNT_FOR_WRITES |
Последовательные сбои записи для вызова переключения на резервный вариант. | 5 |
AZURE_COSMOS_PPCB_ALLOWED_PARTITION_UNAVAILABILITY_DURATION_IN_SECONDS |
Время перед повторной оценкой работоспособности раздела. |
5 секунды |
AZURE_COSMOS_PPCB_STALE_PARTITION_UNAVAILABILITY_REFRESH_INTERVAL_IN_SECONDS |
Интервал для фонового обновления состояния разделов. |
60 секунды |
Замечание
В настоящее время пакет SDK не имеет надежного резервного триггера для операций чтения. Вместо этого средство проверки работоспособности фона постепенно пытается повторно включить исходный регион, когда все четыре реплики реагируют.
Сравнение оптимизаций доступности
Стратегия доступности на основе порогов:
- Преимущество: Уменьшение задержки хвоста путем отправки параллельных запросов на чтение вторичным регионам и повышения доступности путем предупреждения запросов, которые приводят к сетевым таймаутам.
- Компромисс: возникают дополнительные затраты на единицы запросов (RUs) по сравнению с ограничителем, из-за дополнительных параллельных запросов между регионами (но только в периоды, когда превышаются пороговые значения).
- Вариант использования. Оптимальный вариант для рабочих нагрузок с большим количеством операций чтения, где снижается задержка, а некоторые дополнительные затраты (как с точки зрения платы за единицу ЕЗ, так и нагрузку на ЦП клиента) приемлемы. Операции записи также могут воспользоваться преимуществами, если вы решили использовать политику повторных попыток неидемпотентной записи, а учетная запись содержит записи в нескольких регионах.
Ограничитель на уровне раздела:
- Преимущество: Повышает доступность и снижает задержки за счет предотвращения неработоспособных разделов, что обеспечивает маршрутизацию запросов в более стабильные регионы.
- Компромисс: Не несет дополнительных затрат на RU, но может привести к некоторой начальной потере доступности для запросов, которые приводят к сетевым таймаутам.
- Вариант использования: Идеально подходит для рабочих нагрузок с интенсивной записью или смешанных нагрузок, где важна стабильная производительность, особенно при работе с разделами, которые могут периодически стать неработоспособными.
Обе стратегии можно использовать вместе для повышения доступности чтения и записи и уменьшения пиковой задержки. Предохранитель на уровне разделов может обрабатывать различные преходящие сценарии сбоев, включая те, которые могут привести к медленной работе реплик, без необходимости выполнять параллельные запросы. Кроме того, добавление стратегии доступности на основе пороговых значений дополнительно минимизирует хвостовую задержку и устраняет потерю доступности, если дополнительная стоимость RU допустима.
Реализуя эти стратегии, разработчики могут обеспечить устойчивость приложений, обеспечить высокую производительность и повысить производительность даже во время региональных сбоев или условий высокой задержки.
Исключенные регионы
Функция исключенных регионов позволяет точно контролировать маршрутизацию запросов, позволяя исключить определенные регионы из предпочитаемых расположений на основе каждого запроса. Эта функция доступна в пакете SDK для .NET для Azure Cosmos DB версии 3.37.0 и более поздних версий.
Ключевые преимущества:
- Обработка ограничения скорости. При обнаружении ответов 429 (слишком много запросов) автоматически перенаправляйте запросы в альтернативные регионы с доступной пропускной способностью
- Целевая маршрутизация: убедитесь, что запросы обслуживаются из определенных регионов, исключая все остальные
- Обход предпочтительного порядка. Переопределите список предпочтительных регионов по умолчанию для отдельных запросов без создания отдельных клиентов
Configuration:
Исключенные регионы можно настроить на уровне запроса с помощью ExcludeRegions свойства:
CosmosClientOptions clientOptions = new CosmosClientOptions()
{
ApplicationPreferredRegions = new List<string> {"West US", "Central US", "East US"}
};
CosmosClient client = new CosmosClient(connectionString, clientOptions);
Database db = client.GetDatabase("myDb");
Container container = db.GetContainer("myContainer");
//Request will be served out of the West US region
await container.ReadItemAsync<dynamic>("item", new PartitionKey("pk"));
//By using ExcludeRegions, we are able to bypass the ApplicationPreferredRegions list
// and route a request directly to the East US region
await container.ReadItemAsync<dynamic>(
"item",
new PartitionKey("pk"),
new ItemRequestOptions()
{
ExcludeRegions = new List<string>() { "West US", "Central US" }
});
Пример использования— ограничение скорости обработки:
ItemResponse<CosmosItem> item;
item = await container.ReadItemAsync<CosmosItem>("id", partitionKey);
if (item.StatusCode == HttpStatusCode.TooManyRequests)
{
ItemRequestOptions requestOptions = new ItemRequestOptions()
{
ExcludeRegions = new List<string>() { "East US" }
};
item = await container.ReadItemAsync<CosmosItem>("id", partitionKey, requestOptions);
}
Эта функция также работает с запросами и другими операциями:
QueryRequestOptions queryRequestOptions = new QueryRequestOptions()
{
ExcludeRegions = new List<string>() { "East US" }
};
using (FeedIterator<CosmosItem> queryFeedIterator = container.GetItemQueryIterator<CosmosItem>(
queryDefinition,
requestOptions: queryRequestOptions))
{
while(queryFeedIterator.HasMoreResults)
{
var item = await queryFeedIterator.ReadNextAsync();
}
}
Настройка на согласованность и доступность
Функция исключенных регионов предоставляет дополнительный механизм балансировки согласованности и компромиссов доступности в приложении. Эта возможность особенно ценна в динамических сценариях, когда требования могут меняться на основе условий эксплуатации:
Динамическая обработка сбоев: Когда в основном регионе происходит сбой, и пороговые значения схемы защиты на уровне разделов оказываются недостаточными, исключенные регионы обеспечивают немедленное переключение на резервный режим без изменений кода или перезапуска приложения. Это обеспечивает более быстрый ответ на региональные проблемы по сравнению с ожиданием активации автоматического размыкания цепи.
Параметры условной согласованности: приложения могут реализовать различные стратегии согласованности на основе рабочего состояния:
- Устойчивое состояние: приоритизация согласованных операций чтения, исключая все регионы, кроме основного, для обеспечения согласованности данных, что может происходить за счет доступности.
- Сценарии сбоя: Предпочтение доступности перед строгой согласованностью, допускается маршрутизация между регионами, принимая возможность задержки данных в обмен на поддержание доступности служб.
Этот подход позволяет внешним механизмам (например, диспетчерам трафика или подсистемам балансировки нагрузки) координировать решения о переходе на резерв, а приложение сохраняет контроль над требованиями к согласованности через шаблоны исключения регионов.
Если все регионы исключены, запросы будут перенаправлены в основной или центральный регион. Эта функция работает с любыми видами запросов, включая вопросы, и особенно полезна для поддержания одиночных экземпляров клиента при достижении гибкого поведения маршрутизации.
Networking
Политика подключения: использование режима прямого подключения
Для пакета SDK для .NET v3 по умолчанию используется прямое подключение по протоколу TCP. Режим подключения настраивается при создании экземпляра CosmosClient в CosmosClientOptions. Дополнительные сведения о различных вариантах подключения см. в статье Режимы подключения.
CosmosClient client = new CosmosClient(
"<nosql-account-endpoint>",
tokenCredential
new CosmosClientOptions
{
ConnectionMode = ConnectionMode.Gateway // ConnectionMode.Direct is the default
}
);
Временная нехватка портов
При большом числе подключений или высокой интенсивности использования портов на ваших экземплярах необходимо сначала убедиться, что клиентские экземпляры являются одиночными. Иными словами, экземпляры клиента должны быть уникальными в течение всего времени существования приложения.
Когда клиент работает по протоколу TCP, он оптимизирует задержку, используя длительные соединения. Это отличается от протокола HTTPS, который прерывает подключения после двух минут бездействия.
В сценариях с разреженным доступом, если вы видите более высокое число подключений по сравнению с режимом шлюза, вы можете:
- Задать для свойства CosmosClientOptions.PortReuseMode значение
PrivatePortPool(действует с версиями платформы 4.6.1 и более поздними и версиями .NET Core 2.0 и более поздними). Это свойство позволяет пакету SDK использовать небольшой пул временных портов для разных конечных точек назначения Azure Cosmos DB. - Настройте свойство CosmosClientOptions.IdleTcpConnectionTimeout как больше или равно 10 минут. Рекомендуется использовать значения от 20 минут до 24 часов.
Повышение производительности за счет размещения клиентов в одном регионе Azure
Если это возможно, размещайте приложения, выполняющие вызовы к Azure Cosmos DB, в том же регионе, в котором находится база данных Azure Cosmos DB. Для приблизительного сравнения: вызовы к Azure Cosmos DB в пределах региона выполняются в течение 1–2 мс, но задержка между восточным и западным побережьем США превышает 50 мс. Значение задержки может отличаться в зависимости от выбранного маршрута при передаче запроса от клиента к границе центра обработки данных Azure.
Можно достичь минимальной задержки при размещении клиентского приложения в том же регионе Azure, в котором предоставляется конечная точка Azure Cosmos DB. Список доступных регионов см. на странице с регионами Azure.
Увеличение количества потоков или задач
Так как вызовы Cosmos DB выполняются по сети, может потребоваться изменить степень параллелизма запросов, чтобы клиентское приложение тратило минимальное количество времени на ожидание между запросами. Например, если вы используете библиотеку параллельных задач .NET, создайте около нескольких сотен задач считывания или записи в Azure Cosmos DB.
Включите ускоренное сетевое соединение для уменьшения задержки и колебаний производительности ЦП
Рекомендуется выполнить инструкции по включению ускорения сети в виртуальной машине Windows или Linux Azure , чтобы повысить производительность.
Без ускорения сети операции ввода-вывода, передаваемые между виртуальной машиной Azure и другими ресурсами Azure, могут быть ненужно перенаправлены через узел и виртуальный коммутатор, расположенный между виртуальной машиной и ее сетевой картой. Наличие узла и виртуального коммутатора внутри пути данных не только увеличивает задержку и дрожание в коммуникационном канале, но также приводит к краже циклов ЦП у виртуальной машины. С ускорением сети виртуальная машина напрямую взаимодействует с сетевым адаптером без посредников; все сведения о политике сети, обрабатываемые узлом и виртуальным коммутатором, теперь обрабатываются в оборудовании на сетевом адаптере; Обход узла и виртуального коммутатора. При включении ускоренной сети, как правило, можно ожидать снижение задержки и увеличение пропускной способности, а также улучшение согласованности задержки и снижение загрузки ЦП.
Ограничения: ускоренная сеть должна поддерживаться в ОС виртуальной машины и может быть включена только при остановке и освобождении виртуальной машины. Виртуальная машина не может быть развернута с помощью Azure Resource Manager. Служба приложений не включает ускоренную сеть.
Дополнительные сведения см. в инструкциях по Windows и Linux .
Использование пакета SDK
Установка последней версии пакета SDK
Пакеты SDK для Azure Cosmos DB постоянно улучшаются, чтобы обеспечивать самую высокую производительность. Сведения о последней версии пакета SDK и об улучшениях см. в статье о пакете SDK для Azure Cosmos DB.
Использование API-интерфейсов потока
Пакет SDK для .NET v3 содержит API-интерфейсы потока, которые могут получать и возвращать данные без сериализации.
Приложения среднего уровня, которые не используют ответы непосредственно из пакета SDK, но ретранслируют их на другие уровни приложений, могут получить преимущества от API-интерфейсов потока. Примеры обработки потоков см. в разделе с примерами управления элементами.
Использование одного и того же клиента Azure Cosmos DB в течение всего жизненного цикла приложения
Каждый экземпляр CosmosClient является потокобезопасным и эффективно управляет подключениями и кэширует адреса в прямом режиме работы. Чтобы обеспечить эффективное управление подключениями и более высокую производительность клиента пакета SDK, рекомендуется использовать один экземпляр за AppDomain время существования приложения для каждой учетной записи, с которыми взаимодействует ваше приложение.
Для мультитенантных приложений, обрабатывающих несколько учетных записей, см. связанные рекомендации.
При работе с Функции Azure также следует следовать существующим рекомендациям и поддерживать одну инстанцию.
Избегайте блокирующих вызовов
Пакет SDK Для Azure Cosmos DB должен быть разработан для одновременной обработки множества запросов. Асинхронные API позволяют небольшому пулу потоков работать с тысячами одновременных запросов, не дожидаясь блокировки вызовов. Вместо ожидания завершения длительной синхронной задачи поток может работать с другим запросом.
Распространенная проблема с производительностью в приложениях с помощью пакета SDK Azure Cosmos DB блокирует вызовы, которые могут быть асинхронными. Многие синхронные блокирующие вызовы приводят к нехватке пула потоков и ухудшению времени отклика.
Не рекомендуется:
- Блокировать асинхронное выполнение путем вызова Task.Wait или Task.Result.
- Использовать метод Task.Run, чтобы сделать синхронный API асинхронным.
- Получать блокировки в общих участках кода. .NET SDK для Azure Cosmos DB обеспечивает наивысшую производительность при выполнении кода параллельно.
- Вызовите Task.Run и сразу ожидайте его. ASP.NET Core уже запускает код приложения в обычных потоках пула потоков, поэтому вызов Task.Run приводит только к дополнительному ненужному планированию в пуле потоков. Даже если запланированный код блокирует поток, Task.Run не предотвращает это.
- Не используйте ToList() в
Container.GetItemLinqQueryable<T>(), в котором используются блокирующие вызовы для синхронной очистки запроса. Используйте ToFeedIterator() для асинхронной очистки запросов.
Сделайте следующее:
- Асинхронно вызовите API .NET для Azure Cosmos DB.
- Весь стек вызовов является асинхронным, чтобы использовать преимущества шаблонов async/await.
Профилировщик, например PerfView, можно использовать для поиска потоков, часто добавляемых в пул потоков. Событие Microsoft-Windows-DotNETRuntime/ThreadPoolWorkerThread/Start указывает поток, добавленный в пул потоков.
Отключение ответа содержимого при операциях записи
Для рабочих нагрузок, создающих большие объемы данных, установите для параметра запроса EnableContentResponseOnWrite значение false. Служба больше не возвращает созданный или обновленный ресурс в пакет SDK. Как правило, поскольку приложение имеет создаваемый объект, служба не должна его возвращать. Значения заголовков по-прежнему доступны, как, например, плата за запрос. Отключение реагирования на содержимое может помочь повысить производительность, поскольку пакету SDK больше не требуется выделять память или сериализовать текст ответа. Это также сокращает использование пропускной способности сети для еще большего повышения производительности.
ItemRequestOptions requestOptions = new ItemRequestOptions() { EnableContentResponseOnWrite = false };
ItemResponse<Book> itemResponse = await this.container.CreateItemAsync<Book>(book, new PartitionKey(book.pk), requestOptions);
// Resource will be null
itemResponse.Resource
Активируйте режим Bulk для оптимизации пропускной способности вместо минимизации задержки
Включите опцию массовой обработки для сценариев, когда задачи требуют большого объема пропускной способности, а задержка не является критичной. Дополнительные сведения о включении функции массовых операций и о том, для каких сценариев ее следует использовать, см. в разделе Поддержка массовых операций.
Увеличение максимального количества подключений System.Net для каждого узла при использовании режима шлюза
При использовании режима шлюза запросы Azure Cosmos DB выполняются по протоколу HTTPS/REST. К ним применяются ограничения на количество подключений по умолчанию для каждого имени узла или IP-адреса. Может потребоваться задать для параметра MaxConnections более высокое значение (от 100 до 1000), чтобы клиентская библиотека могла использовать несколько одновременных подключений к Azure Cosmos DB. В пакете SDK для .NET 1.8.0 и более поздних версиях значение по умолчанию для ServicePointManager.DefaultConnectionLimit равно 50. Чтобы изменить значение, можно задать для Documents.Client.ConnectionPolicy.MaxConnectionLimit более высокое значение.
Увеличение количества потоков или задач
См. подраздел Увеличение количества потоков или задач раздела "Сеть" этой статьи.
Управление зависимостями Newtonsoft.Json
Overview
Пакет SDK для .NET для Azure Cosmos DB для операций сериализации JSON зависит от Newtonsoft.Json.
Эта зависимость не управляется автоматически — необходимо явно добавить Newtonsoft.Json как прямую зависимость в ваш проект.
Пакет SDK компилируется в Newtonsoft.Json 10.x внутри системы, которая имеет известную уязвимость безопасности. Хотя пакет SDK технически совместим с 10.x, а использование пакета SDK Newtonsoft.Json не подвержено обнаруженной проблеме безопасности, мы по-прежнему рекомендуем использовать версию 13.0.3 или более позднюю , чтобы избежать потенциальных проблем безопасности или конфликтов. Версии 13.x включают критические изменения, но шаблоны использования пакета SDK совместимы с этими изменениями.
Important
Эта зависимость требуется даже при использовании System.Text.Json для определяемых пользователем типов через CosmosClientOptions.UseSystemTextJsonSerializerWithOptions, так как внутренние операции пакета SDK по-прежнему используют Newtonsoft.Json для системных типов.
Рекомендуемая конфигурация
Всегда явно добавлять Newtonsoft.Json версию 13.0.3 или более позднюю в качестве прямой зависимости при использовании пакета SDK для .NET для Azure Cosmos DB версии 3. Не используйте версию 10.x из-за известных уязвимостей системы безопасности.
Для стандартных проектов .csproj
<ItemGroup>
<PackageReference Include="Microsoft.Azure.Cosmos" Version="3.47.0" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.4" />
</ItemGroup>
Для проектов с использованием централизованного управления пакетами
Если проект использует Directory.Packages.props:
<Project>
<ItemGroup>
<PackageVersion Include="Microsoft.Azure.Cosmos" Version="3.47.0" />
<PackageVersion Include="Newtonsoft.Json" Version="13.0.4" />
</ItemGroup>
</Project>
Устранение проблем конфликтов версий
Отсутствует ссылка на Newtonsoft.Json
Если возникает ошибка сборки, например:
The Newtonsoft.Json package must be explicitly referenced with version >= 10.0.2. Please add a reference to Newtonsoft.Json or set the 'AzureCosmosDisableNewtonsoftJsonCheck' property to 'true' to bypass this check.
Эта ошибка намеренно создается целевыми объектами сборки пакета SDK Cosmos DB для обеспечения правильной настройки зависимостей.
Решение для приложений:
Добавьте явную ссылку на Newtonsoft.Json, как показано в разделе рекомендуемой конфигурации выше.
Решение для библиотек:
Если вы создаете библиотеку (не приложение) и хотите перенести зависимость Newtonsoft.Json на пользователей вашей библиотеки, это можно обойти, задав свойство MSBuild в вашем .csproj:
<PropertyGroup>
<AzureCosmosDisableNewtonsoftJsonCheck>true</AzureCosmosDisableNewtonsoftJsonCheck>
</PropertyGroup>
Предупреждение
Используйте этот обходной путь только при создании библиотек, где зависимость Newtonsoft.Json будет предоставляться конечными пользователями. Для приложений всегда добавляйте явную ссылку.
Конфликты версий пакета
При возникновении ошибок сборки, таких как:
error NU1109: Detected package downgrade: Newtonsoft.Json from 13.0.4 to centrally defined 13.0.3
Solution:
Определите требуемую версию , проверив, какие пакеты требуют более новых версий:
dotnet list package --include-transitive | Select-String "Newtonsoft.Json"Обновите централизованную версию пакета , чтобы соответствовать или превышать самую требуемую версию:
<PackageVersion Include="Newtonsoft.Json" Version="13.0.4" />Очистка и перестроение:
dotnet clean dotnet restore dotnet build
Совместимость версий
В следующей таблице показаны минимальные рекомендуемые безопасные версии Newtonsoft.Json для каждой версии пакета SDK Cosmos DB. Хотя пакет SDK может технически работать с 10.x, эти версии никогда не должны использоваться из-за уязвимостей безопасности.
| Версия пакета SDK Cosmos DB | Минимальная безопасная версия | Рекомендуется |
|---|---|---|
| 3.47.0+ | 13.0.3 | 13.0.4 |
| 3.54.0+ | 13.0.4 | 13.0.4 |
Tip
При использовании .NET Aspire 13.0.0 или более поздней, убедитесь, что Aspire Newtonsoft.Json имеет версию 13.0.4, чтобы избежать конфликтов с компонентами Azure.
Лучшие практики
- Всегда добавляйте как прямую зависимость. Пакет SDK не управляет этой зависимостью автоматически.
- Используйте версию 13.0.3 или более поздней. Никогда не используйте 10.x , несмотря на техническую совместимость, из-за известных уязвимостей безопасности
-
Обязательный даже при использовании System.Text.Json — вы должны включить Newtonsoft.Json даже при использовании
UseSystemTextJsonSerializerWithOptions, так как пакет SDK использует его внутренне для системных типов. - Закрепите версию явным образом . Не полагаться на разрешение транзитивной зависимости
- Предупреждения мониторинга - Обработайте предупреждения о понижении уровня пакета NuGet (NU1109) как ошибки в конвейерах CI/CD
Операции запросов
Сведения об операциях запросов см. в советах по производительности запросов.
Политика индексирования
Исключите неиспользуемые пути из индексирования, чтобы ускорить выполнение операций записи
Политика индексирования Azure Cosmos DB также позволяет указать пути к документам для включения или исключения из индексирования с помощью путей индексирования (IndexingPolicy.IncludePaths и IndexingPolicy.ExcludeedPaths).
Индексирование только нужных путей может повысить производительность операций записи, сократить расходы на RU при операциях записи и уменьшить объем хранилища индексов для сценариев, в которых эти запросы известны заранее. Это обусловлено тем, что стоимость индексирования напрямую соотносится с количеством уникальных путей. Например, в следующем коде показано, как исключить весь раздел документов (поддерев) из индексирования с помощью * подстановочного знака:
var containerProperties = new ContainerProperties(id: "excludedPathCollection", partitionKeyPath: "/pk" );
containerProperties.IndexingPolicy.IncludedPaths.Add(new IncludedPath { Path = "/*" });
containerProperties.IndexingPolicy.ExcludedPaths.Add(new ExcludedPath { Path = "/nonIndexedContent/*");
Container container = await this.cosmosDatabase.CreateContainerAsync(containerProperties);
Дополнительные сведения см. в статье Политики индексации Azure Cosmos DB.
Throughput
Измерение и настройка для уменьшения использования RU/s
В Azure Cosmos DB предлагается обширный набор операций базы данных. К этим операциям относятся реляционные и иерархические запросы с определяемыми пользователем функциями (UDFS), хранимыми процедурами и триггерами, всеми работающими на документах в коллекции баз данных.
Затраты, связанные с каждой из этих операций, зависят от типа процессора, операций ввода-вывода и памяти, необходимой для выполнения операции. Вы можете забыть о необходимости управления аппаратными ресурсами, вместо этого рассматривая единицу запроса как универсальную меру оценки ресурсов, требуемых для выполнения различных операций с базами данных и обслуживания запросов приложения.
Пропускная способность выделяется на основе количества единиц запроса, заданного для каждого контейнера. Потребление ресурсных единиц оценивается по скорости "единиц в секунду". Приложения, превышающие выделенную частоту ЕЗ для контейнера, ограничиваются до тех пор, пока скорость не падает ниже выделенного уровня для контейнера. Если вашему приложению требуется более высокий уровень пропускной способности, вы можете увеличить её, выделив больше единиц запросов (RUs).
Сложность запроса влияет на количество операционных единиц, используемых для операции. Количество предикатов и их характер, количество файлов UDF и размер набора исходных данных — все это влияет на плату за операции запроса.
Чтобы измерить затраты на любую операцию (создание, обновление или удаление), проверьте заголовок x-ms-request-charge (или эквивалентное RequestCharge свойство в ResourceResponse<T>FeedResponse<T> пакете SDK для .NET) для измерения количества единиц RUS, потребляемых операциями:
// Measure the performance (Request Units) of writes
ItemResponse<Book> response = await container.CreateItemAsync<Book>(myBook, new PartitionKey(myBook.PkValue));
Console.WriteLine("Insert of item consumed {0} request units", response.RequestCharge);
// Measure the performance (Request Units) of queries
FeedIterator<Book> queryable = container.GetItemQueryIterator<ToDoActivity>(queryString);
while (queryable.HasMoreResults)
{
FeedResponse<Book> queryResponse = await queryable.ExecuteNextAsync<Book>();
Console.WriteLine("Query batch consumed {0} request units", queryResponse.RequestCharge);
}
Затраты на запрос, возвращенные в этом заголовке, — это часть выделенной пропускной способности (то есть, 2000 RU/с). Например, если приведенный выше запрос вернет 1000 документов размером по 1 КБ каждый, затраты на операцию составят 1000. Таким образом, перед ограничением частоты выполнения последующих запросов сервер за одну секунду выполняет лишь два таких запроса. Чтобы узнать больше, ознакомьтесь с единицами запроса и калькулятором единиц запроса.
Обработка ограничения скорости / слишком высокая частота запросов
Если клиент пытается превысить зарезервированную пропускную способность для учетной записи, это не приводит к замедлению работы сервера и не позволяет использовать пропускную способность сверх зарезервированного уровня. Сервер заблаговременно прерывает запрос с кодом состояния RequestRateTooLarge (код статуса HTTP 429). Он возвращает заголовок x-ms-retry-after-ms, который указывает время ожидания (в миллисекундах), по истечении которого пользователь должен выполнить запрос еще раз.
HTTP Status 429,
Status Line: RequestRateTooLarge
x-ms-retry-after-ms :100
Все пакеты SDK автоматически перехватывают этот ответ, соблюдают указанный сервером заголовок retry-after и повторяют запрос. Если к вашей учетной записи параллельно имеет доступ только один клиент, следующая попытка будет успешной.
Если сразу несколько клиентов регулярно выполняют запросы с частотой выше заданной, количество повторных попыток по умолчанию, которое сейчас задано клиентом как 9, может быть недостаточным. В этом случае клиент создает в приложении исключение CosmosException с кодом состояния 429.
Можно изменить число повторных попыток по умолчанию, задав RetryOptions для экземпляра CosmosClientOptions. По умолчанию исключение с кодом состояния 429 (CosmosException) возвращается после совокупного времени ожидания в 30 секунд, если запрос продолжает работать выше скорости запроса. Эта ошибка возвращается, даже если текущее число повторных попыток меньше максимального, независимо от того, является ли текущее значение значением по умолчанию 9 или значением, определенным пользователем.
Автоматическое поведение повторных попыток помогает повысить устойчивость и удобство использования для большинства приложений. Но это может не быть лучшим поведением при выполнении тестов производительности, особенно при измерении задержки. Если эксперимент достигает ограничения сервера и заставляет клиентский SDK повторять попытки в тихом режиме, на стороне клиента могут возникать пиковые задержки. Чтобы избежать пиков задержек во время настройки производительности, проверьте расход ресурсов на каждую операцию и убедитесь, что значение частоты запросов не превышено.
Дополнительные сведения см. в статье Единицы запроса.
Использование документов меньшего размера для обеспечения более высокой пропускной способности
Плата за запрос (т. е. затраты на обработку запросов) указанной операции напрямую коррелирует с размером документа. За операции с большими документами взимается больше единиц запроса, чем за операции с мелкими документами.