Ruby

This is a work in progress, but I figured I might as well get started. Here is a list of Ruby things that I’ve found helpful.

Latest stable version of Ruby?

Some ruby installers might not actually have the latest version of ruby, so it is handy to check this page to figure out what exactly is the latest stable version: Download Ruby.

Not always, but usually it is best to be on the latest stable 1 version below the bleeding edge. In this case Ruby 3.2.0 is the latest, but I’m using 3.1.3 as my default ruby.

Installing Ruby

I currently use a combination of ruby-install and chruby.

ruby-install ruby 3.2.2
exec $SHELL
chruby ruby-3.2.2
echo "ruby-3.2.2" > ~/.ruby-version

Ruby Related Resources

Rubular is a site for playing around with regular expressions:

Rename a hash key

hash[:new_key] = hash.delete :old_key

source

Ensure a Ruby hash is only using symbols

This will convert the hash keys to symbols instead of them being strings.

hash.symbolize_keys!

source

Hash keys are case sensitive

$ cat case.rb 
h = {
  "asdf" => 1,
  "AsDf" => 2
}

puts h["asdf"]
puts h["AsDf"]
puts h["aSdF"]
$ ruby case.rb 
1
2

Get the first X characters of a string

"123456789"[0..4]
# "12345"

But this can be a better way

"123456789".first(5)
# "12345"

especially if you are storing the string length as a constant like this:

MAX = 5
"123456789".first(MAX)
# "12345"
"123456789".first
# "1"

Get the first element in an array

On a related note to using .first on strings you can also use it on arrays:

[1, 2].first
# 1

If you are using Rails you can also use .second:

[1,2,3,4].second    # Rails Only
# 2

or .third:

[1,2,3,4].third     # Rails Only
# 3

but not .forth:

[1,2,3,4].forth     # Not even in Rails
# NoMethodError: undefined method `forth' for #<Array:0x00005583ad7838a0>

However, you can use .forty_two! :rofl:

(1..45).to_a.forty_two     # Rails Only
# 42

source

Subtracting Days in Ruby

I need a unix timestamp for a specific day. You can do that with .to_i on the Time class, but not with Date

Time.now.to_i
# 1632854844

I also need the unix epoch for different dates, so what I can do is subtract days (in seconds) from Time.now

Time.now
# 2021-09-28 12:43:10.3599796 -0600

Time.now - 1 # Don't do this
# 2021-09-28 12:43:17.6062736 -0600

Time.now - 1*24*60*60 # (1 Day ago)
# 2021-09-27 12:43:57.8495587 -0600

Time.now - 2*24*60*60 # (2 Days ago)
# 2021-09-26 12:44:05.9715538 -0600

(Time.now - 3*24*60*60).to_i # (3 Days ago to Unix Epoch)
# 1632595460

source

Zero?

As a better alternative to a.count == 0 use .zero?

a.count.zero?
# true

Remove array element at index

You can use .slice!(index) to remove a specific element from an array.

arr = ['a', 2, 'b']
# ["a", 2, "b"]
arr.slice!(1)
# 2
arr
# ["a", "b"]

Faster alternative to Dir.glob

IO.popen("find . -name '*.txt'").each { |path| parse(path.chomp) }

source

Rails not ruby

Cast to boolean:

[1] pry(main)> ActiveModel::Type::Boolean.new.cast("false")
=> false
[2] pry(main)> ActiveModel::Type::Boolean.new.cast(0)
=> false

.tap

    SiteSetting.defaults.tap do |s|
      s.set_regardless_of_locale(:s3_upload_bucket, 'bucket')
      s.set_regardless_of_locale(:min_post_length, 5)
      s.set_regardless_of_locale(:min_first_post_length, 5)
      s.set_regardless_of_locale(:min_personal_message_post_length, 10)
      s.set_regardless_of_locale(:download_remote_images_to_local, false)
      s.set_regardless_of_locale(:unique_posts_mins, 0)
      s.set_regardless_of_locale(:max_consecutive_replies, 0)
      # disable plugins
      if ENV['LOAD_PLUGINS'] == '1'
        s.set_regardless_of_locale(:discourse_narrative_bot_enabled, false)
      end
    end

    SiteSetting.refresh!

source

uri.scheme

To check if a url is https or not you can use .scheme like this:

irb(main):001:0> uri = URI.parse("https://blake.app")
=> #<URI::HTTPS https://blake.app>
irb(main):002:0> uri.scheme
=> "https"
irb(main):003:0> uri.scheme == "https"
=> true

source

Home Directory

Dir.home - Will return your current home directory. This is handy when writing scripts that will work on Linux, OSX, & Windows.

cd

Dir.chdir - Change the current directory the script is running from.

splitting newlines

I needed to turn the output of a terminal command into an array. Off the top of my head if I didn’t have an active internet connection I would just use .split("\n") but I wanted to see if Ruby had anything better. Turns out they have .lines.

Validating YAML with Ruby command line

ruby -ryaml -e "p YAML.load(STDIN.read)" < file.yml