As instâncias de contêiner elástico Spot (preemptíveis) permitem executar jobs em lote e cargas de trabalho sem estado na capacidade ociosa da Alibaba Cloud com preço reduzido. Este guia mostra como criar um pod baseado em ECI Spot em um cluster Kubernetes adicionando annotations ao manifesto do pod.
Limitações
Antes de prosseguir, observe as seguintes restrições:
As annotations entram em vigor apenas no momento da criação do pod. Adicionar ou modificar annotations em um pod existente não surte efeito.
Para Jobs do Kubernetes, adicione as annotations em
spec.template.metadata, e não nometadatade nível superior.Instâncias Spot exigem 2 ou mais vCPUs quando você especifica recursos por quantidade de vCPU e tamanho de memória.
Quando usar instâncias Spot
Instâncias Spot são adequadas para cargas de trabalho sem estado e tolerantes a falhas que suportam interrupções:
Jobs de batch e big data (Spark, pipelines de ETL)
Renderização de imagens e transcodificação de vídeo
Computação paralela em grande escala
Serviços web com escalabilidade horizontal
Utilize instâncias pay-as-you-go para cargas de trabalho que não toleram interrupções: ferramentas de gerenciamento de cluster, agentes de monitoramento, StatefulSets e bancos de dados.
Como funcionam as instâncias Spot
Faturamento
Ao criar uma instância Spot, o preço de mercado flutua conforme a oferta e a demanda do tipo de instância. Se o seu lance exceder o preço de mercado atual e houver estoque suficiente, o sistema cria a instância e ela entra em um período de proteção (padrão: 1 hora). Durante esse período, o faturamento utiliza o preço de mercado no momento da compra. Após o término da proteção, o faturamento passa a seguir o preço de mercado em tempo real.
Instâncias Spot têm custo inferior ao das instâncias pay-as-you-go. Para mais detalhes, consulte a seção "Billing methods" em Preemptible instances .
Mecanismo de recuperação
Após o fim do período de proteção, o sistema verifica o preço de mercado e o estoque de recursos a cada 5 minutos. Caso o preço de mercado ultrapasse seu lance ou o estoque seja insuficiente, o sistema libera a instância.
O sistema gera um evento SpotToBeReleased aproximadamente 3 minutos antes da liberação.
Depois da liberação, o faturamento cessa, o status da instância ECI muda para Expired e o status do pod altera-se para Failed com o motivo BidFailed.
Métodos de criação
|
Método |
Funcionamento |
Tamanho mínimo |
|
Especificar um tipo de instância ECS |
Faturado pelo preço pay-as-you-go com desconto em tempo real do tipo especificado |
— |
|
Especificar quantidade de vCPU e tamanho de memória |
O sistema seleciona automaticamente um tipo de instância ECS correspondente; faturado pelo preço de mercado com desconto desse tipo |
2 vCPUs |
Ao definir a quantidade de vCPU e o tamanho de memória, as combinações suportadas são:
|
vCPUs |
Memória (GiB) |
|
2 |
2, 4, 8, 16 |
|
4 |
4, 8, 16, 32 |
|
8 |
8, 16, 32, 64 |
|
12 |
12, 24, 48, 96 |
|
16 |
16, 32, 64, 128 |
|
24 |
24, 48, 96, 192 |
|
32 |
32, 64, 128, 256 |
|
52 |
96, 192, 384 |
|
64 |
128, 256, 512 |
Se a combinação especificada não for suportada, o sistema utilizará automaticamente a próxima especificação superior compatível.
Pré-requisitos
Antes de começar, certifique-se de ter:
Um cluster ACK com um nó virtual
O rótulo
alibabacloud.com/eci: "true"configurado para agendamento de ECI
Para escolher um preço de lance, consulte o histórico de preços Spot usando estas operações da API do ECS:
DescribeSpotPriceHistory — preços históricos dos últimos 30 dias
DescribeSpotAdvice — taxa média de liberação e taxa média de desconto
Defina seu lance acima do preço médio de mercado, mas dentro de uma faixa aceitável para o seu negócio. Isso aumenta a chance de criação bem-sucedida e reduz o risco de liberação prematura.
Annotations
Adicione as seguintes annotations em spec.template.metadata.annotations no manifesto do seu pod.
|
Annotation |
Obrigatória |
Padrão |
Descrição |
|
|
Sim |
— |
Política de lance. |
|
|
Não |
— |
Preço máximo por hora, com precisão de 3 casas decimais. Válido apenas quando |
|
|
Não |
|
Período de proteção em horas. Defina como |
|
|
Não |
|
Quando definido como |
Quando SpotAsPriceGo estiver configurado e o tipo de instância especificado tiver estoque insuficiente na zona de destino, defina seu preço máximo por hora próximo ao preço pay-as-you-go desse tipo de instância para melhorar a taxa de sucesso na criação.
Crie uma instância Spot
Todos os exemplos utilizam manifestos de Job do Kubernetes. O rótulo alibabacloud.com/eci: "true" agenda o pod em um nó virtual.
Exemplo 1: Especifique um tipo de instância ECS com limite de preço
Este exemplo cria uma instância Spot baseada em ecs.c6.large com preço máximo por hora de $0,25.
apiVersion: batch/v1
kind: Job
metadata:
name: test
spec:
template:
metadata:
labels:
app: perl
alibabacloud.com/eci: "true"
annotations:
k8s.aliyun.com/eci-use-specs: "ecs.c6.large" # Specify an ECS instance type.
k8s.aliyun.com/eci-spot-strategy: "SpotWithPriceLimit" # Use a price cap.
k8s.aliyun.com/eci-spot-price-limit: "0.25" # Maximum hourly price.
spec:
containers:
- name: pi
image: registry.cn-shanghai.aliyuncs.com/eci_open/perl:5
command: ["perl", "-Mbignum=bpi", "-wle", "print bpi(2000)"]
restartPolicy: Never
Comportamento:
Se o estoque ou a condição de preço não for atendida, o sistema não cria a instância.
Após a criação, inicia-se o período de proteção de 1 hora. Depois que esse período expirar, o sistema liberará a instância caso o preço de mercado exceda $0,25 ou o estoque seja insuficiente.
Exemplo 2: Especifique quantidade de vCPU e tamanho de memória com lance pelo preço de mercado
Use SpotAsPriceGo para dar lances automaticamente pelo preço de mercado atual. Especifique o tamanho da instância por meio dos limites de recursos do pod ou via annotation.
Opção A: Use limites de recursos do pod
apiVersion: batch/v1
kind: Job
metadata:
name: test
spec:
template:
metadata:
labels:
app: perl
alibabacloud.com/eci: "true"
annotations:
k8s.aliyun.com/eci-spot-strategy: "SpotAsPriceGo" # Bid at market price.
spec:
containers:
- name: pi
image: registry.cn-shanghai.aliyuncs.com/eci_open/perl:5
command: ["perl", "-Mbignum=bpi", "-wle", "print bpi(2000)"]
resources:
limits:
cpu: 2000m # 2 vCPUs
memory: 4096Mi # 4 GiB
restartPolicy: Never
Opção B: Use a annotation de especificação
apiVersion: batch/v1
kind: Job
metadata:
name: test
spec:
template:
metadata:
labels:
app: perl
alibabacloud.com/eci: "true"
annotations:
k8s.aliyun.com/eci-use-specs: "2-4Gi" # 2 vCPUs, 4 GiB (minimum 2 vCPUs).
k8s.aliyun.com/eci-spot-strategy: "SpotAsPriceGo" # Bid at market price.
spec:
containers:
- name: pi
image: registry.cn-shanghai.aliyuncs.com/eci_open/perl:5
command: ["perl", "-Mbignum=bpi", "-wle", "print bpi(2000)"]
restartPolicy: Never
Ambas as opções criam uma instância com 2 vCPUs e 4 GiB, com período de proteção de 1 hora.
Exemplo 3: Desative o período de proteção
Exemplo 4: Retorne para pay-as-you-go se o estoque Spot for insuficiente
Defina eci-spot-fallback como true para criar automaticamente uma instância pay-as-you-go quando não houver estoque Spot disponível.
apiVersion: batch/v1
kind: Job
metadata:
name: test
spec:
template:
metadata:
labels:
app: perl
alibabacloud.com/eci: "true"
annotations:
k8s.aliyun.com/eci-use-specs: "ecs.c6.large"
k8s.aliyun.com/eci-spot-strategy: "SpotWithPriceLimit"
k8s.aliyun.com/eci-spot-price-limit: "0.05"
k8s.aliyun.com/eci-spot-fallback: "true" # Fall back to pay-as-you-go.
spec:
containers:
- name: pi
image: registry.cn-shanghai.aliyuncs.com/eci_open/perl:5
command: ["perl", "-Mbignum=bpi", "-wle", "print bpi(2000)"]
restartPolicy: Never
Comportamento:
Se houver estoque Spot suficiente: o sistema cria uma instância Spot com período de proteção de 1 hora.
Se o estoque Spot for insuficiente: o sistema cria uma instância pay-as-you-go e não a libera automaticamente.
Para verificar qual tipo foi criado, execute kubectl describe pod e verifique a seção Events. Um evento SpotDegraded indica que a instância é pay-as-you-go.

