Python intermediário · Guia Scraft

Async e await em Python: o que acontece durante uma espera?

Muitos programas passam parte do tempo esperando rede, arquivos ou outros serviços. A programação assíncrona permite que tarefas compatíveis avancem enquanto outra aguarda. Ela não torna qualquer cálculo mais rápido e não substitui uma escolha cuidadosa de bibliotecas e limites.

Antes de começar

Conheça funções, exceções e fluxo de execução. O exemplo exige Python 3.11 ou superior por usar asyncio.TaskGroup; não há pacotes extras.

O que você vai praticar

  • Distinguir uma corrotina criada de uma tarefa agendada.
  • Sobrepor esperas com TaskGroup e obter resultados após a conclusão do grupo.
  • Reconhecer operações bloqueantes e a necessidade de limites de tempo e concorrência.

async def cria uma corrotina; await acompanha sua conclusão

Ao chamar uma função definida com async def, você obtém um objeto de corrotina. Ele precisa ser aguardado ou agendado para executar. await pode ceder o controle ao event loop enquanto a operação aguarda; se a operação já estiver pronta, essa suspensão pode nem acontecer.

No exemplo, asyncio.sleep simula uma espera sem bloquear o event loop. Duas tarefas são criadas dentro de TaskGroup, disponível desde Python 3.11. Ao sair do bloco, o programa aguarda a conclusão do grupo. asyncio.run inicia o fluxo em um script comum.

import asyncio

async def preparar(nome):
    await asyncio.sleep(0.1)
    return f"{nome} pronto"

async def main():
    async with asyncio.TaskGroup() as grupo:
        primeira = grupo.create_task(preparar("A"))
        segunda = grupo.create_task(preparar("B"))
    print(primeira.result())
    print(segunda.result())

asyncio.run(main())

Resultado esperado

A pronto
B pronto

Esperar em sequência é diferente de criar tarefas

Se você escrever await preparar("A") e só depois await preparar("B"), a segunda operação começa após a primeira terminar. Criar as duas tarefas antes de aguardar o grupo permite sobrepor as esperas. A impressão neste exemplo mantém a ordem A, B porque ocorre depois que o grupo termina.

Uma chamada bloqueante, como time.sleep, ocupa a thread e impede o event loop de avançar nesse intervalo. Para operações de entrada e saída, prefira bibliotecas assíncronas compatíveis ou avalie uma thread para código bloqueante. Trabalho intenso de CPU exige outra análise; escrever async não o distribui automaticamente entre núcleos.

Limite tempo e quantidade de tarefas

Em uma integração real, use um prazo de espera e limite quantas operações podem executar ao mesmo tempo. Criar milhares de tarefas sem controle pode sobrecarregar o serviço de destino. Cancelamentos precisam permitir a limpeza de recursos; evite capturar e ignorar erros indiscriminadamente.

Use o exemplo para observar a ordem de execução antes de conectar uma rede real. Assim, você aprende o mecanismo sem depender de latência externa ou credenciais. Em notebooks que já possuem um event loop, aguarde main diretamente em vez de chamar asyncio.run dentro dele.

Do conceito ao código

Sua vez de praticar

Acrescente uma terceira tarefa ao grupo e mostre seus resultados na ordem A, B, C, independentemente da ordem em que as esperas terminam.

Confira estes casos

  • Cada tarefa retorna uma mensagem própria.
  • A impressão só acontece depois da saída do TaskGroup.
  • As três tarefas são criadas antes de aguardar o fim do grupo.
Preciso de uma dica

Guarde as referências retornadas por create_task e consulte result depois do bloco.

Continue pela documentação oficial

Ler este guia em texto