Maison > développement back-end > Golang > Comment puis-je diffuser des réponses HTTP dans Golang et éviter la mise en mémoire tampon par défaut ?

Comment puis-je diffuser des réponses HTTP dans Golang et éviter la mise en mémoire tampon par défaut ?

Susan Sarandon
Libérer: 2024-12-30 05:07:13
original
606 Les gens l'ont consulté

How Can I Stream HTTP Responses in Golang and Avoid Default Buffering?

Streaming de réponses HTTP dans Golang : contourner la mise en mémoire tampon par défaut

Ce guide aborde le problème de la mise en mémoire tampon dans la gestion des réponses HTTP de Go, où les réponses sont généralement mises en mémoire tampon et envoyées en blocs à le client après le traitement de la demande. Pour les scénarios de streaming, cela n'est peut-être pas souhaitable.

L'extrait de code fourni illustre le problème, où deux lignes de données sont censées être diffusées mais sont plutôt envoyées simultanément en raison de la mise en mémoire tampon.

Mise en œuvre Flushing

Une approche pour résoudre ce problème consiste à vider explicitement le tampon de réponse. ResponseWriter de Go fournit une méthode Flush, mais sa disponibilité dépend de l'implémentation spécifique.

Par exemple, le code modifié suivant intègre le vidage :

func handle(res http.ResponseWriter, req *http.Request) {
  fmt.Fprintf(res, "sending first line of data")
  if f, ok := res.(http.Flusher); ok {
    f.Flush()
  }
  sleep(10) //not real code
  fmt.Fprintf(res, "sending second line of data")
}
Copier après la connexion

Piping External Output

Dans certains scénarios, tels que la diffusion en continu de la sortie d'une commande externe, le vidage direct peut ne pas suffire. Le mécanisme de canal de Go permet une diffusion directe entre la sortie de la commande et l'auteur de la réponse.

Voici un exemple d'implémentation :

pipeReader, pipeWriter := io.Pipe()
cmd.Stdout = pipeWriter
cmd.Stderr = pipeWriter
go writeCmdOutput(res, pipeReader)
err := cmd.Run()
pipeWriter.Close()

func writeCmdOutput(res http.ResponseWriter, pipeReader *io.PipeReader) {
  buffer := make([]byte, BUF_LEN)
  for {
    n, err := pipeReader.Read(buffer)
    if err != nil {
      pipeReader.Close()
      break
    }

    data := buffer[0:n]
    res.Write(data)
    if f, ok := res.(http.Flusher); ok {
      f.Flush()
    }
    //reset buffer
    for i := 0; i < n; i++ {
      buffer[i] = 0
    }
  }
}
Copier après la connexion

Option avancée : piratage TCP

Pour plus de flexibilité , il est possible d'utiliser le TCP Hijacker, qui accorde un contrôle direct sur la connexion TCP. Cependant, cette approche nécessite une compréhension plus approfondie de la programmation réseau et est moins recommandée pour les cas d'utilisation généraux.

Mises en garde

Notez que la mise en mémoire tampon peut toujours se produire dans les composants réseau ou au sein de l'application client, il est donc Il est crucial d'évaluer votre cas d'utilisation spécifique afin de déterminer la nécessité d'un rinçage explicite ou de solutions alternatives.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

source:php.cn
Déclaration de ce site Web
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Derniers articles par auteur
Tutoriels populaires
Plus>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal