From d2da2b6ee347e78b76b896ba1fc3875f44d5f631 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Francisco=20Javier=20L=C3=B3pez?= <fjlopez@gitlab.com>
Date: Thu, 8 Jul 2021 09:45:24 +0200
Subject: [PATCH] Add and refactor Kubernetes menu

In this commit we're refactoring the Kuebernetes
menu in the group sidebar.

We're moving away from partial defined logic to object
contained one. Now menus are defined in objects that
will contain all the information instead of in partials.
---
 .../nav/sidebar/_group_menus.html.haml        | 13 ------
 lib/sidebars/groups/menus/kubernetes_menu.rb  | 41 +++++++++++++++++++
 lib/sidebars/groups/panel.rb                  |  1 +
 .../groups/menus/kubernetes_menu_spec.rb      | 32 +++++++++++++++
 .../nav/sidebar/_group.html.haml_spec.rb      |  8 ++++
 5 files changed, 82 insertions(+), 13 deletions(-)
 create mode 100644 lib/sidebars/groups/menus/kubernetes_menu.rb
 create mode 100644 spec/lib/sidebars/groups/menus/kubernetes_menu_spec.rb

diff --git a/app/views/layouts/nav/sidebar/_group_menus.html.haml b/app/views/layouts/nav/sidebar/_group_menus.html.haml
index 42114287cdff8..4f171f2777ae2 100644
--- a/app/views/layouts/nav/sidebar/_group_menus.html.haml
+++ b/app/views/layouts/nav/sidebar/_group_menus.html.haml
@@ -1,16 +1,3 @@
-- if group_sidebar_link?(:kubernetes)
-  = nav_link(controller: [:clusters]) do
-    = link_to group_clusters_path(@group) do
-      .nav-icon-container
-        = sprite_icon('cloud-gear')
-      %span.nav-item-name
-        = _('Kubernetes')
-    %ul.sidebar-sub-level-items.is-fly-out-only
-      = nav_link(controller: [:clusters], html_options: { class: "fly-out-top-item" } ) do
-        = link_to group_clusters_path(@group), title: _('Kubernetes'), class: 'shortcuts-kubernetes' do
-          %strong.fly-out-top-item-name
-            = _('Kubernetes')
-
 = render 'groups/sidebar/packages'
 
 = render 'layouts/nav/sidebar/analytics_links', links: group_analytics_navbar_links(@group, current_user)
diff --git a/lib/sidebars/groups/menus/kubernetes_menu.rb b/lib/sidebars/groups/menus/kubernetes_menu.rb
new file mode 100644
index 0000000000000..4ea294a4837f1
--- /dev/null
+++ b/lib/sidebars/groups/menus/kubernetes_menu.rb
@@ -0,0 +1,41 @@
+# frozen_string_literal: true
+
+module Sidebars
+  module Groups
+    module Menus
+      class KubernetesMenu < ::Sidebars::Menu
+        override :link
+        def link
+          group_clusters_path(context.group)
+        end
+
+        override :title
+        def title
+          _('Kubernetes')
+        end
+
+        override :sprite_icon
+        def sprite_icon
+          'cloud-gear'
+        end
+
+        override :render?
+        def render?
+          can?(context.current_user, :read_cluster, context.group)
+        end
+
+        override :extra_container_html_options
+        def extra_container_html_options
+          {
+            class: 'shortcuts-kubernetes'
+          }
+        end
+
+        override :active_routes
+        def active_routes
+          { controller: :clusters }
+        end
+      end
+    end
+  end
+end
diff --git a/lib/sidebars/groups/panel.rb b/lib/sidebars/groups/panel.rb
index 398cbd73b2a26..e3fe1e0ea3b72 100644
--- a/lib/sidebars/groups/panel.rb
+++ b/lib/sidebars/groups/panel.rb
@@ -11,6 +11,7 @@ def configure_menus
         add_menu(Sidebars::Groups::Menus::IssuesMenu.new(context))
         add_menu(Sidebars::Groups::Menus::MergeRequestsMenu.new(context))
         add_menu(Sidebars::Groups::Menus::CiCdMenu.new(context))
+        add_menu(Sidebars::Groups::Menus::KubernetesMenu.new(context))
       end
 
       override :render_raw_menus_partial
diff --git a/spec/lib/sidebars/groups/menus/kubernetes_menu_spec.rb b/spec/lib/sidebars/groups/menus/kubernetes_menu_spec.rb
new file mode 100644
index 0000000000000..76e58367c9d22
--- /dev/null
+++ b/spec/lib/sidebars/groups/menus/kubernetes_menu_spec.rb
@@ -0,0 +1,32 @@
+# frozen_string_literal: true
+
+require 'spec_helper'
+
+RSpec.describe Sidebars::Groups::Menus::KubernetesMenu do
+  let_it_be(:owner) { create(:user) }
+  let_it_be(:group) do
+    build(:group, :private).tap do |g|
+      g.add_owner(owner)
+    end
+  end
+
+  let(:user) { owner }
+  let(:context) { Sidebars::Groups::Context.new(current_user: user, container: group) }
+  let(:menu) { described_class.new(context) }
+
+  describe '#render?' do
+    context 'when user can read clusters' do
+      it 'returns true' do
+        expect(menu.render?).to eq true
+      end
+    end
+
+    context 'when user cannot read clusters rules' do
+      let(:user) { nil }
+
+      it 'returns false' do
+        expect(menu.render?).to eq false
+      end
+    end
+  end
+end
diff --git a/spec/views/layouts/nav/sidebar/_group.html.haml_spec.rb b/spec/views/layouts/nav/sidebar/_group.html.haml_spec.rb
index fc62fbda2cc2b..f4e681b70ff69 100644
--- a/spec/views/layouts/nav/sidebar/_group.html.haml_spec.rb
+++ b/spec/views/layouts/nav/sidebar/_group.html.haml_spec.rb
@@ -100,4 +100,12 @@
       expect(rendered).to have_link('Runners', href: group_runners_path(group))
     end
   end
+
+  describe 'Kubernetes menu' do
+    it 'has a link to the group cluster list path' do
+      render
+
+      expect(rendered).to have_link('Kubernetes', href: group_clusters_path(group))
+    end
+  end
 end
-- 
GitLab