Tag: gem

Envlogic – Ruby gem to have a Rails.env like environment behaviour in your non Rails Ruby applications

Envlogic is a simple gem that will help you manage your Ruby application environment. You can use it instead of a really popular solution like this one:

class App
  def self.env
    ENV['APP_ENV'] || ENV['RACK_ENV'] || 'development'
  end
end

How does it work?

Well it uses Rails String Inquirer and a bit of magic to resolve the environment key name. It will try to figure out the ENV key on its own, and if it fails it will fallback to development. To use it, just extend your class/module with Envlogic module:

Class MyApp
  extend Envlogic
end

MyApp.env #=> 'development'
MyApp.env.production? #=> false
MyApp.env.development? #=> true

ENV key name resolving

Envlogic will try to guess the key n few steps:

  • First it will try to guess the key based on the root directory name of your app. If it is called my_app - the key will be MY_APP_ENV (ENV['MY_APP_ENV'])
  • If this fails, it will try to resolve the class/module name in which it is - MyApp will be converted to MY_APP_ENV. It is worth pointing out, that this will also work for namespaced elements, so key for My::SuperApp will be equal to MY_SUPER_APP_ENV
  • It will try RACK_ENV as well
  • And finally will fallback to development

Where can I use it?

Anywhere outside of Rails app (it has a mechanism like this already built it). Just include this gem in your Gemfile and extend your class with it:

gem 'envlogic'

Can I safely replace my string solution with this one?

Yes. The env object (Envlogic::Env) behaves mostly like a typical string, so if you used to compare the env like this:

MyApp.env == 'production'

it will keep working as nothing would happen.

Few simple examples

Based on the app class name:

class MyApp
  extend Envlogic
end

ENV['MY_APP_ENV'] = 'production'

MyApp.env.production? #=> true
MyApp.env.development? #=> false
MyApp.env.test? #=> false

Based on the app dir name (/home/apps/super_app):

class App
  extend Envlogic
end

ENV['SUPER_APP_ENV'] = 'production'

App.env.production? #=> true
App.env.development? #=> false
App.env.test? #=> false

Based on the namespaced class name:

class Ux::App
  extend Envlogic
end

ENV['UX_APP_ENV'] = 'production'

Ux::App.env.production? #=> true
Ux::App::App.env.development? #=> false
Ux::App.env.test? #=> false

ActiveRecord and FriendlyId: slug not generated when field set with before_validation callback

FriendlyId is an awesome gem for slugging and permalinking for Active Record. It works like a charm except one case: when you set friendly_id field in a before_validation callback.

Here's an example:

class User < ActiveRecord::Base
  extend FriendlyId

  friendly_id :login, use: %i( history finders )

  before_validation :set_login

  def set_login
    # This weird method will just generate a random string
    self.login = (0...8).map { (65 + rand(26)).chr }.join
  end
end

User.new.save!
User.last.login #=> 'bhkcjvrd'
User.last.to_param #=> user id
User.last.slug #=> ''

It happens because FriendlyId uses a before_validation callback to set a slug. This method is invoked before any before_validation callbacks that you define in your class.

To fix this you can either invoke friendly_id after you set your before_validation callbacks, or you can just prepend your method before friendly_id:

class User < ActiveRecord::Base
  extend FriendlyId

  friendly_id :login, use: %i( history finders )

  before_validation :set_login
    prepend: true

  def set_login
    # This weird method will just generate a random string
    self.login = (0...8).map { (65 + rand(26)).chr }.join
  end
end

User.new.save!
User.last.login #=> 'bhkcjvrd'
User.last.to_param #=> 'bhkcjvrd'
User.last.slug #=> 'bhkcjvrd'

Copyright © 2023 Closer to Code

Theme by Anders NorenUp ↑