Action Mailer Basics
Send eails using mailer classes and views
Class inherit from ActionMailer::Base and live in app/mailers
Mailers are conceptually similar to controllers
Steps
1. Create the mailer
$ rails generate mailer UserMailer
user_mailer.rb created
class UserMailer < ActionMailer::Base
default from: 'from@example.com' <-- br="" default="" from=""> end 2. It is possible jusst to create the Mailer in app/mailers class MyMailer < ActionMailer::Base end 3. Add a method called welcome def welcome_email(user) @user = user @url = 'http://example.com/login' mail(to: @user.email, subject: 'Welcome to My Awesome Site') end 4. Create the views/user_mailer/welcome.html.erb
Welcome to example.com, <%= @user.name %>
You have successfully signed up to example.com, your username is: <%= @user.login %>.
To login to the site, just follow this link: <%= @url %>.
Thanks for joining and have a great day!
4.1 It is possible to create a text(non html) file too. welcome_email.text.erb With method webcome_email, rails will automatically render both html and text files. 5. In method create of UsersController if @user.save # Tell the UserMailer to send a welcome Email after save UserMailer.welcome_email(@user).deliver
Working with JavaScript in Rails
Unobtrusive JavaScript
Jaav uses a "Unobtrusive javaScript" technique
EX:
< a href="#" data-background-color="#990000">Paint it red< /a>
data-background is called in unobtrusive way because there is no mix between JavaScript and HTML
Call:
paintIt = (element, backgroundColor, textColor) ->
element.style.backgroundColor = backgroundColor
if textColor?
element.style.color = textColor
in CoffeScript, uses
$ -> $("a[data-remote]").on "ajax:success", (e, data, status, xhr) -> alert "The post was deleted."
or in directly
<%= link_to "delete", account, method: :delete, data: { confirm: "You sure?" } %>
button_to
<%= button_to "A post", @post, remote: true %>
The server side
Usually, AJAX requests return JSON rather than HTML
Controller
class UsersController < ApplicationController
def index
@users = User.all
@user = User.new
end
def create
@user = User.new(params[:user])
respond_to do |format|
if @user.save
format.html { redirect_to @user, notice: 'User was successfully created.' }
format.js {}
format.json { render json: @user, status: :created, location: @user }
else
format.html { render action: "new" }
format.json { render json: @user.errors, status: :unprocessable_entity }
end
end
end
index.html.erb
< b >Users< /b >
< ul id="users"> <----- appendto="" br="" fill="" here="" in="" js="" the="" will=""> <% @users.each do |user| %> <%= render user %> <----- _user.html.erb="" br="" render="" the=""> <% end %> < /ul >
<%= f.text_field :name %> <%= f.submit %> <% end %> _user.html.erb < li ><%= user.name %>< /li > create.js.erb It is called by the method create. $("<%= escape_javascript(render @user) %>").appendTo("#users"); Turbolinks Uses AJAX to speed up page rendering in most applications It attaches a click handler to all < a > tags What to do Include turbolinks in Gemfile in app/assets/javascripts/application.js //= require turbolinks To disable turbolink < a href="..." data-no-turbolink>No turbolinks here< /a>.
The Purpose of the Rails Router Simple example: GET /patients/17 Route get '/patients/:id', to: 'patients#show'
Or get '/patients/:id', to: 'patients#show', as: 'patient' and your application contains this code in the controller: @patient = Patient.find(17) and this in the corresponding view: <%= link_to 'Patient Record', patient_path(@patient) %> Route will generate /patients/17 CRUD, Verbs, and Actions If declare resources :photos If creates 7 routes HTTP Verb Path GET /photos index GET /photos/new new POST /photos create GET /photos/:id show GET /photos/:id/edit edit PATCH/PUT /photos/:id update DELETE /photos/:id destroy Singular resources To call /profile route get 'profile', to: 'users#show'
A singular resourceful route generates these helpers: new_photo_path returns / photo /new edit_ photo _path returns / photo /edit photo _path returns / photo Controller Namespaces and routing It is possible to organize groups of controllers under a namespace EX: namespace : admin do resources :posts, :comments end It will create routes for post and comments . For Admin::PostController GET /admin/posts admin_post_path GET /admin/posts/new new_admin_post_path POST /admin/posts/:id admin_post_path(:id) etc Uses Admin::PostController without the prefix /admin, just declares: scope module: ‘admin’ do resources :posts, :comments end OR resources :posts, module:’admin’
To use /admin/post without admin in path. Scope ‘/admin’ do Resources :posts, :comments End Resources :posts, path: ‘/admin/posts’ GET /admin/posts posts_path GET /admin/posts/new new_post_path Nested Resources when there are resources that are children of others. Models: class Magazine < ActiveRecord::Base has_many :ads end end class Ad < ActiveRecord::Base belongs_to :magazine end Resources: resources :magazines do resources :ads end /magazines/:magazine_id/ads /magazines/:magazine_id/ads/new /magazines/:magazine_id/ads The url: edit_magazine_ad_path It is possible to nest 2 levels
resources :publishers do resources :magazines do resources :photos end end Calling: /publishers/1/magazines/2/photos/3 Paths and URLs From Objects resources :magazines do resources :ads end You can pass instances of magazines and ads <%= link_to 'Ad details', magazine_ad_path(@magazine, @ad) %> Or <%= link_to 'Ad details', url_for([@magazine, @ad]) %> Or <%= link_to 'Ad details', [@magazine, @ad] %> Rails will se magazines and ads and create the path. To call Edit <%= link_to 'Edit Ad', [:edit, @magazine, @ad] %> Adding More RESTful Actions Add Member Routes resources :photos do member do get 'preview' end end Provides: GET /photos/1/preview and preview_photo_url and preview_photo_path helpers
If working with
JSON, Rails convert automatically the parameters in parms hash.
Routing
parameters
Hash params always contains
:controller and :action keys
Strong
parameters
Action Controller parameters can
be used in Active Model mass assigments only after they pass through another
method(whitelisted). The params will be
chosen to be exposed.
Ex:
class
PeopleController < ActionController::Base
def
update
person =
current_account.people.find(params[:id])
person.update_attributes!(person_params)
redirect_to
person
end
private
def person_params
params.require(:person).permit(:name,
:age)
end
end
Session
Kinds of session:
ActionDispatch::Session::CookieStore
- Stores everything on the client.
ActionDispatch::Session::CacheStore
- Stores the data in the Rails cache.
ActionDispatch::Session::ActiveRecordStore
- Stores the data in a database using Active Record. (require
activerecord-session_store gem).
ActionDispatch::Session::MemCacheStore
- Stores the data in a memcached cluster
If you need a different session
storage mechanism, you can change it in the
config/initializers/session_store.rb file.