Resource namespace Issue in Rails Engine with ActiveAdmin - ruby-on-rails

I'm having a problem where I've successfully registered a resource in ActiveAdmin, but I can't create or update any records. I think it's due to a namespacing issue. Can I override it using an option while registering the resource?
I'm building a Rails Engine that registers AA resources from within the engine. I followed the instructions here.
My engine contains lib/admin/myengine/myresources.rb
if defined?(ActiveAdmin)
ActiveAdmin.register Myengine::Myresource do
end
end
In the test/dummy app, the relevant schema looks like:
create_table "myengine_myresources", force: :cascade do |t|
t.string "name"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
end
When I run the dummy app server, I successfully navigate to http://localhost:3000/admin/myengine_myresources and click 'New Myengine Myresource'
I type in a name and click 'Create Myresource', but it treats the request as if I've submitted blank attribute values.
The server log shows:
Started POST "/admin/myengine_myresources" for ::1 at 2015-12-02 11:13:52 -0800
Processing by Admin::MyengineMyresourcesController#create as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"stuff", "myresource"=>{"name"=>"Arbitrary Name"}, "commit"=>"Create Myresource"}
(0.1ms) begin transaction
(0.1ms) rollback transaction
Rendered /Users/me/.rvm/gems/ruby-2.2.3/gems/activeadmin-1.0.0.pre2/app/views/active_admin/resource/new.html.arb (190.7ms)
Completed 200 OK in 231ms (Views: 199.4ms | ActiveRecord: 0.2ms)
My working theory is that the params need to be inside :myengine_myresource rather than just :myresource.
Any ideas on how to get that working?

Here's one workaround:
if defined?(ActiveAdmin)
ActiveAdmin.register Myengine::Myeresource do
controller do
def permitted_params
params[:myengine_myresource] = params.delete :myresource
params.permit(myengine_myresource: [:my, :list, :of, :accepted, :params])
end
end
end
end

Related

How to debug simple RoR application

