我有一个有工作的Rails应用程序(使用Active Job
)。我使用resque
和resque-scheduler
宝石对后端进行排队。
我想通过Heroku上的Resque将Rails应用程序连接到Redis-to-go服务器,但在日志中会收到很多错误消息,如下所示:
2019-12-01T12:04:00.942767+00:00 app[worker.1]: resque-scheduler: [INFO] 2019-12-01T12:04:00+00:00: Error connecting to Redis on localhost:6379 (Errno::ECONNREFUSED)
2019-12-01T12:04:01.945657+00:00 app[worker.1]: resque-scheduler: [INFO] 2019-12-01T12:04:01+00:00: Error connecting to Redis on localhost:6379 (Errno::ECONNREFUSED)
2019-12-01T12:04:02.990485+00:00 app[worker.1]: resque-scheduler: [INFO] 2019-12-01T12:04:02+00:00: Error connecting to Redis on localhost:6379 (Errno::ECONNREFUSED)
2019-12-01T12:04:04.004590+00:00 app[worker.1]: resque-scheduler: [INFO] 2019-12-01T12:04:04+00:00: Error connecting to Redis on localhost:6379 (Errno::ECONNREFUSED)
2019-12-01T12:04:05.012344+00:00 app[worker.1]: resque-scheduler: [INFO] 2019-12-01T12:04:05+00:00: Error connecting to Redis on localhost:6379 (Errno::ECONNREFUSED)
一切都适用于开发和生产环境,但不适用于Heroku。我发现了很多问题,但有类似的问题,但是他们的解决方案对我没有帮助。
我在Error connecting to Redis on localhost:6379 (Errno::ECONNREFUSED)
方法中从redis
gem收到一条错误消息establish_connection
。但是,当我从Rails控制台中找出必要的值时,我知道可以。
$ heroku run rails console
Loading production environment (Rails 5.2.3)
irb(main):001:0> Resque.redis
=> #<Resque::DataStore:0x00005643758bd968 @redis=<Redis::Namespace v1.6.0 with client v4.1.2 for redis://spinyfin.redistogo.com:11302/0/resque>, @queue_access=#<Resque::DataStore::QueueAccess:0x00005643758bd8f0 @redis=<Redis::Namespace v1.6.0 with client v4.1.2 for redis://spinyfin.redistogo.com:11302/0/resque>>, @failed_queue_access=#<Resque::DataStore::FailedQueueAccess:0x00005643758bd8c8 @redis=<Redis::Namespace v1.6.0 with client v4.1.2 for redis://spinyfin.redistogo.com:11302/0/resque>>, @workers=#<Resque::DataStore::Workers:0x00005643758bd8a0 @redis=<Redis::Namespace v1.6.0 with client v4.1.2 for redis://spinyfin.redistogo.com:11302/0/resque>>, @stats_access=#<Resque::DataStore::StatsAccess:0x00005643758bd878 @redis=<Redis::Namespace v1.6.0 with client v4.1.2 for redis://spinyfin.redistogo.com:11302/0/resque>>>
irb(main):002:0> REDIS._client
=> #<Redis::Client:0x00005643758be9f8 @options={:url=>"redis://redistogo:[email protected]:11302/", :scheme=>"redis", :host=>"spinyfin.redistogo.com", :port=>11302, :path=>nil, :timeout=>5.0, :password=>"4822b22abf6b11bd0830af5f5797c0fb", :db=>0, :driver=>Redis::Connection::Ruby, :id=>nil, :tcp_keepalive=>0, :reconnect_attempts=>1, :reconnect_delay=>0.0, :reconnect_delay_max=>0.5, :inherit_socket=>false, :role=>:master, :connect_timeout=>5.0, :read_timeout=>5.0, :write_timeout=>5.0, :_parsed=>true}, @reconnect=true, @logger=nil, @connection=nil, @command_map={}, @pending_reads=0, @connector=#<Redis::Client::Connector:0x00005643758bdc60 @options={:url=>"redis://redistogo:[email protected]:11302/", :scheme=>"redis", :host=>"spinyfin.redistogo.com", :port=>11302, :path=>nil, :timeout=>5.0, :password=>"4822b22abf6b11bd0830af5f5797c0fb", :db=>0, :driver=>Redis::Connection::Ruby, :id=>nil, :tcp_keepalive=>0, :reconnect_attempts=>1, :reconnect_delay=>0.0, :reconnect_delay_max=>0.5, :inherit_socket=>false, :role=>:master, :connect_timeout=>5.0, :read_timeout=>5.0, :write_timeout=>5.0, :_parsed=>true}>>
此外,我了解resque
和resque-scheduler
宝石的设置在Heroku上重新启动我的应用程序后可以正常工作,但是由于某些原因,Resque连接到localhost:6379
而不是Redis-to-go服务器。您有什么想法,为什么会这样?以及如何解决这个问题?
我在下面提供了有关设置,使用宝石等的必要信息。
================================================ =========================>
heroku restart
之后的控制台日志
[https://pastebin.com/E9YkxeEP(正文限制为30000个字符,对不起)]
Gemfile
source 'https://rubygems.org' git_source(:github) { |repo| "https://github.com/#{repo}.git" } gem 'bootsnap', '>= 1.1.0', require: false gem 'bootstrap', '~> 4.3.1' gem 'faker' gem 'foreman' gem 'jquery-rails' gem 'local_time' gem 'pg', '>= 0.18', '< 2.0' gem 'puma', '~> 3.11' gem 'rails', '~> 5.2.3' gem 'redis' gem 'resque' gem 'resque-scheduler' gem 'resque-scheduler-web' gem 'resque-web', require: 'resque_web' gem 'sass-rails', '~> 5.0' gem 'turbolinks', '~> 5' gem 'uglifier', '>= 1.3.0' group :development, :test do gem 'action-cable-testing' gem 'byebug', platforms: %i[mri mingw x64_mingw] gem 'factory_bot_rails' gem 'pry-rails' gem 'rails-controller-testing' gem 'rspec-rails', '~> 3.8' gem 'rubocop' gem 'timecop' end group :development do gem 'listen', '>= 3.0.5', '< 3.2' gem 'spring' gem 'spring-watcher-listen', '~> 2.0.0' gem 'web-console', '>= 3.3.0' end gem 'tzinfo-data', platforms: %i[mingw mswin x64_mingw jruby]
Gemfile.lock
GEM remote: https://rubygems.org/ specs: action-cable-testing (0.6.0) actioncable (>= 5.0) actioncable (5.2.3) actionpack (= 5.2.3) nio4r (~> 2.0) websocket-driver (>= 0.6.1) actionmailer (5.2.3) actionpack (= 5.2.3) actionview (= 5.2.3) activejob (= 5.2.3) mail (~> 2.5, >= 2.5.4) rails-dom-testing (~> 2.0) actionpack (5.2.3) actionview (= 5.2.3) activesupport (= 5.2.3) rack (~> 2.0) rack-test (>= 0.6.3) rails-dom-testing (~> 2.0) rails-html-sanitizer (~> 1.0, >= 1.0.2) actionview (5.2.3) activesupport (= 5.2.3) builder (~> 3.1) erubi (~> 1.4) rails-dom-testing (~> 2.0) rails-html-sanitizer (~> 1.0, >= 1.0.3) activejob (5.2.3) activesupport (= 5.2.3) globalid (>= 0.3.6) activemodel (5.2.3) activesupport (= 5.2.3) activerecord (5.2.3) activemodel (= 5.2.3) activesupport (= 5.2.3) arel (>= 9.0) activestorage (5.2.3) actionpack (= 5.2.3) activerecord (= 5.2.3) marcel (~> 0.3.1) activesupport (5.2.3) concurrent-ruby (~> 1.0, >= 1.0.2) i18n (>= 0.7, < 2) minitest (~> 5.1) tzinfo (~> 1.1) arel (9.0.0) ast (2.4.0) autoprefixer-rails (9.6.1.1) execjs bindex (0.8.1) bootsnap (1.4.5) msgpack (~> 1.0) bootstrap (4.3.1) autoprefixer-rails (>= 9.1.0) popper_js (>= 1.14.3, < 2) sassc-rails (>= 2.0.0) builder (3.2.3) byebug (11.0.1) coderay (1.1.2) coffee-rails (5.0.0) coffee-script (>= 2.2.0) railties (>= 5.2.0) coffee-script (2.4.1) coffee-script-source execjs coffee-script-source (1.12.2) commonjs (0.2.7) concurrent-ruby (1.1.5) crass (1.0.4) diff-lcs (1.3) erubi (1.8.0) et-orbi (1.2.2) tzinfo execjs (2.7.0) factory_bot (5.1.0) activesupport (>= 4.2.0) factory_bot_rails (5.1.0) factory_bot (~> 5.1.0) railties (>= 4.2.0) faker (1.9.3) i18n (>= 0.7) ffi (1.11.1) font-awesome-sass (5.11.2) sassc (>= 1.11) foreman (0.86.0) fugit (1.3.3) et-orbi (~> 1.1, >= 1.1.8) raabro (~> 1.1) globalid (0.4.2) activesupport (>= 4.2.0) i18n (1.6.0) concurrent-ruby (~> 1.0) jaro_winkler (1.5.3) jquery-rails (4.3.5) rails-dom-testing (>= 1, < 3) railties (>= 4.2.0) thor (>= 0.14, < 2.0) less (2.6.0) commonjs (~> 0.2.7) less-rails (2.8.0) actionpack (>= 4.0) less (~> 2.6.0) sprockets (> 2, < 4) tilt listen (3.1.5) rb-fsevent (~> 0.9, >= 0.9.4) rb-inotify (~> 0.9, >= 0.9.7) ruby_dep (~> 1.2) local_time (2.1.0) loofah (2.2.3) crass (~> 1.0.2) nokogiri (>= 1.5.9) mail (2.7.1) mini_mime (>= 0.1.1) marcel (0.3.3) mimemagic (~> 0.3.2) method_source (0.9.2) mimemagic (0.3.3) mini_mime (1.0.2) mini_portile2 (2.4.0) minitest (5.11.3) mono_logger (1.1.0) msgpack (1.3.1) multi_json (1.14.1) mustermann (1.0.3) nio4r (2.5.1) nokogiri (1.10.4) mini_portile2 (~> 2.4.0) parallel (1.17.0) parser (2.6.3.0) ast (~> 2.4.0) pg (1.1.4) popper_js (1.14.5) pry (0.12.2) coderay (~> 1.1.0) method_source (~> 0.9.0) pry-rails (0.3.9) pry (>= 0.10.4) puma (3.12.1) raabro (1.1.6) rack (2.0.7) rack-protection (2.0.7) rack rack-test (1.1.0) rack (>= 1.0, < 3) rails (5.2.3) actioncable (= 5.2.3) actionmailer (= 5.2.3) actionpack (= 5.2.3) actionview (= 5.2.3) activejob (= 5.2.3) activemodel (= 5.2.3) activerecord (= 5.2.3) activestorage (= 5.2.3) activesupport (= 5.2.3) bundler (>= 1.3.0) railties (= 5.2.3) sprockets-rails (>= 2.0.0) rails-controller-testing (1.0.4) actionpack (>= 5.0.1.x) actionview (>= 5.0.1.x) activesupport (>= 5.0.1.x) rails-dom-testing (2.0.3) activesupport (>= 4.2.0) nokogiri (>= 1.6) rails-html-sanitizer (1.2.0) loofah (~> 2.2, >= 2.2.2) railties (5.2.3) actionpack (= 5.2.3) activesupport (= 5.2.3) method_source rake (>= 0.8.7) thor (>= 0.19.0, < 2.0) rainbow (3.0.0) rake (12.3.3) rb-fsevent (0.10.3) rb-inotify (0.10.0) ffi (~> 1.0) redis (4.1.2) redis-namespace (1.6.0) redis (>= 3.0.4) resque (2.0.0) mono_logger (~> 1.0) multi_json (~> 1.0) redis-namespace (~> 1.6) sinatra (>= 0.9.2) vegas (~> 0.1.2) resque-scheduler (4.4.0) mono_logger (~> 1.0) redis (>= 3.3) resque (>= 1.26) rufus-scheduler (~> 3.2) resque-scheduler-web (1.1.0) resque-scheduler (~> 4.0) resque-web (~> 0.0.8) resque-web (0.0.12) coffee-rails font-awesome-sass jquery-rails resque sass-rails twitter-bootstrap-rails rspec-core (3.8.2) rspec-support (~> 3.8.0) rspec-expectations (3.8.4) diff-lcs (>= 1.2.0, < 2.0) rspec-support (~> 3.8.0) rspec-mocks (3.8.1) diff-lcs (>= 1.2.0, < 2.0) rspec-support (~> 3.8.0) rspec-rails (3.8.2) actionpack (>= 3.0) activesupport (>= 3.0) railties (>= 3.0) rspec-core (~> 3.8.0) rspec-expectations (~> 3.8.0) rspec-mocks (~> 3.8.0) rspec-support (~> 3.8.0) rspec-support (3.8.2) rubocop (0.72.0) jaro_winkler (~> 1.5.1) parallel (~> 1.10) parser (>= 2.6) rainbow (>= 2.2.2, < 4.0) ruby-progressbar (~> 1.7) unicode-display_width (>= 1.4.0, < 1.7) ruby-progressbar (1.10.1) ruby_dep (1.5.0) rufus-scheduler (3.6.0) fugit (~> 1.1, >= 1.1.6) sass (3.7.4) sass-listen (~> 4.0.0) sass-listen (4.0.0) rb-fsevent (~> 0.9, >= 0.9.4) rb-inotify (~> 0.9, >= 0.9.7) sass-rails (5.1.0) railties (>= 5.2.0) sass (~> 3.1) sprockets (>= 2.8, < 4.0) sprockets-rails (>= 2.0, < 4.0) tilt (>= 1.1, < 3) sassc (2.2.0) ffi (~> 1.9) sassc-rails (2.1.2) railties (>= 4.0.0) sassc (>= 2.0) sprockets (> 3.0) sprockets-rails tilt sinatra (2.0.7) mustermann (~> 1.0) rack (~> 2.0) rack-protection (= 2.0.7) tilt (~> 2.0) spring (2.1.0) spring-watcher-listen (2.0.1) listen (>= 2.7, < 4.0) spring (>= 1.2, < 3.0) sprockets (3.7.2) concurrent-ruby (~> 1.0) rack (> 1, < 3) sprockets-rails (3.2.1) actionpack (>= 4.0) activesupport (>= 4.0) sprockets (>= 3.0.0) thor (0.20.3) thread_safe (0.3.6) tilt (2.0.9) timecop (0.9.1) turbolinks (5.2.1) turbolinks-source (~> 5.2) turbolinks-source (5.2.0) twitter-bootstrap-rails (4.0.0) actionpack (~> 5.0, >= 5.0.1) execjs (~> 2.7) less-rails (~> 2.8, >= 2.8.0) railties (~> 5.0, >= 5.0.1) tzinfo (1.2.5) thread_safe (~> 0.1) uglifier (4.1.20) execjs (>= 0.3.0, < 3) unicode-display_width (1.6.0) vegas (0.1.11) rack (>= 1.0.0) web-console (3.7.0) actionview (>= 5.0) activemodel (>= 5.0) bindex (>= 0.4.0) railties (>= 5.0) websocket-driver (0.7.1) websocket-extensions (>= 0.1.0) websocket-extensions (0.1.4) PLATFORMS ruby DEPENDENCIES action-cable-testing bootsnap (>= 1.1.0) bootstrap (~> 4.3.1) byebug factory_bot_rails faker foreman jquery-rails listen (>= 3.0.5, < 3.2) local_time pg (>= 0.18, < 2.0) pry-rails puma (~> 3.11) rails (~> 5.2.3) rails-controller-testing redis resque resque-scheduler resque-scheduler-web resque-web rspec-rails (~> 3.8) rubocop sass-rails (~> 5.0) spring spring-watcher-listen (~> 2.0.0) timecop turbolinks (~> 5) tzinfo-data uglifier (>= 1.3.0) web-console (>= 3.3.0) BUNDLED WITH 1.17.2
Procfile
worker: RESQUE_SCHEDULER_INTERVAL=1 INTERVAL=1 QUEUE=leramiz* COUNT=1 TERM_CHILD=1 RESQUE_TERM_TIMEOUT=10 bundle exec rake resque:schedule_and_work
lib / tasks / resque.rake
require 'resque/tasks' require 'resque/scheduler/tasks' task 'resque:preload' => :environment namespace :resque do # https://stackoverflow.com/questions/51757169/how-do-you-schedule-resque-jobs-on-heroku # https://grosser.it/2012/04/14/resque-scheduler-on-heroku-without-extra-workers/ desc 'schedule and work, so we only need 1 dyno' task :schedule_and_work do if Process.respond_to?(:fork) if Process.fork sh('rake environment resque:work') else sh('rake resque:scheduler') Process.wait end else # windows pid = Process.spawn 'rake environment resque:work' Rake::Task['resque:scheduler'].invoke Process.wait(pid) end end task :setup do require 'resque' end task setup_schedule: :setup do require 'resque-scheduler' end task scheduler: :setup_schedule end
config / initializers / resque.rb
require 'resque/server' if Rails.env.development? Resque.redis = Redis.new(host: 'localhost', port: '6379') else REDIS = Redis.new(url: ENV['REDISTOGO_URL']) Resque.redis = REDIS end Resque.logger = Logger.new(Rails.root.join('log', "#{Rails.env}_resque.log")) Resque.logger.level = Logger::DEBUG
config / environments / production.rb
Rails.application.configure do # Settings specified here will take precedence over those in config/application.rb. # Code is not reloaded between requests. config.cache_classes = true # Eager load code on boot. This eager loads most of Rails and # your application in memory, allowing both threaded web servers # and those relying on copy on write to perform better. # Rake tasks automatically ignore this option for performance. config.eager_load = true # Full error reports are disabled and caching is turned on. config.consider_all_requests_local = false config.action_controller.perform_caching = true # Ensures that a master key has been made available in either ENV["RAILS_MASTER_KEY"] # or in config/master.key. This key is used to decrypt credentials (and other encrypted files). # config.require_master_key = true # Disable serving static files from the `/public` folder by default since # Apache or NGINX already handles this. config.public_file_server.enabled = ENV['RAILS_SERVE_STATIC_FILES'].present? # Compress JavaScripts and CSS. config.assets.js_compressor = config.assets.js_compressor = Uglifier.new(harmony: true) # config.assets.css_compressor = :sass # Do not fallback to assets pipeline if a precompiled asset is missed. config.assets.compile = false # `config.assets.precompile` and `config.assets.version` have moved to config/initializers/assets.rb # Enable serving of images, stylesheets, and JavaScripts from an asset server. # config.action_controller.asset_host = 'http://assets.example.com' # Specifies the header that your server uses for sending files. # config.action_dispatch.x_sendfile_header = 'X-Sendfile' # for Apache # config.action_dispatch.x_sendfile_header = 'X-Accel-Redirect' # for NGINX # Mount Action Cable outside main process or domain # config.action_cable.mount_path = nil config.action_cable.url = 'wss://cuurjol-leramiz.herokuapp.com/cable' config.action_cable.allowed_request_origins = %w[http://cuurjol-leramiz.herokuapp.com/cable https://cuurjol-leramiz.herokuapp.com/cable] # Force all access to the app over SSL, use Strict-Transport-Security, and use secure cookies. # config.force_ssl = true # Use the lowest log level to ensure availability of diagnostic information # when problems arise. config.log_level = :debug # Prepend all log lines with the following tags. config.log_tags = [:request_id] # Use a different cache store in production. config.cache_store = :redis_cache_store, { url: ENV['REDISTOGO_URL'] } # Use a real queuing backend for Active Job (and separate queues per environment) config.active_job.queue_adapter = :resque config.active_job.queue_name_prefix = "leramiz_#{Rails.env}" # Enable locale fallbacks for I18n (makes lookups for any locale fall back to # the I18n.default_locale when a translation cannot be found). config.i18n.fallbacks = true # Send deprecation notices to registered listeners. config.active_support.deprecation = :notify # Use default logging formatter so that PID and timestamp are not suppressed. config.log_formatter = ::Logger::Formatter.new # Use a different logger for distributed setups. # require 'syslog/logger' # config.logger = ActiveSupport::TaggedLogging.new(Syslog::Logger.new 'app-name') if ENV['RAILS_LOG_TO_STDOUT'].present? logger = ActiveSupport::Logger.new(STDOUT) logger.formatter = config.log_formatter config.logger = ActiveSupport::TaggedLogging.new(logger) end # Do not dump schema after migrations. config.active_record.dump_schema_after_migration = false end
app / jobs / destroy_private_job.rb
class DestroyPrivateRoomJob < ApplicationJob
queue_as :default
def perform(room)
users = room.users.to_a
room.destroy
ActionCable.server.broadcast('room_management_channel', room: room.as_json(only: %i[id is_private token]),
status: 'destroyed')
room_users_list = { room_id: room.id, users: room.users.uniq.as_json(only: :nickname) }
ActionCable.server.broadcast('room_users_list_channel', room_users_list: room_users_list)
users.each do |user|
Rails.cache.write("message_for_user:#{user.id}", "Expiration time for Room ##{room.id} is over")
end
end
end
我有一个有工作的Rails应用程序(使用活动作业)。我使用resque和resque-scheduler gem来对后端进行排队。我想使用Resque将Rails应用程序连接到Redis-to-go服务器...
他们的文档使您看起来只需要设置redis的URL,而不是redis的实例https://github.com/resque/resque/blob/master/README.markdown#configuration