Screencast: Einführung in Draper

Draper ist ein gem mit dem das Decorator Pattern auf domain-getriebene Modelle auf einfache Weise angewendet werden kann. Dabei werden die meisten Helfer in ein objekt-orientieren Ansatz umgewandelt, Filter auf dem Presentation-Layer ermöglicht und eine Schnittstelle zwischen den Controllern und Views zur Verfügung gestellt. Ryan zeigt in diesem Screencast wie es installiert, konfiguriert und benutzt wird.

 

Downloads in verschiedenen Formaten:

mp4
m4v
webm
ogg

 

Resourcen:

bash

[bash]
rails g draper:decorator user
[/bash]

Gemfile

[ruby]
gem ‚draper‘
[/ruby]

app/decorators/user_decorator.rb

[ruby]
class UserDecorator < ApplicationDecorator
decorates :user
allows :username

def avatar
site_link h.image_tag("avatars/#{avatar_name}", class: "avatar")
end

def linked_name
site_link(model.full_name.present? ? model.full_name : model.username)
end

def website
handle_none model.url do
h.link_to model.url, model.url
end
end

def twitter
handle_none model.twitter_name do
h.link_to model.twitter_name, "http://twitter.com/#{model.twitter_name}"
end
end

def bio
handle_none model.bio do
markdown(model.bio)
end
end

def member_since
model.created_at.strftime("%B %e, %Y")
end

private

def handle_none(value)
if value.present?
yield
else
h.content_tag :span, "None given", class: "none"
end
end

def site_link(content)
h.link_to_if model.url.present?, content, model.url
end

def avatar_name
if model.avatar_image_name.present?
model.avatar_image_name
else
"default.png"
end
end
end
[/ruby]

app/decorators/application_decorator.rb

[ruby]
class ApplicationDecorator < Draper::Base
def markdown(text)
Redcarpet.new(text, :hard_wrap, :filter_html, :autolink).to_html.html_safe
end
end
[/ruby]

app/controllers/users_controller.rb

[ruby]
def show
@user = UserDecorator.find(params[:id])
end
[/ruby]

users/show.html.erb

[html]
<div id="profile">
<%= @user.avatar %>
<h1><%= @user.linked_name %></h1>
<dl>
<dt>Username:</dt>
<dd><%= @user.username %></dd>
<dt>Member Since:</dt>
<dd><%= @user.member_since %></dd>
<dt>Website:</dt>
<dd><%= @user.website %></dd>
<dt>Twitter:</dt>
<dd><%= @user.twitter %></dd>
<dt>Bio:</dt>
<dd><%= @user.bio %></dd>
</dl>
</div>
[/html]

Screencast: Tests mit Spork beschleunigen

Ab einer bestimmten Größe können die Testläufe die Entwicklung „verlangsamen“. Spork ist kann in diesem Fall Abhilfe schaffen, indem es die Ladezeiten verbessert. In Verbindung mit Guard bekommt man so schneller Rückmeldung über den aktuellen Stand. Ryan zeigt in diesem Screencast wie Spork eingesetzt werden kann.

 

Downloads in verschiedenen Formaten:

mp4
m4v
webm
ogg

 

Resourcen:

bash

[bash]
rspec .
time rspec .
bundle
spork –bootstrap
spork
rspec . –drb
guard init spork
[/bash]

Gemfile

[ruby]
group :test do
gem "spork", "> 0.9.0.rc"
gem "guard-spork"
end
[/ruby]

Guardfile

[ruby]
guard ’spork‘, :cucumber_env => { ‚RAILS_ENV‘ => ‚test‘ }, :rspec_env => { ‚RAILS_ENV‘ => ‚test‘ } do
watch(‚config/application.rb‘)
watch(‚config/environment.rb‘)
watch(%r{^config/environments/.+.rb$})
watch(%r{^config/initializers/.+.rb$})
watch(’spec/spec_helper.rb‘)
watch(%r{^spec/support/.+.rb$})
end

guard ‚rspec‘, :version => 2, :cli => "–drb", :all_on_start => false, :all_after_pass => false do
# …
end
[/ruby]

spec/spec_helper.rb

[ruby]
require ‚rubygems‘
require ’spork‘

Spork.prefork do
# …
RSpec.configure do |config|
# …
config.treat_symbols_as_metadata_keys_with_true_values = true
config.filter_run :focus => true
config.run_all_when_everything_filtered = true
end
end

Spork.each_run do
# This code will be run each time you run your specs.
FactoryGirl.reload
end
[/ruby]

Screencast: Administrationsfläche über Active Admin

Fast jede Applikation benötigt eine Administrationsfläche, mit der Werte angepasst und Texte verwaltet werden können. Active Admin bringt diese Möglichkeit der Verwaltung für Rails Applikationen mit und sieht obendrein auch nett aus. Ryan zeigt in diesem Screencast wie es installiert und benutzt wird.

 

Downloads in verschiedenen Formaten:

mp4
m4v
webm
ogg

 

Resourcen:

bash

[bash]
bundle rails g active_admin:install rake db:migrate rails g active_admin:resource product
[/bash]

Gemfile

[ruby]
gem ‚activeadmin‘
[/ruby]

app/admin/products.rb

[ruby]
ActiveAdmin.register Product do scope :unreleased index do column :name column :category column "Release Date", :released_at column :price, :sortable => :price do |product| div :class => "price" do number_to_currency product.price end end default_actions end end
[/ruby]

app/admin/dashboards.rb

[ruby]
ActiveAdmin::Dashboards.build do section "Recent Products" do table_for Product.order("released_at desc").limit(5) do column :name do |product| link_to product.name, [:admin, product] end column :released_at end strong { link_to "View All Products", admin_products_path } end end
[/ruby]

app/assets/stylesheets/application.css.scss

[css]
@import "products";
[/css]

config/initializers/active_admin.rb

[ruby]
config.site_title = "Ryan’s Store"
[/ruby]

Screencast: Pry in Rails verwenden

Pry ist eine Alternative zu IRB und bringt einige interessante Features und Funktionen mit. Ryan zeigt diese Woche wie es in Kombination mit Rails eingesetzt werden kann.

 

Downloads in verschiedenen Formaten:

source code
mp4
m4v
webm
ogv

 

Resourcen:

bash

[bash]
gem install pry pry-doc
rvm gemset use global
pry
pry -r ./config/environment
[/bash]

pry

[bash]
help
cd Article
cd first
cd name
nesting
exit
ls
ls -h
ls -m
ls -M
ls Array -M
show-doc Article#in_groups_of
show-doc all
show-doc all.in_groups_of
show-method all.in_groups_of
edit-method all.in_groups_of
.ls
.cat Gemfile
[/bash]

Gemfile

[ruby]
gem ‚pry‘, :group => :development
[/ruby]

models/article.rb

[ruby]
binding.pry
[/ruby]

Screencast: Suchen mit Sunspot

Sunspot ist ein Gem mit dem Solr, eine auf Java basierende, schnelle und mächtige Such-Platform, aus Ruby-Applikationen heraus benutzt werden kann. Der Screencast dieser Woche zeigt wie es installiert wird und verschiedene Suchoperationen durchgeführt werden können.

 

Downloads in verschiedenen Formaten:

source code
mp4
m4v
webm
ogv

 

Resourcen:

bash

[bash]
bundle
rails g sunspot_rails:install
rake sunspot:solr:start
rake sunspot:reindex
[/bash]

Gemfile

[ruby]
gem ’sunspot_rails‘
[/ruby]

models/article.rb

[ruby]
searchable do
text :name, :boost => 5
text :content, :publish_month
text :comments do
comments.map(&:content)
end
time :published_at
string :publish_month
end

def publish_month
published_at.strftime("%B %Y")
end
[/ruby]

articles_controller.rb

[ruby]
def index
@search = Article.search do
fulltext params[:search]
with(:published_at).less_than(Time.zone.now)
facet(:publish_month)
with(:publish_month, params[:month]) if params[:month].present?
end
@articles = @search.results
end
[/ruby]

articles/index.html.erb

[html]
<%= form_tag articles_path, :method => :get do %>
<p>
<%= text_field_tag :search, params[:search] %>
<%= submit_tag "Search", :name => nil %>
</p>
<% end %>

<div id="facets">
<h3>Published</h3>
<ul>
<% for row in @search.facet(:publish_month).rows %>
<li>
<% if params[:month].blank? %>
<%= link_to row.value, :month => row.value %> (<%= row.count %>)
<% else %>
<strong><%= row.value %></strong> (<%= link_to "remove", :month => nil %>)
<% end %>
</li>
<% end %>
</ul>
</div>
[/html]

Screencast: Geocoder

