Rails仅将上传文件类型限制为.xls

时间:2013-12-06 14:16:43

标签: ruby-on-rails ruby

我希望从视图中上传excel表,但只接受excel 2003工作簿。 但是,我的尝试没有奏效。

这是我目前的实施;

视图中的

<%= file_field_tag :contact_file %>

和控制器;

if File.extname( params[:contact_file] ) == 'xls'
      @list = @current_user.lists.build(params[:list])
      @counter =0
      ActiveRecord::Base.transaction do |transaction|
        if @list.save
          if params[:contact_file]
            ap params[:contact_file]
            oo = Spreadsheet.open(params[:contact_file].path).worksheet(0)
            1.upto(oo.last_row_index) do |line|
              @counter+=1
              row = oo.row(line)
              name = row[0]
              phone_number = row[1].to_i.to_s
              new_contact = @current_user.contacts.build
              new_contact.phone_number = phone_number
              new_contact.name = name
              ap new_contact
              if new_contact.valid?
                new_contact.save
                @list.contacts << new_contact
              else
                if not @errors
                  @errors ={}
                end
                @errors["#{@counter+1}"] = new_contact.errors
              end
            end
          end

          if @errors
            render action: 'new'
            raise ActiveRecord::Rollback
          end
          redirect_to @list, notice: 'List was successfully created.'
        else
          render action: 'new'
        end
      end
    else
      flash[:notice] ="Please upload the correct file-format. Upload MS-Excel 2003 workbooks (.xls files)"
      render action: 'new'
    end
  end

可能是什么问题,因为这行File.extname( params[:contact_file] ) == 'xls'似乎不起作用。

请求参数如下所示;

{"utf8"=>"✓", "authenticity_token"=>"tzwsIt6sPhEFEqwS6YraU7SYU+kEvAr1it33j8YzCPk=", "list"=>{"name"=>"acacia", "user_id"=>"1"}, "contact_file"=>#<ActionDispatch::Http::UploadedFile:0xd7ad3b8 @original_filename="NGOs.xlsx", @content_type="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet", @headers="Content-Disposition: form-data; name=\"contact_file\"; filename=\"NGOs.xlsx\"\r\nContent-Type: application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\r\n", @tempfile=#<File:/tmp/RackMultipart20131206-14445-4cpor5>>, "commit"=>"Upload", "action"=>"create", "controller"=>"lists"}

3 个答案:

答案 0 :(得分:1)

File::extname会返回前导.的扩展名。

File.extname('a.xls')
# => ".xls"

它不会小写它。

File.extname('a.XLS')
# => ".XLS"

因此if ..行应替换为:

if File.extname(params[:contact_file].path.downcase) == '.xls'

如果您还想要过滤.xlsxlsx,...,请使用String#end_with?

if params[:contact_file].path.downcase.end_with?('.xls', '.xlsx')

答案 1 :(得分:1)

falsetru的答案很棒;我只是想补充一点,您可能还想考虑Excel文件不一定具有.xls扩展名的事实。实际上,当前版本的Excel的默认扩展名是.xlsx。所以,而不是像现在一样检查单个文件扩展名。

File.extname( params[:contact_file] ) == '.xls'

您可能需要考虑检查集合。所以你可以为你的支票做这样的事情

['.xls','.xlsx', '.xlsb'].include? File.extname(params[:contact_file])

有关Excel扩展程序的完整列表,以便您可以确定应该支持哪些扩展程序,可以查看此处。

http://office.microsoft.com/en-us/excel-help/file-formats-that-are-supported-in-excel-HP010014103.aspx

答案 2 :(得分:0)

File.extname返回.xls,因此if需要

if ['.xls','.xlsx', '.xlsb', '.xlsm'].include? File.extname(params[:contact_file].path.downcase)