diff --git a/CHANGELOG b/CHANGELOG
index 05af03b9b1fa93ac0fd92ed00ad76987b5518546..a455650bed900b65d4a2953fe0d63df0e8a96391 100644
--- a/CHANGELOG
+++ b/CHANGELOG
@@ -30,6 +30,7 @@ v 8.1.0 (unreleased)
   - Fix wrong access level badge on MR comments
   - Hide password in the service settings form
   - Fix anchors to comments in diffs
+  - Move CI web hooks page to project settings area
 
 v 8.0.3
   - Fix URL shown in Slack notifications
diff --git a/app/controllers/ci/web_hooks_controller.rb b/app/controllers/ci/web_hooks_controller.rb
deleted file mode 100644
index 24074a6d9acf4200e25387780aff40b4584b5d77..0000000000000000000000000000000000000000
--- a/app/controllers/ci/web_hooks_controller.rb
+++ /dev/null
@@ -1,53 +0,0 @@
-module Ci
-  class WebHooksController < Ci::ApplicationController
-    before_action :authenticate_user!
-    before_action :project
-    before_action :authorize_access_project!
-    before_action :authorize_manage_project!
-
-    layout 'ci/project'
-
-    def index
-      @web_hooks = @project.web_hooks
-      @web_hook = Ci::WebHook.new
-    end
-
-    def create
-      @web_hook = @project.web_hooks.new(web_hook_params)
-      @web_hook.save
-
-      if @web_hook.valid?
-        redirect_to ci_project_web_hooks_path(@project)
-      else
-        @web_hooks = @project.web_hooks.select(&:persisted?)
-        render :index
-      end
-    end
-
-    def test
-      Ci::TestHookService.new.execute(hook, current_user)
-
-      redirect_to :back
-    end
-
-    def destroy
-      hook.destroy
-
-      redirect_to ci_project_web_hooks_path(@project)
-    end
-
-    private
-
-    def hook
-      @web_hook ||= @project.web_hooks.find(params[:id])
-    end
-
-    def project
-      @project = Ci::Project.find(params[:project_id])
-    end
-
-    def web_hook_params
-      params.require(:web_hook).permit(:url)
-    end
-  end
-end
diff --git a/app/controllers/projects/ci_web_hooks_controller.rb b/app/controllers/projects/ci_web_hooks_controller.rb
new file mode 100644
index 0000000000000000000000000000000000000000..7f40ddcb3f3124e2e3d107bc8a5eeedb827a5ff5
--- /dev/null
+++ b/app/controllers/projects/ci_web_hooks_controller.rb
@@ -0,0 +1,45 @@
+class Projects::CiWebHooksController < Projects::ApplicationController
+  before_action :ci_project
+  before_action :authorize_admin_project!
+
+  layout "project_settings"
+
+  def index
+    @web_hooks = @ci_project.web_hooks
+    @web_hook = Ci::WebHook.new
+  end
+
+  def create
+    @web_hook = @ci_project.web_hooks.new(web_hook_params)
+    @web_hook.save
+
+    if @web_hook.valid?
+      redirect_to namespace_project_ci_web_hooks_path(@project.namespace, @project)
+    else
+      @web_hooks = @ci_project.web_hooks.select(&:persisted?)
+      render :index
+    end
+  end
+
+  def test
+    Ci::TestHookService.new.execute(hook, current_user)
+
+    redirect_to :back
+  end
+
+  def destroy
+    hook.destroy
+
+    redirect_to namespace_project_ci_web_hooks_path(@project.namespace, @project)
+  end
+
+  private
+
+  def hook
+    @web_hook ||= @ci_project.web_hooks.find(params[:id])
+  end
+
+  def web_hook_params
+    params.require(:web_hook).permit(:url)
+  end
+end
diff --git a/app/views/layouts/ci/_nav_project.html.haml b/app/views/layouts/ci/_nav_project.html.haml
index 3a2741367c13c1d46eb02563c97851c191a80ca4..545abc23d995d8d58edec445b6a2df5a5af1640b 100644
--- a/app/views/layouts/ci/_nav_project.html.haml
+++ b/app/views/layouts/ci/_nav_project.html.haml
@@ -11,11 +11,6 @@
       %span
         Commits
         %span.count= @project.commits.count
-    = nav_link path: 'web_hooks#index' do
-      = link_to ci_project_web_hooks_path(@project) do
-        = icon('link fw')
-        %span
-          Web Hooks
     = nav_link path: ['services#index', 'services#edit'] do
       = link_to ci_project_services_path(@project) do
         = icon('share fw')
diff --git a/app/views/layouts/nav/_project_settings.html.haml b/app/views/layouts/nav/_project_settings.html.haml
index 26cccb48f68ccf88c021646dd60c479abd451f49..9279a846623a088b3711099356747bb6c8a9f38c 100644
--- a/app/views/layouts/nav/_project_settings.html.haml
+++ b/app/views/layouts/nav/_project_settings.html.haml
@@ -50,6 +50,11 @@
           = icon('retweet fw')
           %span
             Triggers