Geocoder ist ein Ruby-Gem mit welchem man geografischen Daten nutzen, Koordination finden, Abstände zwischen Orten und mehr in Ruby und Rails einsetzen kann. Ryan zeigt diese Woche wie es installiert und in einer Rails-App verwendet wird.

 

Downloads in verschiedenen Formaten:

source code
mp4
m4v
webm
ogv

 

Resourcen:

bash

[bash]
rails g nifty:scaffold location address:string latitude:float longitude:float
rake db:migrate
bundle
[/bash]

Gemfile

[ruby]
gem ‚geocoder‘
[/ruby]

models/location.rb

[ruby]
geocoded_by :address
after_validation :geocode, :if => :address_changed?
[/ruby]

locations_controller.rb

[ruby]
def index
if params[:search].present?
@locations = Location.near(params[:search], 50, :order => :distance)
else
@locations = Location.all
end
end
[/ruby]

locations/show.html.erb

[html]
<%= image_tag "http://maps.google.com/maps/api/staticmap?size=450×300&sensor=false&zoom=16&markers=#{@location.latitude}%2C#{@location.longitude}" %>

<h3>Nearby locations</h3>
<ul>
<% for location in @location.nearbys(10) %>
<li><%= link_to location.address, location %> (<%= location.distance.round(2) %> miles)</li>
<% end %>
</ul>
[/html]

locations/index.html.erb

[html]
<%= form_tag locations_path, :method => :get do %>
<p>
<%= text_field_tag :search, params[:search] %>
<%= submit_tag "Search Near", :name => nil %>
</p>
<% end %>
[/html]

Screencast: Markdown mit Redcarpet

Markdown ist eine vereinfachte Möglichkeit beliebige Texte in HTML umzuwandeln. Dabei wird eine Syntax benutzt die es erlaubt verschiedene HTML Elemente durch Verwendung von Schlüsselwörter und Einrückungen zu erzeugen. Ryan zeigt diese Woche wie Redcarpet dafür eingesetzt werden kann und zusätzlich wie Syntaxhighlighting für Quellcode-Texte eingebunden wird.

 

Downloads in verschiedenen Formaten:

source code
mp4
m4v
webm
ogv

 

Resourcen:

bash

[bash]
sudo easy_install pygments
[/bash]

Gemfile

[ruby]
gem ‚redcarpet‘
gem ‚albino‘
gem ’nokogiri‘
[/ruby]

application_helper.rb

[ruby]
def markdown(text)
options = [:hard_wrap, :filter_html, :autolink, :no_intraemphasis, :fenced_code, :gh_blockcode]
syntax_highlighter(Redcarpet.new(text, *options).to_html).html_safe
end

def syntax_highlighter(html)
doc = Nokogiri::HTML(html)
doc.search("//pre[@lang]").each do |pre|
pre.replace Albino.colorize(pre.text.rstrip, pre[:lang])
end
doc.to_s
end
[/ruby]

articles/show.html.erb

[html]
<%= markdown(@article.content) %>
[/html]

Screencast: Resque

Resque ist ein Redis-Backend Bibliothek in Ruby um Hintergrundprozesse zu erstellen, diese Prozesse in mehrere Queues zu stellen und später zu verarbeiten. Ryan zeigt in seinem dieswöchigen Screencast wie es in Rails genutzt werden kann

 

Downloads in verschiedenen Formaten:

source code
mp4
m4v
webm
ogv

 

Resourcen:

bash

[bash]
brew install redis
redis-server /usr/local/etc/redis.conf
resque-web
rake resque:work QUEUE=’*‘
[/bash]

Gemfile

[ruby]
gem ‚resque‘, :require => "resque/server"
[/ruby]

lib/tasks/resque.rake

[ruby]
Resque::Server.use(Rack::Auth::Basic) do |user, password|
password == "secret"
end
[/ruby]

snippets_controller.rb

[ruby]
Resque.enqueue(SnippetHighlighter, @snippet.id)
[/ruby]

app/workers/snippet_highlighter.rb

