Back

Rails中使用uploadify 插件 ( using Uploadify in Rails3)

发布时间: 2013-03-17 01:21:00

这个插件非常好用。 可以看作是 SWFupload的后续 (SWFUPLOAD已经停止开发好久好久了)

使用步骤也是一般吧,不是一下就可以搞定(我昨天花了大半天时间才做了个满意的封装,虽然我很讨厌封装),但是也不是特别麻烦。可以说解藕做的不错~  

实现它的缘由
1. 由于我们的图片都保存在一个远程服务器上,所以我们不需要在本地永久保存上传的数据。 对应的数据库中的列也只是一个String类型(varchar(255)),所以,我们只需要获取远程(CDN 服务器)上的IMAGE URL就好了。

2. 由于上传的限制很多(光服务器返回的错误代码就6种以上),所以,把这些出错消息返回给ERB页面很麻烦。所以我的想法就是做成GMAIL上传附件那样。可以即时的返回消息(AJAX方式)。这样用户就知道出错的原因 和解决办法了(原来出错的话没有任何消息)

3. 原有项目中的upload代码 出现很多次,重复的代码太多。这样会导致项目的难以维护。代码越是简洁,维护起来就越方便。开发速度也就越快。

4. 所以,我的方式是: AJAX 图片上传,本地表单项呢,是一个<input text>, 而不是<input file>。这样的话。上传图片后,这个<input text>就有了值,然后表单提交后,controller 用正常的方式 update_attribute(params[:entity]) 就直接把 params[:entity][:image_url]给更新了(假定属性叫 image_url)。 可以说, controller的代码一行都不用变。

5. 保证系统中有一个专门的action 处理AJAX上传。例如: /commons/upload (POST)

步骤如下:(参考它的官方DEMO),以及session的问题: 这个是for Rails2.3 的!!!(http://www.railstips.org/blog/archives/2009/07/21/uploadify-and-rails23/  )

(也不好使。。。不过我根据它的修修改改弄好了)这个是session for Rails3的: http://www.damiangalarza.com/posts/ruby-on-rails/using-uploadify-with-rails-3/

session 问题的关键是:

1. env['HTTP_COOKIE'] 要对的上。

2. authentication_token 要传给Rails. 

如果Rails3 发现以上2个条件,任意一个不对,它都会关闭当前的session, 然后分配给你一个新的session. 

下面是我的具体步骤: 

1. config/environment.rb:

 config.autoload_paths += %W(#{config.root}/app/middleware)

2. app/middleware/flash_session_cookie_middleware.rb 

( 注意!!!session_key 应该是你的APP的!)

( 注意!!! 下面的  env["REQUEST_URI"] == "/commons/upload" 一行,根据你的需要进行修改!~)

require 'rack/utils'

class FlashSessionCookieMiddleware
  def initialize(app, session_key = '_cms_session') # !!! change it to your own! 
    @app = app 
    @session_key = session_key
  end 

  def call(env)
    if env["REQUEST_URI"] == "/commons/upload" # env['HTTP_USER_AGENT'] =~ /^(Adobe|Shockwave) Flash/
      Rails.logger.debug "===== (before frozen) env['HTTP_COOKIE']: #{env['HTTP_COOKIE'].inspect}"
      req = Rack::Request.new(env)
      unless req.params[@session_key].nil?
        env['HTTP_COOKIE'] = [ @session_key, req.params[@session_key] ].join('=').freeze
      end 
      Rails.logger.debug "===== (after frozen) env['HTTP_COOKIE']: #{env['HTTP_COOKIE'].inspect}"
    end 

    @app.call(env)
  end 
end
end

3.config/initializers/session_store.rb, add these lines of code:

 Rails.application.config.middleware.insert_before(
   ActionDispatch::Session::CookieStore,
   FlashSessionCookieMiddleware,
   Rails.application.config.session_options[:key]
 )   
                                                  

4. in your ERB file (where the uploadify affects )

<% session_key = Rails.application.config.session_options[:key] %>
<script>
...
  data['<%= session_key %>'] = '<%= cookies[session_key] %>'
  data['authenticity_token'] = '<%= form_authenticity_token %>'
  ......
  'formData' : data,
  ......

Back