Commit 0399b644 authored by Rémy Coutable's avatar Rémy Coutable

Merge branch 'qa-264' into 'master'

Adding spec to test basic forking functionalities

See merge request gitlab-org/gitlab-ce!20097
parents fc4c7956 29955c9c
...@@ -55,7 +55,7 @@ Since the arguments would be passed to `rspec`, you could use all `rspec` ...@@ -55,7 +55,7 @@ Since the arguments would be passed to `rspec`, you could use all `rspec`
options there. For example, passing `--backtrace` and also line number: options there. For example, passing `--backtrace` and also line number:
``` ```
bin/qa Test::Instance http://localhost qa/specs/features/login/standard_spec.rb:3 --backtrace bin/qa Test::Instance http://localhost qa/specs/features/project/create_spec.rb:3 --backtrace
``` ```
### Overriding the authenticated user ### Overriding the authenticated user
......
...@@ -41,14 +41,17 @@ module QA ...@@ -41,14 +41,17 @@ module QA
autoload :Project, 'qa/factory/resource/project' autoload :Project, 'qa/factory/resource/project'
autoload :MergeRequest, 'qa/factory/resource/merge_request' autoload :MergeRequest, 'qa/factory/resource/merge_request'
autoload :ProjectImportedFromGithub, 'qa/factory/resource/project_imported_from_github' autoload :ProjectImportedFromGithub, 'qa/factory/resource/project_imported_from_github'
autoload :MergeRequestFromFork, 'qa/factory/resource/merge_request_from_fork'
autoload :DeployKey, 'qa/factory/resource/deploy_key' autoload :DeployKey, 'qa/factory/resource/deploy_key'
autoload :Branch, 'qa/factory/resource/branch' autoload :Branch, 'qa/factory/resource/branch'
autoload :SecretVariable, 'qa/factory/resource/secret_variable' autoload :SecretVariable, 'qa/factory/resource/secret_variable'
autoload :Runner, 'qa/factory/resource/runner' autoload :Runner, 'qa/factory/resource/runner'
autoload :PersonalAccessToken, 'qa/factory/resource/personal_access_token' autoload :PersonalAccessToken, 'qa/factory/resource/personal_access_token'
autoload :KubernetesCluster, 'qa/factory/resource/kubernetes_cluster' autoload :KubernetesCluster, 'qa/factory/resource/kubernetes_cluster'
autoload :User, 'qa/factory/resource/user'
autoload :ProjectMilestone, 'qa/factory/resource/project_milestone' autoload :ProjectMilestone, 'qa/factory/resource/project_milestone'
autoload :Wiki, 'qa/factory/resource/wiki' autoload :Wiki, 'qa/factory/resource/wiki'
autoload :Fork, 'qa/factory/resource/fork'
end end
module Repository module Repository
...@@ -107,6 +110,7 @@ module QA ...@@ -107,6 +110,7 @@ module QA
module Main module Main
autoload :Login, 'qa/page/main/login' autoload :Login, 'qa/page/main/login'
autoload :OAuth, 'qa/page/main/oauth' autoload :OAuth, 'qa/page/main/oauth'
autoload :SignUp, 'qa/page/main/sign_up'
end end
module Settings module Settings
...@@ -167,6 +171,10 @@ module QA ...@@ -167,6 +171,10 @@ module QA
autoload :Index, 'qa/page/project/issue/index' autoload :Index, 'qa/page/project/issue/index'
end end
module Fork
autoload :New, 'qa/page/project/fork/new'
end
module Milestone module Milestone
autoload :New, 'qa/page/project/milestone/new' autoload :New, 'qa/page/project/milestone/new'
autoload :Index, 'qa/page/project/milestone/index' autoload :Index, 'qa/page/project/milestone/index'
...@@ -200,6 +208,10 @@ module QA ...@@ -200,6 +208,10 @@ module QA
autoload :Sidebar, 'qa/page/issuable/sidebar' autoload :Sidebar, 'qa/page/issuable/sidebar'
end end
module Layout
autoload :Banner, 'qa/page/layout/banner'
end
module MergeRequest module MergeRequest
autoload :New, 'qa/page/merge_request/new' autoload :New, 'qa/page/merge_request/new'
autoload :Show, 'qa/page/merge_request/show' autoload :Show, 'qa/page/merge_request/show'
......
...@@ -11,6 +11,8 @@ module QA ...@@ -11,6 +11,8 @@ module QA
factory.output factory.output
end end
product(:project) { |factory| factory.project }
def initialize def initialize
@file_name = 'file.txt' @file_name = 'file.txt'
@file_content = '# This is test project' @file_content = '# This is test project'
......
...@@ -5,7 +5,8 @@ module QA ...@@ -5,7 +5,8 @@ module QA
module Repository module Repository
class Push < Factory::Base class Push < Factory::Base
attr_accessor :file_name, :file_content, :commit_message, attr_accessor :file_name, :file_content, :commit_message,
:branch_name, :new_branch, :output, :repository_uri :branch_name, :new_branch, :output, :repository_uri,
:user
attr_writer :remote_branch attr_writer :remote_branch
...@@ -31,9 +32,20 @@ module QA ...@@ -31,9 +32,20 @@ module QA
def fabricate! def fabricate!
Git::Repository.perform do |repository| Git::Repository.perform do |repository|
repository.uri = repository_uri repository.uri = repository_uri
repository.use_default_credentials repository.use_default_credentials
username = 'GitLab QA'
email = 'root@gitlab.com'
if user
repository.username = user.username
repository.password = user.password
username = user.name
email = user.email
end
repository.clone repository.clone
repository.configure_identity('GitLab QA', 'root@gitlab.com') repository.configure_identity(username, email)
if new_branch if new_branch
repository.checkout_new_branch(branch_name) repository.checkout_new_branch(branch_name)
......
module QA
module Factory
module Resource
class Fork < Factory::Base
dependency Factory::Repository::ProjectPush, as: :push
dependency Factory::Resource::User, as: :user
product(:user) { |factory| factory.user }
def fabricate!
push.project.visit!
Page::Project::Show.act { fork_project }
Page::Project::Fork::New.perform do |fork_new|
fork_new.choose_namespace(user.name)
end
Page::Layout::Banner.act { has_notice?('The project was successfully forked.') }
end
end
end
end
end
module QA
module Factory
module Resource
class MergeRequestFromFork < MergeRequest
attr_accessor :fork_branch
dependency Factory::Resource::Fork, as: :fork
dependency Factory::Repository::ProjectPush, as: :push do |push, factory|
push.project = factory.fork
push.branch_name = factory.fork_branch
push.file_name = 'file2.txt'
push.user = factory.fork.user
end
def fabricate!
fork.visit!
Page::Project::Show.act { new_merge_request }
Page::MergeRequest::New.act { create_merge_request }
end
end
end
end
end
...@@ -37,6 +37,7 @@ module QA ...@@ -37,6 +37,7 @@ module QA
page.choose_test_namespace page.choose_test_namespace
page.choose_name(@name) page.choose_name(@name)
page.add_description(@description) page.add_description(@description)
page.set_visibility('Public')
page.create_new_project page.create_new_project
end end
end end
......
require 'securerandom'
module QA
module Factory
module Resource
class User < Factory::Base
attr_accessor :name, :username, :email, :password
def initialize
@name = "name-#{SecureRandom.hex(8)}"
@username = "username-#{SecureRandom.hex(8)}"
@email = "mail#{SecureRandom.hex(8)}@mail.com"
@password = 'password'
end
product(:name) { |factory| factory.name }
product(:username) { |factory| factory.username }
product(:email) { |factory| factory.email }
product(:password) { |factory| factory.password }
def fabricate!
Page::Menu::Main.act { sign_out }
Page::Main::Login.act { switch_to_register_tab }
Page::Main::SignUp.perform do |page|
page.sign_up!(name: name, username: username, email: email, password: password)
end
end
end
end
end
end
module QA
module Page
module Layout
class Banner < Page::Base
view 'app/views/layouts/header/_read_only_banner.html.haml' do
element :flash_notice, ".flash-notice"
end
def has_notice?(message)
page.within('.flash-notice') do
!!find('span', text: message)
end
end
end
end
end
end
...@@ -25,19 +25,24 @@ module QA ...@@ -25,19 +25,24 @@ module QA
element :standard_tab, "link_to 'Standard'" element :standard_tab, "link_to 'Standard'"
end end
view 'app/views/devise/shared/_tabs_normal.html.haml' do
element :sign_in_tab, /nav-link.*login-pane.*Sign in/
element :register_tab, /nav-link.*register-pane.*Register/
end
def initialize def initialize
# The login page is usually the entry point for all the scenarios so # The login page is usually the entry point for all the scenarios so
# we need to wait for the instance to start. That said, in some cases # we need to wait for the instance to start. That said, in some cases
# we are already logged-in so we check both cases here. # we are already logged-in so we check both cases here.
wait(max: 500) do wait(max: 500) do
page.has_css?('.login-page') || page.has_css?('.login-page') ||
Page::Menu::Main.act { has_personal_area? } Page::Menu::Main.act { has_personal_area?(wait: 0) }
end end
end end
def sign_in_using_credentials def sign_in_using_credentials
# Don't try to log-in if we're already logged-in # Don't try to log-in if we're already logged-in
return if Page::Menu::Main.act { has_personal_area? } return if Page::Menu::Main.act { has_personal_area?(wait: 0) }
using_wait_time 0 do using_wait_time 0 do
set_initial_password_if_present set_initial_password_if_present
...@@ -48,12 +53,22 @@ module QA ...@@ -48,12 +53,22 @@ module QA
sign_in_using_gitlab_credentials sign_in_using_gitlab_credentials
end end
end end
Page::Menu::Main.act { has_personal_area? }
end end
def self.path def self.path
'/users/sign_in' '/users/sign_in'
end end
def switch_to_sign_in_tab
click_on 'Sign in'
end
def switch_to_register_tab
click_on 'Register'
end
private private
def sign_in_using_ldap_credentials def sign_in_using_ldap_credentials
......
module QA
module Page
module Main
class SignUp < Page::Base
view 'app/views/devise/shared/_signup_box.html.haml' do
element :name, 'text_field :name'
element :username, 'text_field :username'
element :email_field, 'email_field :email'
element :email_confirmation, 'email_field :email_confirmation'
element :password, 'password_field :password'
element :register_button, 'submit "Register"'
end
def sign_up!(name:, username:, email:, password:)
fill_in :new_user_name, with: name
fill_in :new_user_username, with: username
fill_in :new_user_email, with: email
fill_in :new_user_email_confirmation, with: email
fill_in :new_user_password, with: password
click_button 'Register'
Page::Menu::Main.act { has_personal_area? }
end
end
end
end
end
...@@ -60,9 +60,9 @@ module QA ...@@ -60,9 +60,9 @@ module QA
end end
end end
def has_personal_area? def has_personal_area?(wait: Capybara.default_max_wait_time)
# No need to wait, either we're logged-in, or not. # No need to wait, either we're logged-in, or not.
using_wait_time(0) { page.has_selector?('.qa-user-avatar') } using_wait_time(wait) { page.has_selector?('.qa-user-avatar') }
end end
private private
......
module QA
module Page
module Project
module Fork
class New < Page::Base
view 'app/views/projects/forks/_fork_button.html.haml' do
element :namespace, 'link_to project_forks_path'
end
def choose_namespace(namespace = Runtime::Namespace.path)
click_on namespace
end
end
end
end
end
end
...@@ -14,6 +14,7 @@ module QA ...@@ -14,6 +14,7 @@ module QA
element :project_path, 'text_field :path' element :project_path, 'text_field :path'
element :project_description, 'text_area :description' element :project_description, 'text_area :description'
element :project_create_button, "submit 'Create project'" element :project_create_button, "submit 'Create project'"
element :visibility_radios, 'visibility_level:'
end end
view 'app/views/projects/_import_project_pane.html.haml' do view 'app/views/projects/_import_project_pane.html.haml' do
...@@ -42,6 +43,10 @@ module QA ...@@ -42,6 +43,10 @@ module QA
click_on 'Create project' click_on 'Create project'
end end
def set_visibility(visibility)
choose visibility
end
def go_to_github_import def go_to_github_import
click_link 'GitHub' click_link 'GitHub'
end end
......
...@@ -22,6 +22,11 @@ module QA ...@@ -22,6 +22,11 @@ module QA
element :branches_dropdown element :branches_dropdown
end end
view 'app/views/projects/buttons/_fork.html.haml' do
element :fork_label, "%span= s_('GoToYourFork|Fork')"
element :fork_link, "link_to new_project_fork_path(@project)"
end
view 'app/views/projects/_files.html.haml' do view 'app/views/projects/_files.html.haml' do
element :tree_holder, '.tree-holder' element :tree_holder, '.tree-holder'
end end
...@@ -61,6 +66,10 @@ module QA ...@@ -61,6 +66,10 @@ module QA
click_link 'New issue' click_link 'New issue'
end end
def fork_project
click_on 'Fork'
end
end end
end end
end end
......
module QA
describe 'standard user login', :core do
it 'user logs in using credentials' do
Runtime::Browser.visit(:gitlab, Page::Main::Login)
Page::Main::Login.act { sign_in_using_credentials }
# TODO, since `Signed in successfully` message was removed
# this is the only way to tell if user is signed in correctly.
#
Page::Menu::Main.perform do |menu|
expect(menu).to have_personal_area
end
end
end
end
module QA
describe 'Project fork', :core do
it 'can submit merge requests to upstream master' do
Runtime::Browser.visit(:gitlab, Page::Main::Login)
Page::Main::Login.act { sign_in_using_credentials }
merge_request = Factory::Resource::MergeRequestFromFork.fabricate! do |merge_request|
merge_request.fork_branch = 'feature-branch'
end
Page::Menu::Main.act { sign_out }
Page::Main::Login.act do
switch_to_sign_in_tab
sign_in_using_credentials
end
merge_request.visit!
Page::MergeRequest::Show.act { merge! }
expect(page).to have_content('The changes were merged')
end
end
end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment