Why are my validations not working in rails app? (Daniel Kehoe's Learn Rails Tutorial Book)

81 Views Asked by At

I am on chapter 19 of the learn rails book by Daniel Kehoe and have created a form. However when I deliberately make errors in order to test the validations no messages appear. for example when I submit an empty form it simply renders a new form without the error message and when I enter an incorrect email address, without '@' again it seems to accept my inputs with no errors. so my question is why are the validations not raising any error messages?

here is my model contact.rb

class Contact
    include ActiveModel::Model
    attr_accessor :name, :email, :content

    validates_presence_of :name
    validates_presence_of :email
    validates_presence_of :content
    validates_format_of :email,
        with: /\A[-a-z0-9_+\.]+\@([-a-z0-9]+\.)+[a-z0-9]{2,4}\z/i
    validates_length_of :content, :maximum => 500
end

application layout application.html.erb

<!DOCTYPE html>
<html>
  <head>
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title><%= content_for?(:title) ? yield(:title) : "Workspace" %></title>
    <meta name="description" content="<%= content_for?(:description) ? yield(:description) : "Workspace" %>">
    <%= stylesheet_link_tag 'application', media: 'all', 'data-turbolinks-track' => 'reload' %>
    <%= javascript_include_tag 'application', 'data-turbolinks-track' => 'reload' %>
    <%= csrf_meta_tags %>
  </head>
  <body>
    <header>
      <%= render 'layouts/navigation' %>
    </header>
    <main role="main">
      <%= render 'layouts/messages' %>
      <%= yield %>
    </main>
  </body>
</html>

form view new.html.erb

<% content_for :title do %>Contact<% end %>
<h3>Contact</h3>
<div class="form">
    <%= form_with(model: @contact) do |form| %>
        <%= form.label :name %>
        <%= form.text_field :name, autofocus: true %>
        <br/>
        <br/>
        <%= form.label :email %>
        <%= form.email_field :email %>
        <br/>
        <br/>
        <%= form.label 'message' %>
        <%= form.text_area :content, size: '40x5' %>
        <br/>
        <br/>
        <%= form.submit 'Submit', class: 'submit' %>
    <% end %>
</div>

contacts_controller.rb

    class ContactsController < ApplicationController

  def new
  @contact = Contact.new
  end

  def create
    @contact = Contact.new(secure_params)
    if @contact.valid?
      # TODO send message
      flash[:notice] = "Message sent from #{@contact.name}."
      redirect_to root_path
    else
      render :new
    end
  end

  private
    def secure_params
      params.require(:contact).permit(:name, :email, :content)
    end
end

layout helper _messages.html.erb

<%# Rails flash messages styled for Bootstrap 3.0 %>
<% flash.each do |name, msg| %>
  <% if msg.is_a?(String) %>
    <div class="alert alert-dismissible alert-<%= name.to_s == 'notice' ? 'success' : 'danger' %>">
      <button type="button" class="close" data-dismiss="alert" aria-hidden="true">&times;</button>
      <%= content_tag :div, msg, :id => "flash_#{name}" %>
    </div>
  <% end %>
<% end %>

EDIT 1:

The validations seem to work when I create a new contact in the console manually. But the app is not validating them when created through the app form. see below for my experiment with creating a new contact.

2.3.4 :002 > c=Contact.new
 => #<Contact:0x000000055741a8> 
2.3.4 :003 > c
 => #<Contact:0x000000055741a8> 
2.3.4 :004 > c.name='biggles2'
 => "biggles2" 
2.3.4 :005 > c
 => #<Contact:0x000000055741a8 @name="biggles2"> 
2.3.4 :006 > c.valid?
 => false 
2.3.4 :007 > c.email='[email protected]'
 => "[email protected]" 
2.3.4 :008 > c
 => #<Contact:0x000000055741a8 @name="biggles2", @validation_context=nil, @errors=#<ActiveModel::Errors:0x0000000554a948 @base=#<Contact:0x000000055741a8 ...>, @messages={:email=>["can't be blank", "is invalid"], :content=>["can't be blank"]}, @details={:email=>[{:error=>:blank}, {:error=>:invalid, :value=>nil}], :content=>[{:error=>:blank}]}>, @email="[email protected]"> 
2.3.4 :009 > c.email
 => "[email protected]" 
2.3.4 :010 > c.name
 => "biggles2" 
2.3.4 :011 > c.content='this is some content and its not too long'
 => "this is some content and its not too long" 
2.3.4 :012 > c.valid?
 => true 
2.3.4 :013 > c
 => #<Contact:0x000000055741a8 @name="biggles2", @validation_context=nil, @errors=#<ActiveModel::Errors:0x0000000554a948 @base=#<Contact:0x000000055741a8 ...>, @messages={}, @details={}>, @email="[email protected]", @content="this is some content and its not too long"> 
0

There are 0 best solutions below