diff --git a/app/controllers/homepage_controller.rb b/app/controllers/homepage_controller.rb index f19b88927..533be5d55 100644 --- a/app/controllers/homepage_controller.rb +++ b/app/controllers/homepage_controller.rb @@ -45,8 +45,38 @@ def publish redirect_to show_popular_links_path end + def destroy + if @latest_popular_links.can_delete? + @latest_popular_links.delete ? flash[:success] = "Popular links draft deleted.".html_safe : flash[:danger] = application_error_message + else + flash[:danger] = cannot_delete_published_error_message + end + rescue StandardError => e + Rails.logger.error "Error #{e.class} #{e.message}" + flash[:danger] = application_error_message + ensure + redirect_to show_popular_links_path + end + + def confirm_destroy + if @latest_popular_links.can_delete? + render "homepage/popular_links/confirm_destroy" + else + flash[:danger] = cannot_delete_published_error_message + redirect_to show_popular_links_path + end + end + private + def cannot_delete_published_error_message + "Can't delete an already published edition. Please create a new edition to make changes.".html_safe + end + + def application_error_message + "Due to an application error, the draft couldn't be deleted.".html_safe + end + def rescue_already_published_error(error) already_published_error?(JSON.parse(error.http_body)) ? "Popular links publish was unsuccessful, cannot publish an already published content item.".html_safe : publishing_api_publish_error_message end diff --git a/app/models/popular_links_edition.rb b/app/models/popular_links_edition.rb index 61d8f76aa..e08bfb097 100644 --- a/app/models/popular_links_edition.rb +++ b/app/models/popular_links_edition.rb @@ -59,4 +59,8 @@ def update_type def locale "en".freeze end + + def can_delete? + state == "draft" + end end diff --git a/app/views/homepage/popular_links/_sidebar.html.erb b/app/views/homepage/popular_links/_sidebar.html.erb index f1e96744d..e7af7524a 100644 --- a/app/views/homepage/popular_links/_sidebar.html.erb +++ b/app/views/homepage/popular_links/_sidebar.html.erb @@ -16,8 +16,9 @@ items: [ primary_link_button_for(edit_popular_links_path(@latest_popular_links), "Edit popular links") , secondary_button_for(@latest_popular_links, publish_popular_links_path(@latest_popular_links), "Publish"), - link_to("Preview (opens in new tab)", preview_homepage_path(@latest_popular_links), rel:"noreferrer noopener", target:"_blank", class: "govuk-link") - ] + link_to("Preview (opens in new tab)", preview_homepage_path(@latest_popular_links), rel:"noreferrer noopener", target:"_blank", class: "govuk-link"), + link_to("Delete draft", confirm_destroy_popular_links_path(@latest_popular_links), class: "govuk-link gem-link--destructive") + ] } %> <% end %> - + \ No newline at end of file diff --git a/app/views/homepage/popular_links/confirm_destroy.html.erb b/app/views/homepage/popular_links/confirm_destroy.html.erb new file mode 100644 index 000000000..1cd9f1a0c --- /dev/null +++ b/app/views/homepage/popular_links/confirm_destroy.html.erb @@ -0,0 +1,16 @@ +<% content_for :context, @latest_popular_links.title %> +<% content_for :page_title, "Delete draft" %> +<% content_for :title, "Delete draft" %> + +
+ <%= form_tag delete_popular_links_path(@latest_popular_links), method: :delete do %> +

Are you sure you want to delete this draft?

