I am trying to get a site set up on Heroku using Sinatra and PostgreSQL. It worked locally (connecting to local database), but after pushing it to Heroku and changing my PG.connect to reflect that, I get an Internal Server Error the moment a page tries to access the database.
require 'uri'
require 'pg'
uri = URI.parse(ENV['DATABASE_URL'])
def db(uri)
begin
connection = PG.connect(uri.hostname, uri.port, nil, nil, uri.path[1..-1], uri.user, uri.password)
yield(connection)
ensure
connection.close
end
end
I am pretty sure these are parsing correctly, because ENV['DATABASE_URL'] displays the full postgres://user:password#host:port/database information that I'm expecting, and if I do the same in IRB uri.hostname, ui.port, etc all return what's expected .
This is my first time trying to get a site working on Heroku, so I am not even sure how to troubleshoot this. (And I googled for about all of yesterday.)
Results for heroku pg:
=== DATABASE_URL
Plan: Hobby-dev
Status: Available
Connections: 0/20
PG Version: 9.4.2
Created: 2015-05-30 19:24 UTC
Data Size: 17.7 MB
Tables: 5
Rows: 9320/10000 (In compliance, close to row limit)
Fork/Follow: Unsupported
Rollback: Unsupported
And all the tables show up when when I do heroku pg:psql <database> from the cli.
Some answers I've seen said to add database.yml to my root app directory, so:
production:
adapter: 'postgresql'
database: '<database>'
host: ENV['DATABASE_URL']
username: '<username>'
There's probably something simple I'm missing, but I haven't seen a complete guide for Sinatra/PSQL on Heroku - nothing that goes specifically into setting up and connecting to your database. (Everything seems Rails-related.)
In your database.yml file you need to specify the correct host for the host entry. You are passing what is stored in DATABASE_URL (something like postgres://user:password#host:port/database) but it should just be the host.
You will also need to specify a port if it isn't the default for PostgreSQL.
Edit: should also point out if you plan to store the host (or anything else - you definitely should for username and password) in an environment variable you'll need to wrap it, e.g. <%= ENV['HOST'] %>, not just ENV['HOST'] (i.e. how you have in the database.yml excerpt above)
Related
I have trouble connecting to my cloudant NoSQL database hosted on bluemix with couchrest_model library.
I have similar code written in ruby which works just fine from my computer (running locally, no rails or sinatra):
require 'couchrest'
url = "https://blah-blah#url with credentials.com"
database_name = "testdb"
db = CouchRest.database!(url+"/"+database_name)
db.save_doc('_id':"dog",:name => 'MonthyPython', :date => Date.today)
doc = db.get('dog')
The code above successfully writes data to my database. However, when I tried to do similar thing with the newest 'couchrest_model' gem, I got the
/Users/userpruser/.rvm/rubies/ruby-2.3.0/lib/ruby/2.3.0/net/http.rb:933:in `connect_nonblock': SSL_connect returned=1 errno=0 state=SSLv2/v3 read server hello A: unknown protocol (OpenSSL::SSL::SSLError)
I have viewed several pages, but with no luck. So what is the correct way to make it work with just ruby (no rails) or/and ruby+sinatra? I find this recipe http://recipes.sinatrarb.com/p/models/couchdb but I have no idea how to sed the evniroment variables and how to put it together.
Thanks for any help!
Did you try explicitly setting the port to 443 and the protocol to 'https'? See https://github.com/couchrest/couchrest_model#configuration
It looks like installing
gem install sinatra-config-file
and then requiring
require sinatra/config_file
solved my problem. Thanks to you all!
I've searched several related posts for the issue I'm having but wasn't able to find an answer. I'm a student in a coding program where most people use Mac, but I'm on Windows ( 7, Pro, 64 ) - because of that I'm a bit locked in to the tools/software I'll post here.
I'm trying to open a connection through Ruby with the pg gem, and I'm using Sinatra and PostgreSQL. I've established the server, database, and configuration path variables for PostgreSQL, and I've successfully installed pg gem (didn't have an issue there as in some of the other posts) with the line:
gem install pg -- --with-pg-config=C:\Program Files\PostgreSQL\9.5\bin
So the problem is that when I boot up Sinatra and go to the localhost,
I get a NoMethodError, Undefined Method for nil:NilClass on a method that otherwise works for Mac users.
The method is:
configure :development do
set :db_config, { dbname: "news_aggregator_development" }
end
configure :test do
set :db_config, { dbname: "news_aggregator_test" }
end
def db_connection
begin
connection = PG.connect(Sinatra::Application.db_config)
yield(connection)
ensure
connection.close
end
end
get '/articles' do
#results = db_connection do |conn|
conn.exec("SELECT * FROM articles")
end
erb :index
end
connection returns nil, and so the close method returns with an undefined method error. I don't think there is a syntax error as I've checked with others regarding this, and I'm thinking it might be related to a connection error with pg.
First time post so please go easy on me =) Apologies if I've left out any needed information - let me know what more context could be helpful and I will try to provide it! Thank you!
Two points:
Wrap your Sinatra helpers in a helpers {} block. This will allow you to use settings.db_config instead of Sinatra::Application.db_config:
helpers do
def db_connection
connection = PG.connect(settings.db_config)
yield connection
ensure
connection.close
end
end
In your PG.connect call, you should pass the host, user, password, and any other options necessary for the pg gem to find, connect, and authenticate to your instance. The dbname alone is not enough—at least not on Windows.
configure :development do
set :db_config, {
host: "localhost",
port: 5432,
user: "foo",
password: "bar",
dbname: "news_aggregator_development"
}
end
Good luck!
Current System: Windows XP / Windows 7 (problem occuring for both)
After following the guidelines for deployment from the following:
https://devcenter.heroku.com/articles/python
and by testing by using a simple poll application I am successfully able to push the application through heorku except that after checking the logs the following error appears:
2012-04-27T08:14:42+00:00 app[web.1]: django.core.exceptions.ImproperlyConfigure
d: Error loading either pysqlite2 or sqlite3 modules (tried in that order): No m
odule named _sqlite3
This also occurs when attempting to sync the database.
Here is the current configuration of the database in the settings.py file:
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.sqlite3', # Add 'postgresql_psycopg2', 'mysql', 'sqlite3' or 'oracle'.
'NAME': 'database.sqlite', # Or path to database file if using sqlite3.
'USER': '', # Not used with sqlite3.
'PASSWORD': '', # Not used with sqlite3.
'HOST': '', # Set to empty string for localhost. Not used with sqlite3.
'PORT': '', # Set to empty string for default. Not used with sqlite3.
}
}
I am aware is it a sqlite3 database, and I have been told that it should still allow heroku to deploy the app without any errors.
I have followed through using the following potential solutions that are related to this problem:
No module named _sqlite3
How do I set up SQLite with a Django project?
http://groups.google.com/group/django-users/browse_thread/thread/185f981f432346f1
Any help will be appreciated! Please let me know if additional Information is needed.
Heroku does not support sqlite, since it only provides a read-only filesystem.
I had the same error with the settings file. Looking through the Heroku logs, it turned out that my settings.py file was failing for various reasons. Once I fixed those issues, Django stopped complaining about missing database settings.
One of the things that caused this issue was a monkey patch I was using to allow sub-selects as tables in QuerySet extra(). This patch is at the end of my settings file.
# Override default behaviour of compiler to quote table names when table name is a sub-query
from django.db.models.sql.compiler import SQLCompiler
_quote_name_unless_alias = SQLCompiler.quote_name_unless_alias
SQLCompiler.quote_name_unless_alias = lambda self,name: name if name.startswith('(') else _quote_name_unless_alias(self,name)
This patch apparently requires that DATABASES already be correctly specified at that point. Since Heroku appends the magic DATABASES configuration to the end of the settings file (i.e. after the monkey patch), I had to manually insert their configuration above my monkey patch.
Normally I would set the pool size as
development:
adapter: postgresql
encoding: unicode
database: openkitchen_development
username: rails
host: localhost
pool: 10
password:
in database.yml. However heroku replaces the config file. I'm using girl_friday to
do background db work and need to increase the thread pool size.
Simply add a pool query parameter to the DATABASE_URL in your heroku config. To set the pool size to 15 in your heroku app use something like:
heroku config -s | awk '/^DATABASE_URL=/{print $0 "?pool=15"}' | xargs heroku config:add
For what it's worth, using the URL params method as described in other answers here is not recommended by Heroku. They reserve the right to reset or change this URL at any time, and long term this behavior will likely be removed for the Rails build behavior, anyway.
Setting additional parameters via an after-initialize application callback is the recommended way to modify the configuration of your heroku-postgresql databases per this dev center article.
In config/initializers/database_connection.rb:
Rails.application.config.after_initialize do
ActiveRecord::Base.connection_pool.disconnect!
ActiveSupport.on_load(:active_record) do
config = Rails.application.config.database_configuration[Rails.env]
config['pool'] = 10
ActiveRecord::Base.establish_connection(config)
end
end
Heroku now has a nice article on managing pool sizes - https://devcenter.heroku.com/articles/concurrency-and-database-connections#connection-pool
remvee's answer gets to the heart of what is needed but since his command caused my console to hang I thought I would write up how to do this manually.
heroku config
Look for the DATABASE_URL key. For this example lets say it is:
DATABASE_URL: mysql2://something.example.com/stuff?reconnect=true
Add "&pool=10" to the end of the URL (use & instead of ? because the url already has a parameter)
heroku config:add DATABASE_URL=mysql2://something.example.com/stuff?reconnect=true&pool=10
It's not very straight forward but you could try creating your own buildpack.
You'll nee to fork:
https://github.com/heroku/heroku-buildpack-ruby
Then modify the following:
https://github.com/heroku/heroku-buildpack-ruby/blob/master/lib/language_pack/ruby.rb#L325-387
Just add the pool size you require.
Then you can create a new Heroku app with your custom buildpack:
heroku create --stack cedar --buildpack https://github.com/yourgithubusername/heroku-buildpack-ruby.git
That should be it!
This is just for my weekend project/study, I am very new to Sinatra and MongoDB.
I've installed the gems for mongoDB, such as: mongo, mongo_mapper and mongoid.
When I tried connecting to my database on MongoHQ from localhost, it encountered such an error:
Mongo::ConnectionFailure at /
failed to connect to any given host:port
* file: connection.rb
* location: connect
* line: 489
I found a similar thread on SO, but frankly speaking, I don't quite understand the answers...
Here is my code snippet:
require 'rubygems'
require 'sinatra'
require 'mongo'
require 'mongo_mapper'
get '/' do
MongoMapper.connection = Mongo::Connection.new('flame.mongohq.com', 27044)
MongoMapper.database = 'notes'
MongoMapper.database.authenticate('foo', 'bar')
erb :list
end
I took the above code from here, but it seems not working...
Which part is wrong? Is there another way to do this? In the end this test web app will be deployed onto heroku, so I hope the solution can work with both localhost and my heroku server.
Updated:
I just created a minimal code snippet to test the mongodb connection:
require 'rubygems'
require 'mongo'
db = Mongo::Connection.new("flame.mongohq.com", 27044).db("notes")
But still got the error, after timeout:
$ ruby mongodbtest.rb
/Library/Ruby/Gems/1.8/gems/mongo-1.0.8/lib/../lib/mongo/connection.rb:489:in
`connect': failed to connect to any given host:port (Mongo::ConnectionFailure)
from /Library/Ruby/Gems/1.8/gems/mongo-1.0.8/lib/../lib/mongo/connection.rb:137:in
`initialize'
from mongodbtest.rb:4:in `new'
from mongodbtest.rb:4
The hostname and port are according to mongoHQ documentation, so they must be right.
Thanks for the help in advance.
2nd Update:
I just tested the mongodb connection string using terminal:
mongo mongodb://flame.mongohq.com:27044/notes -u foo -p bar
Unfortunately this would get me an connection failed error, honestly, I don't know why...
I use
uri = URI.parse(ENV['MONGOHQ_URL'])
#mongo_connection = Mongo::Connection.from_uri( uri )
#mongo_db = #mongo_connection.db(uri.path.gsub(/^\//, ''))
#mongo_db.authenticate(uri.user, uri.password)
You can look up your mongo url using the heroku config --long command
Just gave this another try, this time, I was using the ip address taken from ping:
So, if I change :
db = Mongo::Connection.new('flame.mongohq.com', 27060).db("notes")
db.authenticate('fake', 'info')
To:
db = Mongo::Connection.new('184.73.224.5', 27060).db("notes")
db.authenticate('fake', 'info')
That will work...
I still don't understand why the domain name approach won't work, but at least I can finish this off :)