+      = nav_link path: 'ci_web_hooks#index' do
+        = link_to namespace_project_ci_web_hooks_path(@project.namespace, @project) do
+          = icon('link fw')
+          %span
+            CI Web Hooks
       = nav_link path: 'ci_settings#edit' do
         = link_to edit_namespace_project_ci_settings_path(@project.namespace, @project) do
           = icon('building fw')
diff --git a/app/views/ci/web_hooks/index.html.haml b/app/views/projects/ci_web_hooks/index.html.haml
similarity index 85%
rename from app/views/ci/web_hooks/index.html.haml
rename to app/views/projects/ci_web_hooks/index.html.haml
index 78e8203b25e30ceac1ef9951ba9c70d747aef1c7..6aebd7cfc4dd0cc35b6eac8cc7060b996c284b0e 100644
--- a/app/views/ci/web_hooks/index.html.haml
+++ b/app/views/projects/ci_web_hooks/index.html.haml
@@ -1,12 +1,12 @@
 %h3.page-title
-  Web hooks
+  CI Web hooks
 
 %p.light
   Web Hooks can be used for binding events when build completed.
 
 %hr.clearfix
 
-= form_for [:ci, @project, @web_hook], html: { class: 'form-horizontal' } do |f|
+= form_for @web_hook, url: namespace_project_ci_web_hooks_path(@project.namespace, @project), html: { class: 'form-horizontal' } do |f|
   -if @web_hook.errors.any?
     .alert.alert-danger
       - @web_hook.errors.full_messages.each do |msg|
@@ -28,9 +28,9 @@
             %span.monospace= hook.url
         %td
           .pull-right
-            - if @project.commits.any?
-              = link_to 'Test Hook', test_ci_project_web_hook_path(@project, hook), class: "btn btn-sm btn-grouped"
-            = link_to 'Remove', ci_project_web_hook_path(@project, hook), data: { confirm: 'Are you sure?'}, method: :delete, class: "btn btn-remove btn-sm btn-grouped"
+            - if @ci_project.commits.any?
+              = link_to 'Test Hook', test_namespace_project_ci_web_hook_path(@project.namespace, @project, hook), class: "btn btn-sm btn-grouped"
+            = link_to 'Remove', namespace_project_ci_web_hook_path(@project.namespace, @project, hook), data: { confirm: 'Are you sure?'}, method: :delete, class: "btn btn-remove btn-sm btn-grouped"
 
 %h4 Web Hook data example
 
diff --git a/config/routes.rb b/config/routes.rb
index 6d96d8801cd772cff84a59747b80ff7036753b24..7bda7ade817307cbf810daec5d89787fc1b55e13 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -47,12 +47,6 @@ Gitlab::Application.routes.draw do
         end
       end
 
-      resources :web_hooks, only: [:index, :create, :destroy] do
-        member do
-          get :test
-        end
-      end
-
       resources :runner_projects, only: [:create, :destroy]
 
       resources :events, only: [:index]
@@ -591,6 +585,11 @@ Gitlab::Application.routes.draw do
         resource :variables, only: [:show, :update]
         resources :triggers, only: [:index, :create, :destroy]
         resource :ci_settings, only: [:edit, :update, :destroy]
+        resources :ci_web_hooks, only: [:index, :create, :destroy] do
+          member do
+            get :test
+          end
+        end
 
         resources :hooks, only: [:index, :create, :destroy], constraints: { id: /\d+/ } do
           member do
diff --git a/spec/features/ci_web_hooks_spec.rb b/spec/features/ci_web_hooks_spec.rb
new file mode 100644
index 0000000000000000000000000000000000000000..efae0a42c1ef00da94ba694a4a18c0f2de894b30
--- /dev/null
+++ b/spec/features/ci_web_hooks_spec.rb
@@ -0,0 +1,27 @@
+require 'spec_helper'
+
+describe 'CI web hooks' do
+  let(:user) { create(:user) }
+  before { login_as(user) }
+
+  before do
+    @project = FactoryGirl.create :ci_project
+    @gl_project = @project.gl_project
+    @gl_project.team << [user, :master]
+    visit namespace_project_ci_web_hooks_path(@gl_project.namespace, @gl_project)
+  end
+
+  context 'create a trigger' do
+    before do
+      fill_in 'web_hook_url', with: 'http://example.com'
+      click_on 'Add Web Hook'
+    end
+
+    it { expect(@project.web_hooks.count).to eq(1) }
+
+    it 'revokes the trigger' do
+      click_on 'Remove'
+      expect(@project.web_hooks.count).to eq(0)
+    end
+  end
+end