SlideShare une entreprise Scribd logo
1  sur  95
Télécharger pour lire hors ligne
RSpec on Rails
Tutorial
https://ihower.tw
2016/8
Agenda
• Rails RSpec
• Model Spec, Routing Spec, Controller Spec,
View Spec, Helper Spec
• Request Spec Feature Spec
•
• CI (Continuous Integration)
• Web
Install rspec-rails
• gem “rspec-rails”
• bundle
• rails g rspec:install
• git rm -r test
rake -T spec
• rake spec
• bundle exec rspec spec/xxx/xxx
Generators
• rails g model A
• rails g controller B
• rails g scaffold C
spec/rails_helper.rb
spec/spec_helper.rb
config.fail_fast = true
config.profile_examples = 3
config.order = :random
More Matchers
• expect(target).to eq(XXX)
• expect{ Post.find(9999) }.to
raise_error(ActiveRecord::RecordNotFound)
• expect(target).to be_xxx # target.xxx?
• expect(target).to be_a_xxx
• expect(target).to be_an_xxx
• expect(collection).to be_empty
• expect([1,2,3]).to be_include(3)
• expect({ foo: "foo" }).to have_key(:foo)
• expect(3).to be_a_kind_of(Fixnum)
• Custom matcher
rspec-rails
•
• model
• controller ( stub/mock)
• view
• helper
• routing
•
• controller ( stub/mock model )
• ( controllers )
• request
• feature ( capybara)
https://robots.thoughtbot.com/rails-test-types-and-the-testing-pyramid
Model spec syntax
let(:valid_attributes){ { :name => "Train#123"} }
expect(Event.new).to_not be_valid
expect(Event.new(valid_attributes)).to_not be_valid
Exercise 0
• Rails (ticket_office)
• rspec-rails gem
• scaffold
Exercise 1:
Train Model Spec
• Train model
• valid
Kata
• Ticket Office
• GET /trains/{train_id}
• POST /trains/{train_id}/reservations
Routing spec syntax
expect(:get => "/events").to route_to("events#index")
expect(:get => "/widgets/1/edit").not_to be_routable
But…
• ( Rails
)
• resources routing spec model
validations associations
• custom route
Controller spec syntax
get :show
post :create, :params => { :user => { :name => "a" } }
patch :update
delete :destroy
# more arguments
request.cookies[:foo] = "foo"

request.session[:bar] = “bar"
post :create, :params => { :name => "a" },
:session => { :zoo => "zoo" },
:flash => { :notice => "c"},
:format => :html
: params Rails 5.0
Matcher syntax
expect(response).to render_template(:new)
expect(response).to redirect_to(events_url)
expect(response).to have_http_status(200)
expect(assigns(:event)).to be_a_new(Event)
Isolation Mode
• controller spec render view
RSpec
• render_views
Exercise 2:
Train Controller show spec (stub
version)
• trains/show
• Train#find stub
DB
View
isolated from controller too
assign(:widget, double(“Widget”, :name => "slicer"))
render
expect(rendered).to match /slicer/
Helper spec syntax
expect(helper.your_method).to eq("Q_Q")
Exercise 3:
Train show view
• train show json view
• rails4 jbuilder
• Train
stub
Exercise 4:
• Train, Seat, SeatReservation,
Reservation models
• Train#available_seats
• controller view stub
( or Partial Stub )
What have we learned?
• stub&mock
•
stub&mocks
• ActiveRecord
Exercise 5:
• ReservationsController
• Train#reserve mock
• Train#reserve spec
• ReservationsController mock
Exercise 5`:
• Train#reserve spec
• ReservationsController
( mock)
Exercise 6:
• GET /trains/{id}
• POST /trains/{id}/reservations
• POST /trains/{id}/reservations
Factory v.s. Fixtures
• rails fixtures YAML DB
• model
validation
• factory ActiveRecord
• factory_girl gem fabrication gem
•
• ActiveReocrd
• factory_girl trait
unit test
• model object DB build
create build_stubbed
factory_girl
FactoryGirl.define do
factory :user do
firstname "John"
lastname "Doe"
sequence(:email) { |n| "test#{n}@example.com"}
association :profile, :factory => :profile
end
factory :profile do
bio "ooxx"
end
end
factory_girl
before do
@user = build(:user) # DB
@event = create(:event) # DB
end
it "should post user data"
post :create, :params => { :user => attributes_for(:user) }
# ...
end
• https://github.com/thoughtbot/factory_girl/
blob/master/GETTING_STARTED.md
• https://thoughtbot.com/upcase/videos/
factory-girl
Tip: support
Dir[Rails.root.join("spec/support/**/*.rb")].each { |f| require f }
# support/factory_helpers.rb
module FactoryHelpers
# ...
end
Rspec.configure do |config|
config.include FactoryHelpers
end
Exercise 7: Extract to
factory method
• Train Extract support/
factory.rb
Tip: stub
before(:each) {
allow(controller).to receive(:current_user) { ... }
}
Tip: focus
• :focus => true describe
it
• rspec --tag focus
•
config.filter_run :focus => true
config.run_all_when_everything_filtered = true
Request
• full-stack
• stub
• Web APIs JSON, XML
• Request
controllers
• sessions ( )
• Matchers controller spec
Request spec syntax
describe "GET /events" do
it "works! (now write some real specs)" do
get “/events”
expect(response).to have_http_status(200)
end
end
Example: controller
it "creates a Widget and redirects to the Widget's page" do
get "/widgets/new"
expect(response).to render_template(:new)
post "/widgets", :widget => {:name => "My Widget"}
expect(response).to redirect_to(assigns(:widget))
follow_redirect!
expect(response).to render_template(:show)
expect(response.body).to include("Widget was successfully created.")
end
Exercise 8:
• 1. 2. 3.
Feature spec
• capybara gem request spec
• http://rubydoc.info/github/jnicklas/capybara/
master
• Capybara HTML
Capybara example
feature "signing up" do
background do
User.create(:email => 'user@example.com', :password => 'caplin')
end
scenario "signing in with correct credentials" do
visit "/" # or root_path
click_link 'Log In'
within("#session") do
fill_in 'Login', :with => 'user@example.com'
fill_in 'Password', :with => 'caplin'
choose('some_select_option_yes')
check('some_checkbox')
end
click_button 'Sign in'
expect(User.count).to eq(1) # you can test model
expect(page).to have_content 'Login successfuuly' # and/or test page
end
end
find css selector xpath
Debugging
• save_and_open_page
• capybara-screenshot gem
•
JavaScript Driver
• Capybara javascript
• javascript_driver
Ruby README
• https://github.com/teampoltergeist/poltergeist
PhantomJS
• https://github.com/thoughtbot/capybara-webkit
QtWebKit
• https://rubygems.org/gems/selenium-webdriver
Firefox
• test js: true
JavaScript Driver
• Browser tools Rails Ruby
thread
• DB transaction database cleaner
• https://github.com/DatabaseCleaner/database_cleaner
• https://github.com/amatsuda/database_rewinder
• javascript (
Ajax)
• Capybara 5
• Capybara.default_wait_time
• using_wait_time(2) { …. }
https://robots.thoughtbot.com/write-reliable-asynchronous-integration-tests-with-capybara
• Extract behavior to helper methods
• Page Object
https://robots.thoughtbot.com/acceptance-tests-at-a-single-level-of-
abstraction
Page Object
http://www.infoq.com/cn/articles/martin-fowler-basic-rule-of-thumbon-for-Web-testing
Page Object example
https://teamgaslight.com/blog/6-ways-to-remove-pain-from-feature-testing-in-ruby-on-rails
https://thoughtbot.com/upcase/videos/page-objects
https://robots.thoughtbot.com/better-acceptance-tests-with-page-objects
https://medium.com/neo-innovation-ideas/clean-up-after-your-capybara-1a08b47a499b#.oyl7zi44d
https://www.sitepoint.com/testing-page-objects-siteprism/
(1)
• Debugging ?
• puts
• https://tenderlovemaking.com/2016/02/05/i-am-
a-puts-debuggerer.html
• byebug
• --only-failures option
• https://relishapp.com/rspec/rspec-core/docs/
command-line/only-failures
(2)
• Time.now ?
• http://api.rubyonrails.org/classes/
ActiveSupport/Testing/TimeHelpers.html
travel_to
• config.include
ActiveSupport::Testing::TimeHelpers
• Timecop gem
(3)
• email ?
• mail = ActionMailer::Base.deliveries.last
• config.before(:each)
{ ActionMailer::Base.deliveries.clear }
• https://github.com/email-spec/email-
spec/
(4)
• ?
• spec/fixtures/
• File.new(Rails.root + ‘spec/fixtures/
foobar.png') paperclip
Photo.create(:description => "Test", :attachment
=> File.new(Rails.root + ‘spec/fixtures/ac_logo.png'))
• feature spec capybara attach_file
http://www.rubydoc.info/github/jnicklas/capybara/
master/Capybara%2FNode%2FActions%3Aattach_file
(5)
• devise https://github.com/plataformatec/
devise Test helpers
config.include Devise::Test::ControllerHelpers, type: :controller
config.include Devise::Test::ControllerHelpers, type: :view
config.include Devise::Test::IntegrationHelpers, type: :feature
(6)
• sidekiq ?
• http://api.rubyonrails.org/classes/
ActiveJob/TestHelper.html#method-i-
perform_enqueued_jobs
• config.include ActiveJob::TestHelper
• enqueue job
perform_enqueued_jobs
{ … }
(7)
• after_commit ?
• unit test transaction after_commit
• https://github.com/grosser/test_after_commit
• database_cleanner truncation transaction
• trigger
• http://mytrile.github.io/blog/2013/03/28/testing-after-
commit-in-rspec/
• Rails 5.0 workaround
(8)
• rake ?
• model class
method
• model spec
(9)
• legacy ?
• happy path feature spec C/P
• Unit test
•
• Unit Test
(10)
• ?
• Test double (?)
• CPU
• https://github.com/grosser/parallel_tests
• CI concurrent build
Tools
• shoulda rails matcher
• database_cleaner DB
• vcr HTTP response 3-party
service
• simplecov
• cucumber
• CI (continuous integration (CI)
BDD
http://www.tenlong.com.tw/items/9862019484?
item_id=997422
simplecov
?
Coverage
!
CI
• 3-party service
• https://www.codeship.io
• https://circleci.com/
• https://travis-ci.org/
• build your own
• Jenkins
?
Spec
• Rspec spec
•
• Custom Matcher
Test Pyramid
http://watirmelon.com/2012/01/31/introducing-the-software-testing-ice-cream-cone/
http://martinfowler.com/bliki/TestPyramid.html
developer 

QA XD

salesforce ?
https://www.quora.com/What-is-the-best-way-to-test-the-web-application
What is the best way to test the web application?
Why?
• low-level
debug
• high-level
debug
• view
• developer
QA
• bug failures
trace
•
•
( Mocks )
https://thoughtbot.com/upcase/videos/testing-antipatterns
Isolation
• it
Expectation
•
• one failure one problem 

trace
describe "#amount" do
it "should discount" do
user.vip = true
order.amount.should == 900
user.vip = false
order.amount.should == 1000
end
end
context
describe "#amount" do
context "when user is vip" do
it "should discount ten percent" do
user.vip = true
order.amount.should == 900
end
end
context "when user is not vip" do
it "should discount five percent" do
user.vip = false
order.amount.should == 1000
end
end
end
• Private methods
•
Private methods
class Order
def amount
if @user.vip?
self.caculate_amount_for_vip
else
self.caculate_amount_for_non_vip
end
end
private
def caculate_amount_for_vip
# ...
end
def caculate_amount_for_non_vip
# ...
end
end
it "should discount for vip" do
@order.send(:caculate_amount_for_vip).should == 900
end
it "should discount for non vip" do
@order.send(:caculate_amount_for_vip).should == 1000
end
Private methods
• public
private/protect methods
• private
• public
• Public methods
Private/Protected
describe User do
describe '.search' do
it 'searches Google for the given query' do
HTTParty.should_receive(:get).with('http://www.google.com',
:query => { :q => 'foo' } ).and_return([])
User.search query
end
end
end
HTTP
describe User do
describe '.search' do
it 'searches for the given query' do
User.searcher = Searcher
Searcher.should_receive(:search).with('foo').and_return([])
User.search query
end
end
end
class User < ActiveRecord::Base
class_attribute :searcher
def self.search(query)
searcher.search query
end
end
class Searcher
def self.search(keyword, options={})
HTTParty.get(keyword, options)
end
end
?
TATFT
test all the f**king time
bug
bug
bug
DHH Way
• 100% test coverage
• Code-to-test 1:2 1:3
• 1/3
• Active Record associations, validations, or scopes.
• ( Unit Test )
• Cucumber
• Specification by Example
• TDD (DHH 20% TDD)
• Model DB Fixtures
• Controller
• Views system/browser testing
https://signalvnoise.com/posts/3159-testing-like-the-tsa
http://david.heinemeierhansson.com/2014/test-induced-design-damage.html
?
coverage?
code review
pair programming
EPIC FAIL
Unit Test
Reference:
• http://guides.rubyonrails.org/testing.html
• https://github.com/eliotsykes/rspec-rails-examples#api-request-specs-docs--
helpers
• The RSpec Book
• The Rails 3 Way
• Foundation Rails 2
• xUnit Test Patterns
• everyday Rails Testing with RSpec
• http://betterspecs.org/
• http://pure-rspec-rubynation.heroku.com/
• http://jamesmead.org/talks/2007-07-09-introduction-to-mock-objects-in-ruby-at-lrug/
• http://martinfowler.com/articles/mocksArentStubs.html
• http://blog.rubybestpractices.com/posts/gregory/034-issue-5-testing-antipatterns.html
• http://blog.carbonfive.com/2011/02/11/better-mocking-in-ruby/
Thanks.

Contenu connexe

Tendances

Google mock for dummies
Google mock for dummiesGoogle mock for dummies
Google mock for dummies
Harry Potter
 

Tendances (20)

Node.js введение в технологию, КПИ #ITmeetingKPI
Node.js введение в технологию, КПИ  #ITmeetingKPINode.js введение в технологию, КПИ  #ITmeetingKPI
Node.js введение в технологию, КПИ #ITmeetingKPI
 
elasticsearch_적용 및 활용_정리
elasticsearch_적용 및 활용_정리elasticsearch_적용 및 활용_정리
elasticsearch_적용 및 활용_정리
 
なかったらINSERTしたいし、あるならロック取りたいやん?
なかったらINSERTしたいし、あるならロック取りたいやん?なかったらINSERTしたいし、あるならロック取りたいやん?
なかったらINSERTしたいし、あるならロック取りたいやん?
 
本当に怖いパフォーマンスが悪い実装 #phpcon2013
本当に怖いパフォーマンスが悪い実装 #phpcon2013本当に怖いパフォーマンスが悪い実装 #phpcon2013
本当に怖いパフォーマンスが悪い実装 #phpcon2013
 
我的 DevOps 故事
我的 DevOps 故事我的 DevOps 故事
我的 DevOps 故事
 
C# coding standards, good programming principles & refactoring
C# coding standards, good programming principles & refactoringC# coding standards, good programming principles & refactoring
C# coding standards, good programming principles & refactoring
 
モダン PHP テクニック 12 選 ―PsalmとPHP 8.1で今はこんなこともできる!―
モダン PHP テクニック 12 選 ―PsalmとPHP 8.1で今はこんなこともできる!―モダン PHP テクニック 12 選 ―PsalmとPHP 8.1で今はこんなこともできる!―
モダン PHP テクニック 12 選 ―PsalmとPHP 8.1で今はこんなこともできる!―
 
Ninja
NinjaNinja
Ninja
 
C#でわかる こわくないMonad
C#でわかる こわくないMonadC#でわかる こわくないMonad
C#でわかる こわくないMonad
 
Why Task Queues - ComoRichWeb
Why Task Queues - ComoRichWebWhy Task Queues - ComoRichWeb
Why Task Queues - ComoRichWeb
 
関数型プログラミングのデザインパターンひとめぐり
関数型プログラミングのデザインパターンひとめぐり関数型プログラミングのデザインパターンひとめぐり
関数型プログラミングのデザインパターンひとめぐり
 
Mongo db 최범균
Mongo db 최범균Mongo db 최범균
Mongo db 최범균
 
Intro to Asynchronous Javascript
Intro to Asynchronous JavascriptIntro to Asynchronous Javascript
Intro to Asynchronous Javascript
 
Google mock for dummies
Google mock for dummiesGoogle mock for dummies
Google mock for dummies
 
Integrating React.js with PHP projects
Integrating React.js with PHP projectsIntegrating React.js with PHP projects
Integrating React.js with PHP projects
 
SQLアンチパターン - ジェイウォーク
SQLアンチパターン - ジェイウォークSQLアンチパターン - ジェイウォーク
SQLアンチパターン - ジェイウォーク
 
Swaggerで始めるモデルファーストなAPI開発
Swaggerで始めるモデルファーストなAPI開発Swaggerで始めるモデルファーストなAPI開発
Swaggerで始めるモデルファーストなAPI開発
 
Ruby
RubyRuby
Ruby
 
How to Reverse Engineer Web Applications
How to Reverse Engineer Web ApplicationsHow to Reverse Engineer Web Applications
How to Reverse Engineer Web Applications
 
Clean Code
Clean CodeClean Code
Clean Code
 

En vedette

Git 版本控制系統 -- 從微觀到宏觀
Git 版本控制系統 -- 從微觀到宏觀Git 版本控制系統 -- 從微觀到宏觀
Git 版本控制系統 -- 從微觀到宏觀
Wen-Tien Chang
 
[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習
[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習
[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習
台灣資料科學年會
 
Behavior Driven Development - How To Start with Behat
Behavior Driven Development - How To Start with BehatBehavior Driven Development - How To Start with Behat
Behavior Driven Development - How To Start with Behat
imoneytech
 
RubyConf Taiwan 2011 Opening & Closing
RubyConf Taiwan 2011 Opening & ClosingRubyConf Taiwan 2011 Opening & Closing
RubyConf Taiwan 2011 Opening & Closing
Wen-Tien Chang
 
Ruby 程式語言綜覽簡介
Ruby 程式語言綜覽簡介Ruby 程式語言綜覽簡介
Ruby 程式語言綜覽簡介
Wen-Tien Chang
 
Yet another introduction to Git - from the bottom up
Yet another introduction to Git - from the bottom upYet another introduction to Git - from the bottom up
Yet another introduction to Git - from the bottom up
Wen-Tien Chang
 

En vedette (20)

淺談 Startup 公司的軟體開發流程 v2
淺談 Startup 公司的軟體開發流程 v2淺談 Startup 公司的軟體開發流程 v2
淺談 Startup 公司的軟體開發流程 v2
 
ALPHAhackathon: How to collaborate
ALPHAhackathon: How to collaborateALPHAhackathon: How to collaborate
ALPHAhackathon: How to collaborate
 
RubyConf Taiwan 2012 Opening & Closing
RubyConf Taiwan 2012 Opening & ClosingRubyConf Taiwan 2012 Opening & Closing
RubyConf Taiwan 2012 Opening & Closing
 
RSpec 2 Best practices
RSpec 2 Best practicesRSpec 2 Best practices
RSpec 2 Best practices
 
Testing Ruby with Rspec (a beginner's guide)
Testing Ruby with Rspec (a beginner's guide)Testing Ruby with Rspec (a beginner's guide)
Testing Ruby with Rspec (a beginner's guide)
 
Git 版本控制系統 -- 從微觀到宏觀
Git 版本控制系統 -- 從微觀到宏觀Git 版本控制系統 -- 從微觀到宏觀
Git 版本控制系統 -- 從微觀到宏觀
 
那些 Functional Programming 教我的事
那些 Functional Programming 教我的事那些 Functional Programming 教我的事
那些 Functional Programming 教我的事
 
[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習
[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習
[DSC 2016] 系列活動:李宏毅 / 一天搞懂深度學習
 
Practical Scrum with Kent Beck (SD Times Webinar)
Practical Scrum with Kent Beck (SD Times Webinar)Practical Scrum with Kent Beck (SD Times Webinar)
Practical Scrum with Kent Beck (SD Times Webinar)
 
Testing with Rspec 3
Testing with Rspec 3Testing with Rspec 3
Testing with Rspec 3
 
RSpec User Stories
RSpec User StoriesRSpec User Stories
RSpec User Stories
 
RSpec and Rails
RSpec and RailsRSpec and Rails
RSpec and Rails
 
Introduction to test_driven_development
Introduction to test_driven_developmentIntroduction to test_driven_development
Introduction to test_driven_development
 
Monitoring web application behaviour with cucumber-nagios
Monitoring web application behaviour with cucumber-nagiosMonitoring web application behaviour with cucumber-nagios
Monitoring web application behaviour with cucumber-nagios
 
Rspec 101
Rspec 101Rspec 101
Rspec 101
 
Behavior Driven Development - How To Start with Behat
Behavior Driven Development - How To Start with BehatBehavior Driven Development - How To Start with Behat
Behavior Driven Development - How To Start with Behat
 
RSpec: What, How and Why
RSpec: What, How and WhyRSpec: What, How and Why
RSpec: What, How and Why
 
RubyConf Taiwan 2011 Opening & Closing
RubyConf Taiwan 2011 Opening & ClosingRubyConf Taiwan 2011 Opening & Closing
RubyConf Taiwan 2011 Opening & Closing
 
Ruby 程式語言綜覽簡介
Ruby 程式語言綜覽簡介Ruby 程式語言綜覽簡介
Ruby 程式語言綜覽簡介
 
Yet another introduction to Git - from the bottom up
Yet another introduction to Git - from the bottom upYet another introduction to Git - from the bottom up
Yet another introduction to Git - from the bottom up
 

Similaire à RSpec on Rails Tutorial

Ruby on Rails : 簡介與入門
Ruby on Rails : 簡介與入門Ruby on Rails : 簡介與入門
Ruby on Rails : 簡介與入門
Wen-Tien Chang
 
Module, AMD, RequireJS
Module, AMD, RequireJSModule, AMD, RequireJS
Module, AMD, RequireJS
偉格 高
 

Similaire à RSpec on Rails Tutorial (20)

Impression of Rails 3
Impression of Rails 3Impression of Rails 3
Impression of Rails 3
 
Padrino - the Godfather of Sinatra
Padrino - the Godfather of SinatraPadrino - the Godfather of Sinatra
Padrino - the Godfather of Sinatra
 
Play Framework and Activator
Play Framework and ActivatorPlay Framework and Activator
Play Framework and Activator
 
Story ofcorespring infodeck
Story ofcorespring infodeckStory ofcorespring infodeck
Story ofcorespring infodeck
 
Adding Riak to your NoSQL Bag of Tricks
Adding Riak to your NoSQL Bag of TricksAdding Riak to your NoSQL Bag of Tricks
Adding Riak to your NoSQL Bag of Tricks
 
URUG Ruby on Rails Workshop - Sesssion 5
URUG Ruby on Rails Workshop - Sesssion 5URUG Ruby on Rails Workshop - Sesssion 5
URUG Ruby on Rails Workshop - Sesssion 5
 
Scala at Treasure Data
Scala at Treasure DataScala at Treasure Data
Scala at Treasure Data
 
Upgrading to rails3
Upgrading to rails3Upgrading to rails3
Upgrading to rails3
 
Digital Ocean Presentation - Ruby Dev Stackup - The Flatiron School
Digital Ocean Presentation - Ruby Dev Stackup - The Flatiron School Digital Ocean Presentation - Ruby Dev Stackup - The Flatiron School
Digital Ocean Presentation - Ruby Dev Stackup - The Flatiron School
 
Vue.js + Vuexチーム開発実践の事例
Vue.js + Vuexチーム開発実践の事例Vue.js + Vuexチーム開発実践の事例
Vue.js + Vuexチーム開発実践の事例
 
Артем Яворский "Compile like it's 2017"
Артем Яворский "Compile like it's 2017"Артем Яворский "Compile like it's 2017"
Артем Яворский "Compile like it's 2017"
 
Building a spa_in_30min
Building a spa_in_30minBuilding a spa_in_30min
Building a spa_in_30min
 
Building a spa_in_30min
Building a spa_in_30minBuilding a spa_in_30min
Building a spa_in_30min
 
Ruby on Rails : 簡介與入門
Ruby on Rails : 簡介與入門Ruby on Rails : 簡介與入門
Ruby on Rails : 簡介與入門
 
Our Puppet Story (GUUG FFG 2015)
Our Puppet Story (GUUG FFG 2015)Our Puppet Story (GUUG FFG 2015)
Our Puppet Story (GUUG FFG 2015)
 
Module, AMD, RequireJS
Module, AMD, RequireJSModule, AMD, RequireJS
Module, AMD, RequireJS
 
JRuby, Ruby, Rails and You on the Cloud
JRuby, Ruby, Rails and You on the CloudJRuby, Ruby, Rails and You on the Cloud
JRuby, Ruby, Rails and You on the Cloud
 
Can puppet help you run docker on a T2.Micro?
Can puppet help you run docker on a T2.Micro?Can puppet help you run docker on a T2.Micro?
Can puppet help you run docker on a T2.Micro?
 
Schema tools-and-trics-and-quick-intro-to-clojure-spec-22.6.2016
Schema tools-and-trics-and-quick-intro-to-clojure-spec-22.6.2016Schema tools-and-trics-and-quick-intro-to-clojure-spec-22.6.2016
Schema tools-and-trics-and-quick-intro-to-clojure-spec-22.6.2016
 
Harness SharePoint and jQuery to Make Dynamic Displays and Applications
 Harness SharePoint and jQuery to Make Dynamic Displays and Applications Harness SharePoint and jQuery to Make Dynamic Displays and Applications
Harness SharePoint and jQuery to Make Dynamic Displays and Applications
 

Plus de Wen-Tien Chang

Exception Handling: Designing Robust Software in Ruby (with presentation note)
Exception Handling: Designing Robust Software in Ruby (with presentation note)Exception Handling: Designing Robust Software in Ruby (with presentation note)
Exception Handling: Designing Robust Software in Ruby (with presentation note)
Wen-Tien Chang
 
Exception Handling: Designing Robust Software in Ruby
Exception Handling: Designing Robust Software in RubyException Handling: Designing Robust Software in Ruby
Exception Handling: Designing Robust Software in Ruby
Wen-Tien Chang
 
從 Classes 到 Objects: 那些 OOP 教我的事
從 Classes 到 Objects: 那些 OOP 教我的事從 Classes 到 Objects: 那些 OOP 教我的事
從 Classes 到 Objects: 那些 OOP 教我的事
Wen-Tien Chang
 
A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩
A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩
A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩
Wen-Tien Chang
 
A brief introduction to SPDY - 邁向 HTTP/2.0
A brief introduction to SPDY - 邁向 HTTP/2.0A brief introduction to SPDY - 邁向 HTTP/2.0
A brief introduction to SPDY - 邁向 HTTP/2.0
Wen-Tien Chang
 
從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup
從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup
從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup
Wen-Tien Chang
 
BDD style Unit Testing
BDD style Unit TestingBDD style Unit Testing
BDD style Unit Testing
Wen-Tien Chang
 
Service-Oriented Design and Implement with Rails3
Service-Oriented Design and Implement with Rails3Service-Oriented Design and Implement with Rails3
Service-Oriented Design and Implement with Rails3
Wen-Tien Chang
 
Distributed Ruby and Rails
Distributed Ruby and RailsDistributed Ruby and Rails
Distributed Ruby and Rails
Wen-Tien Chang
 
Ruby 入門 第一次就上手
Ruby 入門 第一次就上手Ruby 入門 第一次就上手
Ruby 入門 第一次就上手
Wen-Tien Chang
 

Plus de Wen-Tien Chang (19)

⼤語⾔模型 LLM 應⽤開發入⾨
⼤語⾔模型 LLM 應⽤開發入⾨⼤語⾔模型 LLM 應⽤開發入⾨
⼤語⾔模型 LLM 應⽤開發入⾨
 
Ruby Rails 老司機帶飛
Ruby Rails 老司機帶飛Ruby Rails 老司機帶飛
Ruby Rails 老司機帶飛
 
A brief introduction to Machine Learning
A brief introduction to Machine LearningA brief introduction to Machine Learning
A brief introduction to Machine Learning
 
Exception Handling: Designing Robust Software in Ruby (with presentation note)
Exception Handling: Designing Robust Software in Ruby (with presentation note)Exception Handling: Designing Robust Software in Ruby (with presentation note)
Exception Handling: Designing Robust Software in Ruby (with presentation note)
 
Exception Handling: Designing Robust Software in Ruby
Exception Handling: Designing Robust Software in RubyException Handling: Designing Robust Software in Ruby
Exception Handling: Designing Robust Software in Ruby
 
從 Classes 到 Objects: 那些 OOP 教我的事
從 Classes 到 Objects: 那些 OOP 教我的事從 Classes 到 Objects: 那些 OOP 教我的事
從 Classes 到 Objects: 那些 OOP 教我的事
 
A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩
A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩
A brief introduction to Vagrant – 原來 VirtualBox 可以這樣玩
 
A brief introduction to SPDY - 邁向 HTTP/2.0
A brief introduction to SPDY - 邁向 HTTP/2.0A brief introduction to SPDY - 邁向 HTTP/2.0
A brief introduction to SPDY - 邁向 HTTP/2.0
 
從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup
從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup
從 Scrum 到 Kanban: 為什麼 Scrum 不適合 Lean Startup
 
Git Tutorial 教學
Git Tutorial 教學Git Tutorial 教學
Git Tutorial 教學
 
BDD style Unit Testing
BDD style Unit TestingBDD style Unit Testing
BDD style Unit Testing
 
Git and Github
Git and GithubGit and Github
Git and Github
 
Service-Oriented Design and Implement with Rails3
Service-Oriented Design and Implement with Rails3Service-Oriented Design and Implement with Rails3
Service-Oriented Design and Implement with Rails3
 
Rails3 changesets
Rails3 changesetsRails3 changesets
Rails3 changesets
 
遇見 Ruby on Rails
遇見 Ruby on Rails遇見 Ruby on Rails
遇見 Ruby on Rails
 
Rails Security
Rails SecurityRails Security
Rails Security
 
Rails Performance
Rails PerformanceRails Performance
Rails Performance
 
Distributed Ruby and Rails
Distributed Ruby and RailsDistributed Ruby and Rails
Distributed Ruby and Rails
 
Ruby 入門 第一次就上手
Ruby 入門 第一次就上手Ruby 入門 第一次就上手
Ruby 入門 第一次就上手
 

Dernier

Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire business
panagenda
 

Dernier (20)

WSO2's API Vision: Unifying Control, Empowering Developers
WSO2's API Vision: Unifying Control, Empowering DevelopersWSO2's API Vision: Unifying Control, Empowering Developers
WSO2's API Vision: Unifying Control, Empowering Developers
 
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemkeProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
ProductAnonymous-April2024-WinProductDiscovery-MelissaKlemke
 
Rising Above_ Dubai Floods and the Fortitude of Dubai International Airport.pdf
Rising Above_ Dubai Floods and the Fortitude of Dubai International Airport.pdfRising Above_ Dubai Floods and the Fortitude of Dubai International Airport.pdf
Rising Above_ Dubai Floods and the Fortitude of Dubai International Airport.pdf
 
AWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of TerraformAWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of Terraform
 
Exploring Multimodal Embeddings with Milvus
Exploring Multimodal Embeddings with MilvusExploring Multimodal Embeddings with Milvus
Exploring Multimodal Embeddings with Milvus
 
ICT role in 21st century education and its challenges
ICT role in 21st century education and its challengesICT role in 21st century education and its challenges
ICT role in 21st century education and its challenges
 
Elevate Developer Efficiency & build GenAI Application with Amazon Q​
Elevate Developer Efficiency & build GenAI Application with Amazon Q​Elevate Developer Efficiency & build GenAI Application with Amazon Q​
Elevate Developer Efficiency & build GenAI Application with Amazon Q​
 
TrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data DiscoveryTrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
TrustArc Webinar - Unlock the Power of AI-Driven Data Discovery
 
Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...
Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...
Apidays New York 2024 - Passkeys: Developing APIs to enable passwordless auth...
 
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ..."I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
 
Introduction to Multilingual Retrieval Augmented Generation (RAG)
Introduction to Multilingual Retrieval Augmented Generation (RAG)Introduction to Multilingual Retrieval Augmented Generation (RAG)
Introduction to Multilingual Retrieval Augmented Generation (RAG)
 
CNIC Information System with Pakdata Cf In Pakistan
CNIC Information System with Pakdata Cf In PakistanCNIC Information System with Pakdata Cf In Pakistan
CNIC Information System with Pakdata Cf In Pakistan
 
Strategize a Smooth Tenant-to-tenant Migration and Copilot Takeoff
Strategize a Smooth Tenant-to-tenant Migration and Copilot TakeoffStrategize a Smooth Tenant-to-tenant Migration and Copilot Takeoff
Strategize a Smooth Tenant-to-tenant Migration and Copilot Takeoff
 
Boost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdfBoost Fertility New Invention Ups Success Rates.pdf
Boost Fertility New Invention Ups Success Rates.pdf
 
Platformless Horizons for Digital Adaptability
Platformless Horizons for Digital AdaptabilityPlatformless Horizons for Digital Adaptability
Platformless Horizons for Digital Adaptability
 
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWEREMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
EMPOWERMENT TECHNOLOGY GRADE 11 QUARTER 2 REVIEWER
 
[BuildWithAI] Introduction to Gemini.pdf
[BuildWithAI] Introduction to Gemini.pdf[BuildWithAI] Introduction to Gemini.pdf
[BuildWithAI] Introduction to Gemini.pdf
 
Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire business
 
Navigating the Deluge_ Dubai Floods and the Resilience of Dubai International...
Navigating the Deluge_ Dubai Floods and the Resilience of Dubai International...Navigating the Deluge_ Dubai Floods and the Resilience of Dubai International...
Navigating the Deluge_ Dubai Floods and the Resilience of Dubai International...
 
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost SavingRepurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
Repurposing LNG terminals for Hydrogen Ammonia: Feasibility and Cost Saving
 

RSpec on Rails Tutorial