-
Notifications
You must be signed in to change notification settings - Fork 5
Ruby code style
Marek Hulán edited this page Oct 2, 2015
·
5 revisions
-
UTF-8 file encoding
-
Indent with 2 spaces (never use tabs!)
-
Unix style line endings
-
Spaces around operators
sum = 1 + 2
a, b = 1, 2
1 > 2 ? true : false; puts "Hi"
[1, 2, 3].each { |e| puts e }- No spaces after
(,[and before],)
some(arg).other
[1, 2, 3].length- Use a space after
{and before}as possible
[1, 2, 3].map { |number| number.upcase } # mainly in block it is for better readability
{ :number = > 1 } # in hashes should be used spaces
"Same #{ string }" # optionality to use spaces after / before- Indent when as deep as case. (as suggested in the Pickaxe)
case
when song.name == "Misty"
puts "Not again!" when song.duration > 120
puts "Too long!" when Time.now.hour > 21
puts "It's too late"
else
song.play
end
kind = case year
when 1850..1889 then "Blues"
when 1890..1909 then "Ragtime"
when 1910..1929 then "New Orleans Jazz" when 1930..1939 then "Swing"
when 1940..1950 then "Bebop"
else "Jazz"
end- Use an empty line before the return value of a method (unless it only has one line), and an empty line between defs.
def some_method
do_something
do_something_else
result
end
def some_method
result
end- Use RDoc and its conventions for API documentation. Don’t put an empty line between the comment block and the def. *Use empty lines to break up a method into logical paragraphs.
- Keep lines fewer than 80 characters.
- Avoid trailing whitespace.
- Use def with parentheses when there are arguments. Omit the parentheses when the method doesn’t accept any arguments.
def some_method
# body omitted
end
def some_method_with_arguments(arg1, arg2)
# body omitted
end- Never use for, unless you exactly know why. Most of the time iterators should be used instead.
array = [1, 2, 3]
# bad
for element in array do
puts element
end
# good
array.each { |element| puts element }- Never use
thenfor multi-lineif/unless.
# bad
if x.odd? then
puts "odd"
end
# good
if x.odd?
puts "odd"
end- Use
when x;... for one-line cases. - Use
&&/||for Boolean expressions,and/orfor control flow. (Rule of thumb: If you have to use outer parentheses, you are using the wrong operators.) - Avoid multi-line
?:(the ternary operator), useif/unlessinstead. - Favor modifier
if/unlessusage when you have a single-line body.
# bad
if some_condition
do_something
end
# good
do_something if some_condition
# another good option
some_condition && do_something- Favor unless over if for negative conditions:
# bad
do_something if !some_condition
# good
do_something unless some_condition
# another good option
some_condition || do_something- Suppress superfluous parentheses when calling methods, but keep them when calling "functions", i.e. when you use the return value in the same line.
x = Math.sin(y)
array.delete e-
Prefer
{ ... }overdo ... endfor single-line blocks. Avoid using{ ... }for multi-line blocks. Always usedo ... endfor "control flow" and "method definitions" (e.g. in Rakefiles and certain DSLs.) Avoiddo ... endwhen chaining. -
Avoid return where not required.
# bad
def some_method(some_arr)
return some_arr.size
end
# good
def some_method(some_arr)
some_arr.size
end- Avoid line continuation (
\) where not required. In practice avoid using line continuations at all.
# bad
result = 1 + \
2
# good
result = 1 \
+ 2- Using the
returnvalue of=is okay:
if v = array.grep(/foo/) ...- Use ||= freely.
# set name to Bozhidar, only if it's nil or false
name ||= "Bozhidar"- Avoid using Perl-style global variables(like
$0-9, $ `, ...)
- Use snake_case for methods and variables.
- Use CamelCase for classes and modules. (Keep acronyms like HTTP, RFC, XML uppercase.)
- Use SCREAMING_SNAKE_CASE for other constants.
- When defining binary operators, name the argument "other".
def +(other)
# body omitted
end- Prefer
mapovercollect,findoverdetect,find_alloverselect,sizeoverlength. This is not a hard requirement, though - if the use of the alias enhances readability - it’s ok to use it.
- Write self documenting code and ignore the rest of this section.
- Comments longer than a word are capitalized and use punctuation. Use two spaces after periods.
- Avoid superfluous comments.
- Keep existing comments up-to-date - no comment is better than an outdated comment.
- Write
ruby -wsafe code. - Avoid hashes-as-optional-parameters. Does the method do too much?
- Avoid long methods (longer than 10 LOC). Ideally most methods will be shorter than 5 LOC. Empty line do not contribute to the relevant LOC.
- Avoid long parameter lists (more than 3-4 parameters).
- Use def self.method to define singleton methods. This makes the methods more resistant to refactoring changes.
class TestClass
# bad
def TestClass.some_method
# body omitted
end
# good
def self.some_other_method
# body omitted
end
end- Add "global" methods to
Kernel(if you have to) and make themprivate. - Avoid
aliaswhenalias_methodwill do. - Use
OptionParserfor parsing complex command line options andruby -sfor trivial command line options. - Write for Ruby 1.9. Don’t use legacy Ruby 1.8 constructs
- use the new lambda syntax
->(x) { return x } - methods like inject now accept method names as arguments -
[1, 2, 3].inject(&:+)
- use the new lambda syntax
- Avoid needless meta-programming.
- Code in a functional way, avoid mutation when it makes sense.
- Do not mutate arguments unless that is the purpose of the method.
- Do not mess around in core classes when writing libraries. (do not monkey patch them)
- Do not program defensively.
- Keep the code simple (subjective, but still ...). Each method should have a single well-defined responsibility.
- Avoid more than 3 levels of block nesting.
- Don’t overdesign. Overly complex solutions tend to be brittle and hard to maintain.
- Don’t underdesign. A solution to a problem should be as simple as possible… but it should not be simpler than that. Poor initial design can lead to a lot of problems in the future.
- Be consistent. In an ideal world - be consistent with the points listed here in this guidelines.
- Use common sense.
Original version available at http://batsov.com/Programming/Ruby/2011/09/12/ruby-style-guide.html
For automated checks you can use excellent gem call rubocop. Install it to your project through bundler, put a provided .rubocop.yml file into the same directory and run rubocop.