How Heroku or Rails config a database? - ruby-on-rails

I am new to Rails. I pushed my toy app from cloud9 to Heroku and magically my Heroku app is using a PostgreSQL even though my database.yml from the Heroku toolbelt for my app at Heroku is as follows:
# SQLite version 3.x
# gem install sqlite3
#
# Ensure the SQLite 3 gem is defined in your Gemfile
# gem 'sqlite3'
#
default: &default
adapter: sqlite3
pool: 5
timeout: 5000
development:
<<: *default
database: db/development.sqlite3
# Warning: The database defined as "test" will be erased and
# re-generated from your development database when you run "rake".
# Do not set this db to the same as development or production.
test:
<<: *default
database: db/test.sqlite3
production:
<<: *default
database: db/production.sqlite3
I know it's using a PostgreSQL because I can remotely access the DB using pgAdmin III.
So what's happening inside Heroku?

When using Heroku, the Heroku server will inject its own database yml file (That will use database url).
This is why the database.yml in your code will have no effect.
You can read more here
https://devcenter.heroku.com/articles/rails-database-connection-behavior

Heroku does not allow the use of SQLite. It will use PostgreSQL and will automatically creates one for you when you upload your app.
SQLite is not really made to be a production database. Since SQLite runs in memory, if you used it as a database on Heroku your entire database would be cleared once per day. There is more information here.
I am actually surprised you did not get any errors when deploying. In the past when I had accidentally left SQLite on, I always got a "push failed".
Heroku has a really good tutorial for changing your database from SQLite to PostgreSQL.

Related

Rails : How to configure database.yml for Heroku?

I'm new on RoR. I build a little app using ActiveAdmin and Devise and I wish to deploy it on Heroku.
When I had push my app on Heroku it run properly but the db seems to be empty ! In effect, my local login dont match when I try to log in my ActiveAdmin administration panel...
In addition, the others db of my app are totaly empty...
I guess that i had not fill the database.yml correctly but I dont find how I'm suppose to do it... :/
Database.yml :
# SQLite version 3.x
# gem install sqlite3
#
# Ensure the SQLite 3 gem is defined in your Gemfile
# gem 'sqlite3'
#
default: &default
adapter: sqlite3
pool: <%= ENV.fetch("RAILS_MAX_THREADS") { 5 } %>
timeout: 5000
development:
<<: *default
database: db/development.sqlite3
# Warning: The database defined as "test" will be erased and
# re-generated from your development database when you run "rake".
# Do not set this db to the same as development or production.
test:
<<: *default
database: db/test.sqlite3
production:
<<: *default
database: db/production.sqlite3
I would be grateful if you could help me or direct me to a solution!
Thank you for your attention ! ^^
production:
<<: *default
database: db/production.sqlite3
You can't use sqlite3 on heroku, because it is filesystem-based and on each restart a new dyno is created, with a completely new filesystem. The old dyno is killed and your sqlite3 data file with it.
Use a client-server DB on heroku, like Postgresql. This is well covered in heroku guides.
These steps is how to push the local database to heroku and to create database
heroku pg:backups:restore 'https://s3.amazonaws.com/me/items/3H0q/mydb.dump' DATABASE_URL
Get database info
heroku pg
-> Gave me the name of the database
eg: HEROKU_POSTGRESQL_CYAN
Reset the database on heroku
heroku pg:reset HEROKU_POSTGRESQL_CYAN
Look for the name of the local database
Opened config/database.yml and found the database
name for the development environment.
eg: fashions_development => put the name that the terminal give it to you
Run push the local database to Heroku
Opened config/database.yml and found the database
heroku pg:push fashions_development HEROKU_POSTGRESQL_CYAN

Cloning Heroku postgresql DB to local db for "live" testing

