ruby-on-rails ruby sendfile

¿Cuál es la diferencia entre send_data y send_file en Ruby on Rails?



ruby-on-rails sendfile (2)

send_file puede ser más rápido que send_data

Como se menciona fl00r , send_file toma una ruta y send_data los datos a send_data .

Por send_file tanto, send_file es un subconjunto de send_data , ya que necesita un archivo en el sistema de archivos: por supuesto, puede leer el archivo y usar send_data en él. Pero send_file puede ser más rápido, por lo que es una compensación de rendimiento / generalidad.

send_file puede ser más rápido porque puede enviar el encabezado X-Sendfile en Apache ( X-Accel-Redirect en Nginx) en lugar del contenido del archivo, ya que conoce la ruta.

Este encabezado es consumido por el proxy inverso (Apache o Nginx) que normalmente se ejecuta en frente de Rails en una configuración de producción.

Si X-Sendfile está presente en la respuesta, el proxy inverso ignora la mayor parte de la respuesta actual y crea una nueva que devuelve el archivo en la ruta determinada.

Client <---> Internet <---> Reverse proxy <---> Rails

Esto es mucho más eficiente ya que el proxy inverso está altamente especializado para servir archivos estáticos, y puede hacerlo mucho más rápido que Rails (que no envía los datos del archivo si se envía X-Sendfile ).

El caso de uso típico de send_file es cuando desea controlar el permiso de acceso de los archivos estáticos: no puede ponerlos en /public o de lo contrario se publicarán antes de que Rails tenga la oportunidad de decidir. Esto se trata en: Protección del contenido del público / en una aplicación de Rails

Para usar los encabezados X-Sendfile , debes agregar:

config.action_dispatch.x_sendfile_header = "X-Sendfile" # for apache config.action_dispatch.x_sendfile_header = ''X-Accel-Redirect'' # for nginx

a confing/initializers/production.rb ( no a application.rb , ya que en desarrollo no tiene un servidor proxy y desea que send_file envíe realmente los datos).

X-Sendfile se trata en la Guía de X-Sendfile de activos .

¿Cuál es el mejor para la transmisión y la descarga de archivos?

Por favor proporcione ejemplos.


send_data(_data_, options = {}) send_file(_path_, options = {})

La principal diferencia aquí es que pasa DATA (código binario o lo que sea) con send_data o file PATH con send_file .

Por lo tanto, puede generar algunos datos y enviarlos como texto en línea o como archivo adjunto sin generar archivos en su servidor a través de send_data . O puede enviar un archivo listo con send_file

data = "Hello World!" send_data( data, :filename => "my_file.txt" )

O

data = "Hello World!" file = "my_file.txt" File.open(file, "w"){ |f| f << data } send_file( file )

Para el rendimiento, es mejor generar el archivo una vez y luego enviarlo tantas veces como desee. Así que send_file se ajustará mejor.

Para la transmisión, hasta donde yo entiendo, ambos métodos usan el mismo conjunto de opciones y configuraciones, por lo que puede usar X-Send o lo que sea.

UPD

send_data y guardar archivo:

data = "Hello World!" file = "my_file.txt" File.open(file, "w"){ |f| f << data } send_data( data )