Objeto do mundo pepino

Oi,

recentemente estou trabalhando com testes de aceitação do Cucumber. No começo não fiquei tão surpreso, pois assistia a algumas palestras e apresentações, e estava acostumada a trabalhar com Capivara e Bife.

Mas a situação é que meu projeto atual foi iniciado há algum tempo e agora estou me familiarizando com seus testes de aceitação.

A primeira coisa que me preocupou foi o número de consultas em cada etapa. Isso significa que quase todas as etapas recebem um parâmetro com os valores a serem buscados no banco de dados. Por exemplo:

Scenario: A registered user should be able to edit its profile
Given that I'm a registered user with email "my@email.com" and password "123123"
And I'
m signed in with email "my@email.com" and password "123123"
When I access the user with email "my@email.com" profile page
And I click on "edit" link
Then I should see the profile edition form

Este é um exemplo simples / hipotético, mas pode ser muito possível para um novato em Pepino. As etapas da web para isso foram mais ou menos assim:

Given(/^that I'm a registered user with email "(.*?)" and password "(.*?)"$/) do |email, pw|
User.create(email: email, password: password)
end

Given(/^I'm signed in with email "(.*?)" and password "(.*?)"$/) do |email, pw|
user
= User.where("email = ? AND password = ?", email, pw)

visit sign_in_path

fill_in
"user_email", :with => email
fill_in
"user_password", :with => pw
click_button
"Sign in"
end

When(/^I access the user with email "(.*?)" profile page$/) do |email|
user
= User.find_by_email(email)
visit user_path
(user)
end

And(/^I click on "(.*?)" link$/) do |link|
click_link link

end

And(/^I should see the profile edition form$/) do
page
.should have_selector('#user-profile-edit')
end

O problema e o foco desta dica, são as linhas com o User.where e User.find por email . Essas linhas denotam que toda vez que eu precisar fazer algo com o usuário, sujeito do cenário, vou buscar no banco de dados.

Eu estava lutando com várias etapas usando esse tipo de abordagem, e constantemente me sentindo mal, com problemas de desempenho em meus testes do Cucumber e falta de clareza.

Pesquisando um pouco, encontrei este pequeno artigo https://github.com/cucumber/cucumber/wiki/A-Whole-New-World que mostra como fazer ajudantes usando o objeto Mundo. O seguinte foi extraído do artigo:

Qualquer @instance_variable instanciada em uma Definição de Etapa será atribuída ao Mundo e pode ser acessada em outras Definições de Etapa.

Isso significa que você pode usar @instance_variables em todo o cenário, evitando consultas constantes ao banco de dados, informações que podem estar na memória. Além disso, você pode limpar as etapas do Pepino e escrevê-las de maneira mais clara.

Scenario: A registered user should be able to edit its profile
Given that I'm a registered user
And I'
m signed in
When I access my profile page
And I click on "edit" link
Then I should see the profile edition form

Para mim, isso é muito claro e compreensível que o outro. Agora, as etapas se parecem com isto:

Given(/^that I'm a registered user"$/) do
@user = User.create(email: "my@email.com", password: "123123")
end

And(/^I'm signed in"$/) do
visit sign_in_path

fill_in
"user_email", :with => @user.email
fill_in
"user_password", :with => @user.password
click_button
"Sign in"
end

When(/^I access the user with email "(.*?)" profile page$/) do |email|
visit user_path
(@user)
end

And(/^I click on "(.*?)" link$/) do |link|
click_link link

end

And(/^I should see the profile edition form$/) do
page
.should have_selector('#user-profile-edit')
end

Durante a execução dos cenários, uma instância do mundo é criada e cada @instance_variable é compartilhada entre o plano de fundo e as etapas usadas para esse cenário. Ao final da execução do cenário, essas variáveis ​​são descartadas, um novo cenário é iniciado e assim por diante.

Para mim, esta foi uma grande descoberta, e espero que possa ajudá-lo a escrever melhores cenários do Pepino.

Não se envergonhe de deixar um comentário.