下载XlsxWriter在rails中创建的XLSX文件

时间:2018-07-09 23:38:28

标签: ruby-on-rails ruby

我正在尝试将xlsx文件保存到浏览器下载中,单击浏览器按钮时会激活以下功能

def trip_bit
@car = Car.find(params[:id])
@t = @car.trips.all
@trips = @t.order(:started_at)

if @trips then
  doc = XlsxWriter.new
  doc.quiet_booleans!
  sheet = doc.add_sheet("Vitácora de Viajes "+@car.model+' '+@car.year.to_s)
  sheet.freeze_top_left = 'A2'
  sheet.add_row(['Salida', 'Llegada', 'Origen', 'Destino', 'Distancia', 'Duración', 'Score'])
  @trips.each do |trip|
    sheet.add_row([trip.started_at.to_s, trip.finished_at.to_s, if trip.origin then trip.origin.address end, if trip.destination then trip.destination.address end, trip.distance.to_s+'km', trip.duration.to_s+'min', trip.grade])
  end
  sheet.add_row(["","","","Total", @trips.map { |trip| trip.distance }.sum.to_s+"km", @trips.map { |trip| trip.duration}.sum.to_s+"min", ""])
else
  redirect_to my_car_details_path
  flash.now[:alert] = 'Este coche no tiene viajes registrados'
end

send_file doc, :filename => "bitacora.xlsx"

end

xlsx文件doc已创建并保存到本地文件系统,但是我找不到将其发送到浏览器下载的方法。

1 个答案:

答案 0 :(得分:1)

在查看了send_file和XlsxWriter的文档之后,该错误告诉您它正在期待一个String,但是您向其传递了XlsxWriter类型的对象。您可以尝试使用path方法告诉sendfile文件在...的位置。

send_file(doc.path, :disposition => 'attachment', :filename => "bitacora.xlsx", type: "application/xml")

您未指示Rails应用程序的任何结构,因此我假设这是一种控制器方法。您可能可以执行以下操作:

def trip_bit
@car = Car.find(params[:id])
@t = @car.trips.all
@trips = @t.order(:started_at)

if @trips then
  doc = XlsxWriter.new
  doc.quiet_booleans!
  sheet = doc.add_sheet("Vitácora de Viajes "+@car.model+' '+@car.year.to_s)
  sheet.freeze_top_left = 'A2'
  sheet.add_row(['Salida', 'Llegada', 'Origen', 'Destino', 'Distancia', 'Duración', 'Score'])
  @trips.each do |trip|
    sheet.add_row([trip.started_at.to_s, trip.finished_at.to_s, if trip.origin then trip.origin.address end, if trip.destination then trip.destination.address end, trip.distance.to_s+'km', trip.duration.to_s+'min', trip.grade])
  end
  sheet.add_row(["","","","Total", @trips.map { |trip| trip.distance }.sum.to_s+"km", @trips.map { |trip| trip.duration}.sum.to_s+"min", ""])
else
  redirect_to my_car_details_path
  flash.now[:alert] = 'Este coche no tiene viajes registrados'
end

respond_to do |format|
    format.xlsx
  end

end

上面的代码是一个直截了当的猜测,因为XlsxWriter是C库的绑定,并且从Rails的角度来看文档真的很薄,对我几乎没有用。我一直在使用axlsx_rails gem。它使您可以定义一个模板,并只需将该模板传递给Rails数据结构即可。我强烈建议您通过以下网址进行检查:https://github.com/straydogstudio/axlsx_rails

它允许您以Rails式的方式继续工作。当我要将用户电子表格导出到xlsx时,只需在控制器中执行以下操作:

  def index
    @users = User.active
    respond_to do |format|
      format.html
      format.xlsx
    end
  end

然后在我的index.html.erb旁边的视图中,有一个名为index.xlsx.axlsx的文件,看起来像:

wb = xlsx_package.workbook
wb.add_worksheet(name: "Users") do |sheet|
sheet.add_row ['User', 'User Access Role']
  @users.each do |user|
    sheet.add_row [user.email, user.role.name]
  end
end

如您所见,模板中具有创建电子表格的逻辑。您执行此操作的方式非常容易出错且杂乱无章。