diff options
-rw-r--r-- | app/assets/javascripts/pages/projects/wikis/wikis.js | 42 | ||||
-rw-r--r-- | app/controllers/projects/wikis_controller.rb | 31 | ||||
-rw-r--r-- | app/models/project_wiki.rb | 4 | ||||
-rw-r--r-- | app/views/projects/wikis/_form.html.haml | 18 | ||||
-rw-r--r-- | app/views/projects/wikis/_main_links.html.haml | 6 | ||||
-rw-r--r-- | app/views/projects/wikis/_new.html.haml | 18 | ||||
-rw-r--r-- | app/views/projects/wikis/_sidebar.html.haml | 2 | ||||
-rw-r--r-- | app/views/projects/wikis/edit.html.haml | 11 | ||||
-rw-r--r-- | changelogs/unreleased/46299-wiki-page-creation.yml | 5 | ||||
-rw-r--r-- | config/routes/wiki.rb | 1 | ||||
-rw-r--r-- | doc/user/project/wiki/index.md | 9 | ||||
-rw-r--r-- | locale/gitlab.pot | 18 | ||||
-rw-r--r-- | spec/controllers/projects/wikis_controller_spec.rb | 77 | ||||
-rw-r--r-- | spec/features/projects/wiki/markdown_preview_spec.rb | 93 | ||||
-rw-r--r-- | spec/features/projects/wiki/user_creates_wiki_page_spec.rb | 68 | ||||
-rw-r--r-- | spec/features/projects/wiki/user_updates_wiki_page_spec.rb | 16 | ||||
-rw-r--r-- | spec/features/projects/wiki/user_views_wiki_page_spec.rb | 5 | ||||
-rw-r--r-- | spec/frontend/wikis_spec.js | 74 |
18 files changed, 287 insertions, 211 deletions
diff --git a/app/assets/javascripts/pages/projects/wikis/wikis.js b/app/assets/javascripts/pages/projects/wikis/wikis.js index 9b58d42b47d..d41199f6374 100644 --- a/app/assets/javascripts/pages/projects/wikis/wikis.js +++ b/app/assets/javascripts/pages/projects/wikis/wikis.js @@ -1,6 +1,5 @@ import bp from '../../../breakpoints'; -import { parseQueryStringIntoObject } from '../../../lib/utils/common_utils'; -import { mergeUrlParams, redirectTo } from '../../../lib/utils/url_utility'; +import { s__, sprintf } from '~/locale'; export default class Wikis { constructor() { @@ -12,32 +11,37 @@ export default class Wikis { sidebarToggles[i].addEventListener('click', e => this.handleToggleSidebar(e)); } - this.newWikiForm = document.querySelector('form.new-wiki-page'); - if (this.newWikiForm) { - this.newWikiForm.addEventListener('submit', e => this.handleNewWikiSubmit(e)); + this.isNewWikiPage = Boolean(document.querySelector('.js-new-wiki-page')); + this.editTitleInput = document.querySelector('form.wiki-form #wiki_title'); + this.commitMessageInput = document.querySelector('form.wiki-form #wiki_message'); + this.commitMessageI18n = this.isNewWikiPage + ? s__('WikiPageCreate|Create %{pageTitle}') + : s__('WikiPageEdit|Update %{pageTitle}'); + + if (this.editTitleInput) { + // Initialize the commit message on load + if (this.editTitleInput.value) this.setWikiCommitMessage(this.editTitleInput.value); + + // Set the commit message as the page title is changed + this.editTitleInput.addEventListener('keyup', e => this.handleWikiTitleChange(e)); } window.addEventListener('resize', () => this.renderSidebar()); this.renderSidebar(); } - handleNewWikiSubmit(e) { - if (!this.newWikiForm) return; - - const slugInput = this.newWikiForm.querySelector('#new_wiki_path'); - - const slug = slugInput.value; + handleWikiTitleChange(e) { + this.setWikiCommitMessage(e.target.value); + } - if (slug.length > 0) { - const wikisPath = slugInput.getAttribute('data-wikis-path'); + setWikiCommitMessage(rawTitle) { + let title = rawTitle; - // If the wiki is empty, we need to merge the current URL params to keep the "create" view. - const params = parseQueryStringIntoObject(window.location.search.substr(1)); - const url = mergeUrlParams(params, `${wikisPath}/${slug}`); - redirectTo(url); + // Replace hyphens with spaces + if (title) title = title.replace(/-+/g, ' '); - e.preventDefault(); - } + const newCommitMessage = sprintf(this.commitMessageI18n, { pageTitle: title }); + this.commitMessageInput.value = newCommitMessage; } handleToggleSidebar(e) { diff --git a/app/controllers/projects/wikis_controller.rb b/app/controllers/projects/wikis_controller.rb index d1914c35bd3..b187fdb2723 100644 --- a/app/controllers/projects/wikis_controller.rb +++ b/app/controllers/projects/wikis_controller.rb @@ -16,6 +16,10 @@ class Projects::WikisController < Projects::ApplicationController redirect_to(project_wiki_path(@project, @page)) end + def new + redirect_to project_wiki_path(@project, SecureRandom.uuid, random_title: true) + end + def pages @wiki_pages = Kaminari.paginate_array( @project_wiki.list_pages(sort: params[:sort], direction: params[:direction]) @@ -24,17 +28,25 @@ class Projects::WikisController < Projects::ApplicationController @wiki_entries = WikiPage.group_by_directory(@wiki_pages) end + # `#show` handles a number of scenarios: + # + # - If `id` matches a WikiPage, then show the wiki page. + # - If `id` is a file in the wiki repository, then send the file. + # - If we know the user wants to create a new page with the given `id`, + # then display a create form. + # - Otherwise show the empty wiki page and invite the user to create a page. def show - view_param = @project_wiki.empty? ? params[:view] : 'create' - if @page set_encoding_error unless valid_encoding? render 'show' elsif file_blob send_blob(@project_wiki.repository, file_blob) - elsif can?(current_user, :create_wiki, @project) && view_param == 'create' - @page = build_page(title: params[:id]) + elsif show_create_form? + # Assign a title to the WikiPage unless `id` is a randomly generated slug from #new + title = params[:id] unless params[:random_title].present? + + @page = build_page(title: title) render 'edit' else @@ -110,6 +122,15 @@ class Projects::WikisController < Projects::ApplicationController private + def show_create_form? + can?(current_user, :create_wiki, @project) && + @page.nil? && + # Always show the create form when the wiki has had at least one page created. + # Otherwise, we only show the form when the user has navigated from + # the 'empty wiki' page + (@project_wiki.exists? || params[:view] == 'create') + end + def load_project_wiki @project_wiki = load_wiki @@ -135,7 +156,7 @@ class Projects::WikisController < Projects::ApplicationController params.require(:wiki).permit(:title, :content, :format, :message, :last_commit_sha) end - def build_page(args) + def build_page(args = {}) WikiPage.new(@project_wiki).tap do |page| page.update_attributes(args) # rubocop:disable Rails/ActiveRecordAliases end diff --git a/app/models/project_wiki.rb b/app/models/project_wiki.rb index c91add6439f..4a19e05bf76 100644 --- a/app/models/project_wiki.rb +++ b/app/models/project_wiki.rb @@ -85,6 +85,10 @@ class ProjectWiki list_pages(limit: 1).empty? end + def exists? + !empty? + end + # Lists wiki pages of the repository. # # limit - max number of pages returned by the method. diff --git a/app/views/projects/wikis/_form.html.haml b/app/views/projects/wikis/_form.html.haml index 858731b2dda..a153f527ee0 100644 --- a/app/views/projects/wikis/_form.html.haml +++ b/app/views/projects/wikis/_form.html.haml @@ -1,8 +1,8 @@ -- commit_message = @page.persisted? ? s_("WikiPageEdit|Update %{page_title}") : s_("WikiPageCreate|Create %{page_title}") -- commit_message = commit_message % { page_title: @page.title } +- form_classes = 'wiki-form common-note-form prepend-top-default js-quick-submit' +- form_classes += ' js-new-wiki-page' unless @page.persisted? = form_for [@project.namespace.becomes(Namespace), @project, @page], method: @page.persisted? ? :put : :post, - html: { class: 'wiki-form common-note-form prepend-top-default js-quick-submit' }, + html: { class: form_classes }, data: { uploads_path: uploads_path } do |f| = form_errors(@page) @@ -12,12 +12,14 @@ .form-group.row .col-sm-12= f.label :title, class: 'control-label-full-width' .col-sm-12 - = f.text_field :title, class: 'form-control qa-wiki-title-textbox', value: @page.title - - if @page.persisted? - %span.d-inline-block.mw-100.prepend-top-5 - = icon('lightbulb-o') + = f.text_field :title, class: 'form-control qa-wiki-title-textbox', value: @page.title, required: true, autofocus: !@page.persisted?, placeholder: _('Wiki|Page title') + %span.d-inline-block.mw-100.prepend-top-5 + = icon('lightbulb-o') + - if @page.persisted? = s_("WikiEditPageTip|Tip: You can move this page by adding the path to the beginning of the title.") = link_to icon('question-circle'), help_page_path('user/project/wiki/index', anchor: 'moving-a-wiki-page'), target: '_blank' + - else + = s_("WikiNewPageTip|Tip: You can specify the full path for the new file. We will automatically create any missing directories.") .form-group.row .col-sm-12= f.label :format, class: 'control-label-full-width' .col-sm-12 @@ -43,7 +45,7 @@ .form-group.row .col-sm-12= f.label :commit_message, class: 'control-label-full-width' - .col-sm-12= f.text_field :message, class: 'form-control qa-wiki-message-textbox', rows: 18, value: commit_message + .col-sm-12= f.text_field :message, class: 'form-control qa-wiki-message-textbox', rows: 18, value: nil .form-actions - if @page && @page.persisted? diff --git a/app/views/projects/wikis/_main_links.html.haml b/app/views/projects/wikis/_main_links.html.haml index 643b51e01d1..2e1e176c42a 100644 --- a/app/views/projects/wikis/_main_links.html.haml +++ b/app/views/projects/wikis/_main_links.html.haml @@ -1,9 +1,9 @@ - if (@page && @page.persisted?) - if can?(current_user, :create_wiki, @project) - = link_to '#modal-new-wiki', class: "add-new-wiki btn btn-success", "data-toggle" => "modal" do + = link_to project_wikis_new_path(@project), class: "add-new-wiki btn btn-success", role: "button" do = s_("Wiki|New page") - = link_to project_wiki_history_path(@project, @page), class: "btn" do + = link_to project_wiki_history_path(@project, @page), class: "btn", role: "button" do = s_("Wiki|Page history") - if can?(current_user, :create_wiki, @project) && @page.latest? && @valid_encoding - = link_to project_wiki_edit_path(@project, @page), class: "btn js-wiki-edit" do + = link_to project_wiki_edit_path(@project, @page), class: "btn js-wiki-edit", role: "button" do = _("Edit") diff --git a/app/views/projects/wikis/_new.html.haml b/app/views/projects/wikis/_new.html.haml deleted file mode 100644 index 2c675c0de9c..00000000000 --- a/app/views/projects/wikis/_new.html.haml +++ /dev/null @@ -1,18 +0,0 @@ -#modal-new-wiki.modal - .modal-dialog - .modal-content - .modal-header - %h3.page-title= s_("WikiNewPageTitle|New Wiki Page") - %button.close{ type: "button", "data-dismiss": "modal", "aria-label" => _('Close') } - %span{ "aria-hidden": true } × - .modal-body - %form.new-wiki-page - .form-group - = label_tag :new_wiki_path do - %span= s_("WikiPage|Page slug") - = text_field_tag :new_wiki_path, nil, placeholder: s_("WikiNewPagePlaceholder|how-to-setup"), class: 'form-control', required: true, :'data-wikis-path' => project_wikis_path(@project), autofocus: true - %span.d-inline-block.mw-100.prepend-top-5 - = icon('lightbulb-o') - = s_("WikiNewPageTip|Tip: You can specify the full path for the new file. We will automatically create any missing directories.") - .form-actions - = button_tag s_("Wiki|Create page"), class: "build-new-wiki btn btn-success" diff --git a/app/views/projects/wikis/_sidebar.html.haml b/app/views/projects/wikis/_sidebar.html.haml index 28353927135..a9d21470944 100644 --- a/app/views/projects/wikis/_sidebar.html.haml +++ b/app/views/projects/wikis/_sidebar.html.haml @@ -19,5 +19,3 @@ .block = link_to project_wikis_pages_path(@project), class: 'btn btn-block' do = s_("Wiki|More Pages") - -= render 'projects/wikis/new' diff --git a/app/views/projects/wikis/edit.html.haml b/app/views/projects/wikis/edit.html.haml index e8b59a3b8c4..815b4a51261 100644 --- a/app/views/projects/wikis/edit.html.haml +++ b/app/views/projects/wikis/edit.html.haml @@ -13,14 +13,11 @@ %h2.wiki-page-title - if @page.persisted? = link_to @page.human_title, project_wiki_path(@project, @page) - - else - = @page.human_title - %span.light - · - - if @page.persisted? + %span.light + · = s_("Wiki|Edit Page") - - else - = s_("Wiki|Create Page") + - else + = s_("Wiki|Create New Page") .nav-controls - if @page.persisted? diff --git a/changelogs/unreleased/46299-wiki-page-creation.yml b/changelogs/unreleased/46299-wiki-page-creation.yml new file mode 100644 index 00000000000..2e8f2accf45 --- /dev/null +++ b/changelogs/unreleased/46299-wiki-page-creation.yml @@ -0,0 +1,5 @@ +--- +title: Remove wiki page slug dialog step when creating wiki page +merge_request: 31362 +author: +type: changed diff --git a/config/routes/wiki.rb b/config/routes/wiki.rb index 2ca52e55fca..d439c99270e 100644 --- a/config/routes/wiki.rb +++ b/config/routes/wiki.rb @@ -2,6 +2,7 @@ scope(controller: :wikis) do scope(path: 'wikis', as: :wikis) do get :git_access get :pages + get :new get '/', to: redirect('%{namespace_id}/%{project_id}/wikis/home') post '/', to: 'wikis#create' end diff --git a/doc/user/project/wiki/index.md b/doc/user/project/wiki/index.md index e3c6cd6d6ff..d1bab47de25 100644 --- a/doc/user/project/wiki/index.md +++ b/doc/user/project/wiki/index.md @@ -28,11 +28,12 @@ NOTE: **Note:** Requires Developer [permissions](../../permissions.md). Create a new page by clicking the **New page** button that can be found -in all wiki pages. You will be asked to fill in the page name from which GitLab -will create the path to the page. You can specify a full path for the new file -and any missing directories will be created automatically. +in all wiki pages. -![New page modal](img/wiki_create_new_page_modal.png) +You will be asked to fill in a title for your new wiki page. Wiki titles +also determine the path to the wiki page. You can specify a full path +(using "`/`" for subdirectories) for the new title and any missing +directories will be created automatically. Once you enter the page name, it's time to fill in its content. GitLab wikis support Markdown, RDoc and AsciiDoc. For Markdown based pages, all the diff --git a/locale/gitlab.pot b/locale/gitlab.pot index e580433fcaa..6776bc3ea24 100644 --- a/locale/gitlab.pot +++ b/locale/gitlab.pot @@ -12888,15 +12888,9 @@ msgstr "" msgid "WikiMarkdownTip|To link to a (new) page, simply type %{link_example}" msgstr "" -msgid "WikiNewPagePlaceholder|how-to-setup" -msgstr "" - msgid "WikiNewPageTip|Tip: You can specify the full path for the new file. We will automatically create any missing directories." msgstr "" -msgid "WikiNewPageTitle|New Wiki Page" -msgstr "" - msgid "WikiPageConfirmDelete|Are you sure you want to delete this page?" msgstr "" @@ -12912,19 +12906,16 @@ msgstr "" msgid "WikiPageConflictMessage|the page" msgstr "" -msgid "WikiPageCreate|Create %{page_title}" +msgid "WikiPageCreate|Create %{pageTitle}" msgstr "" -msgid "WikiPageEdit|Update %{page_title}" -msgstr "" - -msgid "WikiPage|Page slug" +msgid "WikiPageEdit|Update %{pageTitle}" msgstr "" msgid "WikiPage|Write your content or drag files here…" msgstr "" -msgid "Wiki|Create Page" +msgid "Wiki|Create New Page" msgstr "" msgid "Wiki|Create page" @@ -12945,6 +12936,9 @@ msgstr "" msgid "Wiki|Page history" msgstr "" +msgid "Wiki|Page title" +msgstr "" + msgid "Wiki|Page version" msgstr "" diff --git a/spec/controllers/projects/wikis_controller_spec.rb b/spec/controllers/projects/wikis_controller_spec.rb index fbca1d5740f..6fea6bca4f2 100644 --- a/spec/controllers/projects/wikis_controller_spec.rb +++ b/spec/controllers/projects/wikis_controller_spec.rb @@ -3,11 +3,11 @@ require 'spec_helper' describe Projects::WikisController do - let(:project) { create(:project, :public, :repository) } - let(:user) { project.owner } + set(:project) { create(:project, :public, :repository) } + set(:user) { project.owner } let(:project_wiki) { ProjectWiki.new(project, user) } let(:wiki) { project_wiki.wiki } - let(:wiki_title) { 'page-title-test' } + let(:wiki_title) { 'page title test' } before do create_page(wiki_title, 'hello world') @@ -19,6 +19,21 @@ describe Projects::WikisController do destroy_page(wiki_title) end + describe 'GET #new' do + subject { get :new, params: { namespace_id: project.namespace, project_id: project } } + + it 'redirects to #show and appends a `random_title` param' do + subject + + expect(response).to have_http_status(302) + expect(Rails.application.routes.recognize_path(response.redirect_url)).to include( + controller: 'projects/wikis', + action: 'show' + ) + expect(response.redirect_url).to match(/\?random_title=true\Z/) + end + end + describe 'GET #pages' do subject { get :pages, params: { namespace_id: project.namespace, project_id: project, id: wiki_title } } @@ -75,40 +90,62 @@ describe Projects::WikisController do describe 'GET #show' do render_views - subject { get :show, params: { namespace_id: project.namespace, project_id: project, id: wiki_title } } + let(:random_title) { nil } - it 'limits the retrieved pages for the sidebar' do - expect(controller).to receive(:load_wiki).and_return(project_wiki) + subject { get :show, params: { namespace_id: project.namespace, project_id: project, id: id, random_title: random_title } } - # empty? call - expect(project_wiki).to receive(:list_pages).with(limit: 1).and_call_original - # Sidebar entries - expect(project_wiki).to receive(:list_pages).with(limit: 15).and_call_original + context 'when page exists' do + let(:id) { wiki_title } - subject + it 'limits the retrieved pages for the sidebar' do + expect(controller).to receive(:load_wiki).and_return(project_wiki) + expect(project_wiki).to receive(:list_pages).with(limit: 15).and_call_original + + subject + + expect(response).to have_http_status(:ok) + expect(assigns(:page).title).to eq(wiki_title) + end + + context 'when page content encoding is invalid' do + it 'sets flash error' do + allow(controller).to receive(:valid_encoding?).and_return(false) - expect(response).to have_http_status(:ok) - expect(response.body).to include(wiki_title) + subject + + expect(response).to have_http_status(:ok) + expect(flash[:notice]).to eq('The content of this page is not encoded in UTF-8. Edits can only be made via the Git repository.') + end + end end - context 'when page content encoding is invalid' do - it 'sets flash error' do - allow(controller).to receive(:valid_encoding?).and_return(false) + context 'when the page does not exist' do + let(:id) { 'does not exist' } + before do subject + end - expect(response).to have_http_status(:ok) - expect(flash[:notice]).to eq 'The content of this page is not encoded in UTF-8. Edits can only be made via the Git repository.' + it 'builds a new wiki page with the id as the title' do + expect(assigns(:page).title).to eq(id) + end + + context 'when a random_title param is present' do + let(:random_title) { true } + + it 'builds a new wiki page with no title' do + expect(assigns(:page).title).to be_empty + end end end context 'when page is a file' do include WikiHelpers - let(:path) { upload_file_to_wiki(project, user, file_name) } + let(:id) { upload_file_to_wiki(project, user, file_name) } before do - get :show, params: { namespace_id: project.namespace, project_id: project, id: path } + subject end context 'when file is an image' do diff --git a/spec/features/projects/wiki/markdown_preview_spec.rb b/spec/features/projects/wiki/markdown_preview_spec.rb index 7b511c4d3d5..5c6b04a7141 100644 --- a/spec/features/projects/wiki/markdown_preview_spec.rb +++ b/spec/features/projects/wiki/markdown_preview_spec.rb @@ -3,7 +3,7 @@ require 'spec_helper' describe 'Projects > Wiki > User previews markdown changes', :js do - let(:user) { create(:user) } + set(:user) { create(:user) } let(:project) { create(:project, :wiki_repo, namespace: user.namespace) } let(:wiki_page) { create(:wiki_page, wiki: project.wiki, attrs: { title: 'home', content: '[some link](other-page)' }) } let(:wiki_content) do @@ -20,23 +20,12 @@ describe 'Projects > Wiki > User previews markdown changes', :js do project.add_maintainer(user) sign_in(user) - - visit project_wiki_path(project, wiki_page) end context "while creating a new wiki page" do context "when there are no spaces or hyphens in the page name" do it "rewrites relative links as expected" do - find('.add-new-wiki').click - page.within '#modal-new-wiki' do - fill_in :new_wiki_path, with: 'a/b/c/d' - click_button 'Create page' - end - - page.within '.wiki-form' do - fill_in :wiki_content, with: wiki_content - click_on "Preview" - end + create_wiki_page('a/b/c/d', content: wiki_content) expect(page).to have_content("regular link") @@ -50,16 +39,7 @@ describe 'Projects > Wiki > User previews markdown changes', :js do context "when there are spaces in the page name" do it "rewrites relative links as expected" do - click_link 'New page' - page.within '#modal-new-wiki' do - fill_in :new_wiki_path, with: 'a page/b page/c page/d page' - click_button 'Create page' - end - - page.within '.wiki-form' do - fill_in :wiki_content, with: wiki_content - click_on "Preview" - end + create_wiki_page('a page/b page/c page/d page', content: wiki_content) expect(page).to have_content("regular link") @@ -73,16 +53,7 @@ describe 'Projects > Wiki > User previews markdown changes', :js do context "when there are hyphens in the page name" do it "rewrites relative links as expected" do - click_link 'New page' - page.within '#modal-new-wiki' do - fill_in :new_wiki_path, with: 'a-page/b-page/c-page/d-page' - click_button 'Create page' - end - - page.within '.wiki-form' do - fill_in :wiki_content, with: wiki_content - click_on "Preview" - end + create_wiki_page('a-page/b-page/c-page/d-page', content: wiki_content) expect(page).to have_content("regular link") @@ -96,23 +67,9 @@ describe 'Projects > Wiki > User previews markdown changes', :js do end context "while editing a wiki page" do - def create_wiki_page(path) - find('.add-new-wiki').click - - page.within '#modal-new-wiki' do - fill_in :new_wiki_path, with: path - click_button 'Create page' - end - - page.within '.wiki-form' do - fill_in :wiki_content, with: 'content' - click_on "Create page" - end - end - context "when there are no spaces or hyphens in the page name" do it "rewrites relative links as expected" do - create_wiki_page 'a/b/c/d' + create_wiki_page('a/b/c/d') click_link 'Edit' fill_in :wiki_content, with: wiki_content @@ -130,7 +87,7 @@ describe 'Projects > Wiki > User previews markdown changes', :js do context "when there are spaces in the page name" do it "rewrites relative links as expected" do - create_wiki_page 'a page/b page/c page/d page' + create_wiki_page('a page/b page/c page/d page') click_link 'Edit' fill_in :wiki_content, with: wiki_content @@ -148,7 +105,7 @@ describe 'Projects > Wiki > User previews markdown changes', :js do context "when there are hyphens in the page name" do it "rewrites relative links as expected" do - create_wiki_page 'a-page/b-page/c-page/d-page' + create_wiki_page('a-page/b-page/c-page/d-page') click_link 'Edit' fill_in :wiki_content, with: wiki_content @@ -166,7 +123,7 @@ describe 'Projects > Wiki > User previews markdown changes', :js do context 'when rendering the preview' do it 'renders content with CommonMark' do - create_wiki_page 'a-page/b-page/c-page/common-mark' + create_wiki_page('a-page/b-page/c-page/common-mark') click_link 'Edit' fill_in :wiki_content, with: "1. one\n - sublist\n" @@ -180,25 +137,31 @@ describe 'Projects > Wiki > User previews markdown changes', :js do end it "does not linkify double brackets inside code blocks as expected" do - click_link 'New page' - page.within '#modal-new-wiki' do - fill_in :new_wiki_path, with: 'linkify_test' - click_button 'Create page' - end + wiki_content = <<-HEREDOC + `[[do_not_linkify]]` + ``` + [[also_do_not_linkify]] + ``` + HEREDOC - page.within '.wiki-form' do - fill_in :wiki_content, with: <<-HEREDOC - `[[do_not_linkify]]` - ``` - [[also_do_not_linkify]] - ``` - HEREDOC - click_on "Preview" - end + create_wiki_page('linkify_test', wiki_content) expect(page).to have_content("do_not_linkify") expect(page.html).to include('[[do_not_linkify]]') expect(page.html).to include('[[also_do_not_linkify]]') end + + private + + def create_wiki_page(path, content = 'content') + visit project_wiki_path(project, wiki_page) + + click_link 'New page' + + fill_in :wiki_title, with: path + fill_in :wiki_content, with: content + + click_button 'Create page' + end end diff --git a/spec/features/projects/wiki/user_creates_wiki_page_spec.rb b/spec/features/projects/wiki/user_creates_wiki_page_spec.rb index cc6dbaa6eb8..56d0518015d 100644 --- a/spec/features/projects/wiki/user_creates_wiki_page_spec.rb +++ b/spec/features/projects/wiki/user_creates_wiki_page_spec.rb @@ -42,10 +42,10 @@ describe "User creates wiki page" do click_link("link test") - expect(page).to have_content("Create Page") + expect(page).to have_content("Create New Page") end - it "shows non-escaped link in the pages list", :js, :quarantine do + it "shows non-escaped link in the pages list", :quarantine do fill_in(:wiki_title, with: "one/two/three-test") page.within(".wiki-form") do @@ -58,7 +58,9 @@ describe "User creates wiki page" do expect(page).to have_xpath("//a[@href='/#{project.full_path}/wikis/one/two/three-test']") end - it "has `Create home` as a commit message" do + it "has `Create home` as a commit message", :js do + wait_for_requests + expect(page).to have_field("wiki[message]", with: "Create home") end @@ -81,7 +83,7 @@ describe "User creates wiki page" do expect(current_path).to eq(project_wiki_path(project, "test")) page.within(:css, ".nav-text") do - expect(page).to have_content("test").and have_content("Create Page") + expect(page).to have_content("Create New Page") end click_link("Home") @@ -93,7 +95,7 @@ describe "User creates wiki page" do expect(current_path).to eq(project_wiki_path(project, "api")) page.within(:css, ".nav-text") do - expect(page).to have_content("Create").and have_content("api") + expect(page).to have_content("Create") end click_link("Home") @@ -105,7 +107,7 @@ describe "User creates wiki page" do expect(current_path).to eq(project_wiki_path(project, "raketasks")) page.within(:css, ".nav-text") do - expect(page).to have_content("Create").and have_content("rake") + expect(page).to have_content("Create") end end @@ -150,6 +152,8 @@ describe "User creates wiki page" do let(:project) { create(:project, :wiki_repo, namespace: create(:group, :public)) } it "has `Create home` as a commit message" do + wait_for_requests + expect(page).to have_field("wiki[message]", with: "Create home") end @@ -181,20 +185,15 @@ describe "User creates wiki page" do it "creates a page with a single word" do click_link("New page") - page.within("#modal-new-wiki") do - fill_in(:new_wiki_path, with: "foo") - - click_button("Create page") + page.within(".wiki-form") do + fill_in(:wiki_title, with: "foo") + fill_in(:wiki_content, with: "My awesome wiki!") end # Commit message field should have correct value. expect(page).to have_field("wiki[message]", with: "Create foo") - page.within(".wiki-form") do - fill_in(:wiki_content, with: "My awesome wiki!") - - click_button("Create page") - end + click_button("Create page") expect(page).to have_content("foo") .and have_content("Last edited by #{user.name}") @@ -204,20 +203,15 @@ describe "User creates wiki page" do it "creates a page with spaces in the name" do click_link("New page") - page.within("#modal-new-wiki") do - fill_in(:new_wiki_path, with: "Spaces in the name") - - click_button("Create page") + page.within(".wiki-form") do + fill_in(:wiki_title, with: "Spaces in the name") + fill_in(:wiki_content, with: "My awesome wiki!") end # Commit message field should have correct value. expect(page).to have_field("wiki[message]", with: "Create Spaces in the name") - page.within(".wiki-form") do - fill_in(:wiki_content, with: "My awesome wiki!") - - click_button("Create page") - end + click_button("Create page") expect(page).to have_content("Spaces in the name") .and have_content("Last edited by #{user.name}") @@ -227,10 +221,9 @@ describe "User creates wiki page" do it "creates a page with hyphens in the name" do click_link("New page") - page.within("#modal-new-wiki") do - fill_in(:new_wiki_path, with: "hyphens-in-the-name") - - click_button("Create page") + page.within(".wiki-form") do + fill_in(:wiki_title, with: "hyphens-in-the-name") + fill_in(:wiki_content, with: "My awesome wiki!") end # Commit message field should have correct value. @@ -251,12 +244,6 @@ describe "User creates wiki page" do it "shows the emoji autocompletion dropdown" do click_link("New page") - page.within("#modal-new-wiki") do - fill_in(:new_wiki_path, with: "test-autocomplete") - - click_button("Create page") - end - page.within(".wiki-form") do find("#wiki_content").native.send_keys("") @@ -274,20 +261,15 @@ describe "User creates wiki page" do it "creates a page" do click_link("New page") - page.within("#modal-new-wiki") do - fill_in(:new_wiki_path, with: "foo") - - click_button("Create page") + page.within(".wiki-form") do + fill_in(:wiki_title, with: "foo") + fill_in(:wiki_content, with: "My awesome wiki!") end # Commit message field should have correct value. expect(page).to have_field("wiki[message]", with: "Create foo") - page.within(".wiki-form") do - fill_in(:wiki_content, with: "My awesome wiki!") - - click_button("Create page") - end + click_button("Create page") expect(page).to have_content("foo") .and have_content("Last edited by #{user.name}") diff --git a/spec/features/projects/wiki/user_updates_wiki_page_spec.rb b/spec/features/projects/wiki/user_updates_wiki_page_spec.rb index 2aab8fda62d..3f3711f9eb8 100644 --- a/spec/features/projects/wiki/user_updates_wiki_page_spec.rb +++ b/spec/features/projects/wiki/user_updates_wiki_page_spec.rb @@ -70,7 +70,7 @@ describe 'User updates wiki page' do context 'in a user namespace' do let(:project) { create(:project, :wiki_repo) } - it 'updates a page' do + it 'updates a page', :js do # Commit message field should have correct value. expect(page).to have_field('wiki[message]', with: 'Update home') @@ -82,6 +82,18 @@ describe 'User updates wiki page' do expect(page).to have_content('My awesome wiki!') end + it 'updates the commit message as the title is changed', :js do + fill_in(:wiki_title, with: 'Wiki title') + + expect(page).to have_field('wiki[message]', with: 'Update Wiki title') + end + + it 'does not allow XSS', :js do + fill_in(:wiki_title, with: '<script>') + + expect(page).to have_field('wiki[message]', with: 'Update <script>') + end + it 'shows a validation error message' do fill_in(:wiki_content, with: '') click_button('Save changes') @@ -129,7 +141,7 @@ describe 'User updates wiki page' do context 'in a group namespace' do let(:project) { create(:project, :wiki_repo, namespace: create(:group, :public)) } - it 'updates a page' do + it 'updates a page', :js do # Commit message field should have correct value. expect(page).to have_field('wiki[message]', with: 'Update home') diff --git a/spec/features/projects/wiki/user_views_wiki_page_spec.rb b/spec/features/projects/wiki/user_views_wiki_page_spec.rb index 05742b63c43..77e725e7f11 100644 --- a/spec/features/projects/wiki/user_views_wiki_page_spec.rb +++ b/spec/features/projects/wiki/user_views_wiki_page_spec.rb @@ -101,8 +101,7 @@ describe 'User views a wiki page' do click_on('image') expect(current_path).to match("wikis/#{path}") - expect(page).to have_content('New Wiki Page') - expect(page).to have_content('Create page') + expect(page).to have_content('Create New Page') end end @@ -156,6 +155,6 @@ describe 'User views a wiki page' do find('.shortcuts-wiki').click click_link "Create your first page" - expect(page).to have_content('Home · Create Page') + expect(page).to have_content('Create New Page') end end diff --git a/spec/frontend/wikis_spec.js b/spec/frontend/wikis_spec.js new file mode 100644 index 00000000000..b2475488d97 --- /dev/null +++ b/spec/frontend/wikis_spec.js @@ -0,0 +1,74 @@ +import Wikis from '~/pages/projects/wikis/wikis'; +import { setHTMLFixture } from './helpers/fixtures'; + +describe('Wikis', () => { + describe('setting the commit message when the title changes', () => { + const editFormHtmlFixture = args => `<form class="wiki-form ${ + args.newPage ? 'js-new-wiki-page' : '' + }"> + <input type="text" id="wiki_title" value="My title" /> + <input type="text" id="wiki_message" /> + </form>`; + + let wikis; + let titleInput; + let messageInput; + + describe('when the wiki page is being created', () => { + const formHtmlFixture = editFormHtmlFixture({ newPage: true }); + + beforeEach(() => { + setHTMLFixture(formHtmlFixture); + + titleInput = document.getElementById('wiki_title'); + messageInput = document.getElementById('wiki_message'); + wikis = new Wikis(); + }); + + it('binds an event listener to the title input', () => { + wikis.handleWikiTitleChange = jest.fn(); + + titleInput.dispatchEvent(new Event('keyup')); + + expect(wikis.handleWikiTitleChange).toHaveBeenCalled(); + }); + + it('sets the commit message when title changes', () => { + titleInput.value = 'My title'; + messageInput.value = ''; + + titleInput.dispatchEvent(new Event('keyup')); + + expect(messageInput.value).toEqual('Create My title'); + }); + + it('replaces hyphens with spaces', () => { + titleInput.value = 'my-hyphenated-title'; + titleInput.dispatchEvent(new Event('keyup')); + + expect(messageInput.value).toEqual('Create my hyphenated title'); + }); + }); + + describe('when the wiki page is being updated', () => { + const formHtmlFixture = editFormHtmlFixture({ newPage: false }); + + beforeEach(() => { + setHTMLFixture(formHtmlFixture); + + titleInput = document.getElementById('wiki_title'); + messageInput = document.getElementById('wiki_message'); + wikis = new Wikis(); + }); + + it('sets the commit message when title changes, prefixing with "Update"', () => { + titleInput.value = 'My title'; + messageInput.value = ''; + + titleInput.dispatchEvent(new Event('keyup')); + + expect(messageInput.value).toEqual('Update My title'); + }); + }); + }); +}); |