1

For example, I have Post model in my Ruby on Rails application. And I want to create a way that user without code experience could set expiration date for all posts on production.

What I mean, for example, Post was create at 21:00 and admin wants to expires all posts in n hours. And you ask from admin the n value. (and the n value will be the same for all posts)

You won't create a new table in you db just for one record, right? But you need a place to save this value. What other options do I have?

Hope I make my self clear, thank you!

Andrey Drozdov
  • 571
  • 1
  • 5
  • 22
  • Possible duplicate of [Persist a single variable in rails](http://stackoverflow.com/questions/23235604/persist-a-single-variable-in-rails) – jaynetics May 14 '17 at 18:44

3 Answers3

1

There are a number of options (including a new table on your db), but the one that could best fit your scenario is to use an environment variable.

An environment variable can easily be updated by an admin and will be available to your app right after been updated.


Setting environment variable

Add this line to /.bash_profile (in Mac OS X) and /etc/environment (in Ubuntu):

export MY_VARIABLE=VALUE

Where MY_VARIABLE is the name of your variable and VALUE is its value.

Getting values from environment variable

Anywhere in your rails app you can access the environment variable with ENV["MY_VARIABLE"], for example:

my_env_variable = ENV["MY_VARIABLE"]

Answer for additional questions

where this env vars are saved?

.bash_profile and /etc/environment files.

How can I override them for example from controller?

You should be able to change its value with

ENV["MY_VARIABLE"] = new_value

but i recommend against it, you will lose the advantage of using env variables.

How long are they kept?

As long as they remain specified in .bash_profile and /etc/environment files.

Deploy affect theme?

No.

How can I view list of env vars?

Run this command:

$ printenv
Gerry
  • 10,337
  • 3
  • 31
  • 40
  • I think it's a better idea to lock the expiration date inside a class constant, so that the change can be reference by author and date via source control. – Dan May 14 '17 at 19:43
  • @Dan That was my first option (a good one), but if the value will change often (and it think it will) then an environment variable is more convenient (you won't need to change code, deploy and restart app). If the value will remain the same always, then a constant would definitely be better. – Gerry May 14 '17 at 19:49
  • Env variable = `config/secrets.yml` file? And how to update it through, for example submit form? – Andrey Drozdov May 14 '17 at 21:52
  • @AndreyDrozdov No, the env variable is not part of your code, i mean, you wont configure it there, you will call it form your code (i.e. `hours_to_expire = ENV["EXP_HOURS"]` where `EXP_HOURS` is the name of the variable). How to set (and update) a variable depends on the OS where your app is running. What is your OS? – Gerry May 14 '17 at 22:08
  • Development - Mac, Server - Ubuntu 14.04 But I have so many questions: where this env vars are saved? How can I override them for example from controller? How long are they kept? Deploy affect theme? How can I view list of env vars? – Andrey Drozdov May 14 '17 at 22:14
  • Thank you, one more question: but i recommend against it, you will lose the advantage of using env variables - why exactly? – Andrey Drozdov May 14 '17 at 22:59
  • @AndreyDrozdov If you change the value on your code then you will need to modify the code to change its value (since every time will override whatever value you set), snd its better to use a constant for that (see Dan's answer). The advantage of using the env variable is to be free to change its value and make it available to your app without deploy/restart. – Gerry May 14 '17 at 23:03
  • @AndreyDrozdov You could add a condition in your code to use a fixed value if some condition is met or use the env variable otherwise; for example: `my_var = my_condition ? 250 : ENV["MY_VARIABLE"]`. – Gerry May 14 '17 at 23:07
  • Note that environment variables are not shared between instances running on different nodes. – Dani May 15 '17 at 11:32
0

Use a constant! In your Post model, set a constant bound to the date you want to lock expiration at:

class Post # ... EXPIRATION_DATE = Date.new(2017,05,14) # ... end

Then reference that constant where needed:

Post.create!(expiration_date: Post::EXPIRATION_DATE, # ... )

Dan
  • 389
  • 3
  • 13
0

I think your question includes two parts:

  1. How to model and persist the fact that some posts have been expired?

A simple way would be to add a boolean expired column to the posts database table to indicate whether a post has be expired. Usually with matching expired_at and expired_by columns for an audit trail.

  1. How to make the operation of expiring posts available for a "user without code experience"?

If you are using rails you could use a gem for an admin view management UI (e.g. rails_admin). You could then add your custom logic to be invoked through the admin UI only. Another option would be to expose this logic as a custom rake task and invoke is through a terminal (no GUI).

Dani
  • 1,012
  • 9
  • 15