Commit f29f4487 authored by Imre Farkas's avatar Imre Farkas

Merge branch 'fj-snippets-refactoring' into 'master'

Snippets views refactoring

See merge request gitlab-org/gitlab!19582
parents 3eabe600 6a4d84fc
...@@ -141,11 +141,7 @@ module BlobHelper ...@@ -141,11 +141,7 @@ module BlobHelper
if @build && @entry if @build && @entry
raw_project_job_artifacts_url(@project, @build, path: @entry.path, **kwargs) raw_project_job_artifacts_url(@project, @build, path: @entry.path, **kwargs)
elsif @snippet elsif @snippet
if @snippet.project_id reliable_raw_snippet_url(@snippet)
raw_project_snippet_url(@project, @snippet, **kwargs)
else
raw_snippet_url(@snippet, **kwargs)
end
elsif @blob elsif @blob
project_raw_url(@project, @id, **kwargs) project_raw_url(@project, @id, **kwargs)
end end
......
...@@ -11,22 +11,40 @@ module SnippetsHelper ...@@ -11,22 +11,40 @@ module SnippetsHelper
end end
end end
def reliable_snippet_path(snippet, opts = nil) def reliable_snippet_path(snippet, opts = {})
reliable_snippet_url(snippet, opts.merge(only_path: true))
end
def reliable_raw_snippet_path(snippet, opts = {})
reliable_raw_snippet_url(snippet, opts.merge(only_path: true))
end
def reliable_snippet_url(snippet, opts = {})
if snippet.project_id? if snippet.project_id?
project_snippet_path(snippet.project, snippet, opts) project_snippet_url(snippet.project, snippet, nil, opts)
else else
snippet_path(snippet, opts) snippet_url(snippet, nil, opts)
end end
end end
def download_snippet_path(snippet) def reliable_raw_snippet_url(snippet, opts = {})
if snippet.project_id if snippet.project_id?
raw_project_snippet_path(@project, snippet, inline: false) raw_project_snippet_url(snippet.project, snippet, nil, opts)
else else
raw_snippet_path(snippet, inline: false) raw_snippet_url(snippet, nil, opts)
end end
end end
def download_raw_snippet_button(snippet)
link_to(icon('download'),
reliable_raw_snippet_path(snippet, inline: false),
target: '_blank',
rel: 'noopener noreferrer',
class: "btn btn-sm has-tooltip",
title: 'Download',
data: { container: 'body' })
end
# Return the path of a snippets index for a user or for a project # Return the path of a snippets index for a user or for a project
# #
# @returns String, path to snippet index # @returns String, path to snippet index
...@@ -114,30 +132,45 @@ module SnippetsHelper ...@@ -114,30 +132,45 @@ module SnippetsHelper
{ snippet_object: snippet, snippet_chunks: snippet_chunks } { snippet_object: snippet, snippet_chunks: snippet_chunks }
end end
def snippet_embed def snippet_embed_tag(snippet)
"<script src=\"#{url_for(only_path: false, overwrite_params: nil)}.js\"></script>" content_tag(:script, nil, src: reliable_snippet_url(snippet, format: :js, only_path: false))
end end
def embedded_snippet_raw_button def snippet_badge(snippet)
blob = @snippet.blob return unless attrs = snippet_badge_attributes(snippet)
return if blob.empty? || blob.binary? || blob.stored_externally?
snippet_raw_url = if @snippet.is_a?(PersonalSnippet) css_class, text = attrs
raw_snippet_url(@snippet) tag.span(class: ['badge', 'badge-gray']) do
else concat(tag.i(class: ['fa', css_class]))
raw_project_snippet_url(@snippet.project, @snippet) concat(' ')
concat(text)
end
end end
link_to external_snippet_icon('doc-code'), snippet_raw_url, class: 'btn', target: '_blank', rel: 'noopener noreferrer', title: 'Open raw' def snippet_badge_attributes(snippet)
if snippet.private?
['fa-lock', _('private')]
end
end end
def embedded_snippet_download_button def embedded_raw_snippet_button
download_url = if @snippet.is_a?(PersonalSnippet) blob = @snippet.blob
raw_snippet_url(@snippet, inline: false) return if blob.empty? || blob.binary? || blob.stored_externally?
else
raw_project_snippet_url(@snippet.project, @snippet, inline: false) link_to(external_snippet_icon('doc-code'),
reliable_raw_snippet_url(@snippet),
class: 'btn',
target: '_blank',
rel: 'noopener noreferrer',
title: 'Open raw')
end end
link_to external_snippet_icon('download'), download_url, class: 'btn', target: '_blank', title: 'Download', rel: 'noopener noreferrer' def embedded_snippet_download_button
link_to(external_snippet_icon('download'),
reliable_raw_snippet_url(@snippet, inline: false),
class: 'btn',
target: '_blank',
title: 'Download',
rel: 'noopener noreferrer')
end end
end end
- snippet_blob = chunk_snippet(snippet_blob, @search_term) - snippet_blob = chunk_snippet(snippet_blob, @search_term)
- snippet = snippet_blob[:snippet_object] - snippet = snippet_blob[:snippet_object]
- snippet_chunks = snippet_blob[:snippet_chunks] - snippet_chunks = snippet_blob[:snippet_chunks]
- snippet_path = reliable_snippet_path(snippet)
.search-result-row .search-result-row
%span %span
...@@ -11,7 +12,6 @@ ...@@ -11,7 +12,6 @@
= snippet.author_name = snippet.author_name
%span.light= time_ago_with_tooltip(snippet.created_at) %span.light= time_ago_with_tooltip(snippet.created_at)
%h4.snippet-title %h4.snippet-title
- snippet_path = reliable_snippet_path(snippet)
.file-holder .file-holder
.js-file-title.file-title .js-file-title.file-title
= link_to snippet_path do = link_to snippet_path do
......
...@@ -2,10 +2,7 @@ ...@@ -2,10 +2,7 @@
%h4.snippet-title.term %h4.snippet-title.term
= link_to reliable_snippet_path(snippet_title) do = link_to reliable_snippet_path(snippet_title) do
= truncate(snippet_title.title, length: 60) = truncate(snippet_title.title, length: 60)
- if snippet_title.private? = snippet_badge(snippet_title)
%span.badge.badge-gray
%i.fa.fa-lock
= _("private")
%span.cgray.monospace.tiny.float-right.term %span.cgray.monospace.tiny.float-right.term
= snippet_title.file_name = snippet_title.file_name
......
...@@ -8,7 +8,6 @@ ...@@ -8,7 +8,6 @@
.btn-group{ role: "group" }< .btn-group{ role: "group" }<
= copy_blob_source_button(blob) = copy_blob_source_button(blob)
= open_raw_blob_button(blob) = open_raw_blob_button(blob)
= download_raw_snippet_button(@snippet)
= link_to icon('download'), download_snippet_path(@snippet), target: '_blank', class: "btn btn-sm has-tooltip", title: 'Download', data: { container: 'body' }
= render 'projects/blob/content', blob: blob = render 'projects/blob/content', blob: blob
...@@ -17,7 +17,7 @@ ...@@ -17,7 +17,7 @@
.file-actions.d-none.d-sm-block .file-actions.d-none.d-sm-block
.btn-group{ role: "group" }< .btn-group{ role: "group" }<
= embedded_snippet_raw_button = embedded_raw_snippet_button
= embedded_snippet_download_button = embedded_snippet_download_button
%article.file-holder.snippet-file-content %article.file-holder.snippet-file-content
......
...@@ -44,7 +44,7 @@ ...@@ -44,7 +44,7 @@
%li %li
%button.js-share-btn.btn.btn-transparent{ type: 'button' } %button.js-share-btn.btn.btn-transparent{ type: 'button' }
%strong.embed-toggle-list-item= _("Share") %strong.embed-toggle-list-item= _("Share")
%input.js-snippet-url-area.snippet-embed-input.form-control{ type: "text", autocomplete: 'off', value: snippet_embed } %input.js-snippet-url-area.snippet-embed-input.form-control{ type: "text", autocomplete: 'off', value: snippet_embed_tag(@snippet) }
.input-group-append .input-group-append
= clipboard_button(title: _('Copy'), class: 'js-clipboard-btn snippet-clipboard-btn btn btn-default', target: '.js-snippet-url-area') = clipboard_button(title: _('Copy'), class: 'js-clipboard-btn snippet-clipboard-btn btn btn-default', target: '.js-snippet-url-area')
.clearfix .clearfix
...@@ -3,33 +3,217 @@ ...@@ -3,33 +3,217 @@
require 'spec_helper' require 'spec_helper'
describe SnippetsHelper do describe SnippetsHelper do
include Gitlab::Routing
include IconsHelper include IconsHelper
describe '#embedded_snippet_raw_button' do let_it_be(:public_personal_snippet) { create(:personal_snippet, :public) }
it 'gives view raw button of embedded snippets for project snippets' do let_it_be(:public_project_snippet) { create(:project_snippet, :public) }
@snippet = create(:project_snippet, :public)
describe '#reliable_snippet_path' do
subject { reliable_snippet_path(snippet) }
context 'personal snippets' do
let(:snippet) { public_personal_snippet }
context 'public' do
it 'returns a full path' do
expect(subject).to eq("/snippets/#{snippet.id}")
end
end
end
context 'project snippets' do
let(:snippet) { public_project_snippet }
it 'returns a full path' do
expect(subject).to eq("/#{snippet.project.full_path}/snippets/#{snippet.id}")
end
end
end
describe '#reliable_snippet_url' do
subject { reliable_snippet_url(snippet) }
context 'personal snippets' do
let(:snippet) { public_personal_snippet }
context 'public' do
it 'returns a full url' do
expect(subject).to eq("http://test.host/snippets/#{snippet.id}")
end
end
end
context 'project snippets' do
let(:snippet) { public_project_snippet }
it 'returns a full url' do
expect(subject).to eq("http://test.host/#{snippet.project.full_path}/snippets/#{snippet.id}")
end
end
end
describe '#reliable_raw_snippet_path' do
subject { reliable_raw_snippet_path(snippet) }
expect(embedded_snippet_raw_button.to_s).to eq("<a class=\"btn\" target=\"_blank\" rel=\"noopener noreferrer\" title=\"Open raw\" href=\"#{raw_project_snippet_url(@snippet.project, @snippet)}\">#{external_snippet_icon('doc-code')}</a>") context 'personal snippets' do
let(:snippet) { public_personal_snippet }
context 'public' do
it 'returns a full path' do
expect(subject).to eq("/snippets/#{snippet.id}/raw")
end
end
end
context 'project snippets' do
let(:snippet) { public_project_snippet }
it 'returns a full path' do
expect(subject).to eq("/#{snippet.project.full_path}/snippets/#{snippet.id}/raw")
end
end
end
describe '#reliable_raw_snippet_url' do
subject { reliable_raw_snippet_url(snippet) }
context 'personal snippets' do
let(:snippet) { public_personal_snippet }
context 'public' do
it 'returns a full url' do
expect(subject).to eq("http://test.host/snippets/#{snippet.id}/raw")
end end
end
end
context 'project snippets' do
let(:snippet) { public_project_snippet }
it 'returns a full url' do
expect(subject).to eq("http://test.host/#{snippet.project.full_path}/snippets/#{snippet.id}/raw")
end
end
end
describe '#embedded_raw_snippet_button' do
subject { embedded_raw_snippet_button.to_s }
it 'gives view raw button of embedded snippets for personal snippets' do it 'returns view raw button of embedded snippets for personal snippets' do
@snippet = create(:personal_snippet, :public) @snippet = create(:personal_snippet, :public)
expect(embedded_snippet_raw_button.to_s).to eq("<a class=\"btn\" target=\"_blank\" rel=\"noopener noreferrer\" title=\"Open raw\" href=\"#{raw_snippet_url(@snippet)}\">#{external_snippet_icon('doc-code')}</a>") expect(subject).to eq(download_link("http://test.host/snippets/#{@snippet.id}/raw"))
end
it 'returns view raw button of embedded snippets for project snippets' do
@snippet = create(:project_snippet, :public)
expect(subject).to eq(download_link("http://test.host/#{@snippet.project.path_with_namespace}/snippets/#{@snippet.id}/raw"))
end
def download_link(url)
"<a class=\"btn\" target=\"_blank\" rel=\"noopener noreferrer\" title=\"Open raw\" href=\"#{url}\">#{external_snippet_icon('doc-code')}</a>"
end end
end end
describe '#embedded_snippet_download_button' do describe '#embedded_snippet_download_button' do
it 'gives download button of embedded snippets for project snippets' do subject { embedded_snippet_download_button }
it 'returns download button of embedded snippets for personal snippets' do
@snippet = create(:personal_snippet, :public)
expect(subject).to eq(download_link("http://test.host/snippets/#{@snippet.id}/raw"))
end
it 'returns download button of embedded snippets for project snippets' do
@snippet = create(:project_snippet, :public) @snippet = create(:project_snippet, :public)
expect(embedded_snippet_download_button.to_s).to eq("<a class=\"btn\" target=\"_blank\" title=\"Download\" rel=\"noopener noreferrer\" href=\"#{raw_project_snippet_url(@snippet.project, @snippet, inline: false)}\">#{external_snippet_icon('download')}</a>") expect(subject).to eq(download_link("http://test.host/#{@snippet.project.path_with_namespace}/snippets/#{@snippet.id}/raw"))
end end
it 'gives download button of embedded snippets for personal snippets' do def download_link(url)
@snippet = create(:personal_snippet, :public) "<a class=\"btn\" target=\"_blank\" title=\"Download\" rel=\"noopener noreferrer\" href=\"#{url}?inline=false\">#{external_snippet_icon('download')}</a>"
end
end
describe '#snippet_embed_tag' do
subject { snippet_embed_tag(snippet) }
context 'personal snippets' do
let(:snippet) { public_personal_snippet }
context 'public' do
it 'returns a script tag with the snippet full url' do
expect(subject).to eq(script_embed("http://test.host/snippets/#{snippet.id}"))
end
end
end
context 'project snippets' do
let(:snippet) { public_project_snippet }
it 'returns a script tag with the snippet full url' do
expect(subject).to eq(script_embed("http://test.host/#{snippet.project.path_with_namespace}/snippets/#{snippet.id}"))
end
end
def script_embed(url)
"<script src=\"#{url}.js\"></script>"
end
end
describe '#download_raw_snippet_button' do
subject { download_raw_snippet_button(snippet) }
expect(embedded_snippet_download_button.to_s).to eq("<a class=\"btn\" target=\"_blank\" title=\"Download\" rel=\"noopener noreferrer\" href=\"#{raw_snippet_url(@snippet, inline: false)}\">#{external_snippet_icon('download')}</a>") context 'with personal snippet' do
let(:snippet) { public_personal_snippet }
it 'returns the download button' do
expect(subject).to eq(download_link("/snippets/#{snippet.id}/raw"))
end
end
context 'with project snippet' do
let(:snippet) { public_project_snippet }
it 'returns the download button' do
expect(subject).to eq(download_link("/#{snippet.project.path_with_namespace}/snippets/#{snippet.id}/raw"))
end
end
def download_link(url)
"<a target=\"_blank\" rel=\"noopener noreferrer\" class=\"btn btn-sm has-tooltip\" title=\"Download\" data-container=\"body\" href=\"#{url}?inline=false\"><i aria-hidden=\"true\" data-hidden=\"true\" class=\"fa fa-download\"></i></a>"
end
end
describe '#snippet_badge' do
let(:snippet) { build(:personal_snippet, visibility) }
subject { snippet_badge(snippet) }
context 'when snippet is private' do
let(:visibility) { :private }
it 'returns the snippet badge' do
expect(subject).to eq "<span class=\"badge badge-gray\"><i class=\"fa fa-lock\"></i> private</span>"
end
end
context 'when snippet is public' do
let(:visibility) { :public }
it 'does not return anything' do
expect(subject).to be_nil
end
end
context 'when snippet is internal' do
let(:visibility) { :internal }
it 'does not return anything' do
expect(subject).to be_nil
end
end end
end end
end end
# frozen_string_literal: true
require 'spec_helper'
describe PersonalSnippet do
describe '#embeddable?' do
[
{ snippet: :public, embeddable: true },
{ snippet: :internal, embeddable: false },
{ snippet: :private, embeddable: false }
].each do |combination|
it 'returns true when snippet is public' do
snippet = build(:personal_snippet, combination[:snippet])
expect(snippet.embeddable?).to eq(combination[:embeddable])
end
end
end
end
...@@ -10,4 +10,25 @@ describe ProjectSnippet do ...@@ -10,4 +10,25 @@ describe ProjectSnippet do
describe "Validation" do describe "Validation" do
it { is_expected.to validate_presence_of(:project) } it { is_expected.to validate_presence_of(:project) }
end end
describe '#embeddable?' do
[
{ project: :public, snippet: :public, embeddable: true },
{ project: :internal, snippet: :public, embeddable: false },
{ project: :private, snippet: :public, embeddable: false },
{ project: :public, snippet: :internal, embeddable: false },
{ project: :internal, snippet: :internal, embeddable: false },
{ project: :private, snippet: :internal, embeddable: false },
{ project: :public, snippet: :private, embeddable: false },
{ project: :internal, snippet: :private, embeddable: false },
{ project: :private, snippet: :private, embeddable: false }
].each do |combination|
it 'only returns true when both project and snippet are public' do
project = create(:project, combination[:project])
snippet = build(:project_snippet, combination[:snippet], project: project)
expect(snippet.embeddable?).to eq(combination[:embeddable])
end
end
end
end end
...@@ -451,41 +451,4 @@ describe Snippet do ...@@ -451,41 +451,4 @@ describe Snippet do
expect(blob.data).to eq(snippet.content) expect(blob.data).to eq(snippet.content)
end end
end end
describe '#embeddable?' do
context 'project snippet' do
[
{ project: :public, snippet: :public, embeddable: true },
{ project: :internal, snippet: :public, embeddable: false },
{ project: :private, snippet: :public, embeddable: false },
{ project: :public, snippet: :internal, embeddable: false },
{ project: :internal, snippet: :internal, embeddable: false },
{ project: :private, snippet: :internal, embeddable: false },
{ project: :public, snippet: :private, embeddable: false },
{ project: :internal, snippet: :private, embeddable: false },
{ project: :private, snippet: :private, embeddable: false }
].each do |combination|
it 'only returns true when both project and snippet are public' do
project = create(:project, combination[:project])
snippet = create(:project_snippet, combination[:snippet], project: project)
expect(snippet.embeddable?).to eq(combination[:embeddable])
end
end
end
context 'personal snippet' do
[
{ snippet: :public, embeddable: true },
{ snippet: :internal, embeddable: false },
{ snippet: :private, embeddable: false }
].each do |combination|
it 'only returns true when snippet is public' do
snippet = create(:personal_snippet, combination[:snippet])
expect(snippet.embeddable?).to eq(combination[:embeddable])
end
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