It seems like Rails' console (script/console or rails console) is like in a controller, but self.class gives Object (Rails 3.0.1 with Ruby 1.9.2), so is it controller or none of M, V, or C?
It's nothing - as it's not part of your production stack, but just a tool that sets up a useful debugging environment for you.
And it's certainly not a part of your application, so it doesn't fit into the whole MVC model.
https://github.com/rails/rails/blob/3-0-1-security/railties/lib/rails/commands/console.rb
You can see it basically just parses command-line options and then starts an IRB session. Helper methods like "reload!" are defined here.
Related
I use the following code in one of my models
def jasper_amount
ActionController::Base.helpers.number_to_currency(amount)
end
I know that it breaks MVC. However, in this case it is the best solution. I have to pass data to Jasper via the Ruby Java Bridge and formatting in Jasper would be much more complicated.
Calling object.jasper_amount from the rails console works fine and prints the expected results. This works fine in development and production.
Now, to pass the data to Jasper I first have to create an xml version of the object's attributes using object.to_xml(methods: [:jasper_amount]).to_s This works in development but not in production. In production the value for jasper_amount that is passed to Jasper is "0.00 €". However, if I remove number_to_currency from def jasper_amount (just returning unformatted amount) it works. What's even more confusing is the fact that calling jasper_amount from the rails console in productions works. I guess the culprit must be to_xml, but I have no idea why it works in development and not in production.
The problem was with Ruby Java Bridge (rjb) and BigDecimal. If you use BigDecimal with rjb, you have to include the "BigDecimal" gem in your Gemfile. Otherwise all your BigDecimals will be 0 (and that all over your app!)
I set a variable inside a Controller and I'm trying to just do something as simple as read that variable in the rails console.
I thought about just doing #test in the console which is the name of the variable. but it shows as >null. When I do puts under where I set the variable it traces out the correct value in my terminal window.
Any ideas what I need to do to get to this variable via the console.
I tried putting the name of the controller first and then .variable but that threw an error
I can see what's inside my models by just using the model name and some attributes like .first and .last
You'd have to instantiate the controller and provide a public accessor to get the value in rails console.
If you're trying to debug something, I recommend you check out Pry. It's a Ruby debugging REPL. Do a require 'pry' in your controller, and put binding.pry somewhere in an action, when you execute that controller method--either interactively in a browser, or via a functional test (I recommend the latter)--it will open the Pry REPL and #test will be in scope there.
Check out this Railscast for some help using it.
Alternately, just rely on good unit or functional testing. Write a test around the method and add an assertion on assigns(:#test) to compare the value to your expectation. Check out the RSpec controller spec documentation.
Resque jobs are just plain old ruby objects. I can use puts calls inside them to produce output into the console, or I can instantiate a standard Ruby Logger class with STDOUT and use that.
But is there a correct approach to logging in Rails, from places that aren't controllers or models? I see Rails.logger returns a BufferedLogger, but when I call info or warn etc on it, nothing happens. If I call flush on it, it just returns an empty array and nothing is output.
What's the convention here?
I'm not really sure that there is a convention. I had a pretty ugly logging system up until just recently. Now I use lumber to integrate log4r with Rails. That really made logging much nicer because I now have named loggers (e.g., logger matches the class name -- great for filtering output) and I can control log levels on a per-logger (i.e., per-class) basis.
There's also a GELF adapter for log4r if you want to use graylog2 to aggregate your logs.
I am experimenting with gem development, right now specifically generators. So far I have successfully created two generators that do their job just perfectly. These two generators are in the same directory.
However, right now I have to call each of them separately.
What I'd like to do is just call one generator and have that generator call all the other ones. Just would type
rails g generator_name
and this would call x other generators.
Does anyone know how would I got about doing this?
Help is much appreciated, thanks!
In your generator, you can just call
generate "some:generator" # can be anything listed by 'rails g'
for example:
module MyGem
class InstallGenerator < Rails::Generators::Base
def run_other_generators
generate "jquery:install" # or whatever you want here
end
end
end
By the way, if you are working on Rails 3 gems, this question can also help out:
Rails 3 generators in gem
Another possibility is to use something like
invoke 'active_record:model', 'foo bar:string baz:float'
which is not as clean as generate, but has one advantage: When your generator gets called via rails destroy, this call -- like may other of Thors actions -- will try to revoke the action of the generator you invoke.
There's a catch however: Probably due to Thors dependency management, this only works once per generator you want to call, meaning that a second invoke of the same generator will do nothing. This can be circumvented by using a statement like
Rails::Generators.invoke 'active_record:model', '...', behavior: behavior
instead. In this case you have to explicitly pass through the behavior of your generator (which is a method returning values like :invoke, :revoke and possibly others, depending on which command -- rails generate, rails destroy, rails update, etc. -- called your generator) to achieve the same result as above. If you don't do this, the generator you call with Rails::Generators.invoke will also be executed when running your generator with rails destroy.
Alternatively you could stick to invoke and try to tamper with Thors invocation system. See also here for example.
Generators are based off of Thor, so you can use the apply method.
This is what the Rails Templater gem does. (Here's a walk through the Rails Templater gem.)
Take a look at the scaffold generator that comes with rails.
/Users/XYZ/sources/rails/railties/lib/rails_generator/generators/components/scaffold/scaffold_generator.rb
def manifest
record do |m|
#....rest of the source is removed for brevity....
m.dependency 'model', [name] + #args, :collision => :skip
end
end
Here the scaffold generator is using the model generator. So take a look at the dependency method. You can find the API docs for it over here.
I've been doing some development with rails 3 and I was wondering why calling the "puts" method doesn't output to standard out.
How do I get this back?
Instead of puts, use logger.info:
logger.info #collection.inspect
You can also use the standard ruby way by calling STDOUT << 'your output'. Method put is not a rails speciality, it comes with ruby. If you use rails, you can also rely on the logger object.