Skip to content
Snippets Groups Projects
Commit 5cb27e9f authored by Douwe Maan's avatar Douwe Maan
Browse files

Add rich blob viewers

parent f112a03c
No related branches found
No related tags found
No related merge requests found
Showing
with 135 additions and 18 deletions
Loading
Loading
@@ -134,12 +134,15 @@ module BlobHelper
end
end
 
def blob_raw_url
namespace_project_raw_path(@project.namespace, @project, @id)
end
# SVGs can contain malicious JavaScript; only include whitelisted
# elements and attributes. Note that this whitelist is by no means complete
# and may omit some elements.
def sanitize_svg(blob)
blob.data = Gitlab::Sanitizers::SVG.clean(blob.data)
blob
def sanitize_svg_data(data)
Gitlab::Sanitizers::SVG.clean(data)
end
 
# If we blindly set the 'real' content type when serving a Git blob we
Loading
Loading
Loading
Loading
@@ -6,6 +6,14 @@ class Blob < SimpleDelegator
MAXIMUM_TEXT_HIGHLIGHT_SIZE = 1.megabyte
 
RICH_VIEWERS = [
BlobViewer::Image,
BlobViewer::PDF,
BlobViewer::Sketch,
BlobViewer::BinarySTL,
BlobViewer::TextSTL,
BlobViewer::Notebook,
BlobViewer::SVG,
BlobViewer::Markup,
].freeze
 
attr_reader :project
Loading
Loading
module BlobViewer
class BinarySTL < Base
include Rich
include ClientSide
self.partial_name = 'stl'
self.extensions = %w(stl)
self.text_based = false
end
end
module BlobViewer
class Image < Base
include Rich
include ClientSide
self.partial_name = 'image'
self.extensions = UploaderHelper::IMAGE_EXT
self.text_based = false
self.switcher_icon = 'picture-o'
self.switcher_title = 'image'
end
end
module BlobViewer
class Markup < Base
include Rich
include ServerSide
self.partial_name = 'markup'
self.extensions = Gitlab::MarkupHelper::EXTENSIONS
self.text_based = true
end
end
module BlobViewer
class Notebook < Base
include Rich
include ClientSide
self.partial_name = 'notebook'
self.extensions = %w(ipynb)
self.text_based = true
self.switcher_icon = 'file-text-o'
self.switcher_title = 'notebook'
end
end
module BlobViewer
class PDF < Base
include Rich
include ClientSide
self.partial_name = 'pdf'
self.extensions = %w(pdf)
self.text_based = false
self.switcher_icon = 'file-pdf-o'
self.switcher_title = 'PDF'
end
end
module BlobViewer
module Rich
extend ActiveSupport::Concern
included do
self.type = :rich
self.switcher_icon = 'file-text-o'
self.switcher_title = 'rendered file'
end
end
end
module BlobViewer
module ServerSide
extend ActiveSupport::Concern
included do
self.client_side = false
self.max_size = 2.megabytes
self.absolute_max_size = 5.megabytes
end
end
end
module BlobViewer
class Sketch < Base
include Rich
include ClientSide
self.partial_name = 'sketch'
self.extensions = %w(sketch)
self.text_based = false
self.switcher_icon = 'file-image-o'
self.switcher_title = 'preview'
end
end
module BlobViewer
class SVG < Base
include Rich
include ServerSide
self.partial_name = 'svg'
self.extensions = %w(svg)
self.text_based = true
self.switcher_icon = 'picture-o'
self.switcher_title = 'image'
end
end
module BlobViewer
class TextSTL < Base
include Rich
include ClientSide
self.partial_name = 'stl'
self.extensions = %w(stl)
self.text_based = true
end
end
.file-content.image_file
%img{ src: namespace_project_raw_path(@project.namespace, @project, @id), alt: blob.name }
- if blob.size_within_svg_limits?
-# We need to scrub SVG but we cannot do so in the RawController: it would
-# be wrong/strange if RawController modified the data.
- blob.load_all_data!(@repository)
- blob = sanitize_svg(blob)
.file-content.image_file
%img{ src: "data:#{blob.mime_type};base64,#{Base64.encode64(blob.data)}", alt: blob.name }
- else
= render 'too_large'
.file-content.image_file
%img{ src: blob_raw_url, alt: viewer.blob.name }
- blob = viewer.blob
.file-content.wiki
= render_markup(blob.name, blob.data)
Loading
Loading
@@ -2,4 +2,4 @@
= page_specific_javascript_bundle_tag('common_vue')
= page_specific_javascript_bundle_tag('notebook_viewer')
 
.file-content#js-notebook-viewer{ data: { endpoint: namespace_project_raw_path(@project.namespace, @project, @id) } }
.file-content#js-notebook-viewer{ data: { endpoint: blob_raw_url } }
Loading
Loading
@@ -2,4 +2,4 @@
= page_specific_javascript_bundle_tag('common_vue')
= page_specific_javascript_bundle_tag('pdf_viewer')
 
.file-content#js-pdf-viewer{ data: { endpoint: namespace_project_raw_path(@project.namespace, @project, @id) } }
.file-content#js-pdf-viewer{ data: { endpoint: blob_raw_url } }
Loading
Loading
@@ -2,6 +2,6 @@
= page_specific_javascript_bundle_tag('common_vue')
= page_specific_javascript_bundle_tag('sketch_viewer')
 
.file-content#js-sketch-viewer{ data: { endpoint: namespace_project_raw_path(@project.namespace, @project, @id) } }
.file-content#js-sketch-viewer{ data: { endpoint: blob_raw_url } }
.js-loading-icon.text-center.prepend-top-default.append-bottom-default.js-loading-icon{ 'aria-label' => 'Loading Sketch preview' }
= icon('spinner spin 2x', 'aria-hidden' => 'true');
Loading
Loading
@@ -2,7 +2,7 @@
= page_specific_javascript_bundle_tag('stl_viewer')
 
.file-content.is-stl-loading
.text-center#js-stl-viewer{ data: { endpoint: namespace_project_raw_path(@project.namespace, @project, @id) } }
.text-center#js-stl-viewer{ data: { endpoint: blob_raw_url } }
= icon('spinner spin 2x', class: 'prepend-top-default append-bottom-default', 'aria-hidden' => 'true', 'aria-label' => 'Loading')
.text-center.prepend-top-default.append-bottom-default.stl-controls
.btn-group
Loading
Loading
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment