I was testing some DB entries in our production server in Rails Console where almost all the commands were producing a huge number of lines of output and causing the ssh channel to hang.
Is there a way to suppress the console/irb screenfuls?
You can append ; nil to your statements.
Example:
users = User.all; nil
irb prints the return value of the last executed statement; thus in this case it'll print only nil since nil is the last executed valid statement.
In search of a solution how to silence the irb/console output, I also found an answer at austinruby.com:
silence irb:
conf.return_format = ""
default output:
conf.return_format = "=> %s\n"
limit to eg 512 chars:
conf.return_format = "=> limited output\n %.512s\n"
running the following within irb works for me:
irb_context.echo = false
irb --simple-prompt --noecho
--simple-prompt - Uses a simple prompt - just >>
--noecho - Suppresses the result of operations
Here, add this to your ~/.irbrc:
require 'ctx'
require 'awesome_print'
module IRB
class Irb
ctx :ap do
def output_value()
ap(#context.last_value)
end
end
ctx :puts do
def output_value()
puts(#context.last_value)
end
end
ctx :p do
def output_value()
p(#context.last_value)
end
end
ctx :quiet do
def output_value()
end
end
end
end
def irb_mode(mode)
ctx(mode) { irb }
end
(Note: You must install the ctx gem first, though awesome_print is optional, of course.)
Now when you are on any console that uses irb, you can do the following:
Normal mode:
irb(main):001:0> { this:'is a complex object', that:[ { will:'probably'}, { be:'good to read' } ], in:{ some:{ formatted:'way'} } }
=> {:this=>"is a complex object", :that=>[{:will=>"probably"}, {:be=>"good to read"}], :in=>{:some=>{:formatted=>"way"}}}
...yep, just what you expect.
awesome_print mode:
irb(main):002:0> irb_mode(:ap)
irb#1(main):001:0> { this:'is a complex object', that:[ { will:'probably'}, { be:'good to read' } ], in:{ some:{ formatted:'way'} } }
=> {
:this => "is a complex object",
:that => [
[0] {
:will => "probably"
},
[1] {
:be => "good to read"
}
],
:in => {
:some => {
:formatted => "way"
}
}
}
...wow, now everything is printing out awesomely! :)
Quiet mode:
irb#1(main):002:0> irb_mode(:quiet)
irb#1(main):001:0> { this:'is a complex object', that:[ { will:'probably'}, { be:'good to read' } ], in:{ some:{ formatted:'way'} } }
irb#1(main):002:0>
... whoah, no output at all? Nice.
Anyways, you can add whatever mode you like, and when you're finished with that mode, just exit out or it, and you'll be back in the previous mode.
Hope that was helpful! :)
Supress Output, In General
Also, depending on your needs, have a look at using quietly or silence_stream for suppressing output in general, not just in the irb/console:
silence_stream(STDOUT) do
users = User.all
end
NOTE: silence_stream removed in Rails 5+.
NOTE: quietly will be deprecated in Ruby 2.2.0 and will eventually be removed. (Thanks BenMorganIO!)
More information can be found here.
Work Around for Rails 5+.
As mentioned above, silence_stream is no longer available because it is not thread safe. There is no thread safe alternative. But if you still want to use silence_stream and are aware that it is not thread safe and are not using it in a multithreaded manner, you can manually add it back as an initializer.
config/initializer/silence_stream.rb
# Re-implementation of `silence_stream` that was removed in Rails 5 due to it not being threadsafe.
# This is not threadsafe either so only use it in single threaded operations.
# See https://api.rubyonrails.org/v4.2.5/classes/Kernel.html#method-i-silence_stream.
#
def silence_stream( stream )
old_stream = stream.dup
stream.reopen( File::NULL )
stream.sync = true
yield
ensure
stream.reopen( old_stream )
old_stream.close
end
Adding nil as a fake return value to silence output works fine, but I prefer to have some indication of what happened. A simple count is often enough. A lot of times, that's easily done by tacking on a count function. So when I'm doing something to a bunch of Discourse topics, I don't want a printout of each of the topic objects. So I add .count at the end of the loop:
Topic.where(...).each do |topic|
...
end.count
Same thing if I'm just assigning something:
(users = User.all).count
Silencing output altogether (or making it something static like nil) deprives me of useful feedback.
Related
I was trying to DRY up a Rails controller by extracting a method that includes a guard clause to return prematurely from the controller method in the event of an error. I thought this may be possible using a to_proc, like this pure Ruby snippet:
def foo(string)
processed = method(:breaker).to_proc.call(string)
puts "This step should not be executed in the event of an error"
processed
end
def breaker(string)
begin
string.upcase!
rescue
puts "Well you messed that up, didn't you?"
return
end
string
end
My thinking was that having called to_proc on the breaker method, calling the early return statement in the rescue clause should escape the execution of foo. However, it didn't work:
2.4.0 :033 > foo('bar')
This step should not be executed in the event of an error
=> "BAR"
2.4.0 :034 > foo(2)
Well you messed that up, didn't you?
This step should not be executed in the event of an error
=> nil
Can anyone please
Explain why this doesn't work
Suggest a way of achieving this effect?
Thanks in advance.
EDIT: as people are wondering why the hell I would want to do this, the context is that I'm trying to DRY up the create and update methods in a Rails controller. (I'm trying to be agressive about it as both methods are about 60 LoC. Yuck.) Both methods feature a block like this:
some_var = nil
if (some complicated condition)
# do some stuff
some_var = computed_value
elsif (some marginally less complicated condition)
#error_msg = 'This message is the same in both actions.'
render partial: "show_user_the_error" and return
# rest of controller actions ...
Hence, I wanted to extract this as a block, including the premature return from the controller action. I thought this might be achievable using a Proc, and when that didn't work I wanted to understand why (which I now do thanks to Marek Lipa).
What about
def foo(string)
processed = breaker(string)
puts "This step should not be executed in the event of an error"
processed
rescue ArgumentError
end
def breaker(string)
begin
string.upcase!
rescue
puts "Well you messed that up, didn't you?"
raise ArgumentError.new("could not call upcase! on #{string.inspect}")
end
string
end
After all this is arguably a pretty good use case for an exception.
It seems part of the confusion is that a Proc or lambda for that matter are distinctly different than a closure (block).
Even if you could convert Method#to_proc to a standard Proc e.g. Proc.new this would simply result in a LocalJumpError because the return would be invalid in this context.
You can use next to break out of a standard Proc but the result would be identical to the lambda that you have now.
The reason Method#to_proc returns a lambda is because a lambda is far more representative of a method call than a standard Proc
For Example:
def foo(string)
string
end
bar = ->(string) { string } #lambda
baz = Proc.new {|string| string }
foo
#=> ArgumentError: wrong number of arguments (given 0, expected 1)
bar.()
#=> ArgumentError: wrong number of arguments (given 0, expected 1)
baz.()
#=> nil
Since you are converting a method to a proc object I am not sure why you would also want the behavior to change as this could cause ambiguity and confusion. Please note that for this reason you can not go in the other direction either e.g. lambda(&baz) does not result in a lambda either as metioned Here.
Now that we have explained all of this and why it shouldn't really be done, it is time to remember that nothing is impossible in ruby so this would technically work:
def foo(string)
# place assignment in the guard clause
# because the empty return will result in `nil` a falsey value
return unless processed = method(:breaker).to_proc.call(string)
puts "This step should not be executed in the event of an error"
processed
end
def breaker(string)
begin
string.upcase!
rescue
puts "Well you messed that up, didn't you?"
return
end
string
end
Example
With Ruby on Rails, I am running a Selenium service. I am running through a web page many times.
Having a bit of trouble as I need it to sometimes wait for the the 'button' to be active (in a not disabled state).
# wait for a specific element to show up
wait = Selenium::WebDriver::Wait.new(:timeout => 10) # seconds
wait.until { driver.find_element(:id => "foo") }
So I am trying to use
the wait.until method below but can't get the syntax. I tried this.
```
def css_removed_timeout(css)
wait = Selenium::WebDriver::Wait.new(timeout: 10)
wait.until { !find_css(css).displayed? }
end```
Is there anyway to detect 'not displayed'? ( is there an 'is_empty' equivalent in Ruby)?
There's an .empty? method on Arrays.
If you include ActiveSupport, there's a .blank? method which works on arrays, strings, and hashes.
More simply you could check if array.length == 0
My goal is to replace methods in the String class with other methods that do additional work (this is for a research project). This works for many methods by writing code in the String class similar to
alias_method :center_OLD, :center
def center(args*)
r = self.send(*([:center_OLD] + args))
#do some work here
#return something
end
For some methods, I need to handle a Proc as well, which is no problem. However, for the scan method, invoking it has the side effect of setting special global variables from the regular expression match. As documented, these variables are local to the thread and the method.
Unfortunately, some Rails code makes calls to scan which makes use of the $& variable. That variable gets set inside my version of the scan method, but because it's local, it doesn't make it back to the original caller which uses the variable.
Does anyone know a way to work around this? Please let me know if the problem needs clarification.
If it helps at all, all the uses I've seen so far of the $& variable are inside a Proc passed to the scan function, so I can get the binding for that Proc. However, the user doesn't seem to be able to change $& at all, so I don't know how that will help much.
Current Code
class String
alias_method :scan_OLD, :scan
def scan(*args, &b)
begin
sargs = [:scan_OLD] + args
if b.class == Proc
r = self.send(*sargs, &b)
else
r = self.send(*sargs)
end
r
rescue => error
puts error.backtrace.join("\n")
end
end
end
Of course I'll do more things before returning r, but this even is problematic -- so for simplicity we'll stick with this. As a test case, consider:
"hello world".scan(/l./) { |x| puts x }
This works fine both with and without my version of scan. With the "vanilla" String class this produces the same thing as
"hello world".scan(/l./) { puts $&; }
Namely, it prints "ll" and "ld" and returns "hello world". With the modified string class it prints two blank lines (since $& was nil) and then returns "hello world". I'll be happy if we can get that working!
You cannot set $&, because it is derived from $~, the last MatchData.
However, $~ can be set and that actually does what you want.
The trick is to set it in the block binding.
The code is inspired by the old Ruby implementation of Pathname.
(The new code is in C and does not need to care about Ruby frame-local variables)
class String
alias_method :scan_OLD, :scan
def scan(*args, &block)
sargs = [:scan_OLD] + args
if block
self.send(*sargs) do |*bargs|
Thread.current[:string_scan_matchdata] = $~
eval("$~ = Thread.current[:string_scan_matchdata]", block.binding)
yield(*bargs)
end
else
self.send(*sargs)
end
end
end
The saving of the thread-local (well, actually fiber-local) variable seems unnecessary since it is only used to pass the value and the thread never reads any other value than the last one set. It probably is there to restore the original value (most likely nil, because the variable did not exist).
One way to avoid thread-locals at all is to create a setter of $~ as a lambda (but it does create a lambda for each call):
self.send(*sargs) do |*bargs|
eval("lambda { |m| $~ = m }", block.binding).call($~)
yield(*bargs)
end
With any of these, your example works!
I wrote simple code simulating the problem:
"hello world".scan(/l./) { |x| puts x }
"hello world".scan(/l./) { puts $&; }
class String
alias_method :origin_scan, :scan
def scan *args, &b
args.unshift :origin_scan
#mutex ||= Mutex.new
begin
self.send *args do |a|
break if !block_given?
#mutex.synchronize do
p $&
case b.arity
when 0
b.call
when 1
b.call a
end
end
end
rescue => error
p error, error.backtrace.join("\n")
end
end
end
"hello world".scan(/l./) { |x| puts x }
"hello world".scan(/l./) { puts $& }
And found the following. The change of containment of the variable $& became inside a :call function, i.e. on 3-rd step before :call $& contains a valid value, but inside the block it becomes the invalid. I guess this become due to the singularity stack and variable restoration during the change process/thread context, because, probably, :call function can't access the :scan local state.
I see two variants: the first is to avoid to use global variables in the specific function redefinitions, and second, may to dig sources of ruby more deeply.
can any body tell me what command is used to clear all variables in rails console?
e.g.
1.9.1 :001 > permissions = {:show => true}
=> {:show=>true}
1.9.1 :001 > foo = "bar"
=> "bar"
I need a command that can get all variables reset to nil without a restart of rails console itself.
Any advice would be very much appreciated.
local_variables.each { |e| eval("#{e} = nil") }
local_variables returns the list of symbols of all local variables in the current scope
a, b = 5, 10
local_variables # => [:b, :a]
Using each you can iterate over this list an use eval to assign their values to nil.
You can also do the same thing with instance_variables and global_variables. For example
(local_variables + instance_variables).each { |e| eval("#{e} = nil") }
By the way, if you are going to use it more than once, it might be helpful to define such method in ~/.irbrc file to make it accessible for all irb sessions (didn't test it in rails console).
class Binding
def clear
eval %q{ local_variables.each { |e| eval("#{e} = nil") } }
end
end
Then, inside irb session
a = 5
binding.clear
a # => nil
Do one thing, type
irb 'another'
and then press ctrl+l
now check the values of your variables.
It works.
I have a bunch of very repetitive rspec tests that all have the same format:
it "inserts the correct ATTRIBUTE_NAME" do
#o.ATTRIBUTE_NAME.should eql(VALUE)
end
It would be nice if I could just make one line tests like:
compare_value(ATTRIBUTE_NAME, VALUE)
But shoulda doesn't seem to be geared toward these types of tests. Are there other alternatives?
Sometimes I regret exposing subject as an end-user device. It was introduced to support extensions (like shoulda matchers), so you can write examples like:
it { should do_something }
Examples like this, however, do not read well:
it { subject.attribute.should do_something }
If you're going to use subject explicitly, and then reference it explicitly in the example, I recommend using specify instead of it:
specify { subject.attribute.should do_something }
The underlying semantics are the same, but this ^^ can be read aloud.
I would write a custom RSpec helper if you want it to read more clearly and be only 1 line. Suppose we have the following class we want to test:
class MyObject
attr_accessor :first, :last, :phone
def initialize first = nil, last = nil, phone = nil
self.first = first
self.last = last
self.phone = phone
end
end
We could write the following matcher:
RSpec::Matchers.define :have_value do |attribute, expected|
match do |obj|
obj.send(attribute) == expected
end
description do
"have value #{expected} for attribute #{attribute}"
end
end
Then to write the tests we could do something like:
describe MyObject do
h = {:first => 'wes', :last => 'bailey', :phone => '111.111.1111'}
subject { MyObject.new h[:first], h[:last], h[:phone] }
h.each do |k,v|
it { should have_value k, v}
end
end
If you put all of this in a file call matcher.rb and run it the following is output:
> rspec -cfn matcher.rb
MyObject
should have value wes for attribute first
should have value bailey for attribute last
should have value 111.111.1111 for attribute phone
Finished in 0.00143 seconds
3 examples, 0 failures
I found this which works great:
specify { #o.attribute.should eql(val) }
subject { #o }
it { attribute.should == value }