Commit 858dbd08 authored by Charles Bushong's avatar Charles Bushong

Updating to persist a params snippets variable

parent b1411e90
...@@ -5,6 +5,7 @@ class SearchController < ApplicationController ...@@ -5,6 +5,7 @@ class SearchController < ApplicationController
@project = Project.find_by(id: params[:project_id]) if params[:project_id].present? @project = Project.find_by(id: params[:project_id]) if params[:project_id].present?
@group = Group.find_by(id: params[:group_id]) if params[:group_id].present? @group = Group.find_by(id: params[:group_id]) if params[:group_id].present?
@scope = params[:scope] @scope = params[:scope]
@show_snippets = params[:snippets].eql? 'true'
@search_results = if @project @search_results = if @project
return access_denied! unless can?(current_user, :download_code, @project) return access_denied! unless can?(current_user, :download_code, @project)
...@@ -14,7 +15,7 @@ class SearchController < ApplicationController ...@@ -14,7 +15,7 @@ class SearchController < ApplicationController
end end
Search::ProjectService.new(@project, current_user, params).execute Search::ProjectService.new(@project, current_user, params).execute
elsif params[:snippets].eql? 'true' elsif @show_snippets
unless %w(snippet_blobs snippet_titles).include?(@scope) unless %w(snippet_blobs snippet_titles).include?(@scope)
@scope = 'snippet_blobs' @scope = 'snippet_blobs'
end end
......
...@@ -178,7 +178,7 @@ module ApplicationHelper ...@@ -178,7 +178,7 @@ module ApplicationHelper
def search_placeholder def search_placeholder
if @project && @project.persisted? if @project && @project.persisted?
"Search in this project" "Search in this project"
elsif @snippet || @snippets || (params && params[:snippets] == 'true') elsif @snippet || @snippets || @show_snippets
'Search snippets' 'Search snippets'
elsif @group && @group.persisted? elsif @group && @group.persisted?
"Search in this group" "Search in this group"
......
- unless params[:snippets] .dropdown.inline
.dropdown.inline %a.dropdown-toggle.btn.btn-small{href: '#', "data-toggle" => "dropdown"}
%a.dropdown-toggle.btn.btn-small{href: '#', "data-toggle" => "dropdown"} %i.icon-tags
%i.icon-tags %span.light Group:
%span.light Group: - if @group.present?
- if @group.present? %strong= @group.name
%strong= @group.name - else
- else Any
%b.caret
%ul.dropdown-menu
%li
= link_to search_filter_path(group_id: nil) do
Any Any
%b.caret - current_user.authorized_groups.sort_by(&:name).each do |group|
%ul.dropdown-menu
%li %li
= link_to search_filter_path(group_id: nil) do = link_to search_filter_path(group_id: group.id, project_id: nil) do
Any = group.name
- current_user.authorized_groups.sort_by(&:name).each do |group|
%li
= link_to search_filter_path(group_id: group.id, project_id: nil) do
= group.name
.dropdown.inline.prepend-left-10.project-filter .dropdown.inline.prepend-left-10.project-filter
%a.dropdown-toggle.btn.btn-small{href: '#', "data-toggle" => "dropdown"} %a.dropdown-toggle.btn.btn-small{href: '#', "data-toggle" => "dropdown"}
%i.icon-tags %i.icon-tags
%span.light Project: %span.light Project:
- if @project.present? - if @project.present?
%strong= @project.name_with_namespace %strong= @project.name_with_namespace
- else - else
Any
%b.caret
%ul.dropdown-menu
%li
= link_to search_filter_path(project_id: nil) do
Any Any
%b.caret - current_user.authorized_projects.sort_by(&:name_with_namespace).each do |project|
%ul.dropdown-menu
%li %li
= link_to search_filter_path(project_id: nil) do = link_to search_filter_path(project_id: project.id, group_id: nil) do
Any = project.name_with_namespace
- current_user.authorized_projects.sort_by(&:name_with_namespace).each do |project|
%li
= link_to search_filter_path(project_id: project.id, group_id: nil) do
= project.name_with_namespace
%h4 %h4
#{@search_results.total_count} results found #{@search_results.total_count} results found
- unless params[:snippets].eql? 'true' - unless @show_snippets
- if @project - if @project
for #{link_to @project.name_with_namespace, @project} for #{link_to @project.name_with_namespace, @project}
- elsif @group - elsif @group
...@@ -12,7 +12,7 @@ ...@@ -12,7 +12,7 @@
.col-sm-3 .col-sm-3
- if @project - if @project
= render "project_filter" = render "project_filter"
- elsif params[:snippets].eql? 'true' - elsif @show_snippets
= render 'snippet_filter' = render 'snippet_filter'
- else - else
= render "global_filter" = render "global_filter"
......
...@@ -9,8 +9,9 @@ ...@@ -9,8 +9,9 @@
= submit_tag 'Search', class: "btn btn-create" = submit_tag 'Search', class: "btn btn-create"
.form-group .form-group
.col-sm-2 .col-sm-2
.col-sm-10 - unless params[:snippets].eql? 'true'
= render 'filter', f: f .col-sm-10
= render 'filter', f: f
= hidden_field_tag :project_id, params[:project_id] = hidden_field_tag :project_id, params[:project_id]
= hidden_field_tag :group_id, params[:group_id] = hidden_field_tag :group_id, params[:group_id]
= hidden_field_tag :snippets, params[:snippets] = hidden_field_tag :snippets, params[:snippets]
......
@dashboard
Feature: Snippet Search
Background:
Given I sign in as a user
And I have public "Personal snippet one" snippet
And I have private "Personal snippet private" snippet
And I have a public many lined snippet
Scenario: I should see my public and private snippets
When I search for "snippet" in snippet titles
Then I should see "Personal snippet one" in results
And I should see "Personal snippet private" in results
Scenario: I should see three surrounding lines on either side of a matching snippet line
When I search for "line seven" in snippet contents
Then I should see "line four" in results
And I should see "line seven" in results
And I should see "line ten" in results
And I should not see "line three" in results
And I should not see "line eleven" in results
module SharedSearch
include Spinach::DSL
def search_snippet_contents(query)
visit "/search?search=#{URI::encode(query)}&snippets=true&scope=snippet_blobs"
end
def search_snippet_titles(query)
visit "/search?search=#{URI::encode(query)}&snippets=true&scope=snippet_titles"
end
end
...@@ -18,4 +18,12 @@ module SharedSnippet ...@@ -18,4 +18,12 @@ module SharedSnippet
private: true, private: true,
author: current_user) author: current_user)
end end
And 'I have a public many lined snippet' do
create(:personal_snippet,
title: "Many lined snippet",
content: "line one\nline two\nline three\nline four\nline five\nline six\nline seven\nline eight\nline nine\nline ten\nline eleven\nline twelve\nline thirteen\nline fourteen",
file_name: "many_lined_snippet.rb",
private: true,
author: current_user)
end
end end
class Spinach::Features::SnippetSearch < Spinach::FeatureSteps
include SharedAuthentication
include SharedPaths
include SharedSnippet
include SharedUser
include SharedSearch
step 'I search for "snippet" in snippet titles' do
search_snippet_titles "snippet"
end
step 'I search for "snippet private" in snippet titles' do
search_snippet_titles "snippet private"
end
step 'I search for "line seven" in snippet contents' do
search_snippet_contents "line seven"
end
step 'I should see "line seven" in results' do
page.should have_content "line seven"
end
step 'I should see "line four" in results' do
page.should have_content "line four"
end
step 'I should see "line ten" in results' do
page.should have_content "line ten"
end
step 'I should not see "line eleven" in results' do
page.should_not have_content "line eleven"
end
step 'I should not see "line three" in results' do
page.should_not have_content "line three"
end
Then 'I should see "Personal snippet one" in results' do
page.should have_content "Personal snippet one"
end
And 'I should see "Personal snippet private" in results' do
page.should have_content "Personal snippet private"
end
Then 'I should not see "Personal snippet one" in results' do
page.should_not have_content "Personal snippet one"
end
And 'I should not see "Personal snippet private" in results' do
page.should_not have_content "Personal snippet private"
end
end
...@@ -48,53 +48,84 @@ module Gitlab ...@@ -48,53 +48,84 @@ module Gitlab
'snippet_blobs' 'snippet_blobs'
end end
def bounded_line_numbers(line, min, max, surrounding_lines) # Get an array of line numbers surrounding a matching
# line, bounded by min/max.
#
# @returns Array of line numbers
def bounded_line_numbers(line, min, max)
lower = line - surrounding_lines > min ? line - surrounding_lines : min lower = line - surrounding_lines > min ? line - surrounding_lines : min
upper = line + surrounding_lines < max ? line + surrounding_lines : max upper = line + surrounding_lines < max ? line + surrounding_lines : max
(lower..upper).to_a (lower..upper).to_a
end end
def chunk_snippet(snippet) # Returns a sorted set of lines to be included in a snippet preview.
surrounding_lines = 3 # This ensures matching adjacent lines do not display duplicated
# surrounding code.
#
# @returns Array, unique and sorted.
def matching_lines(lined_content)
used_lines = [] used_lines = []
lined_content = snippet.content.split("\n")
lined_content.each_with_index do |line, line_number| lined_content.each_with_index do |line, line_number|
used_lines.concat bounded_line_numbers( used_lines.concat bounded_line_numbers(
line_number, line_number,
0, 0,
lined_content.size, lined_content.size
surrounding_lines
) if line.include?(query) ) if line.include?(query)
end end
used_lines = used_lines.uniq.sort used_lines.uniq.sort
end
# 'Chunkify' entire snippet. Splits the snippet data into matching lines +
# surrounding_lines() worth of unmatching lines.
#
# @returns a hash with {snippet_object, snippet_chunks:{data,start_line}}
def chunk_snippet(snippet)
lined_content = snippet.content.split("\n")
used_lines = matching_lines(lined_content)
snippet_chunk = [] snippet_chunk = []
snippet_chunks = [] snippet_chunks = []
snippet_start_line = 0 snippet_start_line = 0
last_line = -1 last_line = -1
# Go through each used line, and add consecutive lines as a single chunk
# to the snippet chunk array.
used_lines.each do |line_number| used_lines.each do |line_number|
if last_line < 0 if last_line < 0
# Start a new chunk.
snippet_start_line = line_number snippet_start_line = line_number
snippet_chunk << lined_content[line_number] snippet_chunk << lined_content[line_number]
elsif last_line == line_number - 1 elsif last_line == line_number - 1
# Consecutive line, continue chunk.
snippet_chunk << lined_content[line_number] snippet_chunk << lined_content[line_number]
else else
# Non-consecutive line, add chunk to chunk array.
snippet_chunks << { snippet_chunks << {
data: snippet_chunk.join("\n"), data: snippet_chunk.join("\n"),
start_line: snippet_start_line + 1 start_line: snippet_start_line + 1
} }
# Start a new chunk.
snippet_chunk = [lined_content[line_number]] snippet_chunk = [lined_content[line_number]]
snippet_start_line = line_number snippet_start_line = line_number
end end
last_line = line_number last_line = line_number
end end
# Add final chunk to chunk array
snippet_chunks << { snippet_chunks << {
data: snippet_chunk.join("\n"), data: snippet_chunk.join("\n"),
start_line: snippet_start_line + 1 start_line: snippet_start_line + 1
} }
# Return snippet with chunk array
{ snippet_object: snippet, snippet_chunks: snippet_chunks } { snippet_object: snippet, snippet_chunks: snippet_chunks }
end end
# Defines how many unmatching lines should be
# included around the matching lines in a snippet
def surrounding_lines
3
end
end end
end end
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment