Увеличение масштаба типа узла, отличного от первичного узла, в кластере Service Fabric
В этой статье описывается, как увеличить масштаб кластера Service Fabric, отличного от основного типа узла, с минимальным временем простоя. Обновления SKU на месте не поддерживаются на узлах кластера Service Fabric, так как такие операции могут привести к потере данных и доступности. Ниже описан самый надежный и рекомендуемый способ масштабирования типа узла Service Fabric.
Добавьте новый тип узла в кластер Service Fabric на основе обновленного (или измененного) SKU и конфигурации масштабируемого набора виртуальных машин. Этот шаг также включает настройку новой подсистемы балансировки нагрузки, подсети и общедоступного IP-адреса для масштабируемого набора.
После параллельного выполнения исходных и обновленных масштабируемых наборов перенесите рабочую нагрузку, установив ограничения размещения для приложений в новый тип узла.
Проверьте работоспособность кластера, а затем удалите исходный масштабируемый набор (и связанные ресурсы) и состояние узла для удаленных узлов.
Ниже описан процесс обновления размера виртуальной машины и операционной системы виртуальных машин, не являющихся основными виртуальными машинами типа узлов примера кластера с устойчивостью Silver, поддерживаемым одним масштабируемым набором с пятью узлами, используемыми в качестве дополнительного типа узла. Основной тип узла со службами системы Service Fabric останется неотвредимым. Мы обновим тип узла, отличный от первичного:
- размер виртуальной машины будет изменен со Standard_D2_V2 на Standard_D4_V2;
- Из операционной системы виртуальной машины Windows Server 2019 Datacenter в Windows Server 2022 Datacenter.
Предупреждение
Прежде чем выполнять эту процедуру для кластера рабочей среды, рекомендуется изучить образцы шаблонов и применить шаги для тестового кластера.
Не пытайтесь выполнить процедуру масштабирования типа узла, не являющегося первичным, если состояние кластера неработоспособно, так как это приведет только к дестабилизировать кластер дальше. Мы будем использовать пошаговые шаблоны развертывания Azure, используемые в руководстве по масштабированию основного узла кластера Service Fabric. Однако мы изменим их так, чтобы они не относятся к типам первичных узлов. Шаблоны доступны на сайте GitHub.
Настройка тестового кластера
Создадим начальный тестовый кластер Service Fabric. Сначала скачайте примеры шаблонов Azure Resource Manager, которые мы используем для выполнения этого сценария.
Затем войдите в учетную запись Azure.
# Sign in to your Azure account
Login-AzAccount -SubscriptionId "<subscription ID>"
Затем откройте файл parameters.json и измените значение параметра clusterName
на уникальное (в Azure).
Следующие команды помогут создать новый самозаверяющий сертификат и развернуть тестовый кластер. Если у вас уже есть сертификат, который вы хотите использовать, перейдите к шагу Развертывание кластера с использованием существующего сертификата.
Создание самозаверяющего сертификата и развертывание кластера
Сначала назначьте переменные, которые потребуются для развертывания кластера Service Fabric. Измените значения resourceGroupName
, certSubjectName
, parameterFilePath
и templateFilePath
в соответствии со своей учетной записью и средой:
# Assign deployment variables
$resourceGroupName = "sftestupgradegroup"
$certOutputFolder = "c:\certificates"
$certPassword = "Password!1" | ConvertTo-SecureString -AsPlainText -Force
$certSubjectName = "sftestupgrade.southcentralus.cloudapp.azure.com"
$parameterFilePath = "C:\parameters.json"
$templateFilePath = "C:\Initial-TestClusterSetup.json"
Примечание.
Перед выполнением команды для развертывания нового кластера Service Fabric убедитесь, что на локальном компьютере существует расположение certOutputFolder
.
Затем разверните тестовый кластер Service Fabric.
# Deploy the initial test cluster
New-AzServiceFabricCluster `
-ResourceGroupName $resourceGroupName `
-CertificateOutputFolder $certOutputFolder `
-CertificatePassword $certPassword `
-CertificateSubjectName $certSubjectName `
-TemplateFile $templateFilePath `
-ParameterFile $parameterFilePath
После завершения развертывания найдите PFX-файл ($certPfx
) на локальном компьютере и импортируйте его в хранилище сертификатов.
cd c:\certificates
$certPfx = ".\sftestupgradegroup20200312121003.pfx"
Import-PfxCertificate `
-FilePath $certPfx `
-CertStoreLocation Cert:\CurrentUser\My `
-Password (ConvertTo-SecureString Password!1 -AsPlainText -Force)
Эта операция вернет отпечаток сертификата, который можно использовать для подключения к новому кластеру и проверки его состояния работоспособности. (Пропустите следующий раздел, в котором описан альтернативный подход к развертыванию кластера.)
Развертывание кластера с использованием существующего сертификата
Для развертывания тестового кластера также можно использовать существующий сертификат Azure Key Vault. Для этого необходимо получить ссылки на Key Vault и отпечаток сертификата.
# Key Vault variables
$certUrlValue = "https://sftestupgradegroup.vault.azure.net/secrets/sftestupgradegroup20200309235308/dac0e7b7f9d4414984ccaa72bfb2ea39"
$sourceVaultValue = "/subscriptions/########-####-####-####-############/resourceGroups/sftestupgradegroup/providers/Microsoft.KeyVault/vaults/sftestupgradegroup"
$thumb = "BB796AA33BD9767E7DA27FE5182CF8FDEE714A70"
Затем назначьте для кластера имя группы ресурсов и укажите расположения templateFilePath
и parameterFilePath
.
Примечание.
Указанная группа ресурсов должна уже существовать и находиться в том же регионе, что и Key Vault.
$resourceGroupName = "sftestupgradegroup"
$templateFilePath = "C:\Initial-TestClusterSetup.json"
$parameterFilePath = "C:\parameters.json"
Наконец, выполните следующую команду, чтобы развернуть исходный тестовый кластер:
# Deploy the initial test cluster
New-AzResourceGroupDeployment `
-ResourceGroupName $resourceGroupName `
-TemplateFile $templateFilePath `
-TemplateParameterFile $parameterFilePath `
-CertificateThumbprint $thumb `
-CertificateUrlValue $certUrlValue `
-SourceVaultValue $sourceVaultValue `
-Verbose
Подключение к новому кластеру и проверка состояния работоспособности
Подключитесь к кластеру и убедитесь, что пять его узлов работоспособны (замените переменные clusterName
и thumb
, указав значения для своего кластера).
# Connect to the cluster
$clusterName = "sftestupgrade.southcentralus.cloudapp.azure.com:19000"
$thumb = "BB796AA33BD9767E7DA27FE5182CF8FDEE714A70"
Connect-ServiceFabricCluster `
-ConnectionEndpoint $clusterName `
-KeepAliveIntervalInSec 10 `
-X509Credential `
-ServerCertThumbprint $thumb `
-FindType FindByThumbprint `
-FindValue $thumb `
-StoreLocation CurrentUser `
-StoreName My
# Check cluster health
Get-ServiceFabricClusterHealth
После этого все готово к процедуре обновления.
Развертывание нового типа узла, отличного от основного, с обновленным масштабируемым набором
Чтобы обновить (вертикально масштабировать) тип узла, сначала необходимо развернуть узел нового типа на базе нового масштабируемого набора и вспомогательных ресурсов. Новый масштабируемый набор будет помечен как не первичный (isPrimary: false
так же, как и исходный масштабируемый набор). Если вы хотите увеличить масштаб основного типа узла, см. статью "Масштабирование типа основного узла кластера Service Fabric". Ресурсы, созданные в следующем разделе, в конечном итоге станут новым типом узла в кластере, а исходные ресурсы типа узла будут удалены.
Обновление шаблона кластера с использованием обновленного масштабируемого набора
Ниже приведены изменения в разделах исходного шаблона развертывания кластера для добавления нового типа узла и вспомогательных ресурсов.
Большинство необходимых изменений для этого шага уже были внесены в файл шаблона Step1-AddPrimaryNodeType.json . Однако необходимо внести дополнительное изменение, чтобы файл шаблона работал для типов узлов, не являющихся первичными. В следующих разделах подробно описаны эти изменения, и вызовы будут сделаны, когда необходимо внести изменения.
Примечание.
Убедитесь, что вы используете имена, уникальные из исходного типа узла, масштабируемого набора, подсистемы балансировки нагрузки, общедоступного IP-адреса и подсети исходного типа узла, не являющегося первичным, так как эти ресурсы будут удалены на следующем этапе процесса.
Создание новой подсети в виртуальной сети
{
"name": "[variables('subnet1Name')]",
"properties": {
"addressPrefix": "[variables('subnet1Prefix')]"
}
}
Создание нового общедоступного IP-адреса с уникальным значением domainNameLabel
{
"apiVersion": "[variables('publicIPApiVersion')]",
"type": "Microsoft.Network/publicIPAddresses",
"name": "[concat(variables('lbIPName'),'-',variables('vmNodeType1Name'))]",
"location": "[variables('computeLocation')]",
"properties": {
"dnsSettings": {
"domainNameLabel": "[concat(variables('dnsName'),'-','nt1')]"
},
"publicIPAllocationMethod": "Dynamic"
},
"tags": {
"resourceType": "Service Fabric",
"clusterName": "[parameters('clusterName')]"
}
}
Создание новой подсистемы балансировки нагрузки для общедоступного IP-адреса
"dependsOn": [
"[concat('Microsoft.Network/publicIPAddresses/',concat(variables('lbIPName'),'-',variables('vmNodeType1Name')))]"
]
Создание нового масштабируемого набора виртуальных машин (с обновленными SKU виртуальных машин и ОС)
Справка по типам узлов
"nodeTypeRef": "[variables('vmNodeType1Name')]"
SKU виртуальной машины
"sku": {
"name": "[parameters('vmNodeType1Size')]",
"capacity": "[parameters('nt1InstanceCount')]",
"tier": "Standard"
}
SKU ОС
"imageReference": {
"publisher": "[parameters('vmImagePublisher1')]",
"offer": "[parameters('vmImageOffer1')]",
"sku": "[parameters('vmImageSku1')]",
"version": "[parameters('vmImageVersion1')]"
}
Также включите все дополнительные расширения, необходимые для вашей рабочей нагрузки.
Добавление нового типа узла, отличного от основного, в кластер
Теперь, когда новый тип узла (vmNodeType1Name) имеет собственное имя, подсеть, IP-адрес, подсистему балансировки нагрузки и масштабируемый набор, он может повторно использовать все другие переменные из исходного типа узла (напримерnt0applicationEndPort
, и nt0applicationStartPort
).nt0fabricTcpGatewayPort
В существующем файле isPrimary
шаблона параметр устанавливается true
для руководства по масштабированию основного узла кластера Service Fabric. Перейдите isPrimary
к типу узла, отличному от false
основного типа:
"name": "[variables('vmNodeType1Name')]",
"applicationPorts": {
"endPort": "[variables('nt0applicationEndPort')]",
"startPort": "[variables('nt0applicationStartPort')]"
},
"clientConnectionEndpointPort": "[variables('nt0fabricTcpGatewayPort')]",
"durabilityLevel": "Bronze",
"ephemeralPorts": {
"endPort": "[variables('nt0ephemeralEndPort')]",
"startPort": "[variables('nt0ephemeralStartPort')]"
},
"httpGatewayEndpointPort": "[variables('nt0fabricHttpGatewayPort')]",
"isPrimary": false,
"reverseProxyEndpointPort": "[variables('nt0reverseProxyEndpointPort')]",
"vmInstanceCount": "[parameters('nt1InstanceCount')]"
После внесения всех изменений в файлы шаблонов и параметров перейдите к следующему разделу, чтобы получить ссылки Key Vault и развернуть обновления в кластере.
Получение ссылок Key Vault
Для развертывания обновленной конфигурации потребуется несколько ссылок на сертификат кластера, хранящийся в Key Vault. Проще всего найти эти значения через портал Azure. Что вам понадобится:
URL-адрес сертификата кластера в хранилище ключей. В хранилище Key Vault на портале Azure выберите Сертификаты>нужный вам сертификат>Идентификатор секрета:
$certUrlValue="https://sftestupgradegroup.vault.azure.net/secrets/sftestupgradegroup20200309235308/dac0e7b7f9d4414984ccaa72bfb2ea39"
Отпечаток сертификата кластера. (Возможно, у вас уже есть эти значения, если вы подключились к первоначальному кластеру для проверки его работоспособности.) Из той же колонки сертификата (Сертификаты>нужный вам сертификат) на портале Azure скопируйте отпечаток X. 509 SHA-1 (в шестнадцатеричном формате):
$thumb = "BB796AA33BD9767E7DA27FE5182CF8FDEE714A70"
Идентификатор ресурса для хранилища ключей. В хранилище Key Vault на портале Azure выберите Свойства>Идентификатор ресурса:
$sourceVaultValue = "/subscriptions/########-####-####-####-############/resourceGroups/sftestupgradegroup/providers/Microsoft.KeyVault/vaults/sftestupgradegroup"
Развертывание обновленного шаблона
Измените параметр templateFilePath
соответствующим образом и выполните приведенную ниже команду.
# Deploy the new node type and its resources
$templateFilePath = "C:\Step1-AddPrimaryNodeType.json"
New-AzResourceGroupDeployment `
-ResourceGroupName $resourceGroupName `
-TemplateFile $templateFilePath `
-TemplateParameterFile $parameterFilePath `
-CertificateThumbprint $thumb `
-CertificateUrlValue $certUrlValue `
-SourceVaultValue $sourceVaultValue `
-Verbose
После завершения развертывания снова проверьте работоспособность кластера и убедитесь, что все узлы обоих типов работоспособны.
Get-ServiceFabricClusterHealth
Перенос рабочих нагрузок в новый тип узла
Подождите, пока все приложения переместятся в новый тип узла и будут работоспособными.
Отключение узлов в наборе масштабирования исходного типа узла
После миграции всех начальных узлов в новый масштабируемый набор можно отключить узлы исходного набора.
# Disable the nodes in the original scale set.
$nodeType = "nt0vm"
$nodes = Get-ServiceFabricNode
Write-Host "Disabling nodes..."
foreach($node in $nodes)
{
if ($node.NodeType -eq $nodeType)
{
$node.NodeName
Disable-ServiceFabricNode -Intent RemoveNode -NodeName $node.NodeName -Force
}
}
Для отслеживания перехода узлов в исходном масштабируемом наборе из состояния Отключение в состояние Отключен используйте Service Fabric Explorer. Подождите, пока все узлы будут достигнуть отключенного состояния.
Отключение обработки данных на отключенных узлах
Теперь можно отключить обработку данных на отключенных узлах.
# Stop data on the disabled nodes.
foreach($node in $nodes)
{
if ($node.NodeType -eq $nodeType)
{
$node.NodeName
Start-ServiceFabricNodeTransition -Stop -OperationId (New-Guid) -NodeInstanceId $node.NodeInstanceId -NodeName $node.NodeName -StopDurationInSeconds 10000
}
}
Удаление исходного типа узла и очистка ресурсов
Теперь мы готовы удалить исходный тип узла и связанные с ним ресурсы, чтобы завершить процедуру вертикального масштабирования.
Удаление исходного масштабируемого набора
Сначала удалите базовый масштабируемый набор типа узла.
$scaleSetName = "nt0vm"
$scaleSetResourceType = "Microsoft.Compute/virtualMachineScaleSets"
Remove-AzResource -ResourceName $scaleSetName -ResourceType $scaleSetResourceType -ResourceGroupName $resourceGroupName -Force
Удаление исходных ресурсов IP-адреса и подсистемы балансировки нагрузки
Теперь можно удалить исходные ресурсы IP-адреса и подсистемы балансировки нагрузки. На этом шаге вы также обновите DNS-имя.
Примечание.
Этот шаг является необязательным, если уже используются общедоступный IP-адрес и подсистема балансировки нагрузки SKU уровня Стандартный. В этом случае в одной подсистеме балансировки нагрузки может быть несколько масштабируемых наборов или типов узлов.
Выполните следующие команды, изменив значение $lbname
.
# Delete the original IP and load balancer resources
$lbName = "LB-sftestupgrade-nt0vm"
$lbResourceType = "Microsoft.Network/loadBalancers"
$ipResourceType = "Microsoft.Network/publicIPAddresses"
$oldPublicIpName = "PublicIP-LB-FE-nt0vm"
$newPublicIpName = "PublicIP-LB-FE-nt1vm"
$oldPublicIP = Get-AzPublicIpAddress -Name $oldPublicIpName -ResourceGroupName $resourceGroupName
$nonPrimaryDNSName = $oldNonPrimaryPublicIP.DnsSettings.DomainNameLabel
$nonPrimaryDNSFqdn = $oldNonPrimaryPublicIP.DnsSettings.Fqdn
Remove-AzResource -ResourceName $lbName -ResourceType $lbResourceType -ResourceGroupName $resourceGroupName -Force
Remove-AzResource -ResourceName $oldPublicIpName -ResourceType $ipResourceType -ResourceGroupName $resourceGroupName -Force
$PublicIP = Get-AzPublicIpAddress -Name $newPublicIpName -ResourceGroupName $resourceGroupName
$PublicIP.DnsSettings.DomainNameLabel = $nonPrimaryDNSName
$PublicIP.DnsSettings.Fqdn = $nonPrimaryDNSFqdn
Set-AzPublicIpAddress -PublicIpAddress $PublicIP
Удаление состояния узла из исходного типа узла
Для узлов исходного типа теперь в качестве состояния работоспособности будет отображаться ошибка. Удалите состояние узла из кластера.
# Remove state of the obsolete nodes from the cluster
$nodeType = "nt0vm"
$nodes = Get-ServiceFabricNode
Write-Host "Removing node state..."
foreach($node in $nodes)
{
if ($node.NodeType -eq $nodeType)
{
$node.NodeName
Remove-ServiceFabricNodeState -NodeName $node.NodeName -Force
}
}
Теперь в Service Fabric Explorer должны отражаться только пять узлов нового типа узла (nt1vm) с состоянием работоспособности ОК. Мы устраним эту ошибку на следующем шаге: обновим шаблон, чтобы отразить в нем последние изменения, и повторно развернем его.
Обновите шаблон развертывания, чтобы отразить только что масштабируемый тип узла, отличного от первичного.
Большинство необходимых изменений для этого шага уже были внесены в файл шаблона Step3-CleanupOriginalPrimaryNodeType.json . Однако необходимо внести дополнительное изменение, чтобы файл шаблона работал для типов узлов, не являющихся первичными. В следующих разделах подробно описаны эти изменения, и вызовы будут сделаны, когда необходимо внести изменения.
Обновление конечной точки управления кластером
Обновите кластер managementEndpoint
в шаблоне развертывания таким образом, чтобы в нем использовался новый IP-адрес (путем изменения параметра vmNodeType0Name на vmNodeType1Name).
"managementEndpoint": "[concat('https://',reference(concat(variables('lbIPName'),'-',variables('vmNodeType1Name'))).dnsSettings.fqdn,':',variables('nt0fabricHttpGatewayPort'))]",
Удаление ссылки на исходный тип узла
Удалите исходную ссылку на тип узла из ресурса Service Fabric в шаблоне развертывания.
В существующем файле isPrimary
шаблона параметр устанавливается true
для руководства по масштабированию основного узла кластера Service Fabric. Перейдите isPrimary
к типу узла, отличному от false
основного типа:
"name": "[variables('vmNodeType0Name')]",
"applicationPorts": {
"endPort": "[variables('nt0applicationEndPort')]",
"startPort": "[variables('nt0applicationStartPort')]"
},
"clientConnectionEndpointPort": "[variables('nt0fabricTcpGatewayPort')]",
"durabilityLevel": "Bronze",
"ephemeralPorts": {
"endPort": "[variables('nt0ephemeralEndPort')]",
"startPort": "[variables('nt0ephemeralStartPort')]"
},
"httpGatewayEndpointPort": "[variables('nt0fabricHttpGatewayPort')]",
"isPrimary": false,
"reverseProxyEndpointPort": "[variables('nt0reverseProxyEndpointPort')]",
"vmInstanceCount": "[parameters('nt0InstanceCount')]"
Настройка политик работоспособности для игнорирования существующих ошибок
Только для кластеров с уровнем устойчивости Silver и выше: обновите ресурс кластера в шаблоне и настройте политики работоспособности так, чтобы игнорировать работоспособность приложения fabric:/System
, добавив applicationDeltaHealthPolicies в свойства ресурса кластера, как показано ниже. Приведенная ниже политика должна игнорировать существующие ошибки, но при этом не допускать новых ошибок работоспособности.
"upgradeDescription":
{
"forceRestart": false,
"upgradeReplicaSetCheckTimeout": "10675199.02:48:05.4775807",
"healthCheckWaitDuration": "00:05:00",
"healthCheckStableDuration": "00:05:00",
"healthCheckRetryTimeout": "00:45:00",
"upgradeTimeout": "12:00:00",
"upgradeDomainTimeout": "02:00:00",
"healthPolicy": {
"maxPercentUnhealthyNodes": 100,
"maxPercentUnhealthyApplications": 100
},
"deltaHealthPolicy":
{
"maxPercentDeltaUnhealthyNodes": 0,
"maxPercentUpgradeDomainDeltaUnhealthyNodes": 0,
"maxPercentDeltaUnhealthyApplications": 0,
"applicationDeltaHealthPolicies":
{
"fabric:/System":
{
"defaultServiceTypeDeltaHealthPolicy":
{
"maxPercentDeltaUnhealthyServices": 0
}
}
}
}
}
Удаление вспомогательных ресурсов для исходного типа узла
Удалите из шаблона ARM и файла параметров все прочие ресурсы, связанные с исходным типом узла. Удалите:
"vmImagePublisher": {
"value": "MicrosoftWindowsServer"
},
"vmImageOffer": {
"value": "WindowsServer"
},
"vmImageSku": {
"value": "2019-Datacenter"
},
"vmImageVersion": {
"value": "latest"
},
Развертывание окончательной версии шаблона
Наконец, разверните измененный шаблон Azure Resource Manager.
# Deploy the updated template file
$templateFilePath = "C:\Step3-CleanupOriginalPrimaryNodeType"
New-AzResourceGroupDeployment `
-ResourceGroupName $resourceGroupName `
-TemplateFile $templateFilePath `
-TemplateParameterFile $parameterFilePath `
-CertificateThumbprint $thumb `
-CertificateUrlValue $certUrlValue `
-SourceVaultValue $sourceVaultValue `
-Verbose
Примечание.
Выполнение этого шага занимает определенное время, обычно не более двух часов.
В результате этого обновления изменятся параметры для InfrastructureService, в связи с чем потребуется перезагрузка узла. В данном случае значение параметра forceRestart игнорируется. Параметр upgradeReplicaSetCheckTimeout
задает максимальное время, в течение которого Service Fabric ожидает перехода секции в безопасное состояние, если она еще не находится в нем. После завершения проверок безопасности для всех секций на узле Service Fabric начинает обновление на этом узле. Значение параметра upgradeTimeout
можно уменьшить до 6 часов, однако для максимальной безопасности следует использовать значение 12 часов.
После завершения развертывания убедитесь на портале Azure, что ресурс Service Fabric находится в состоянии Готов. Убедитесь, что вы можете подключиться к новой конечной точке Service Fabric Explorer, состояние работоспособности кластера — ОК, а все развернутые приложения работают правильно.
При этом вы вертикально масштабировали тип узла, отличного от первичного узла!
Следующие шаги
- Узнайте, как добавить тип узла в кластер.
- Дополнительные сведения об обновлениях приложений.
- Руководство. Масштабирование кластера Service Fabric
- Масштабируйте кластер Azure программно, используя свободный пакет SDK для вычислений Azure.
- Увеличение и уменьшение масштаба автономного кластера.