[ruby]
class SnippetHighlighter
@queue = :snippets_queue
def self.perform(snippet_id)
snippet = Snippet.find(snippet_id)
uri = URI.parse(‚http://pygments.appspot.com/‘)
request = Net::HTTP.post_form(uri, {‚lang‘ => snippet.language, ‚code‘ => snippet.plain_code})
snippet.update_attribute(:highlighted_code, request.body)
end
end
[/ruby]

config/routes.rb

[ruby]
mount Resque::Server, :at => "/resque"
[/ruby]

config/initializers/resque_auth.rb

[ruby]
Resque::Server.use(Rack::Auth::Basic) do |user, password|
password == "secret"
end
[/ruby]

Screencast: Clientseitige Validierung von Formularen

Clientseitige Validierung, also die Überprüfung von eingegebenen Werten innerhalb des Webbrowsers, können dem Benutzer bereits bei der Eingabe über die Korrektheit der Daten informieren. Dies kann unter Umständen den einen oder anderen Korrigier-Zyklus ersparen. Wie dies innerhalb von Rails eingesetzt werden kann zeigt Ryan diese Woche anhand eines gems, welches die Entwicklung erleichtert.

 

Download:

Download(20.2 MB, 8:42)
Alternativer Download für iPod & Apple TV(19.3 MB, 8:42)

 

Resourcen:

 

Quellcode:

[bash]
bundle
rails g client_side_validations:install
[/bash]

[ruby]
# Gemfile
gem ‚client_side_validations‘

# models/user.rb
validates_uniqueness_of :username, :email
validates :email, :email_format => true

# lib/email_format_validator.rb
class EmailFormatValidator < ActiveModel::EachValidator
def validate_each(object, attribute, value)
unless value =~ /^([^@s]+)@((?:[-a-z0-9]+.)+[a-z]{2,})$/i
object.errors.add(attribute, :email_format, options)
end
end
end

# config/application.rb
config.autoload_paths << "#{config.root}/lib"
[/ruby]

[html]
<!– users/_form.html.erb –>
<%= form_for @user, :validate => true do |f| %>

<!– layouts/application.html.erb –>
<%= javascript_include_tag :defaults, "rails.validations", "rails.validations.custom" %>
[/html]

[text]
# locals/en.yml
en:
errors:
messages:
email_format: "is not formatted properly"
[/text]

[javascript]
/* rails.validations.custom.js */
clientSideValidations.validators.local["email_format"] = function(element, options) {
if (!/^([^@s]+)@((?:[-a-z0-9]+.)+[a-z]{2,})$/i.test(element.val())) {
return options.message;
}
}
[/javascript]

Screencast: Daten-Bäume mit Ancestry verwenden

Ancestry ist ein gem über welches man auf einfache Weise Baumstrukturen in Rails (2+3) /Ruby-Applikationen einsetzen kann. Neben allen zu erwartenenden Funktionen wie zum Beispiel für Eltern, Kinder und Nachbar-Elementen, unterstützt Ancestry auch STI (Single Table Inheritance). Auch Funktionen zum Sortieren, Integretäts-Test und Rückwärtskombatibilität sind verfügbar.
Ryan zeigt in dieser Woche wie es in eingesetzt werden kann.

 

Download:

Download(15.7 MB, 9:39)
Alternativer Download für iPod & Apple TV(15.1 MB, 9:39)

 

Resourcen:

 

Quellcode:

[bash]
bundle
rails g migration add_ancestry_to_messages ancestry:string
rake db:migrate
[/bash]

[ruby]
# Gemfile
gem ‚ancestry‘

# migration.rb
class AddAncestryToMessages < ActiveRecord::Migration
def self.up
add_column :messages, :ancestry, :string
add_index :messages, :ancestry
end

def self.down
remove_index :messages, :ancestry
remove_column :messages, :ancestry
end
end

# messages_controller.rb
def new
@message = Message.new(:parent_id => params[:parent_id])
end

# messages_helper.rb
def nested_messages(messages)
messages.map do |message, sub_messages|
render(message) + content_tag(:div, nested_messages(sub_messages), :class => "nested_messages")
end.join.html_safe
end
[/ruby]

[html]
<!– messages/index.html.erb –>
<%= nested_messages @messages.arrange(:order => :created_at) %>

<!– messages/show.html.erb –>
<%= nested_messages @message.subtree.arrange(:order => :created_at) %>

<!– messages/_form.html.erb –>
<%= f.hidden_field :parent_id %>

<!– messages/_message.html.erb –>
<%= link_to message.content, message %>

<%= link_to "Reply", new_message_path(:parent_id => message) %> |
[/html]

[css]
/* application.css */

.nested_messages {
margin-left: 30px;
}

.nested_messages .nested_messages .nested_messages .nested_messages {
margin-left: 0;
}
[/css]