parent
bff8926898
commit
1da55e4095
@ -0,0 +1,199 @@ |
|||||||
|
require 'spec_helper' |
||||||
|
|
||||||
|
require 'features/work_packages/shared_contexts' |
||||||
|
require 'features/work_packages/details/inplace_editor/shared_examples' |
||||||
|
|
||||||
|
describe 'activity comments', |
||||||
|
with_settings: { text_formatting: 'markdown' }, |
||||||
|
js: true do |
||||||
|
let(:project) { FactoryGirl.create :project, is_public: true } |
||||||
|
let!(:work_package) { |
||||||
|
FactoryGirl.create(:work_package, |
||||||
|
project: project, |
||||||
|
journal_notes: initial_comment) |
||||||
|
} |
||||||
|
let(:wp_page) { Pages::SplitWorkPackage.new(work_package, project) } |
||||||
|
let(:selector) { '.work-packages--activity--add-comment' } |
||||||
|
let(:comment_field) { |
||||||
|
WorkPackageEditorField.new wp_page, |
||||||
|
'comment', |
||||||
|
selector: selector |
||||||
|
} |
||||||
|
let(:initial_comment) { 'the first comment in this WP' } |
||||||
|
|
||||||
|
before do |
||||||
|
login_as(current_user) |
||||||
|
allow(current_user.pref).to receive(:warn_on_leaving_unsaved?).and_return(false) |
||||||
|
end |
||||||
|
|
||||||
|
context 'with permission' do |
||||||
|
let(:current_user) { FactoryGirl.create :admin } |
||||||
|
|
||||||
|
before do |
||||||
|
wp_page.visit! |
||||||
|
wp_page.ensure_page_loaded |
||||||
|
end |
||||||
|
|
||||||
|
context 'in edit state' do |
||||||
|
before do |
||||||
|
comment_field.activate! |
||||||
|
end |
||||||
|
|
||||||
|
describe 'submitting comment' do |
||||||
|
it 'does not submit with enter' do |
||||||
|
comment_field.input_element.set 'this is a comment' |
||||||
|
comment_field.submit_by_enter |
||||||
|
|
||||||
|
expect(page).to_not have_selector('.user-comment .message', text: 'this is a comment') |
||||||
|
end |
||||||
|
|
||||||
|
it 'submits with click' do |
||||||
|
comment_field.input_element.set 'this is a comment!1' |
||||||
|
comment_field.submit_by_click |
||||||
|
|
||||||
|
expect(page).to have_selector('.user-comment .message', text: 'this is a comment!1') |
||||||
|
end |
||||||
|
|
||||||
|
it 'submits comments repeatedly' do |
||||||
|
comment_field.input_element.set 'this is my first comment!1' |
||||||
|
comment_field.submit_by_click |
||||||
|
|
||||||
|
expect(page).to have_selector('.user-comment > .message', count: 2) |
||||||
|
expect(page).to have_selector('.user-comment > .message', |
||||||
|
text: 'this is my first comment!1') |
||||||
|
|
||||||
|
expect(comment_field.editing?).to be false |
||||||
|
comment_field.activate! |
||||||
|
expect(comment_field.editing?).to be true |
||||||
|
|
||||||
|
comment_field.input_element.set 'this is my second comment!1' |
||||||
|
comment_field.submit_by_click |
||||||
|
|
||||||
|
expect(page).to have_selector('.user-comment > .message', count: 3) |
||||||
|
expect(page).to have_selector('.user-comment > .message', |
||||||
|
text: 'this is my second comment!1') |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
describe 'cancel comment' do |
||||||
|
it do |
||||||
|
expect(comment_field.editing?).to be true |
||||||
|
comment_field.input_element.set 'this is a comment' |
||||||
|
|
||||||
|
# Escape should NOT cancel the editing |
||||||
|
comment_field.cancel_by_escape |
||||||
|
expect(comment_field.editing?).to be true |
||||||
|
|
||||||
|
expect(page).to_not have_selector('.user-comment .message', text: 'this is a comment') |
||||||
|
|
||||||
|
# Click should cancel the editing |
||||||
|
comment_field.cancel_by_click |
||||||
|
expect(comment_field.editing?).to be false |
||||||
|
|
||||||
|
expect(page).to_not have_selector('.user-comment .message', text: 'this is a comment') |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
describe 'autocomplete' do |
||||||
|
before do |
||||||
|
skip 'at.js/autocompleter does not work (yet) in CKEditor' |
||||||
|
end |
||||||
|
|
||||||
|
describe 'work packages' do |
||||||
|
let!(:wp2) { FactoryGirl.create(:work_package, project: project, subject: 'AutoFoo') } |
||||||
|
it 'autocompletes the other work package' do |
||||||
|
comment_field.input_element.send_keys("##{wp2.id}") |
||||||
|
expect(page).to have_selector('.atwho-view-ul li', text: wp2.to_s.strip) |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
describe 'users' do |
||||||
|
it_behaves_like 'a principal autocomplete field' do |
||||||
|
let(:field) { comment_field } |
||||||
|
end |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
describe 'quoting' do |
||||||
|
it 'can quote a previous comment' do |
||||||
|
expect(page).to have_selector('.user-comment .message', |
||||||
|
text: initial_comment) |
||||||
|
|
||||||
|
# Hover comment |
||||||
|
page.find('.user-comment > .message').hover |
||||||
|
|
||||||
|
# Quote this comment |
||||||
|
page.find('.comments-icons .icon-quote').click |
||||||
|
expect(comment_field.editing?).to be true |
||||||
|
|
||||||
|
# Add our comment |
||||||
|
quote = comment_field.input_element[:value] |
||||||
|
expect(quote).to include("> #{initial_comment}") |
||||||
|
quote << "\nthis is **some remark** under a quote" |
||||||
|
comment_field.input_element.set(quote) |
||||||
|
comment_field.submit_by_click |
||||||
|
|
||||||
|
expect(page).to have_selector('.user-comment > .message', count: 2) |
||||||
|
expect(page).to have_selector('.user-comment > .message blockquote') |
||||||
|
expect(page).to have_selector('.user-comment > .message strong') |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
describe 'with an existing comment' do |
||||||
|
it 'allows to edit an existing comment' do |
||||||
|
comment_field.input_element.set 'Comment with **bold text**' |
||||||
|
comment_field.submit_by_click |
||||||
|
|
||||||
|
expect(page).to have_selector('.user-comment .message strong', text: 'bold text') |
||||||
|
expect(page).to have_selector('.user-comment .message', text: 'Comment with bold text') |
||||||
|
|
||||||
|
# Hover the new activity |
||||||
|
activity = page.find('#activity-2') |
||||||
|
page.driver.browser.action.move_to(activity.native).perform |
||||||
|
|
||||||
|
# Check the edit textarea |
||||||
|
activity.find('.icon-edit').click |
||||||
|
edit = WorkPackageEditorField.new wp_page, |
||||||
|
'comment', |
||||||
|
selector: '.user-comment--form' |
||||||
|
|
||||||
|
edit.expect_value 'Comment with **bold text**' |
||||||
|
edit.set_value 'Comment with _italic text_' |
||||||
|
|
||||||
|
edit.submit_by_click |
||||||
|
expect(page).to have_selector('.user-comment .message em', text: 'italic text') |
||||||
|
expect(page).to have_selector('.user-comment .message', text: 'Comment with italic text') |
||||||
|
|
||||||
|
# Clear the comment |
||||||
|
activity = page.find('#activity-2') |
||||||
|
page.driver.browser.action.move_to(activity.native).perform |
||||||
|
|
||||||
|
# Check the edit textarea |
||||||
|
activity.find('.icon-edit').click |
||||||
|
edit = WorkPackageEditorField.new wp_page, |
||||||
|
'comment', |
||||||
|
selector: '.user-comment--form' |
||||||
|
|
||||||
|
edit.set_value '' |
||||||
|
edit.submit_by_click |
||||||
|
|
||||||
|
expect(page).to have_no_selector('#activity-2 .user-comment .message em', text: 'italic text') |
||||||
|
end |
||||||
|
end |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
context 'with no permission' do |
||||||
|
let(:current_user) { FactoryGirl.create(:user, member_in_project: project, member_through_role: role) } |
||||||
|
let(:role) { FactoryGirl.create :role, permissions: %i(view_work_packages) } |
||||||
|
|
||||||
|
before do |
||||||
|
wp_page.visit! |
||||||
|
wp_page.ensure_page_loaded |
||||||
|
end |
||||||
|
|
||||||
|
it 'does not show the field' do |
||||||
|
expect(page).to have_no_selector(selector, visible: true) |
||||||
|
end |
||||||
|
end |
||||||
|
end |
@ -0,0 +1,130 @@ |
|||||||
|
#-- copyright |
||||||
|
# OpenProject is a project management system. |
||||||
|
# Copyright (C) 2012-2018 the OpenProject Foundation (OPF) |
||||||
|
# |
||||||
|
# This program is free software; you can redistribute it and/or |
||||||
|
# modify it under the terms of the GNU General Public License version 3. |
||||||
|
# |
||||||
|
# OpenProject is a fork of ChiliProject, which is a fork of Redmine. The copyright follows: |
||||||
|
# Copyright (C) 2006-2017 Jean-Philippe Lang |
||||||
|
# Copyright (C) 2010-2013 the ChiliProject Team |
||||||
|
# |
||||||
|
# This program is free software; you can redistribute it and/or |
||||||
|
# modify it under the terms of the GNU General Public License |
||||||
|
# as published by the Free Software Foundation; either version 2 |
||||||
|
# of the License, or (at your option) any later version. |
||||||
|
# |
||||||
|
# This program is distributed in the hope that it will be useful, |
||||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||||
|
# GNU General Public License for more details. |
||||||
|
# |
||||||
|
# You should have received a copy of the GNU General Public License |
||||||
|
# along with this program; if not, write to the Free Software |
||||||
|
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. |
||||||
|
# |
||||||
|
# See docs/COPYRIGHT.rdoc for more details. |
||||||
|
#++ |
||||||
|
|
||||||
|
require 'spec_helper' |
||||||
|
require 'features/work_packages/details/inplace_editor/shared_examples' |
||||||
|
require 'features/work_packages/shared_contexts' |
||||||
|
require 'support/work_packages/work_package_field' |
||||||
|
require 'features/work_packages/work_packages_page' |
||||||
|
|
||||||
|
describe 'description inplace editor', js: true, selenium: true do |
||||||
|
let(:project) { FactoryGirl.create :project_with_types, is_public: true } |
||||||
|
let(:property_name) { :description } |
||||||
|
let(:property_title) { 'Description' } |
||||||
|
let(:description_text) { 'Ima description' } |
||||||
|
let!(:work_package) { |
||||||
|
FactoryGirl.create( |
||||||
|
:work_package, |
||||||
|
project: project, |
||||||
|
description: description_text |
||||||
|
) |
||||||
|
} |
||||||
|
let(:user) { FactoryGirl.create :admin } |
||||||
|
let(:field) { WorkPackageEditorField.new wp_page, 'description' } |
||||||
|
let(:wp_page) { Pages::SplitWorkPackage.new(work_package, project) } |
||||||
|
|
||||||
|
before do |
||||||
|
login_as(user) |
||||||
|
|
||||||
|
wp_page.visit! |
||||||
|
wp_page.ensure_page_loaded |
||||||
|
end |
||||||
|
|
||||||
|
context 'with permission' do |
||||||
|
it 'allows editing description field' do |
||||||
|
field.expect_state_text(description_text) |
||||||
|
|
||||||
|
# Regression test #24033 |
||||||
|
# Cancelling an edition several tiems properly resets the value |
||||||
|
field.activate! |
||||||
|
|
||||||
|
field.set_value "My intermittent edit 1" |
||||||
|
field.cancel_by_escape |
||||||
|
|
||||||
|
field.activate! |
||||||
|
field.set_value "My intermittent edit 2" |
||||||
|
field.cancel_by_click |
||||||
|
|
||||||
|
field.activate! |
||||||
|
field.expect_value description_text |
||||||
|
field.cancel_by_click |
||||||
|
|
||||||
|
# Activate the field |
||||||
|
field.activate! |
||||||
|
|
||||||
|
# Pressing escape does nothing here |
||||||
|
field.cancel_by_escape |
||||||
|
field.expect_active! |
||||||
|
|
||||||
|
# Cancelling through the action panel |
||||||
|
field.cancel_by_click |
||||||
|
field.expect_inactive! |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
context 'when is empty' do |
||||||
|
let(:description_text) { '' } |
||||||
|
|
||||||
|
it 'renders a placeholder' do |
||||||
|
field.expect_state_text 'Click to enter description...' |
||||||
|
|
||||||
|
field.activate! |
||||||
|
# An empty description is also allowed |
||||||
|
field.expect_save_button(enabled: true) |
||||||
|
field.set_value 'A new hope ...' |
||||||
|
field.expect_save_button(enabled: true) |
||||||
|
field.submit_by_click |
||||||
|
|
||||||
|
wp_page.expect_notification message: I18n.t('js.notice_successful_update') |
||||||
|
field.expect_state_text 'A new hope ...' |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
context 'with no permission' do |
||||||
|
let(:user) { FactoryGirl.create(:user, member_in_project: project, member_through_role: role) } |
||||||
|
let(:role) { FactoryGirl.create :role, permissions: %i(view_work_packages) } |
||||||
|
|
||||||
|
it 'does not show the field' do |
||||||
|
expect(page).to have_no_selector('.wp-edit-field.description.-editable') |
||||||
|
|
||||||
|
field.display_element.click |
||||||
|
field.expect_inactive! |
||||||
|
end |
||||||
|
|
||||||
|
context 'when is empty' do |
||||||
|
let(:description_text) { '' } |
||||||
|
|
||||||
|
it 'renders a placeholder' do |
||||||
|
field.expect_state_text '' |
||||||
|
end |
||||||
|
end |
||||||
|
end |
||||||
|
|
||||||
|
it_behaves_like 'a workpackage autocomplete field' |
||||||
|
it_behaves_like 'a principal autocomplete field' |
||||||
|
end |
Loading…
Reference in new issue