2014-09-16 24 views
6

JQuery 1.11 ile Ruby 2.1.2, Rails 3.2.19 kullanıyoruz, varlık boru hattı kullanılmıyor (bu nedenle JQuery-ujs kullanmıyoruz, ancak ilgili rails.js'yi açıkça kullanıyoruz)). Çoğu kullanıcı için, JQuery ve diğer ilgili ortak eklentiler Google CDN'den çekilir (jquery.form 3.50 dahil). Etkilenen web sunucusu Ubuntu 14.04, Nginx 1.6 ve Yolcu 4.x'dir.Raf atma EOFError (kötü içerik gövdesi)

üretim sunucusunda kullanıcılarının yaklaşık% 10 için (yükleri önemli değil gibi görünüyor), öncelikle bir URL için, böyle dökümü bir yığın alıyoruz ama diğerleri vardır:

/gems/rack-1.4.5/lib/rack/multipart/parser.rb:74 in "block in fast_forward_to_first_boundary" 
/gems/rack-1.4.5/lib/rack/multipart/parser.rb:72 in "loop" 
/gems/rack-1.4.5/lib/rack/multipart/parser.rb:72 in "fast_forward_to_first_boundary" 
/gems/rack-1.4.5/lib/rack/multipart/parser.rb:15 in "parse" 
/gems/rack-1.4.5/lib/rack/multipart.rb:25 in "parse_multipart" 
/gems/rack-1.4.5/lib/rack/request.rb:336 in "parse_multipart" 
/gems/rack-1.4.5/lib/rack/request.rb:201 in "POST" 
/gems/actionpack-3.2.19/lib/action_dispatch/http/request.rb:237 in "POST" 
/gems/actionpack-3.2.19/lib/action_dispatch/http/parameters.rb:10 in "parameters" 
/gems/actionpack-3.2.19/lib/action_dispatch/http/filter_parameters.rb:31 in "filtered_parameters" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/rails3/action_controller.rb:31 in "process_action" 
/gems/actionpack-3.2.19/lib/abstract_controller/base.rb:121 in "process" 
/gems/actionpack-3.2.19/lib/abstract_controller/rendering.rb:45 in "process" 
/gems/actionpack-3.2.19/lib/action_controller/metal.rb:203 in "dispatch" 
/gems/actionpack-3.2.19/lib/action_controller/metal/rack_delegation.rb:14 in "dispatch" 
/gems/actionpack-3.2.19/lib/action_controller/metal.rb:246 in "block in action" 
/gems/actionpack-3.2.19/lib/action_dispatch/routing/route_set.rb:73 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/routing/route_set.rb:73 in "dispatch" 
/gems/actionpack-3.2.19/lib/action_dispatch/routing/route_set.rb:36 in "call" 
/gems/journey-1.0.4/lib/journey/router.rb:68 in "block in call" 
/gems/journey-1.0.4/lib/journey/router.rb:56 in "each" 
/gems/journey-1.0.4/lib/journey/router.rb:56 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/routing/route_set.rb:608 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/rack/error_collector.rb:50 in "traced_call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:55 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/rack/agent_hooks.rb:26 in "traced_call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:55 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/rack/browser_monitoring.rb:23 in "traced_call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:55 in "call" 
/gems/oink-0.10.1/lib/oink/middleware.rb:17 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/warden-1.2.3/lib/warden/manager.rb:35 in "block in call" 
/gems/warden-1.2.3/lib/warden/manager.rb:34 in "catch" 
/gems/warden-1.2.3/lib/warden/manager.rb:34 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/best_standards_support.rb:17 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-1.4.5/lib/rack/etag.rb:23 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-1.4.5/lib/rack/conditionalget.rb:25 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/head.rb:14 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/params_parser.rb:21 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/flash.rb:242 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-1.4.5/lib/rack/session/abstract/id.rb:210 in "context" 
/gems/rack-1.4.5/lib/rack/session/abstract/id.rb:205 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/cookies.rb:341 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/activerecord-3.2.19/lib/active_record/query_cache.rb:64 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/activerecord-3.2.19/lib/active_record/connection_adapters/abstract/connection_pool.rb:479 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/callbacks.rb:28 in "block in call" 
/gems/activesupport-3.2.19/lib/active_support/callbacks.rb:405 in "_run__3807242266783802268__call__1942732928323145202__callbacks" 
/gems/activesupport-3.2.19/lib/active_support/callbacks.rb:405 in "__run_callback" 
/gems/activesupport-3.2.19/lib/active_support/callbacks.rb:385 in "_run_call_callbacks" 
/gems/activesupport-3.2.19/lib/active_support/callbacks.rb:81 in "run_callbacks" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/callbacks.rb:27 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-1.4.5/lib/rack/sendfile.rb:102 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/remote_ip.rb:31 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/debug_exceptions.rb:16 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/show_exceptions.rb:56 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/railties-3.2.19/lib/rails/rack/logger.rb:32 in "call_app" 
/gems/railties-3.2.19/lib/rails/rack/logger.rb:18 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/actionpack-3.2.19/lib/action_dispatch/middleware/request_id.rb:22 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-1.4.5/lib/rack/methodoverride.rb:21 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-1.4.5/lib/rack/runtime.rb:17 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/activesupport-3.2.19/lib/active_support/cache/strategy/local_cache.rb:72 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-1.4.5/lib/rack/lock.rb:15 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/rack-cache-1.2/lib/rack/cache/context.rb:136 in "forward" 
/gems/rack-cache-1.2/lib/rack/cache/context.rb:245 in "fetch" 
/gems/rack-cache-1.2/lib/rack/cache/context.rb:185 in "lookup" 
/gems/rack-cache-1.2/lib/rack/cache/context.rb:66 in "call!" 
/gems/rack-cache-1.2/lib/rack/cache/context.rb:51 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/railties-3.2.19/lib/rails/engine.rb:484 in "call" 
/gems/railties-3.2.19/lib/rails/application.rb:231 in "call" 
/gems/railties-3.2.19/lib/rails/railtie/configurable.rb:30 in "method_missing" 
/gems/rack-1.4.5/lib/rack/urlmap.rb:64 in "block in call" 
/gems/rack-1.4.5/lib/rack/urlmap.rb:49 in "each" 
/gems/rack-1.4.5/lib/rack/urlmap.rb:49 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/gems/sass-3.2.19/lib/sass/plugin/rack.rb:54 in "call" 
/gems/newrelic_rpm-3.9.3.241/lib/new_relic/agent/instrumentation/middleware_tracing.rb:57 in "call" 
/var/www/.rvm/gems/ruby-2.1.2/gems/passenger-4.0.45/lib/phusion_passenger/rack/thread_handler_extension.rb:74 in "process_request" 
/var/www/.rvm/gems/ruby-2.1.2/gems/passenger-4.0.45/lib/phusion_passenger/request_handler/thread_handler.rb:141 in "accept_and_process_next_request" 
/var/www/.rvm/gems/ruby-2.1.2/gems/passenger-4.0.45/lib/phusion_passenger/request_handler/thread_handler.rb:109 in "main_loop" 
/var/www/.rvm/gems/ruby-2.1.2/gems/passenger-4.0.45/lib/phusion_passenger/request_handler.rb:448 in "block (3 levels) in start_threads" 

bir önce 1.5 (!) JQuery 1.11 yükseltin, bu hata oluşmadı (ya da eğer, o çok nadir oldu). Şu ana kadar bu hatayı evreleme sunucumuzda veya bir geliştirme ortamında yeniden üretemedik. Bir destek görevlisi bunu bir kez üretimde (birkaç kez denedim) gördü, ancak evreleme üzerinde çoğalamadı (üretim ile aynı çevre, daha küçük kaynak olsa da). JQuery migrate çalışırken herhangi bir sorun göstermiyor ve söylediğim gibi çoğu kullanıcı için çalışıyor gibi görünüyor; hata ayıklama oturumları sırasında hiçbir şey yanlış görünüyor. OS/platform veya tarayıcı için belirgin bir desen yoktur (birkaçda çoğaltılmaya çalışılmıştır ve günlükler, emin olmak için yeterince elemek için bir model belirtmez). İlgili birincil URL, bir form denetleyicisindeki #new eylemidir. Platformda başka birçok formumuz var ve bunlar hiçbir sorun göstermiyor.

Yeniden üretemediğimden, bir kod parçacığı vermek mümkün değil - Ne hakkında bilgi vereceğimi bilmiyorum.

bugüne kadar (yığın dökümü ilk satırında dayanarak) Hatanın Benim yorumlanması üç şeylerden biridir:

  1. içerik, aksi doğru, ancak tam bir şekilde oluşmuş değil
  2. içeriğidir
: kötü bir Ruby hata ( olsa belki JS)
  • kötü kodlama düşündüren oluşturulmuştur (açık olmasını ben Ruby form_for kullanıyorum ve hatta "gerçek çok parçalı" attı)

    Rafın 4.x'te ilgili çok parçalı bir EOFError sorunuyla uğraştığını görüyoruz, ancak eski bir sürümde bizi kilitleyen ve Rails 4.x sürümüne yükseltme yapmak için Rails 3.2.19 kullanıyoruz. Bir test olarak, JQuery'yi 1.7'ye kadar geri döndürdüm, ancak davranışı değiştirmedim (herhangi bir eski ve JQuery 1.8+ için gereken kod güncellemelerini bırakmak zorunda kaldım).

    JQuery kodunun JS'mizde değişiklikler gerektirdiğinden, gerekli bazı JS değişikliklerini kaçırdığımı sanmıştım, ancak hiçbir şey yanlış görünüyor. Yakınlarda bazı CSS değişiklikleri de vardı, ancak bunların nasıl etkileyebileceğini göremiyorum (her şey çeşitli test ortamlarımızda geçiyordu, diğer değişiklikler de dağıtıma dahil edildi).

    JS sorunlarından öncelikli olarak şüpheleniyorum, ancak üretim ile ilgili bazı sınırlı testler (canlı sunucuda dikkatli olmak zorundayım, bu yüzden çok agresif olamıyorum) herhangi bir ipucu göstermediniz veya ilgili herhangi bir hata atmayın .

    Arka plan olarak, Ruby ve JS ile (diğer programlama platformlarında çok daha fazla yıl olsa da) yaklaşık bir yıllık deneyimim var. Tamamen mümkün olmayan temel bir şey.

    Bu konuda bir tanıtıcıya odaklanmak için daraltma ile zor bir zaman geçiriyorum. Teşhis veya çözme konusunda herhangi bir tavsiye var mı?

    GÜNCELLEME (10/11/14) ben maymun Rack::Multipart::Parser.fast_forward_to_first_boundary (teşekkürler, Isaac Betesh!) Günlük izlerini eklemek yamalı ve bu işlevi (ulaştığında ayrıştırıcı geçirilen içeriği boş olduğunu doğruladı yani Çok parçalı ayrıştırma sırasında @env['rack.input'] tarafından belirtilen StringIO veri döndürmez). Benim teorim şimdi, hiçbiri olmadığında hatalı bir şekilde çok parçalı verileri beklemesidir. Yine, bu sadece aralıklı olarak gerçekleşir ve aynı sayfanın diğer birçok davetleri için para cezası keser. Yolcu 4.x ve Nginx altında çalıştığımız için arabelleğe alma sorununu çözmedim.

  • +1

    Rails 3 sürümü kilitlediğinden Raf'ı yükseltemiyorsanız, tekil bir dosyayı yığının üstündeki dosyaya maymun-yamalamayı deneyin. iz. Bunun neden olduğunu anlamayabilirsiniz, ancak yine de etkili bir çözüm olabilir. –

    +0

    Yapabilirim, ancak üretimdeki stok kodunun değiştirilmesi konusunda endişeliydim (gerçekten üreme olmadan bunu gerçekten test edemediğimden), davranışı değiştirir ve kullanıcı için hayatı kolaylaştırırsa, bu bana bir ipucu verebilir. zahmete değmek. Teşekkürler. – rdnewman

    +0

    Ayrıca, bu aynı kod JQuery'e yükseltmeden önce ve JS'deki ilgili değişikliklerden önce de iyi görünüyordu. Yani Jquery'deki değişim, Rack'daki başarısızlığı bir şekilde tetiklemek zorunda kalacaktı, bu yüzden benim başka tereddüt sebebim de buydu. – rdnewman

    cevap

    8

    Bu nihayet çözüldü ve başkalarına yardımcı olması durumunda ne olduğunu yayınlıyorum. Özet orijinal kod

    çok parçalı/form-veri kodlama ile (POST gibi) Bir form JS (jquery.form eklentisi ile) bir ajaxSubmit ihtiva (şimdiye kadar iyi). Gönderimi gerçekleştiren raylar denetleyicisi, verileri normal olarak işledi ve ,'u ikinci bir href'e (GET olarak) yönlendirdi. Tarayıcı (belki de success geri arama işleyicisine dönmeden önce jquery.form eklentisi üzerinden işleniyor) yönlendirmeyi aldı ve çok parçalı/form-veri kodlama tipini korudu. Raf, hala belirtilmiş çok parçalı kodlama ile GET aldığında, ayrıştırmak için çok parçalı bir veri olmadığından, bu durum aşıldı.

    Üzgünüm, bunların çoğu OP'mde kanıt değildi. Ve bunun neden JQuery ve JQuery.form eklentisinin eski bir sürümü altında çalıştığı ya da neden bazen yeni JQuery/JQuery.form altında başarılı olduğu açık değildir.

    Çözüm artık yönlendirmek değil, orijinal ajaxSubmit ait success geri arama işleyicisi için (bir metin işlemek gibi) bir URL dönmek için denetleyici Refactored. success işleyicisi şimdi döndürülen URL'de bir AJAX GET yapar, böylece iş akışını bozulmadan bırakır, ancak GET isteğinde çok satırlı kodlamayı ortadan kaldırır.

    tl; dr:

    kod şimdiye değiştirildi Önce

    biz jQuery karıştığı bir yol vardı.Bu gibi bir şeydi formu (kod örneği çalıştırılabilir olması amacıyla değil, sadece bir örnek olarak): (şekilde sunulmadan için HAML olarak)

    Ruby görünümü:

    = form_for @someObject, html: {:multipart => true, :class => "someformclass"} do |f| 
        = f.error_messages 
        = hidden_field_tag :submitted, true 
        =# some more fields 
        %p.submits 
        = f.submit "Submit", class: "submit" 
    

    Ruby kontrol:

    class OurController < ApplicationController 
        layout false 
        before_filter :authenticate_user! 
    
        # some other actions 
    
        def create 
        # some processing 
    
        someObject.save 
        redirect_to new_feedback_path, :method => :get, :notice => "notice text", status: 303 
        end 
    
        # some other actions 
    end 
    

    JS:

    (Şekilde sunulmadan için HAML içinde)

    Ruby görünüşüdür: değişmeden

    Ruby kontrol:

    (sadece bir gösterimidir yine) aşağıdaki gibi

    Bu

    $(document).on('click', '.someformclass .submit', function() { 
        ... 
        $(this).parents('form').ajaxSubmit({  // uses jquery.form 
        ... 
        beforeSubmit: function(someargs) { 
         ... blah blah 
        }, 
        success: function(responseText) { 
         // ... code to display flash message 
         if (typeof(window.history.pushState) == 'function') { 
         window.history.pushState('html', 'sometext', $.cookie('current_url')); 
         matchFiltersClass(window.location.pathname); 
         } else { 
         window.location.hash = '#!' + $.cookie('current_path'); 
         matchFiltersClass($.cookie('current_path')); 
         } 
         $('#main_content').html(responseText); 
        } 
        }); 
        return false; 
    }); 
    
    tekrar elden edildi
    class OurController < ApplicationController 
        layout false 
        before_filter :authenticate_user! 
    
        # some other actions 
    
        def create 
        # some processing 
    
        someObject.save 
        flash[:notice] = 'notice text' # NEW LINE 
        render text: new_feedback path, status: accepted #CHANGED LINE 
        end 
    
        # some other actions 
    end 
    

    JS: (! Teşekkürler Dan Axtman)

    $(document).on('click', '.someformclass .submit', function() { 
        ... 
        $(this).parents('form').ajaxSubmit({  // uses jquery.form 
        ... 
        beforeSubmit: function(someargs) { 
         ... blah blah 
        }, 
        success: function(responseText) { 
         // ... code to display flash message 
         $.get(responseText, function(data) {  // NEW LINE 
         if (typeof(window.history.pushState) == 'function') { 
          window.history.pushState('html', 'sometext', $.cookie('current_url')); 
          matchFiltersClass(window.location.pathname); 
         } else { 
          window.location.hash = '#!' + $.cookie('current_path'); 
          matchFiltersClass($.cookie('current_path')); 
         } 
         $('#main_content').html(responseText); 
         });  // NEW LINE 
        } 
        }); 
        return false; 
    }); 
    

    Bu çözüm değil Rafa maymun-yamalı günlük zaman adil bir miktar (teşekkürler olmadan yerel geliştirici ile bazı yardımıyla tespit edildi Isaac Betesh!). En azından Rack ile ilgili birşeyler öğrendim ve bu süreçte maymun yaması ...