I have setup capistrano for deployment with the exact same config/setup as found in the railscasts Pro episode http://railscasts.com/episodes/335-deploying-to-a-vps?view=asciicast.
All of the deploy:check, status and cold tasks run and complete successfully (after some tinkering). However, the app not running and shows the classic "something went wrong" error page. When I check my unicorn.log it shows the error below:
I have tried requiring the module before including it to address threadsafe issues and also autoloading the absolute path in application.rb. Note this all works in development environment.
How can I amend my code to fix this NameError issue?
unicorn.log
E, [2013-10-16T04:15:00.313177 #12996] ERROR -- : uninitialized constant AnswersController::Teebox (NameError)
/home/andrew/rails/teebox/releases/20131016032538/app/controllers/answers_controller.rb:5:in `<class:AnswersController>'
/home/andrew/rails/teebox/releases/20131016032538/app/controllers/answers_controller.rb:1:in `<top (required)>'
answers_controller.rb
class AnswersController < ApplicationController
before_filter :authenticate_user!, except: [:index, :show]
load_and_authorize_resource
require 'teebox/commentable'
include Teebox::Commentable # Offending line
...
end
lib/teebox/commentable.rb
require 'active_support/concern'
module Teebox::Commentable
extend ActiveSupport::Concern
included do
before_filter :comments
end
def comments
#comment = Comment.new
end
end
application.rb
# Custom directories with classes and modules you want to be autoloadable.
config.autoload_paths += %W(#{config.root}/decorators)
config.autoload_paths += %W(#{config.root}/lib)
config.autoload_paths += %W(#{config.root}/lib/teebox/commentable.rb)
specs:
capistrano 2.15.5
rails 3.2.14
ruby 1.9.3-p488
ubuntu 12.04
If anyone needs more code just shout.
I had an naming convention which wasn't an issue on Mac but was an issue on a case sensitive Linux box.
I had a lib/Teebox/commentable.rb folder structure and was then calling:
include Teebox::Commentable.
So I switched this to lib/teebox/commentable.rb (Lowercase teebox) and this solved the error.
Related
I'm trying to update my app from Rails 5.2 to 6.1, and use Zeitwerk autoload, and I am having some issues for autoloading /lib classes.
I included this in config/application.rb:
config.load_defaults 5.2
config.autoloader = :zeitwerk
config.enable_dependency_loading = true
config.autoload_paths += Dir[Rails.root.join('lib/**/*')]
config.eager_load_paths += Dir[Rails.root.join('lib/**/*')]
And, when I run zeitwerk:check, it alerts me that:
Hold on, I am eager loading the application.
expected file lib/facades/coconut/v2/foo.rb to define constant Foo
It is declared as:
# /lib/facades/coconut/v2/foo.rb
module Coconut
module V2
class Foo
# ...
end
end
end
When I try to debug it (putting a binding.pry in some test file), Zeitwerk says it do not defined, until I call it without modules (namespaces):
[1] pry(#<#filename>)> Coconut::V2::Foo
NameError: uninitialized constant Coconut::V2::Foo
from (pry):1:in `setup`
[2] pry(#<#filename>)> Foo
Zeitwerk::NameError: expected file /my-app/lib/api/coconut/v2/foo.rb to define constant Foo, but didn't
from /usr/local/bundle/gems/zeitwerk-2.5.4/lib/zeitwerk/loader/callbacks.rb:25:in `on_file_autoloaded'
[3] pry(#<#filename>)> Coconut::V2::Foo
=> Coconut::V2::Foo
It sounds really strange, because there are another classes in /lib that follows the same structure, but it works well, example
# /lib/api/services/youtube/client.rb
module Services
module Youtube
class Client
# ...
end
end
end
Inspecting it with binding.pry in some test:
pry(#<#filename>)> Services::Youtube::Client
=> Services::Youtube::Client
Has anyone had this problem or know what could be happening?
System:
ruby 2.7.6p219
Rails 6.1.6
Zeitwerk (2.5.4)
An autoload path is a root directory, not its contents.
You need to remove the wildcards as documented here.
For a Rails project I'm working on, I'm having an issue with loading Sidekiq and having nested modules in the lib directory.
my lib/scraper/v2.rb looks like this:
require 'scraper/v2/client'
module Scraper
module V2
end
end
my lib/scraper/v2/client.rb looks like this:
module Scraper
module V2
class Client
def initialize
...
end
end
end
end
I then have a Sidekiq job in the jobs directory that looks like this:
class RefreshTokenJob < ApplicationJob
queue_as :default
def perform
client = Scraper::V2::Client.new
...
end
end
If I run bundle exec sidekiq with this configuration, Sidekiq starts, but running Scraper::V2::Client.new form the Rails console returns:
NameError: uninitialized constant Scraper::V2
If I add config.autoload_paths += %W(#{config.root}/lib) to my application.rb file, I can run Scraper::V2::Client.new, but starting Sidekiq gives me and uninitialized constant error from a completely different file (within app/jobs/concerns/).
Any help with this would be much appreciated!
You must follow Rails' conventions for naming files if you want Rails autoloading to work correctly.
For a module named Scraper::V2, it should be in a file named scraper/v2.rb, not scraper_v2.rb.
I have created a simple module and placed it in the lib directory and have included in the controller file.
below is the controller code.
class UserController < ApplicationController
include Departments
def create
user_data = Hash.new
user_data["data"] = "hello world!"
user_data["price"] = 12
render :json => user_data
end
end
when i try to execute it i see the below error
ActionController::RoutingError (uninitialized constant UserController:: Departments):
I have searched forums and see that adding
config.autoload_paths += %W(#{config.root}/lib)
solves the issue, but it did not in my case. I am using Rails 4.2.7.1 and ruby ruby 1.9.3p547.
Can anyone point out what could be the issue, Thanks.
I had the naming convestion wrong, i created a sub directory under the lib folder by the name of my module and then created the file with the class name.rb and it worked.
Reference: "Uninitialized constant" error when including a module
I am trying to learn Middlewares and been practising how to mount it in the Rails application. I have followed the railscast
So far I have implemented these steps:
1) Created a new Rails 4.2 application called: Blog
2) Added a file in the lib folder named as response_timer.rb.
class ResponseTimer
def initialize(app)
#app = app
end
def call(env)
[200, {"Content-Type" => "text/html"}, "Hello World"]
end
end
3) Added config.middleware.use "ResponseTimer" in application.rb.
config.middleware.use "ResponseTimer"
But as i'm hitting the command rake middleware in the terminal, it is reporting this error:
rake aborted!
NameError: uninitialized constant ResponseTimer
I tried also to add the config.middleware.use "ResponseTimer" in the development.rb but again facing the same error.
What am i missing here?
Please help.
Referenced article: http://guides.rubyonrails.org/rails_on_rack.html
Middleware has to have an accompanying module / class, and needs to be loaded in the app before it can be referenced. The way to do this in Rails is with autoloading (lib files aren't autoloaded by default):
#config/application.rb
config.autoload_paths += Dir["#{config.root}/lib/**/"]
config.middleware.use "ResponseTimer"
The above should work for you.
I followed this answer: https://stackoverflow.com/a/24122424
I tried it before but maybe missed something before.
In appliation.rb
require 'rails/all'
require_relative '../lib/response_timer'
module Blog
class Application < Rails::Application
...
config.middleware.use ResponseTimer
end
end
I've placed the file rack_app.rb with simple Rack application in the lib directory:
class RackApp
def call env
[200, {}, 'Hello']
end
end
Then I've added this route:
match 'rack' => RackApp
And when I try to launch the rails server I get the following error:
config/routes.rb:65: uninitialized constant RackApp (NameError)
Rails 3 has no more autoloading by default. So you need require your file
require 'lib/rack_app.rb'
Or come back the autoloading in application.rb
config.autoload_paths += %W( #{config.root}/lib )
Include require 'email_format_validator' in the model.