Monitore e trate a liberação de instâncias
Detecte uma liberação iminente
O sistema gera um evento SpotToBeReleased aproximadamente 3 minutos antes da liberação de uma instância Spot. Use kubectl describe ou kubectl get events para monitorar esse evento.
# kubectl describe output
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Warning SpotToBeReleased 3m32s kubelet, eci Spot ECI will be released in 3 minutes
# kubectl get events output
LAST SEEN TYPE REASON OBJECT MESSAGE
3m39s Warning SpotToBeReleased pod/pi-frmr8 Spot ECI will be released in 3 minutes
Verifique o status após a liberação
Após a liberação, o faturamento cessa, o status da instância ECI muda para Expired e o status do pod altera-se para Failed com o motivo BidFailed.
# kubectl get pod output
NAME READY STATUS RESTARTS AGE
pi-frmr8 1/1 BidFailed 0 3h5m
# kubectl describe output
Status: Failed
Reason: BidFailed
Message: The pod is spot instance, and have been released at 2020-04-08T12:36Z
Encerramento gracioso
Para ativar o encerramento gracioso quando o sistema recuperar uma instância Spot, adicione a annotation k8s.aliyun.com/eci-spot-release-strategy: api-evict ao seu pod. Quando um nó virtual recebe um evento SpotToBeReleased, ele chama a Eviction API do Kubernetes para remover o pod de forma graciosa, em vez de encerrá-lo imediatamente.
O encerramento gracioso via Eviction API requer ack-virtual-node 2.11.0 ou posterior. Para mais informações, consulte ACK Virtual Node.
Quando o nó virtual recebe o evento SpotToBeReleased, a condição ContainerInstanceExpired é definida como true no pod, iniciando a sequência de remoção:
O nó virtual chama a Eviction API.
O servidor de API verifica o PodDisruptionBudget (PDB) do pod.
O timestamp de exclusão do pod é atualizado com o período de carência configurado. O servidor de API marca o pod para encerramento.
O kubelet no nó virtual inicia o encerramento gracioso.
O plano de controle desassocia o pod dos Endpoints e EndpointSlices. Após o término do período de carência (
terminationGracePeriodSeconds), o kubelet encerra o pod forçadamente.O kubelet notifica o servidor de API, que exclui o pod.
Se o pod for gerenciado por um ReplicaSet, StatefulSet, Job, SparkApplication ou um workflow configurado com definições de tolerância a falhas, o controlador cria automaticamente um pod substituto após a remoção.
Se o PDB estiver mal configurado ou se muitos pods não estiverem no estado Ready , a remoção pode estagnar. Caso a remoção não seja concluída quando a instância expirar, o sistema a liberará imediatamente, independentemente disso.
Próximos passos
Armazene dados críticos em discos independentes ou armazenamento externo, como o Apsara File Storage NAS, para protegê-los contra a liberação de instâncias.
Configure um PodDisruptionBudget (PDB) para controlar quantos pods podem ser removidos simultaneamente.
Para ativar o encerramento gracioso, atualize o ack-virtual-node para a versão 2.11.0 ou posterior.