+
+ <%= render "govuk_publishing_components/components/button", { + text: "Delete", + destructive: true, + } %> + <%= link_to("Cancel", show_popular_links_path, class: "govuk-link govuk-link--no-visited-state") %> +
+ <% end %> +
diff --git a/config/routes.rb b/config/routes.rb index ffede8933..3194bb031 100644 --- a/config/routes.rb +++ b/config/routes.rb @@ -82,6 +82,9 @@ patch "/homepage/popular-links/:id" => "homepage#update", as: "update_popular_links" post "/homepage/popular-links/:id/publish" => "homepage#publish", as: "publish_popular_links" + delete "/homepage/popular-links/:id" => "homepage#destroy", as: "delete_popular_links" + get "homepage/popular-links/:id/confirm-destroy" => "homepage#confirm_destroy", as: "confirm_destroy_popular_links" + mount GovukAdminTemplate::Engine, at: "/style-guide" mount Flipflop::Engine => "/flipflop" mount GovukPublishingComponents::Engine, at: "/component-guide" diff --git a/test/functional/homepage_controller_test.rb b/test/functional/homepage_controller_test.rb index b62d04f44..e6d32a439 100644 --- a/test/functional/homepage_controller_test.rb +++ b/test/functional/homepage_controller_test.rb @@ -254,6 +254,86 @@ class HomepageControllerTest < ActionController::TestCase end end + context "#confirm_destroy" do + should "render confirm destroy page for draft edition" do + popular_links = FactoryBot.create(:popular_links, state: "draft") + + get :confirm_destroy, params: { id: popular_links.id } + + assert_template "homepage/popular_links/confirm_destroy" + end + + should "redirect with error message if edition is published" do + popular_links = FactoryBot.create(:popular_links, state: "published") + + get :confirm_destroy, params: { id: popular_links.id } + + assert_redirected_to show_popular_links_path + assert_equal "Can't delete an already published edition. Please create a new edition to make changes.", flash[:danger] + end + end + + context "#destroy" do + context "edition is draft" do + setup do + @popular_links = FactoryBot.create(:popular_links, state: "draft") + get :confirm_destroy, params: { id: @popular_links.id } + end + + should "delete the popular links from the database and display success message" do + assert_equal 1, PopularLinksEdition.count + + delete :destroy, params: { id: @popular_links.id } + + assert_equal 0, PopularLinksEdition.count + assert_equal "Popular links draft deleted.", flash[:success] + end + + should "redirect to show path on success" do + delete :destroy, params: { id: @popular_links.id } + + assert_redirected_to show_popular_links_path + end + + should "redirect to show page with 'application error' if delete edition returns false" do + PopularLinksEdition.any_instance.stubs(:delete).returns(false) + + delete :destroy, params: { id: @popular_links.id } + + assert_equal "Due to an application error, the draft couldn't be deleted.", flash[:danger] + assert_redirected_to show_popular_links_path + end + end + + context "edition is published" do + setup do + @popular_links = FactoryBot.create(:popular_links, state: "published", version_number: "2") + end + + should "show 'cant delete published edition' when trying to delete a published edition" do + delete :destroy, params: { id: @popular_links.id } + + assert_equal "Can't delete an already published edition. Please create a new edition to make changes.", flash[:danger] + assert_redirected_to show_popular_links_path + end + end + + context "database errors" do + setup do + @popular_links = FactoryBot.create(:popular_links, state: "draft") + end + + should "redirect to show page and alert 'application error'" do + PopularLinksEdition.any_instance.stubs(:delete).raises(Mongoid::Errors::MongoidError.new) + + delete :destroy, params: { id: @popular_links.id } + + assert_equal "Due to an application error, the draft couldn't be deleted.", flash[:danger] + assert_redirected_to show_popular_links_path + end + end + end + private def stub_publishing_api_publish_already_published_error diff --git a/test/integration/homepage_popular_links_test.rb b/test/integration/homepage_popular_links_test.rb index 9fb0f8305..bb25687e9 100644 --- a/test/integration/homepage_popular_links_test.rb +++ b/test/integration/homepage_popular_links_test.rb @@ -69,6 +69,12 @@ class HomepagePopularLinksTest < JavascriptIntegrationTest assert page.has_link?("Preview (opens in new tab)", href: /#{Plek.external_url_for('draft-origin')}/) end + should "have 'delete draft' link navigating to 'confirm destroy' page" do + click_button("Create new edition") + + assert page.has_link?("Delete draft", href: /confirm-destroy/) + end + should "create a new record with next version and 'draft' status" do row = find_all(".govuk-summary-list__row") assert row[0].has_text?("Edition") @@ -158,6 +164,47 @@ class HomepagePopularLinksTest < JavascriptIntegrationTest end end + context "#confirm_destroy" do + setup do + click_button("Create new edition") + end + + should "show the 'Delete draft' confirmation page" do + click_link("Delete draft") + + assert page.has_text?("Delete draft") + assert page.has_text?("Are you sure you want to delete this draft?") + end + + should "navigate to show page when 'Cancel' button is clicked" do + click_link("Delete draft") + click_link("Cancel") + + assert_title "Popular on GOV.UK" + end + end + + context "#destroy" do + setup do + click_button("Create new edition") + end + + should "show the previously published edition when a draft is deleted" do + row = find_all(".govuk-summary-list__row") + assert row[0].has_text?("Edition") + assert row[0].has_text?("2") + assert row[1].has_text?("Draft") + + click_link("Delete draft") + click_button("Delete") + + row = find_all(".govuk-summary-list__row") + assert row[0].has_text?("Edition") + assert row[0].has_text?("1") + assert row[1].has_text?("Published") + end + end + def visit_popular_links visit "/homepage/popular-links" end