So I've followed all of the guides I can find online for this issue, including similar stack posts, but things are not working.
I ran the command
heroku config:get DATABASE_URL
and got
postgres://<username>:<password>#<host_name>:<port>/<dbname>
(with all of the <> parts being my DB info of course) and ran
pg_dump --host=<host_name> --port=<port> --username=<username> --password <dbname> > output.sql
At this point I needed to run
psql -d <local_database_name> -f output.sql
but my rails app followed the Michael Hartl tutorial which uses sqlite3, so I had to switch things over. I tried this by changing my database.yml file to
# SQLite version 3.x
# gem install sqlite3
#
# Ensure the SQLite 3 gem is defined in your Gemfile
# gem 'sqlite3'
#
default: &default
adapter: postgresql
encoding: unicode
# adapter: sqlite3
pool: 5
timeout: 5000
development:
<<: *default
database: db/development
# database: db/development.sqlite3
# Warning: The database defined as "test" will be erased and
# re-generated from your development database when you run "rake".
# Do not set this db to the same as development or production.
test:
<<: *default
database: db/test
# database: db/test.sqlite3
production:
<<: *default
database: db/production
# database: db/production.sqlite3
I also changed the Gemfile to use 'pg' instead of 'sqlite3' in development. At this point I ran bundle install and tried rails db:setup and rails db:migrate which did not create the databases (.. uh oh) and when I run the final step of
psql -d db/development -f db/output.sql
I get plenty of console output, but when I run a rails console sandbox, there is no user info from my Heroku database. Did I miss a step? What's going on? (I'm working on Ubuntu 14.04)
Edit:
First, I undid all of the local changes I made above. Then, I ended up following a combo of the above and the guide here http://manuelvanrijn.nl/blog/2012/01/18/convert-postgresql-to-sqlite/. I used heroku config:get DATABASE_URL to get all of the needed host, port, username, etc. info and then pulled the data with
pg_dump --host=<host_name> --port=<port> --username=<username> --password --data-only --inserts <dbname> > dump.sql
After that I followed the postgresql to sqlite database conversion (the "Longer story a.k.a please explain a little more." version) I linked above. I did all of the edits described in step 2 as well as having to remove a bunch of SELECT statements at the end of dump.sql. Another change I had to make was replacing all INSERT INTO instances with INSERT OR REPLACE INTO to satisfy some unique constraint errors in step 4. That did it!

How to setup a MySQL DB with rails in google could SQL

I have a rails app setup on a google cloud instance. I want to have the db in a SQL instance for the extra performance. But I cant see how to do this for a rails app.
I understand you create the SQL instance, start it, install mysql, on it but then how can I have the db and tables added? Creating them manually isn't going to be the solution because normally with rails apps you run rake db:create and rake db:migrate create the DB with tables and columns but this just makes a development.sqlite3 file not a mysql db..
I haven't deployed a rails app before so I think I'm missing something.
Here is my config/databast.yml file
default: &default
adapter: sqlite3
pool: 5
timeout: 5000
development:
<<: *default
database: db/development.sqlite3
mysql_settings: &mysql_settings
adapter: mysql2
encoding: utf8
pool: 5
username: root
password: root
host: 130.211.71.150
database: dbname
test:
<<: *default
database: db/test.sqlite3
production:
<<: *default
database: db/production.sqlite3
I cant find out what needs to be done to have the db be created and tables and columns migrated into the mysql DB.
In your gem file you can put the sqlite gem under a development/test block and you can add the mysql gem in a production block.
In your database.yml file you can keep the development settings you have currently but then add another setting for production settings. Here you can include your mysql db settings (including the host and port of your SQL instance node)
When you launch your app, you can then launch it locally in development mode to use sqlite for development, but when deploying you can launch in production mode to utilize the mysql specific settings. From there you should be able to use db:create db:migrate etc to connect to that host and setup your Db.
Here is a nice article describes this process.
https://www.digitalocean.com/community/tutorials/scaling-ruby-on-rails-setting-up-a-dedicated-mysql-server-part-2
As a team, we chose to use mysql for local development as it more closely mimics what your prod environment will be like.

Fresh rails app defaulting to Postgres instead of SQLite3

I've just installed rbenv, ruby 2.2.3 and rails 4.2.4 for the first time on this machine. I've started my rails application with no change to any of the code, just the default generated documents from using rails new ., I then started the server with rails server.
When hitting http://localhost:3000 I'm getting the following error:
"Specified 'postgresql' for database adapter, but the gem is not loaded. Add gem 'pg' to your Gemfile (and ensure its version is at the minimum required by ActiveRecord)."
I've got postgres installed from a previous project with Node, but my database.yml still reads as you'd expect from a new application:
# SQLite version 3.x
# gem install sqlite3
#
# Ensure the SQLite 3 gem is defined in your Gemfile
# gem 'sqlite3'
#
default: &default
adapter: sqlite3
pool: 5
timeout: 5000
development:
<<: *default
database: db/development.sqlite3
# Warning: The database defined as "test" will be erased and
# re-generated from your development database when you run "rake".
# Do not set this db to the same as development or production.
test:
<<: *default
database: db/test.sqlite3
production:
<<: *default
database: db/production.sqlite3
I don't really want to use Postgres at the moment, I'm just starting out and I'd rather keep things simple with SQLite3 for a bit. Does anyone know what may be going on and what I could do to get it using SQLite3 so that this error stops?
There is another solution, for those who actually need to keep the DATABASE_URL environment variable without affecting Rails (like me). You can use a url sub key:
development:
<<: *default
url: sqlite3:db/development.sqlite3
This is documented here.
The problem is that when you start the server it is looking for environment variable DATABASE_URL which is probably set to postgres and this takes precedence over the database.yml file. You can delete the environment variable, and it should work, or you can reset it to SQLite.
It's an old post but maybe somebody will find this useful.
In my case I had the DATABASE_URL variable exported in ~/.bash_profile like so
# Postgres installation
export DATABASE_URL=postgres:///$(whoami)
On Linux it might be in ~/.bashrc file.
Just remove or comment out the export line if you don't use Postgres anymore or use AlienBishop's solution if you do.
As IliaAptsiauri mentioned, without DATABASE_URL variable applications should use settings from database.yml file.

"rails server" using the wrong database

I recently switched a relatively new rails app from sqlite3 to Amazon RDS and configured my database.yml file to use the RDS database in the production environment only.
But now, whenever I try to do any local action on my database (e.g. rails server, rails console, rake db:migrate, etc.) it does that action to the production DB on Amazon's servers rather than my local sqlite3 DB, which is my development DB.
# database.yml
development:
adapter: sqlite3
database: db/development.sqlite3
pool: 5
timeout: 5000
test:
adapter: sqlite3
database: db/test.sqlite3
pool: 5
timeout: 5000
production:
adapter: mysql2
host: mydb.mydbhost.us-east-1.rds.amazonaws.com
reconnect: false
database: mydb
username: myusername
password: mypassword
What am I doing wrong?
UPDATE: Here's my environment.rb file:
# environment.rb
# Load the rails application
require File.expand_path('../application', __FILE__)
# Heroku environment variables for local use
heroku_env = File.join(Rails.root, 'config', 'heroku_env.rb')
load(heroku_env) if File.exists?(heroku_env)
# Initialize the rails application
Myapp::Application.initialize!
your not using productions settings
try
rails s -e production
or
RAILS_ENV=production rails s
RAILS_ENV=production rake db:migrate
Figured out the problem after taking a day to get away from it. It's a silly mistake on my part, but I thought I'd post the solution in case someone else encounters a similar issue.
As you can see from my environment.rb file above, I have a heroku_env.rb file, which contains all of my heroku-specific environment variables on my local machine for development purposes. In that file, I declared a ENV['DATABASE_URL'] variable, which links to my Amazon RDS database. Deleting this from the file solved the problem!
Thanks to everyone who offered answers to help!

Resources