So far, to a very experienced Java EE developer with years of experience in many different languages, I am having real difficulties with Ruby on Rails. I am using: ruby 2.3.1p112 (2016-04-26 revision 54768) [x86_64-darwin15] and Rails 5.0.0. I am following a very simple on-line tutorial on building a private library web application, BUT, in order to learn something, instead of having Books with a linked table of Subjects, I changed Subjects to Authors since many books have the same authors. I am using SQLLite for development and MySQL for production( haven't gotten there yet! ). I find that when you follow exactly the directions in most tutorials, you end up with whatever application you were building. But, IF you deviate in any fashion, things just don't work and it's very hard to figure out what happened. You get error messages ( sometimes ) in the logs that you've got an undefined variable or constant. Normally, you would search for where that variable is used, then be sure you define it or spell it correctly. However, in RoR, that constant doesn't appear anywhere except in the log, if there. RoR, due to its conventions, has either created or assumed that you had such a variable, when in fact, you may have named a "view" folder in the singular instead of the plural. It "invented" a variable to point to that, but it didn't match the pattern, so it fails with very poor error messages.
The server doesn't complain, just does a rollback, and goes on. The log has some unmeaningful message, as per above. I end up spending hours trying different patterns for routes suggested by people, or renaming things, but it's all guesswork.
I enjoy working with frameworks and systems where I understand them. This seems to be a collection of different pieces which parse in yml, yaml, erb, rb, sass, haml, etc. I've tried logging, but to no avail. How do you located simple mistakes?
Here is my "books_controller.rb":
class BooksController < ApplicationController
def list
#books = Book.all
end
def show
#book = Book.find(params[:id])
end
def new
#book = Book.new
#authors = Author.all
end
def create
#book = Book.new(book_params)
if #book.save
logger.debug 'Redirecting to list'
redirect_to :action => 'list'
else
#authors = Author.all
render :action => 'new'
end
end
def edit
#book = Book.find(params[:id])
#authors = Author.all
end
def update
#book = Book.find(params[:id])
if #book.update_attributes(book_params)
redirect_to :action => 'show', :id => #book
else
#authors = Author.all
render :action => 'edit'
end
end
def delete
Book.find(params[:id]).destroy
redirect_to :action => 'list'
end
def show_authors
#author = Author.find(params[:id])
end
def book_params
params.require(:books).permit(:title, :description, :author_id)
end
end
The new.html.erb under app/views/books is:
<h1>Add new book</h1>
<%= form_tag :action => 'create' do %>
<p><label for = "book_title">Title</label>:
<%= text_field 'books', 'title' %></p>
<p><label for = "book_author_id">Author</label>:
<%= collection_select(:book, :author_id, #authors, :id, :name, prompt: true) %></p>
<p><label for = "book_description">Description</label><br/>
<%= text_area 'books', 'description' %></p>
<%= submit_tag "Create" %>
<% end -%>
<%= link_to 'Back', {:action => 'list'} %>
routes.rb is:
Rails.application.routes.draw do
# For details on the DSL available within this file, see http://guides.rubyonrails.org/routing.html
resources :books
#get 'books/list'
#post 'books/create'
#get 'books/new'
#patch 'books/update'
#get 'books/show'
#get 'books/edit'
#get 'books/delete'
get 'books/show_authors'
get 'authors/list'
post 'authors/create'
get 'authors/new'
patch 'authors/update'
get 'authors/show'
get 'authors/edit'
root :to => 'books#list'
end
When I try to add a new book, I enter the title, select an author, and put in a description and click "Create". It then just returns to the new screen. The console has:
Started GET "/books/new" for ::1 at 2016-08-04 17:18:22 -0400
Processing by BooksController#new as HTML
Rendering books/new.html.erb within layouts/application
Author Load (0.1ms) SELECT "authors".* FROM "authors"
Rendered books/new.html.erb within layouts/application (5.4ms)
Completed 200 OK in 26ms (Views: 21.6ms | ActiveRecord: 0.5ms)
Started POST "/books" for ::1 at 2016-08-04 17:18:28 -0400
Processing by BooksController#create as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"noRmEq8rHE6RLs0cPNrlZoQXq//2sr+SAOSHEFc0U3zqbSJZOSKDmdgwpdm5/nVswItHp4Ken0mjggt47ph46Q==", "books"=>{"title"=>"sdfasdf", "description"=>"asdfasdf"}, "book"=>{"author_id"=>"2"}, "commit"=>"Create"}
(0.1ms) begin transaction
(0.1ms) rollback transaction
Rendering books/new.html.erb within layouts/application
Author Load (0.1ms) SELECT "authors".* FROM "authors"
Rendered books/new.html.erb within layouts/application (2.0ms)
Completed 200 OK in 24ms (Views: 20.3ms | ActiveRecord: 0.2ms)
and the development log has:
Started GET "/books/new" for ::1 at 2016-08-04 17:18:22 -0400
Processing by BooksController#new as HTML
Rendering books/new.html.erb within layouts/application
[1m[36mAuthor Load (0.1ms)[0m [1m[34mSELECT "authors".* FROM "authors"[0m
Rendered books/new.html.erb within layouts/application (5.4ms)
Completed 200 OK in 26ms (Views: 21.6ms | ActiveRecord: 0.5ms)
Started POST "/books" for ::1 at 2016-08-04 17:18:28 -0400
Processing by BooksController#create as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"noRmEq8rHE6RLs0cPNrlZoQXq//2sr+SAOSHEFc0U3zqbSJZOSKDmdgwpdm5/nVswItHp4Ken0mjggt47ph46Q==", "books"=>{"title"=>"sdfasdf", "description"=>"asdfasdf"}, "book"=>{"author_id"=>"2"}, "commit"=>"Create"}
[1m[35m (0.1ms)[0m [1m[36mbegin transaction[0m
[1m[35m (0.1ms)[0m [1m[31mrollback transaction[0m
Rendering books/new.html.erb within layouts/application
[1m[36mAuthor Load (0.1ms)[0m [1m[34mSELECT "authors".* FROM "authors"[0m
Rendered books/new.html.erb within layouts/application (2.0ms)
Completed 200 OK in 24ms (Views: 20.3ms | ActiveRecord: 0.2ms)
Yes, the transaction was rolled back. WHY? How can I get information on what caused the database to "rollback"? The two tables in the database are:
class CreateBooks < ActiveRecord::Migration[5.0]
def change
create_table :books do |t|
t.string :title
t.integer :author_id
t.string :description
t.timestamp :created
t.timestamps
end
end
end
class CreateAuthors < ActiveRecord::Migration[5.0]
def change
create_table :authors do |t|
t.string :name
t.timestamps
end
end
end
class Book < ApplicationRecord
belongs_to :author
validates_presence_of :title
end
class Author < ApplicationRecord
has_many :books
end
I can create a book in rails console as:
b=Book.create :title=>'Test', :author_id=>1, :description=>'Desc'
(0.1ms) begin transaction
Author Load (0.1ms) SELECT "authors".* FROM "authors" WHERE "authors"."id" = ? LIMIT ? [["id", 1], ["LIMIT", 1]]
SQL (0.3ms) INSERT INTO "books" ("title", "author_id", "description", "created_at", "updated_at") VALUES (?, ?, ?, ?, ?) [["title", "Test"], ["author_id", 1], ["description", "Desc"], ["created_at", 2016-08-04 20:17:40 UTC], ["updated_at", 2016-08-04 20:17:40 UTC]]
(2.4ms) commit transaction
=> #<Book id: 1, title: "Test", author_id: 1, description: "Desc", created: nil, created_at: "2016-08-04 20:17:40", updated_at: "2016-08-04 20:17:40">
I would appreciate input and especially help on understanding why what happened actually happened. It seems that a very simple error is being made, but I can't see it.
------------------ Added after several answers and "guesses" by me.
I changed the form_tag to a form_for as I'll show below.
----new.html.erb------
<%= form_for(#book) do |f| %>
Title: <%= f.text_field :title %><br/>
Author: <%= select("book", "author_id", Author.all.collect{|p| [p.name,p.id]}, prompt: 'Select') %><br/>
Description: <%= f.text_area :description %><br/>
<%= f.submit "Create" %>
<% end -%>
<%= link_to 'Back', {:action => 'list'} %>
I get in the browser:
Validation failed: Author must exist, Title can't be blank
Extracted source (around line #18):
16
17
18
19
20
21
def create
#book = Book.new
if #book.save!
redirect_to :action => 'list'
else
#authors = Author.all
Rails.root: /Users/woo/Development/rails/library
Application Trace | Framework Trace | Full Trace
app/controllers/books_controller.rb:18:in `create'
Request
Parameters:
{"utf8"=>"✓",
"authenticity_token"=>"gi+wVGV3MIlkJsRjO8Ig1cS3YV/OIADSevFJg7ItBesokIiHFDThycTO8/kob+2E1fuPFquFUK+b7bGksWRZGQ==",
"book"=>{"title"=>"Book", "author_id"=>"2", "description"=>"test"},
"commit"=>"Create"}
As far as I can see, book does have a title, and an author_id, and a description. Why "Author must exist, Title can't be blank"?
Try using form_for instead of form_tag in your books/new view. This is the Rails way to create forms for model object.
Check a handy guide on form_for here.
How to debug ....
There are several tools to help debug a Rails application. One you have already discovered: the log file in log/development.log.
Another is Byebug. Add the gem to your Gemfile and insert the following in the create action after the 'else':
require 'byebug'
byebug
then post the form again. The development server will bring up a Byebug console where you can inspect local variables, instance variables, and the stack trace. Try inspecting:
#book.errors
When an ActiveRecord model fails to save it is usually because validations failed. Errors encountered when saving are added to the errors object on the model instance.
The reason for the failure is probably that the form is not passing the expected parameters. By convention, Rails expects attributes for the model to be in a hash where the key is the model name, so params[:book][:title], not params[:title]. See the documentation for the form_for helper for more info.
Thanks for the help. With your suggestions and a lot of guessing from ready various Google sites, I combined them and in the new.html.erb put form_for(#book), and then in the create method of books_controller.rb, I put #book - Book.new(book_params), where book_params is:
def book_params
params.require(:book).permit(:title, :author_id, :description)
end
I'm guessing that this is to handle the strong attribution required by Rails 4 and up. Before I had books as the first argument and since it existed, but book was not filled, I got the weird error. After using form_for with #book as an argument, that set the values from the form into the book hash. Then the params.require with :book as the first argument, looked in that hash to extract title, author_id, and description.
Again, many thanks for the help and I learned about bye bug and save! and so forth. I find information is very sketchy and ofter the version is not mentioned, thus leading one astray many times.

Rails - Options saving into DB (onchange)

I'm trying to save options to DB.
Getting this in DB while saving in console:
Right selected value: "result"=>"1" its 1-4
Right value of updating id: "id"=>"4" its 1-100
I'll appreciate any advice or help with that, trying to figured out for couple hours.
But still getting this error:
CONSOLE
Started POST "/update_result/4" for 65.200.165.210 at 2016-05-03 22:42:16 +0000
Cannot render console from 65.200.165.210! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by DashboardController#update_result as JS
Parameters: {"utf8"=>"✓", "bitbucket"=>{"result"=>"1"}, "id"=>"4"}
Bitbucket Load (0.5ms) SELECT "bitbuckets".* FROM "bitbuckets" WHERE "bitbuckets"."id" = ? LIMIT 1 [["id", 4]]
(0.1ms) begin transaction
(0.2ms) rollback transaction
Completed 500 Internal Server Error in 34ms (ActiveRecord: 0.8ms)
ArgumentError (When assigning attributes, you must pass a hash as an argument.):
app/controllers/dashboard_controller.rb:13:in `update_result'
Rendered /usr/local/rvm/gems/ruby-2.3.0/gems/actionpack-4.2.5/lib/action_dispatch/middleware/templates/rescues/_source.erb (12.0ms)
Rendered /usr/local/rvm/gems/ruby-2.3.0/gems/actionpack-4.2.5/lib/action_dispatch/middleware/templates/rescues/_trace.text.erb (5.9ms)
Rendered /usr/local/rvm/gems/ruby-2.3.0/gems/actionpack-4.2.5/lib/action_dispatch/middleware/templates/rescues/_request_and_response.text.erb (1.7ms)
Rendered /usr/local/rvm/gems/ruby-2.3.0/gems/actionpack-4.2.5/lib/action_dispatch/middleware/templates/rescues/diagnostics.text.erb (183.9ms)
ROUTES
post 'update_result/:id', to: 'dashboard#update_result', as: :update_result
CONTROLLER
def update_result
#result = Bitbucket.find(params[:id])
#result.update_attributes(params[:result])
end
FORM IN VIEW
<%= form_for(commit, url: update_result_path(commit), :method => :post, :remote => true) do |r| %>
<%= r.select :result, [['Waiting', 1], ['Success', 2], ['Broken - Not Submitted', 3], ['Broken - Quick Win', 4]], { selected: commit.result }, { onclick: "$(this).parent('form').submit();" } %>
<% end %>
DB MIGRATION
create_table :bitbuckets do |t|
t.string :name
t.text :message
t.text :date
t.datetime :remain, :null => false, :default => Time.now
t.integer :assignee
t.integer :result
t.timestamps null: false
end
Solved by adding private function in controller:
CONTROLLER
def update_result
#result = Bitbucket.find(params[:id])
#result.update_attributes(update_params)
end
private
def update_params
params.require(:bitbucket).permit(:result)
end

Rails: def create does not add data to table using Rest

I want to add data to table through rest api with url: localhost:3000/api/v1/shoppinglists#create?grocery=fruits
I have created a model already, my controller is located under api/v1/shoppinglists_controller.rb and the code for that is:
shoppinglists_controller.rb:
module Api
module V1
class ShoppinglistsController < ApplicationController
def index
shop = Shoppinglist.all
render json: shop.to_json
end
def create
#tst = Shoppinglist.create(grocery: params[:grocery])
end
end
end
end
routes.rb:
Rails.application.routes.draw do
namespace :api do
namespace :v1 do
get '/shoppinglists' => 'shoppinglists#index'
post '/shoppinglists' => 'shoppinglists#create'
end
end
end
Model-migration: shoppinglist.rb:
class CreateShoppinglists < ActiveRecord::Migration
def change
create_table :shoppinglists do |t|
t.integer :shopid
t.string :type
t.string :grocery
t.string :status
t.timestamps null: false
end
end
end
By default, def index gets triggered but when I do: localhost:3000/api/v1/shoppinglist#create?grocery=fruits then I check on commandline, I still see:
Started GET "/api/v1/shoppinglists" for ::1 at 2015-06-23 23:59:06 -0400
Processing by Api::V1::ShoppinglistsController#index as HTML
Shoppinglist Load (0.3ms) SELECT "shoppinglists".* FROM "shoppinglists"
Completed 200 OK in 44ms (Views: 0.2ms | ActiveRecord: 0.4ms)
and my table is empty. There are 2 problems:
I dont understand why still index is getting triggered and how can I make def create to actually insert value in grocery column through rest api.
[Solved] I used a client called Postman to solve this problem but still facing problem (2) as all null values are entered in my table and not the one being entered through url. My command line logs now say [logs]
Once it gets triggered then is my code right for "create" def?
[Solved] Issue was with the way I was sending values through post. I had to add values to form-data tab (key,val) in Postman instead of through url for it to work
[logs]
Started POST "/api/v1/shoppinglists" for ::1 at 2015-06-24 01:03:44 -0400
Processing by Api::V1::ShoppinglistsController#create as */*
Can't verify CSRF token authenticity
(0.2ms) begin transaction
SQL (0.3ms) INSERT INTO "shoppinglists" ("created_at", "updated_at") VALUES (?, ?) [["created_at", "2015-06-24 05:03:44.714945"], ["updated_at", "2015-06-24 05:03:44.714945"]]
(8.2ms) commit transaction
Completed 200 OK in 12ms (ActiveRecord: 8.7ms)
Create action requires a POST request and when you visit localhost:3000/api/v1/shoppinglist#create?grocery=fruits in a browser, it sends a GET request instead of a POST request, treating it as a URI and hence triggering index action. To send a POST request you can use CURL command in terminal or httparty
curl -H 'Content-Type: application/json'-H 'Accept: application/json' -X POST http://localhost:3000/api/v1/shoppinglists -d {"grocery": "fruits"}
where -H refers to the headers set in request and -X is for changing default GET verb and -d is for the data that you want to send. For details refer to curl

What is the "Views" referring to in: Completed 200 OK in 989ms (Views: 968.5ms | ActiveRecord: 13.9ms)

I have an action that looks like this:
def facebook_login
render json: {users:User.all}
end
My local server running on a MacBook Pro Early 2013 outputs this:
Completed 200 OK in 989ms (Views: 968.5ms | ActiveRecord: 13.9ms)
Heroku outputs this for the same API call:
Completed 200 OK in 3849ms (Views: 3782.6ms | ActiveRecord: 49.4ms)
The Users table contains 3000 records.
This is the schema of the users table:
create_table "users", force: :cascade do |t|
t.string "email"
t.string "first_name"
t.string "last_name"
t.string "gender"
t.string "birthday"
t.string "bio"
t.string "facebook_id"
t.string "avatar"
t.string "password_digest"
t.string "auth_token"
t.boolean "admin", default: false, null: false
end
My log from the rails server:
Started POST "/facebook_login.json" for 192.168.1.7 at 2015-07-06 03:39:07 -0400
Cannot render console from 192.168.1.7! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255
Processing by HomeController#facebook_login as JSON
Parameters: {"avatar"=>"https://fbcdn-profile-a.akamaihd.net/hprofile-ak-xpa1/v/t1.0-1/10891984_10100428479784882_2780393036688516385_n.jpg?oh=b745f67a9aa8f12eeb283962473bade0&oe=5621674B&__gda__=1444484154_c3db5d55964941a930530b70aa6ef44c", "first_name"=>"Tara", "bio"=>"", "last_name"=>"Lloyd", "birthday"=>"07/08/1985", "email"=>"tlloyd07#gmail.com", "facebook_id"=>"10100528233672292", "auth_token"=>"750435390234913", "home"=>{"avatar"=>"https://fbcdn-profile-a.akamaihd.net/hprofile-ak-xpa1/v/t1.0-1/10891984_10100428479784882_2780393036688516385_n.jpg?oh=b745f67a9aa8f12eeb283962473bade0&oe=5621674B&__gda__=1444484154_c3db5d55964941a930530b70aa6ef44c", "first_name"=>"Tara", "bio"=>"", "last_name"=>"Lloyd", "birthday"=>"07/08/1985", "email"=>"tlloyd07#gmail.com", "facebook_id"=>"10100528233672292", "auth_token"=>"750435390234913"}}
User Load (13.6ms) SELECT "users".* FROM "users"
Completed 200 OK in 989ms (Views: 968.5ms | ActiveRecord: 13.9ms)
I'm building a Rails App that pulls data from a database and returns a json. There are no images or views to be rendered. Why is the "Views" above almost one second (4 seconds on Heroku) while the ActiveRecord is only 14ms? What is this "Views" doing? All this API call is reading back 3000 records from the Users table, so why is so much time being spent on "Views"? Am I missing something?
I tried doing config.cache_classes = true in my environments/development.rb but it didn't change anything.
Also, I don't understand why I've been given six points off for this question. Did I offend anyone but insinuating that Rails is slow?
EDIT:
After replacing
render json: {users:User.all}
with:
render json: MultiJson.dump({users:User.all})
I see this in the Heroku logs:
Completed 200 OK in 5223ms (Views: 0.3ms | ActiveRecord: 57.6ms)
However, 0.3ms + 57.5ms does NOT equal 5223ms, so what are those other five seconds spent on?
After a lot of work and investigation, I've learned that rendering json in Rails is always going to be much slower than doing it in the database. Thus the solution is to bypass ActiveRecord and write direct SQL queries to Postgres:
res = []
res << ActiveRecord::Base.connection.execute("select listings from listings;")
res << ActiveRecord::Base.connection.execute("select users from users;")
render json: MultiJson.dump(res)
Following this I am seeing a 10x improvement in performance and speed:
Started GET "/listings.json?data=(%0A%20%20%20%20settings,%0A%20%20%20%20listings,%0A%20%20%20%20users%0A)" for 192.168.1.7 at 2015-07-07 00:27:33 -0400
Processing by HomeController#listings as JSON
Parameters: {"data"=>"(\n settings,\n listings,\n users\n)", "home"=>{}}
(24.4ms) select listings from listings;
(9.3ms) select users from users;
Completed 200 OK in 200ms (Views: 0.1ms | ActiveRecord: 33.7ms)

Contact form: error on seeding and error messages of the form don't work properly

The app I'm building includes a contact form. On seeding it generates an error message that I don't understand:
ActiveRecord::StatementInvalid: PG::NotNullViolation: ERROR: null value in column "name" violates not-null constraint
DETAIL: Failing row contains (1, null, null, null, 2015-06-06 13:43:12.339477, 2015-06-06 13:43:12.339477).
: INSERT INTO "messages" ("created_at", "updated_at") VALUES ($1, $2) RETURNING "id"
Below is the relevant code for the form. If I remove the line attr_accessor :name, :email, :content from the model file it succesfully seeds (I have no idea why this makes a difference for seeding). But even then on the development server, if I go to the contact form and submit without any values, the error messages don't seem to function properly. No matter the error it just gives a single error message "An error occurred while delivering this message", while for all other forms, the error message specifies the variable(s) and type of error. What could be causing this behavior?
The model file for the contact form:
class Message < ActiveRecord::Base
attr_accessor :name, :email, :content
validates :name, presence: true,
length: { maximum: 255 }
VALID_EMAIL_REGEX = /\A[\w+\-.]+#[a-z\d\-]+(\.[a-z\d\-]+)*\.[a-z]+\z/i
validates :email, presence: true,
length: { maximum: 255 },
format: { with: VALID_EMAIL_REGEX }
validates :content, presence: true,
length: { maximum: 600 }
end
The migration file includes:
t.string :name, null: false, limit: 255
t.string :email, null: false, limit: 255
t.string :content, null: false, limit: 600
In my seeds file I have:
Message.create!(email: "example#example.com",
name: "Example User",
content: "This is my message")
Update: Regarding the error message, I have the following controller method:
def create
#message = Message.new(message_params)
if #message.valid?
MessageMailer.new_message(#message).deliver_now
flash[:success] = "Your messages has been sent."
redirect_to contact_path
else
flash[:alert] = "An error occurred while delivering this message."
render 'new'
end
end
I removed the flash alert line. Other forms that I have that do function properly, don't have this line either and I though this flash message might be overwriting the other, more specific error messages. After removing this line and submitting invalid information, the form just makes the invalid fields red but shows no error messages at all. In other forms I would for example get these kinds of error messages:
The form contains 5 errors.
Email can't be blank
Email is invalid
Username can't be blank
Username is too short (minimum is 6 characters)
Username is invalid
The log file is:
Started GET "/contact" for xx.xxx.xx.xxx at 2015-06-06 14:15:43 +0000
ActiveRecord::SchemaMigration Load (0.5ms) SELECT "schema_migrations".* FROM "schema_migrations"
Processing by MessagesController#new as HTML
Rendered messages/new.html.erb within layouts/application (493.2ms)
Rendered layouts/_shim.html.erb (0.4ms)
Rendered layouts/_header.html.erb (10.5ms)
Rendered layouts/_footer.html.erb (0.8ms)
Completed 200 OK in 1454ms (Views: 1429.3ms | ActiveRecord: 3.1ms)
Started POST "/contact" for xx.xxx.xx.xxx at 2015-06-06 14:15:49 +0000
Processing by MessagesController#create as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"zAxxxSKMYKey/jxmqqvxxxr***43g2Ud9r6SQ==", "message"=>{"name"=>"", "email"=>"", "content"=>""}, "commit"=>"Send"}
Rendered messages/new.html.erb within layouts/application (7.3ms)
Rendered layouts/_shim.html.erb (0.1ms)
Rendered layouts/_header.html.erb (3.2ms)
Rendered layouts/_footer.html.erb (0.3ms)
Completed 200 OK in 849ms (Views: 844.9ms | ActiveRecord: 0.0ms)
Adding attr_accessor :name is equivalent to the following code
def name
#name
end
def name=(val)
#name = val
end
So if you have a column named name in your database, it will not be written. That is what happens here. Since you set those columns to be null: false, postgres raises an error if they are null.

Resources