Cette fois, afin d'approfondir ma compréhension du code de test, je vais résumer comment écrire le code de test en utilisant RSpec. Quand j'ai écrit le code de test pour la première fois, je me souviens de l'avoir écrit en l'imitant sans savoir pourquoi j'avais besoin du code de test, alors j'aimerais revenir au début et l'écrire avec le plus de détails possible. À propos, une explication détaillée des termes est omise. Veuillez consulter l'article qui est résumé de manière simple à comprendre. Recommandé => Introduction à RSpec utilisable, partie 1 "Comprendre la syntaxe de base et les fonctions utiles de RSpec"
Il s'agit de garantir la qualité en laissant le contrôle de fonctionnement de l'application à l'ordinateur. Si une personne vérifie manuellement le fonctionnement, une omission peut se produire. Vous pouvez éliminer l'erreur humaine en automatisant le test. Même s'il y a d'autres changements dans les spécifications, vous n'avez qu'à vérifier les changements, vous pouvez donc éviter de redémarrer tous les tests à partir de 1.
RSpec est un joyau utilisé pour écrire du code de test pour Ruby on Rails. Ruby on Rails a une fonction de test standard appelée Minitest, mais sur le site de développement actuel utilisant Rails, les tests avec RSpec semblent être la norme, donc je l'utilise comme une pratique.
Cette fois, nous avons trois modèles d'utilisateur, de salle et de message dans notre propre application de chat, et nous écrirons le flux du code de test pour chaque modèle d'utilisateur. Le but du code de test unitaire du modèle utilisateur est de vérifier si l'enregistrement de l'utilisateur est correct et si la validation d'ensemble fonctionne.
・ MacOS Catalina 10.15.6 ・ Rubis 2.6.5 ・ Rails 6.0.3 ・ Gem FactoryBot ・ Gem RSpec ・ Gem Faker
Tout d'abord, nous présenterons FactoryBot, RSpec et Faker.
Gemfile
(Abréviation)
group :development, :test do
#Cette fois, nous utiliserons la dernière version, nous ne spécifions donc pas la version
gem 'rspec-rails'
#FactoryBot est utilisé pour créer automatiquement une instance. Vous n'êtes pas obligé, mais c'est aussi une pratique.
gem 'factory_bot_rails'
#Faker générera au hasard un nom et un mot de passe pour vous. C'est également pratique, alors habituons-nous-y.
gem 'faker'
end
(Abréviation)
Effectuer l'installation du bundle
% bundle install
Créons les fichiers nécessaires pour RSpec.
% rails g rspec:install
Je pense que vous avez créé des fichiers.
create .rspec
create spec
create spec/spec_helper.rb
create spec/rails_helper.rb
Écrivez ce qui suit dans votre fichier .rspec
.rspec
--require spec_helper
--format documentation
Cette description vous permet de voir les résultats du code de test sur votre terminal. Exécutez la commande suivante pour créer un fichier pour tester le modèle utilisateur requis. Cette fois, seul le modèle User est utilisé, mais la procédure est la même pour les autres modèles.
% rails g rspec:model user
Vous devriez maintenant avoir les fichiers nécessaires.
create spec/models/user_spec.rb
invoke factory_bot
create spec/factories/users.rb
Si le fichier users.rb n'est pas créé, créez le répertoire factories dans le répertoire spec et créez le fichier users.rb dedans.
Nous allons mettre en place FactoryBot. Écrivez ce qui suit dans spec / factories / users.rb.
spec/factories/users.rb
#C'est une description de l'utilisation de FactoryBot
FactoryBot.define do
#Classe d'utilisateur en écrivant comme suit(Modèle utilisateur)Il jugera automatiquement que
factory :user do
#Générer aléatoirement le contenu à enregistrer sous nom
name {Faker::Name.first_name}
#Générer automatiquement des e-mails
email {Faker::Internet.email}
#Pour le mot de passe, vous devez entrer la même valeur deux fois, y compris pour confirmation, donc générer aléatoirement la valeur sous forme de variable
#Le mot de passe du périphérique doit comporter au moins 6 caractères, donc min_Définir la longueur à 6 caractères ou plus
password = Faker::Internet.password(min_length: 6)
#Définissez le mot de passe et la variable définie ci-dessus dans le cadre de confirmation du mot de passe
password {password}
password_confirmation {password}
end
end
Cette fois, seuls le nom, l'adresse e-mail et le mot de passe sont disponibles, mais s'il existe d'autres éléments pour lesquels la validation est définie, veuillez les ajouter. Ceci termine les réglages de FactoryBot. Lançons la console dans le terminal et vérifions-la.
% rails c
[1] pry(main)> FactoryBot.build(:user)
=> #<User id: nil, name: "颯", email: "[email protected]", created_at: nil, updated_at: nil>
S'il s'agit d'une sortie comme celle-ci, c'est OK! (Le nom et l'e-mail sont générés aléatoirement par Faker, donc ils changent à chaque fois.)
Écrivons maintenant le code de test. Commencez par vérifier le fichier user_spec.rb.
spec/models/spec_user.rb
require 'rails_helper'
RSpec.describe User, type: :model do
- pending "add some examples to (or delete) #{__FILE__}"
+ describe '#create' do
+ before do
+ @user = FactoryBot.build(:user)
+ end
+ end
end
Tout d'abord, j'écrirai comme ça. Puisque décrire signifie expliquer, il décrit en quoi consiste le test. Créez une instance d'utilisateur basée sur le contenu défini dans le fichier spec / factories / users.rb dans le bloc après avant et en faire une variable. Puisqu'il sera utilisé dans une portée différente après cela, ce sera une variable d'instance.
De là, j'écrirai une brève explication dans le code
spec/models/spec_user.rb
RSpec.describe User, type: :model do
#Créer un nouvel utilisateur(enregistrement)Parce que c'est un test à faire#Je crée
describe '#create' do
# spec/factories/user.Faire du contenu de rb une variable d'appel
#Pas une variable locale car sa portée est différente@Pour en faire une variable d'instance
before do
@user = FactoryBot.build(:user)
end
#Décrivez la condition / situation en contexte
context 'Si vous pouvez vous inscrire en tant qu'utilisateur' do
#Décrivez l'article à tester
it 'name, email, password, password_Si la confirmation est correctement saisie, vous pouvez vous enregistrer à nouveau' do
#Si les informations utilisateur créées par FactoryBot sont correctes, elles ne seront pas validées et_réussir le test avec une
expect(@user).to be_valid
end
end
end
end
La syntaxe du code de test RSpec place souvent une condition après le contexte. Considérez le contenu de ce contexte comme la partie if (true) de l'instruction if ~ else. Par conséquent, on suppose que le contenu peut également être enregistré en tant qu'utilisateur. Décrivez ensuite les résultats attendus du test sous la forme expect (X) .to Y. Ce domaine est expliqué d'une manière très facile à comprendre dans l'article suivant.
Reference => Introduction à RSpec utilisable, Partie 1 "Comprendre la syntaxe de base et les fonctions utiles de RSpec" Cette fois, nous attendons le résultat que les informations utilisateur contenues dans la variable d'instance peuvent être nouvellement enregistrées sans être validées. Écrivez les détails de ce que vous voulez tester entre les ~ faire. Il est souhaitable que les autres voient de quoi il s'agit.
Vérifions si le résultat du test est correct. Entrez la commande suivante dans le terminal.
% bundle exec rspec spec/models/user_spec.rb
Si ce qui suit est émis vers le terminal, il est correctement enregistré.
1 examples, 0 failure
Ensuite, nous testerons le cas où l'enregistrement n'est pas possible. Soit dit en passant, il y a un système normal et un système anormal dans le test, et le but initial qui confirme la fonction de l'objectif initial tel que l'enregistrement d'un nouvel utilisateur qui a testé en premier est le système normal, et inversement il ne peut pas être enregistré en raison de la validation. On appelle cela un système anormal pour s'assurer que ce qui précède ne peut pas être atteint. Après cela, nous testerons le système anormal.
Écrivons comme suit.
spec/models/user_spec.rb
(Abréviation)
context 'Si vous pouvez vous inscrire en tant qu'utilisateur' do
#Décrivez l'article à tester
it 'name, email, password, password_Si la confirmation est correctement saisie, vous pouvez vous enregistrer à nouveau' do
#Si les informations utilisateur créées par FactoryBot sont correctes, elles ne seront pas validées et_réussir le test avec une
expect(@user).to be_valid
end
end
context 'Si vous ne pouvez pas vous inscrire en tant qu'utilisateur' do
#Testé que l'enregistrement ne peut pas être effectué en raison de la validation lors de la tentative d'enregistrement sans entrer un nom d'utilisateur
it 'Impossible de s'inscrire si le nom est vide' do
#Mettre à jour le nom de l'utilisateur pour qu'il soit vide
@user.name = nil
# valid?Jugez s'il réussit la validation et, s'il échoue, générez un message d'erreur
@user.valid?
# @user.errors.full_Afficher un message d'erreur avec des messages
#Décrivez le message d'erreur affiché après inclure
#Le nom peut si la devise n'est pas traduite en japonais'Je pense que vous obtiendrez le message d'erreur t être vide
expect(@user.errors.full_messages).to include("Veuillez entrer un nom")
end
end
En bref, en définissant le nom sur nil et en utilisant la méthode? Valide, un message d'erreur dû à la validation est généré. Si Gem's'pry-rails 'est installé, écrivez binding.pry après user.valid?, Exécutez le code de test, et lorsque le processus s'arrête, entrez user.errors dans la console, et une erreur se produit. Vous pouvez également vérifier le message d'erreur en tapant user.erros.full_messages. À propos, si la chaîne de caractères dans l'inclusion du code ci-dessus est différente même d'un caractère, la sortie suivante sera sortie et le test ne passera pas.
Failures:
1) User#créer Si l'enregistrement de l'utilisateur n'est pas possible L'enregistrement n'est pas possible si le nom est vide
Failure/Error: expect(@user.errors.full_messages).to include("Name can't be blank")
expected ["Veuillez entrer un nom"] to include "Name can't be blank"
# ./spec/models/user_spec.rb:28:in `block (4 levels) in <top (required)>'
Cela signifie que je m'attendais à ce que le message d'erreur soit "Le nom ne peut pas être vide", mais c'est en fait "Entrer le nom". (J'ai oublié que la devise était traduite en japonais et j'ai fait une erreur ...) Lors de la vérification de l'instruction d'erreur, le message d'erreur réel est émis après l'attente, donc si vous copiez et collez ceci, le test réussira.
Ceci est le code final.
spec/models/user_spec.rb
require 'rails_helper'
#Décrivez en quoi consiste le test Décrivez
#Cette fois, il s'agit d'un test du modèle User, donc ce sera comme ça
RSpec.describe User, type: :model do
#Créer un nouvel utilisateur(enregistrement)Parce que c'est un test à faire#Je crée
describe '#create' do
# spec/factories/user.Faire du contenu de rb une variable d'appel
#Pas une variable locale car sa portée est différente@Pour en faire une variable d'instance
before do
@user = FactoryBot.build(:user)
end
#Décrivez la condition / situation en contexte
context 'Si vous pouvez vous inscrire en tant qu'utilisateur' do
#Décrivez l'article à tester
it 'name, email, password, password_Si la confirmation est correctement saisie, vous pouvez vous enregistrer à nouveau' do
#Si les informations utilisateur créées par FactoryBot sont correctes, elles ne seront pas validées et_réussir le test avec une
expect(@user).to be_valid
end
end
context 'Si vous ne pouvez pas vous inscrire en tant qu'utilisateur' do
#Testé que l'enregistrement ne peut pas être effectué en raison de la validation lors de la tentative d'enregistrement sans entrer un nom d'utilisateur
it 'Impossible de s'inscrire si le nom est vide' do
#Mettre à jour le nom de l'utilisateur pour qu'il soit vide
@user.name = nil
# valid?Jugez s'il réussit la validation et, s'il échoue, générez un message d'erreur
@user.valid?
# @user.errors.full_Afficher un message d'erreur avec des messages
#Décrivez le message d'erreur affiché après inclure
#Le nom peut si la devise n'est pas traduite en japonais'Je pense que vous obtiendrez le message d'erreur t être vide
expect(@user.errors.full_messages).to include("Veuillez entrer un nom")
end
it 'Impossible de s'inscrire si l'e-mail est vide' do
@user.email = nil
@user.valid?
expect(@user.errors.full_messages).to include("Veuillez entrer votre email")
end
#Par défaut, devise a une validation que le même contenu d'unicité ne peut pas être enregistré.
it 'Le même e-mail ne peut pas être enregistré s'il est déjà utilisé' do
#Préparez deux utilisateurs pour confirmer l'unicité
# @Enregistrer l'utilisateur
@user.save
#Créer un deuxième utilisateur
another_user = FactoryBot.build(:user)
# another_email de l'utilisateur@Mettre à jour avec le même e-mail que l'utilisateur
another_user.email = @user.email
another_user.valid?
expect(another_user.errors.full_messages).to include("L'email existe déjà")
end
it 'Impossible de s'inscrire si le mot de passe est vide' do
@user.password = nil
@user.valid?
expect(@user.errors.full_messages).to include("s'il vous plait entrez votre mot de passe", "Le mot de passe (pour confirmation) et l'entrée du mot de passe ne correspondent pas")
end
#Par défaut, l'appareil a une validation que vous ne pouvez pas enregistrer à moins que 6 caractères ou plus apparaissent dans le mot de passe
it 'Impossible d'enregistrer si le mot de passe est de 6 caractères ou moins' do
#Définir le mot de passe sur 5 caractères
@user.password = "12345"
@user.password_confirmation = "12345"
@user.valid?
expect(@user.errors.full_messages).to include("Veuillez saisir le mot de passe d'au moins 6 caractères")
end:tired_face:
it 'mot de passe même si le mot de passe est correct_Impossible de s'inscrire si la confirmation ne correspond pas' do
# #Si vous définissez ce paramètre sur nul, il ne passera pas le test.""Doit être
@user.password_confirmation = ""
@user.valid?
expect(@user.errors.full_messages).to include("Le mot de passe (pour confirmation) et l'entrée du mot de passe ne correspondent pas")
end
end
end
end
Ce à quoi je n'ai pas pensé au début, c'est que je ne pouvais pas m'inscrire si mon adresse e-mail était la même que celle des autres utilisateurs. Le but était de créer d'abord deux utilisateurs et de mettre à jour la première adresse e-mail avec la même valeur que la deuxième adresse e-mail, intentionnellement la même.
Un autre point est la dernière partie, "Même si le mot de passe est correct, il ne peut être enregistré que si le mot de passe_confirmation correspond." Si vous définissez la confirmation du mot de passe sur nil, cela ne fonctionnera pas, vous devez donc indiquer explicitement qu'il est vide avec "". Au contraire, d'autres noms et e-mails peuvent être "".
Ce qui précède est le contenu du code de test unitaire du modèle User implémenté cette fois. J'ai essayé de l'écrire avec le plus de détails possible, mais c'est devenu assez long, mais la prochaine fois, j'aimerais que ce soit plus facile à comprendre. Ensuite, j'aimerais pouvoir écrire sur le code de test d'intégration. Je vous serais reconnaissant si vous pouviez signaler des erreurs ou des parties déroutantes.
Référence => FactoryBot Github Référence => RSpec Github Référence => Faker Github
Recommended Posts