Recent notes
RSS feedThe purpose of this method
This method keeps track of whether a hidden id field needs to be created when the form builder is generating fields for a nested model. It gets set to true by #hidden_field when that method is used to create a field named ‘id’.
Here’s an example of what this can be useful for: http://railsforum.com/viewtopic.php?id=39640
Help Link :)
www.relishapp.com/rspec/rspec-mocks/docs/message-expectations/receive-counts!
Your scope cannot be called 'locked'
-
see: http://github.com/rails/rails/pull/6985
class Article < ActiveRecord::Base scope :locked, where(... end
will cause intermittent problems of the type
undefined method 'locked' for #<Class:0x007fdab3025298>
Use something like ‘access_locked’ instead
How does enum#each_index differ from enum#with_each_index ?
Here is the working one each_with__index:
a=[11,22,31,224,44].each_with_index { |val,index| puts "index: #{index} for #{val}" if val < 30} index: 0 for 11 index: 1 for 22 => [11, 22, 31, 224, 44]
Below couldn’t produce the output, as with_index couldn’t work on the array.To make it workble, we need to first convert it to enumerator. And that can be done via the help of .to_enum, .each, or .map
a = [11,22,31,224,44].with_index { |val,index| puts "index: #{index} for #{val}" if val < 30} =>NoMethodError: undefined method `with_index' for [11, 22, 31, 224, 44]:Array from (irb):2 from C:/Ruby193/bin/irb:12:in `<main>'
Here is the working one with_index:
a = [11,22,31,224,44].each.with_index { |val,index| puts "index: #{index} for #{val}" if val < 30} index: 0 for 11 index: 1 for 22 => [11, 22, 31, 224, 44]
Difference between enum#with_object and enum#each_with_object
I found a very good post on SO - which clearly explained the difference between enum#with_object and enum#each_with_object. The link is as follows:
Enumerator#with_index has confusing documentation
Enumerator#with_index has confusing documentation, but hopefully this will make it clearer.
Code example
a=[11,22,31,224,44].to_enum => [11, 22, 31, 224, 44] a.with_index { |val,index| puts "index: #{index} for #{val}" } index: 0 for 11 index: 1 for 22 index: 2 for 31 index: 3 for 224 index: 4 for 44 a=[11,22,31,224,44].to_enum => #<Enumerator: [11, 22, 31, 224, 44]:each> a.with_index(2){ |val,index| puts "index: #{index} for #{val}" if val > 30 } index: 4 for 31 index: 5 for 224 index: 6 for 44 => [11, 22, 31, 224, 44
Other Example
##
class Exam cattr_reader :code, :description, :points, :instance_reader => false @@code = "EXM" @@description = "Sent Exam" @@points = 1000 end
In this case it’s possible to use
Exam.code # => EXM Exam.description # => Sent Exam Exam.points # => 1000
Works also with Mongoid
What works for Active Record, also works for Mongoid:
de: mongoid: attributes: picture: explanation: Description
Use sqlite3, not sqlite
Note that typically if you want to connect to an SQLite database the adapter would be “sqlite3”; not “sqlite” as depicted in the documentation above. Just using the term “sqlite” might result in the error message: “database configuration specifies nonexistent sqlite adapter”
Using an unobtrusive Ajax (UJS) :onchange call to the controller#action
An :onchange call can be made using the Rails 3 jquery-ujs helper in the form:
check_box_tag( name, value, checked, html_and_other_options)
For example:
select_tag( "my_tag_id", entity.id, class: "progress bar update_msg", disabled: disabled? data: { remote: true, url: url_for( action: :my_controller_action, id: my_id) // application symbols progress_bar: "progress_bar_div_id", update: "message_div_id" } )
The jquery_ujs looks for data-remote and data-url. These can be spelled-out or placed in the data hash. The url must be formed as select_tag does not call url_for, unlike some of the other related tags. Values for application symbols can also be passed through. jQuery triggers will work on the Ajax events that occur. This generates the following:
<input class="progress_bar update_msg" data-progress-bar="progress_bar_div_id" data-remote="true" data-update="message_div_id" data-url="/my_controller/my_controller_action/my_id" id="my_tag_id" name="my_tag_id" type="checkbox" value="4"/>
In this example, by tying into the events the program makes visible an existing hidden progress bar while awaiting a server response, and then displays a div containing a message returned by the server and hides the progress bar. If the div contains a class= for notice or error, then they will fade out.
$(".layout") .on('ajax:beforeSend', ".progress_bar", function(){ // get id of element to make visible var progress_bar_id = '#' + this.getAttribute('data-progress-bar'); $(progress_bar_id).show(); }) .on('ajax:complete', ".progress_bar", function(){ // get id of element to hide var progress_bar_id = '#' + this.getAttribute('data-progress-bar'); $(progress_bar_id).hide(); }) .on('ajax:complete', ".update_msg", function(evt, xhr, options){ // get id of element to contain message var update = this.getAttribute('data-update'); $("#" + update).replaceWith($(xhr.responseText).attr("id", update)); // cause responses with these classes to fade away... $('.notice').fadeOut(2500); $('.error').fadeOut(8000); });
for rails >= 3
template_root= is deprecated, use prepend_view_path instead
source: ActionMailer/DeprecatedApi/ClassMethods/template_root
Some documentation available in RailsGuides
The Rails engines getting started guide discusses the usage of isolate_namespace: http://edgeguides.rubyonrails.org/engines.html
Pass a block
While this example is not so obvious on first look what the block passed does, here’s a small explanation:
when the block is passed to this function, the uniqueness is checked based on a value returned by that block.
For example if it’s array of objects with “user_id” method, then this would be:
tasks.uniq{|t| t.user_id } # returns only tasks with unique user_id
Note sure if doco is correct
(Note this was an issue in Ruby 1.9.2, 1.9.3 has been corrected, not sure why the generated doc is still incorrect)
Both exist? and exists? use the same underlying C function
file.c, line 5444
define_filetest_function("exist?", rb_file_exist_p, 1); define_filetest_function("exists?", rb_file_exist_p, 1);
rb_file_exist_p does an rb_stat call, and just checks for no error.
rb_stat returns the result of a call to fstat, if the passed in value is a IO object, or stat (or your platforms equivalent). Both these return 0 on success, -1 on failure.
So both really just check that the underlying “thing” can respond to “stat” correctly. There are many things in a unix-style filesystem that have a “file” structure, not just traditional files. These functions help when you don’t care what type an entry is, just that it exists.
There doesn’t seem to be any difference in the two methods
File.directory? can test if a named file is a dir
Minor edit of pluralize_without_count
patrickberkeley’s method works great. I corrected the grammar a bit for inflection (the singular error).
application_helper.rb
def pluralize_without_count(count, noun, text = nil) if count != 0 count == 1 ? "an #{noun}#{text}" : "#{noun.pluralize}#{text}" end end
This should work in much older versions of Rails also.
Helper Methods inside of a Controller
When needing to include a helper method inside of a controller, instead of including the ENTIRE helper module, simply use this method like so:
module ApplicationHelper def fancy_helper(str) str.titleize end end class MyController < ApplicationController def index @title = view_context.fancy_helper "dogs are awesome" end end
Changing time/date separators
@hayafirst — it is possible to remove that “:” or change it to something else. Just pass `:time_separator` option. Inspect ActionView::Helpers::DateTimeSelector#separator method for more.
Using an unobtrusive Ajax (UJS) :onchange call to the controller#action
An :onchange call can be made using the Rails 3 jquery-ujs helper in the form:
select_tag( name, option_tags, misc_html_options, html_5_data-stuff)
For example:
select_tag( "my_tag_id", get_ids(@entity), class: "progress_and_message", data: { remote: true, url: url_for( action: :my_controller_action, id: my_id) // application symbols progress_bar: "progress_bar_div_id", update: "message_div_id" } )
The jquery_ujs looks for data-remote and data-url. These can be spelled out or placed in the data hash. The url must be formed as select_tag does not call url_for, unlike some of the other related tags. Values for application symbols can also be passed through. jQuery triggers will work on the Ajax events that occur. This generates the following:
<select class="progress_and_message" data-progress-bar="progress_bar_div_id" data-remote="true" data-update="message_div_id" data-url="/my_controller/my_controller_action/my_id" id="my_tag_id" name="my_tag_id"><option value=etc...></option>
For example, tying into the events in this case the program makes visible an existing hidden progress bar while awaiting a server response, and then displays a div containing a message returned by the server and hides the progress bar. If the div contains a class= for notice or error, then they will fade out.
$(".layout") .on('ajax:beforeSend', ".progress_and_message", function(){ // get id of element to make visible var progress_bar_id = '#' + this.getAttribute('data-progress-bar'); $(progress_bar_id).show(); }) .on('ajax:complete', ".progress_and_message", function(evt, xhr, options){ // get id of element to contain message and to hide var update = this.getAttribute('data-update'); var progress_bar_id = '#' + this.getAttribute('data-progress-bar'); $("#" + update).replaceWith($(xhr.responseText).attr("id", update)); $(progress_bar_id).hide(); // cause responses with these classes to fade away... $('.notice').fadeOut(2500); $('.error').fadeOut(8000); });
Example
NOTE: you pass all the keys and values in one long list:
fruit = ActiveSupport::OrderedHash[ 'apple', 'Apple', 'banana', 'Banana', 'kiwi', 'Kiwi fruit', ] fruit.keys => ["apple", "banana", "kiwi"]
Now called class_attribute in Rails 3.2.x
See github.com/novafabrica/make_exportable/pull/4
@drewyoung1
Including module in a class does not automatically over-write methods defined with the same name.
Ex:
module Mod
def exit(code = 0) puts "Exiting with code #{code}" super end
end
class OriginalClass
include Mod def exit puts "Original message" end
end
OriginalClass.new.exit 99
Produces:
exit': wrong number of arguments (1 for 0) (ArgumentError)
if you use this construct, the alias_method will work similar to super:
module Mod
alias_method :super_exit, :exit def self.included base base.instance_eval do def exit(code = 0) puts "Exiting with code #{code}" super_exit end end end
end
Beware: default system crypt functionality silently ignores characters beyond the 8th
On some systems:
"1".crypt('aa') => "aacFCuAIHhrCM" "12".crypt('aa') => "aa8dJzr7DFMPA" "123".crypt('aa') => "aamrgyQfDFSHw" "1234".crypt('aa') => "aatxRPdZ/m52." "12345".crypt('aa') => "aajt.4s3e3SZA" "123456".crypt('aa') => "aaAN1ZUwjW7to" "1234567".crypt('aa') => "aaOK9MRbwVNmQ" "12345678".crypt('aa') => "aaNN3X.PL2piw" "123456789".crypt('aa') => "aaNN3X.PL2piw" "1234567890".crypt('aa') => "aaNN3X.PL2piw" "1234567890abcdefghij".crypt('aa') => "aaNN3X.PL2piw"
you will be redirect to signin, when you want to create post before signin
code
def test_should_signin_first_before_add_post get "/admin/posts/new" follow_redirect! end
post user authentication info to sessions create action
post_via_redirect(“sessions”, {:user=>{:email=> user.email, :password => user.password}})
This method is deprecated in rspec 2.0
-
be_close(1, 0.1) is deprecated.
-
please use be_within(0.1).of(1) instead.
Beware: virtual attributes are ignored
Even though validations are called, virtual attributes are ignored.
Can't find documention on :find_by option
I found code that had a :find_by option on belongs_to. I’m sure it’s more or less self explanatory, but I couldn’t find it listed anywhere as an option.
My bad, belongs_to was in a controller, not a model.
String to date conversion not necessarily symmetric
Note that converting from Date to String and back again is not necessarily symmetric, because the conversion to string may result in a format that is not properly converted by `to_date`.
For one thing, `to_date` sets the century argument in _parse to false. Thus if the default date format has a two-digit year, like the :short one, the century will be dropped.
Date.today.to_s.to_date #=> Mon, 28 Nov 0012
Use collect instead of inject/reduce
You can still use collect when you nest content_tag . Just join the collection in the end and remember to add html_safe if you don’t want your html to be escaped.
a = ['a','b','c'] content_tag(:ul, :class => 'a class') do a.collect do |item| content_tag(:li, item) end.join.html_safe end