DEV: Make `CookedPostProcessor#post_process_images` method private.
This commit is contained in:
parent
baf7eac704
commit
f54e4b71b1
|
@ -65,15 +65,6 @@ class CookedPostProcessor
|
|||
BadgeGranter.grant(Badge.find(Badge::FirstReplyByEmail), @post.user, post_id: @post.id) if @post.is_reply_by_email?
|
||||
end
|
||||
|
||||
def post_process_images
|
||||
extract_images.each do |img|
|
||||
unless add_image_placeholder!(img)
|
||||
limit_size!(img)
|
||||
convert_to_link!(img)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def post_process_quotes
|
||||
@doc.css("aside.quote").each do |q|
|
||||
post_number = q['data-post']
|
||||
|
@ -688,6 +679,15 @@ class CookedPostProcessor
|
|||
|
||||
private
|
||||
|
||||
def post_process_images
|
||||
extract_images.each do |img|
|
||||
unless add_image_placeholder!(img)
|
||||
limit_size!(img)
|
||||
convert_to_link!(img)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
def process_inline_onebox(element)
|
||||
inline_onebox = InlineOneboxer.lookup(
|
||||
element.attributes["href"].value,
|
||||
|
|
|
@ -6,11 +6,7 @@ require "file_store/s3_store"
|
|||
|
||||
describe CookedPostProcessor do
|
||||
context "#post_process" do
|
||||
fab!(:upload) do
|
||||
Fabricate(:upload,
|
||||
url: '/uploads/default/original/1X/1/1234567890123456.jpg'
|
||||
)
|
||||
end
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: <<~RAW)
|
||||
|
@ -254,409 +250,408 @@ describe CookedPostProcessor do
|
|||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context "#post_process_images" do
|
||||
|
||||
before do
|
||||
SiteSetting.responsive_post_image_sizes = ""
|
||||
end
|
||||
|
||||
context "responsive images" do
|
||||
before { SiteSetting.responsive_post_image_sizes = "1|1.5|3" }
|
||||
|
||||
it "includes responsive images on demand" do
|
||||
upload = Fabricate(:upload, width: 2000, height: 1500, filesize: 10000)
|
||||
post = Fabricate(:post, raw: "hello <img src='#{upload.url}'>")
|
||||
|
||||
# fake some optimized images
|
||||
OptimizedImage.create!(
|
||||
url: '/uploads/default/666x500.jpg',
|
||||
width: 666,
|
||||
height: 500,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.jpg',
|
||||
filesize: 500,
|
||||
version: OptimizedImage::VERSION
|
||||
)
|
||||
|
||||
# fake 3x optimized image, we lose 2 pixels here over original due to rounding on downsize
|
||||
OptimizedImage.create!(
|
||||
url: '/uploads/default/1998x1500.jpg',
|
||||
width: 1998,
|
||||
height: 1500,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.jpg',
|
||||
filesize: 800
|
||||
)
|
||||
|
||||
# Fake a loading image
|
||||
optimized_image = OptimizedImage.create!(
|
||||
url: '/uploads/default/10x10.png',
|
||||
width: CookedPostProcessor::LOADING_SIZE,
|
||||
height: CookedPostProcessor::LOADING_SIZE,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.png',
|
||||
filesize: 123
|
||||
)
|
||||
|
||||
cpp = CookedPostProcessor.new(post)
|
||||
|
||||
cpp.add_to_size_cache(upload.url, 2000, 1500)
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
html = cpp.html
|
||||
|
||||
expect(html).to include(%Q|data-small-upload="//test.localhost/uploads/default/10x10.png"|)
|
||||
# 1.5x is skipped cause we have a missing thumb
|
||||
expect(html).to include('srcset="//test.localhost/uploads/default/666x500.jpg, //test.localhost/uploads/default/1998x1500.jpg 3x"')
|
||||
expect(html).to include('src="//test.localhost/uploads/default/666x500.jpg"')
|
||||
|
||||
# works with CDN
|
||||
set_cdn_url("http://cdn.localhost")
|
||||
|
||||
cpp = CookedPostProcessor.new(post)
|
||||
cpp.add_to_size_cache(upload.url, 2000, 1500)
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
html = cpp.html
|
||||
|
||||
expect(html).to include(%Q|data-small-upload="//cdn.localhost/uploads/default/10x10.png"|)
|
||||
expect(html).to include('srcset="//cdn.localhost/uploads/default/666x500.jpg, //cdn.localhost/uploads/default/1998x1500.jpg 3x"')
|
||||
expect(html).to include('src="//cdn.localhost/uploads/default/666x500.jpg"')
|
||||
end
|
||||
|
||||
it "doesn't include response images for cropped images" do
|
||||
upload = Fabricate(:upload, width: 200, height: 4000, filesize: 12345)
|
||||
post = Fabricate(:post, raw: "hello <img src='#{upload.url}'>")
|
||||
|
||||
# fake some optimized images
|
||||
OptimizedImage.create!(
|
||||
url: 'http://a.b.c/200x500.jpg',
|
||||
width: 200,
|
||||
height: 500,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.jpg',
|
||||
filesize: 500
|
||||
)
|
||||
|
||||
cpp = CookedPostProcessor.new(post)
|
||||
cpp.add_to_size_cache(upload.url, 200, 4000)
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
expect(cpp.html).to_not include('srcset="')
|
||||
end
|
||||
end
|
||||
|
||||
shared_examples "leave dimensions alone" do
|
||||
it "doesn't use them" do
|
||||
expect(cpp.html).to match(/src="http:\/\/foo.bar\/image.png" width="" height=""/)
|
||||
expect(cpp.html).to match(/src="http:\/\/domain.com\/picture.jpg" width="50" height="42"/)
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
end
|
||||
|
||||
context "with image_sizes" do
|
||||
fab!(:post) { Fabricate(:post_with_image_urls) }
|
||||
let(:cpp) { CookedPostProcessor.new(post, image_sizes: image_sizes) }
|
||||
|
||||
context "processing images" do
|
||||
before do
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
SiteSetting.responsive_post_image_sizes = ""
|
||||
end
|
||||
|
||||
context "valid" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 111, "height" => 222 } } }
|
||||
context "responsive images" do
|
||||
before { SiteSetting.responsive_post_image_sizes = "1|1.5|3" }
|
||||
|
||||
it "uses them" do
|
||||
expect(cpp.html).to match(/src="http:\/\/foo.bar\/image.png" width="111" height="222"/)
|
||||
it "includes responsive images on demand" do
|
||||
upload = Fabricate(:upload, width: 2000, height: 1500, filesize: 10000)
|
||||
post = Fabricate(:post, raw: "hello <img src='#{upload.url}'>")
|
||||
|
||||
# fake some optimized images
|
||||
OptimizedImage.create!(
|
||||
url: '/uploads/default/666x500.jpg',
|
||||
width: 666,
|
||||
height: 500,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.jpg',
|
||||
filesize: 500,
|
||||
version: OptimizedImage::VERSION
|
||||
)
|
||||
|
||||
# fake 3x optimized image, we lose 2 pixels here over original due to rounding on downsize
|
||||
OptimizedImage.create!(
|
||||
url: '/uploads/default/1998x1500.jpg',
|
||||
width: 1998,
|
||||
height: 1500,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.jpg',
|
||||
filesize: 800
|
||||
)
|
||||
|
||||
# Fake a loading image
|
||||
optimized_image = OptimizedImage.create!(
|
||||
url: '/uploads/default/10x10.png',
|
||||
width: CookedPostProcessor::LOADING_SIZE,
|
||||
height: CookedPostProcessor::LOADING_SIZE,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.png',
|
||||
filesize: 123
|
||||
)
|
||||
|
||||
cpp = CookedPostProcessor.new(post)
|
||||
|
||||
cpp.add_to_size_cache(upload.url, 2000, 1500)
|
||||
cpp.post_process
|
||||
|
||||
html = cpp.html
|
||||
|
||||
expect(html).to include(%Q|data-small-upload="//test.localhost/uploads/default/10x10.png"|)
|
||||
# 1.5x is skipped cause we have a missing thumb
|
||||
expect(html).to include('srcset="//test.localhost/uploads/default/666x500.jpg, //test.localhost/uploads/default/1998x1500.jpg 3x"')
|
||||
expect(html).to include('src="//test.localhost/uploads/default/666x500.jpg"')
|
||||
|
||||
# works with CDN
|
||||
set_cdn_url("http://cdn.localhost")
|
||||
|
||||
cpp = CookedPostProcessor.new(post)
|
||||
cpp.add_to_size_cache(upload.url, 2000, 1500)
|
||||
cpp.post_process
|
||||
|
||||
html = cpp.html
|
||||
|
||||
expect(html).to include(%Q|data-small-upload="//cdn.localhost/uploads/default/10x10.png"|)
|
||||
expect(html).to include('srcset="//cdn.localhost/uploads/default/666x500.jpg, //cdn.localhost/uploads/default/1998x1500.jpg 3x"')
|
||||
expect(html).to include('src="//cdn.localhost/uploads/default/666x500.jpg"')
|
||||
end
|
||||
|
||||
it "doesn't include response images for cropped images" do
|
||||
upload = Fabricate(:upload, width: 200, height: 4000, filesize: 12345)
|
||||
post = Fabricate(:post, raw: "hello <img src='#{upload.url}'>")
|
||||
|
||||
# fake some optimized images
|
||||
OptimizedImage.create!(
|
||||
url: 'http://a.b.c/200x500.jpg',
|
||||
width: 200,
|
||||
height: 500,
|
||||
upload_id: upload.id,
|
||||
sha1: SecureRandom.hex,
|
||||
extension: '.jpg',
|
||||
filesize: 500
|
||||
)
|
||||
|
||||
cpp = CookedPostProcessor.new(post)
|
||||
cpp.add_to_size_cache(upload.url, 200, 4000)
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to_not include('srcset="')
|
||||
end
|
||||
end
|
||||
|
||||
shared_examples "leave dimensions alone" do
|
||||
it "doesn't use them" do
|
||||
expect(cpp.html).to match(/src="http:\/\/foo.bar\/image.png" width="" height=""/)
|
||||
expect(cpp.html).to match(/src="http:\/\/domain.com\/picture.jpg" width="50" height="42"/)
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
end
|
||||
|
||||
context "invalid width" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 0, "height" => 222 } } }
|
||||
include_examples "leave dimensions alone"
|
||||
end
|
||||
|
||||
context "invalid height" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 111, "height" => 0 } } }
|
||||
include_examples "leave dimensions alone"
|
||||
end
|
||||
|
||||
context "invalid width & height" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 0, "height" => 0 } } }
|
||||
include_examples "leave dimensions alone"
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with unsized images" do
|
||||
|
||||
fab!(:post) { Fabricate(:post_with_unsized_images) }
|
||||
let(:cpp) { CookedPostProcessor.new(post) }
|
||||
|
||||
it "adds the width and height to images that don't have them" do
|
||||
FastImage.expects(:size).returns([123, 456])
|
||||
cpp.post_process_images
|
||||
expect(cpp.html).to match(/width="123" height="456"/)
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with large images" do
|
||||
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
fab!(:post) { Fabricate(:post_with_large_image) }
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.max_image_height = 2000
|
||||
SiteSetting.create_thumbnails = true
|
||||
FastImage.expects(:size).returns([1750, 2000])
|
||||
end
|
||||
|
||||
it "generates overlay information" do
|
||||
Upload.expects(:get_from_url).returns(upload)
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost/uploads/default/original/1X/1234567890123456.jpg" data-download-href="//test.localhost/uploads/default/#{upload.sha1}" title="logo.png"><img src="//test.localhost/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">logo.png</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
describe 'when image is inside onebox' do
|
||||
let(:url) { 'https://image.com/my-avatar' }
|
||||
let(:post) { Fabricate(:post, raw: url) }
|
||||
context "with image_sizes" do
|
||||
fab!(:post) { Fabricate(:post_with_image_urls) }
|
||||
let(:cpp) { CookedPostProcessor.new(post, image_sizes: image_sizes) }
|
||||
|
||||
before do
|
||||
Oneboxer.stubs(:onebox).with(url, anything).returns("<img class='onebox' src='/uploads/default/original/1X/1234567890123456.jpg' />")
|
||||
cpp.post_process
|
||||
end
|
||||
|
||||
it 'should not add lightbox' do
|
||||
cpp.post_process_oneboxes
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
context "valid" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 111, "height" => 222 } } }
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><img class="onebox" src="//test.localhost/uploads/default/original/1X/1234567890123456.jpg" width="690" height="788"></p>
|
||||
HTML
|
||||
it "uses them" do
|
||||
expect(cpp.html).to match(/src="http:\/\/foo.bar\/image.png" width="111" height="222"/)
|
||||
expect(cpp.html).to match(/src="http:\/\/domain.com\/picture.jpg" width="50" height="42"/)
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
end
|
||||
|
||||
context "invalid width" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 0, "height" => 222 } } }
|
||||
include_examples "leave dimensions alone"
|
||||
end
|
||||
|
||||
context "invalid height" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 111, "height" => 0 } } }
|
||||
include_examples "leave dimensions alone"
|
||||
end
|
||||
|
||||
context "invalid width & height" do
|
||||
let(:image_sizes) { { "http://foo.bar/image.png" => { "width" => 0, "height" => 0 } } }
|
||||
include_examples "leave dimensions alone"
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
describe 'when image is an svg' do
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: '<img src="/uploads/default/original/1X/1234567890123456.svg">')
|
||||
context "with unsized images" do
|
||||
|
||||
fab!(:post) { Fabricate(:post_with_unsized_images) }
|
||||
let(:cpp) { CookedPostProcessor.new(post) }
|
||||
|
||||
it "adds the width and height to images that don't have them" do
|
||||
FastImage.expects(:size).returns([123, 456])
|
||||
cpp.post_process
|
||||
expect(cpp.html).to match(/width="123" height="456"/)
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
it 'should not add lightbox' do
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
end
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><img src="//test.localhost/uploads/default/original/1X/1234567890123456.svg" width="690" height="788"></p>
|
||||
context "with large images" do
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: <<~HTML)
|
||||
<img src="#{upload.url}">
|
||||
HTML
|
||||
end
|
||||
|
||||
describe 'when image src is an URL' do
|
||||
let(:post) do
|
||||
Fabricate(:post, raw: '<img src="http://test.discourse/uploads/default/original/1X/1234567890123456.svg?somepamas">')
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.max_image_height = 2000
|
||||
SiteSetting.create_thumbnails = true
|
||||
FastImage.expects(:size).returns([1750, 2000])
|
||||
end
|
||||
|
||||
it "generates overlay information" do
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost#{upload.url}" data-download-href="//test.localhost/uploads/default/#{upload.sha1}" title="logo.png"><img src="//test.localhost/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">logo.png</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
describe 'when image is inside onebox' do
|
||||
let(:url) { 'https://image.com/my-avatar' }
|
||||
let(:post) { Fabricate(:post, raw: url) }
|
||||
|
||||
before do
|
||||
Oneboxer.stubs(:onebox).with(url, anything).returns("<img class='onebox' src='/uploads/default/original/1X/1234567890123456.jpg' />")
|
||||
end
|
||||
|
||||
it 'should not add lightbox' do
|
||||
SiteSetting.crawl_images = true
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match_html("<p><img src=\"http://test.discourse/uploads/default/original/1X/1234567890123456.svg?somepamas\" width=\"690\"\ height=\"788\"></p>")
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><img class="onebox" src="//test.localhost/uploads/default/original/1X/1234567890123456.jpg" width="690" height="788"></p>
|
||||
HTML
|
||||
end
|
||||
end
|
||||
|
||||
describe 'when image is an svg' do
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: '<img src="/uploads/default/original/1X/1234567890123456.svg">')
|
||||
end
|
||||
|
||||
it 'should not add lightbox' do
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><img src="//test.localhost/uploads/default/original/1X/1234567890123456.svg" width="690" height="788"></p>
|
||||
HTML
|
||||
end
|
||||
|
||||
describe 'when image src is an URL' do
|
||||
let(:post) do
|
||||
Fabricate(:post, raw: '<img src="http://test.discourse/uploads/default/original/1X/1234567890123456.svg?somepamas">')
|
||||
end
|
||||
|
||||
it 'should not add lightbox' do
|
||||
SiteSetting.crawl_images = true
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match_html("<p><img src=\"http://test.discourse/uploads/default/original/1X/1234567890123456.svg?somepamas\" width=\"690\"\ height=\"788\"></p>")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with tall images" do
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: <<~HTML)
|
||||
<img src="#{upload.url}">
|
||||
HTML
|
||||
end
|
||||
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.create_thumbnails = true
|
||||
FastImage.expects(:size).returns([860, 2000])
|
||||
OptimizedImage.expects(:resize).never
|
||||
OptimizedImage.expects(:crop).returns(true)
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "crops the image" do
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match(/width="690" height="500">/)
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with iPhone X screenshots" do
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: <<~HTML)
|
||||
<img src="#{upload.url}">
|
||||
HTML
|
||||
end
|
||||
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.create_thumbnails = true
|
||||
FastImage.expects(:size).returns([1125, 2436])
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
OptimizedImage.expects(:crop).never
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "crops the image" do
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost#{upload.url}" data-download-href="//test.localhost/uploads/default/#{upload.sha1}" title="logo.png"><img src="//test.localhost/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_230x500.png" width="230" height="500"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">logo.png</span><span class="informations">1125×2436 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with large images when using subfolders" do
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: <<~HTML)
|
||||
<img src="/subfolder#{upload.url}">
|
||||
HTML
|
||||
end
|
||||
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
let(:base_url) { "http://test.localhost/subfolder" }
|
||||
let(:base_uri) { "/subfolder" }
|
||||
|
||||
before do
|
||||
SiteSetting.max_image_height = 2000
|
||||
SiteSetting.create_thumbnails = true
|
||||
Discourse.stubs(:base_url).returns(base_url)
|
||||
Discourse.stubs(:base_uri).returns(base_uri)
|
||||
FastImage.expects(:size).returns([1750, 2000])
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "generates overlay information" do
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html). to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost/subfolder#{upload.url}" data-download-href="//test.localhost/subfolder/uploads/default/#{upload.sha1}" title="logo.png"><img src="//test.localhost/subfolder/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">logo.png</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
it "should escape the filename" do
|
||||
upload.update!(original_filename: "><img src=x onerror=alert('haha')>.png")
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost/subfolder#{upload.url}" data-download-href="//test.localhost/subfolder/uploads/default/#{upload.sha1}" title="&gt;&lt;img src=x onerror=alert(&#39;haha&#39;)&gt;.png"><img src="//test.localhost/subfolder/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">&gt;&lt;img src=x onerror=alert(&#39;haha&#39;)&gt;.png</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with title" do
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
|
||||
fab!(:post) do
|
||||
Fabricate(:post, raw: <<~HTML)
|
||||
<img src="#{upload.url}" title="WAT">
|
||||
HTML
|
||||
end
|
||||
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.max_image_height = 2000
|
||||
SiteSetting.create_thumbnails = true
|
||||
FastImage.expects(:size).returns([1750, 2000])
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "generates overlay information" do
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost#{upload.url}" data-download-href="//test.localhost/uploads/default/#{upload.sha1}" title="WAT"><img src="//test.localhost/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" title="WAT" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">WAT</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "topic image" do
|
||||
let(:topic) { build(:topic, id: 1) }
|
||||
let(:post) { Fabricate(:post_with_uploaded_image, topic: topic) }
|
||||
let(:cpp) { CookedPostProcessor.new(post) }
|
||||
|
||||
it "adds a topic image if there's one in the first post" do
|
||||
FastImage.stubs(:size)
|
||||
expect(post.topic.image_url).to eq(nil)
|
||||
|
||||
cpp.post_process
|
||||
post.topic.reload
|
||||
expect(post.topic.image_url).to be_present
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
context "post image" do
|
||||
let(:reply) { Fabricate(:post_with_uploaded_image, post_number: 2) }
|
||||
let(:cpp) { CookedPostProcessor.new(reply) }
|
||||
|
||||
context "with tall images" do
|
||||
|
||||
let(:upload) { Fabricate(:upload) }
|
||||
let(:post) { Fabricate(:post_with_large_image) }
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.create_thumbnails = true
|
||||
|
||||
Upload.expects(:get_from_url).returns(upload)
|
||||
FastImage.expects(:size).returns([860, 2000])
|
||||
OptimizedImage.expects(:resize).never
|
||||
OptimizedImage.expects(:crop).returns(true)
|
||||
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "crops the image" do
|
||||
cpp.post_process_images
|
||||
expect(cpp.html).to match(/width="690" height="500">/)
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with iPhone X screenshots" do
|
||||
|
||||
let(:upload) { Fabricate(:upload) }
|
||||
let(:post) { Fabricate(:post_with_large_image) }
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.create_thumbnails = true
|
||||
|
||||
Upload.expects(:get_from_url).returns(upload)
|
||||
FastImage.expects(:size).returns([1125, 2436])
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
OptimizedImage.expects(:crop).never
|
||||
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "crops the image" do
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost/uploads/default/original/1X/1234567890123456.jpg" data-download-href="//test.localhost/uploads/default/#{upload.sha1}" title="logo.png"><img src="//test.localhost/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_230x500.png" width="230" height="500"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">logo.png</span><span class="informations">1125×2436 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with large images when using subfolders" do
|
||||
|
||||
fab!(:upload) { Fabricate(:upload) }
|
||||
fab!(:post) { Fabricate(:post_with_large_image_on_subfolder) }
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
let(:base_url) { "http://test.localhost/subfolder" }
|
||||
let(:base_uri) { "/subfolder" }
|
||||
|
||||
before do
|
||||
SiteSetting.max_image_height = 2000
|
||||
SiteSetting.create_thumbnails = true
|
||||
Discourse.stubs(:base_url).returns(base_url)
|
||||
Discourse.stubs(:base_uri).returns(base_uri)
|
||||
|
||||
Upload.expects(:get_from_url).returns(upload)
|
||||
FastImage.expects(:size).returns([1750, 2000])
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "generates overlay information" do
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
expect(cpp.html). to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost/subfolder/uploads/default/original/1X/1234567890123456.jpg" data-download-href="//test.localhost/subfolder/uploads/default/#{upload.sha1}" title="logo.png"><img src="//test.localhost/subfolder/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">logo.png</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
it "should escape the filename" do
|
||||
upload.update!(original_filename: "><img src=x onerror=alert('haha')>.png")
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost/subfolder/uploads/default/original/1X/1234567890123456.jpg" data-download-href="//test.localhost/subfolder/uploads/default/#{upload.sha1}" title="&gt;&lt;img src=x onerror=alert(&#39;haha&#39;)&gt;.png"><img src="//test.localhost/subfolder/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">&gt;&lt;img src=x onerror=alert(&#39;haha&#39;)&gt;.png</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "with title" do
|
||||
|
||||
let(:upload) { Fabricate(:upload) }
|
||||
let(:post) { Fabricate(:post_with_large_image_and_title) }
|
||||
let(:cpp) { CookedPostProcessor.new(post, disable_loading_image: true) }
|
||||
|
||||
before do
|
||||
SiteSetting.max_image_height = 2000
|
||||
SiteSetting.create_thumbnails = true
|
||||
|
||||
Upload.expects(:get_from_url).returns(upload)
|
||||
FastImage.expects(:size).returns([1750, 2000])
|
||||
OptimizedImage.expects(:resize).returns(true)
|
||||
|
||||
FileStore::BaseStore.any_instance.expects(:get_depth_for).returns(0)
|
||||
end
|
||||
|
||||
it "generates overlay information" do
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
|
||||
expect(cpp.html).to match_html <<~HTML
|
||||
<p><div class="lightbox-wrapper"><a class="lightbox" href="//test.localhost/uploads/default/original/1X/1234567890123456.jpg" data-download-href="//test.localhost/uploads/default/#{upload.sha1}" title="WAT"><img src="//test.localhost/uploads/default/optimized/1X/#{upload.sha1}_#{OptimizedImage::VERSION}_690x788.png" title="WAT" width="690" height="788"><div class="meta">
|
||||
<svg class="fa d-icon d-icon-far-image svg-icon" aria-hidden="true"><use xlink:href="#far-image"></use></svg><span class="filename">WAT</span><span class="informations">1750×2000 1.21 KB</span><svg class="fa d-icon d-icon-discourse-expand svg-icon" aria-hidden="true"><use xlink:href="#discourse-expand"></use></svg>
|
||||
</div></a></div></p>
|
||||
HTML
|
||||
|
||||
expect(cpp).to be_dirty
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "topic image" do
|
||||
let(:topic) { build(:topic, id: 1) }
|
||||
let(:post) { Fabricate(:post_with_uploaded_image, topic: topic) }
|
||||
let(:cpp) { CookedPostProcessor.new(post) }
|
||||
|
||||
it "adds a topic image if there's one in the first post" do
|
||||
FastImage.stubs(:size)
|
||||
expect(post.topic.image_url).to eq(nil)
|
||||
cpp.update_post_image
|
||||
post.topic.reload
|
||||
expect(post.topic.image_url).to be_present
|
||||
it "adds a post image if there's one in the post" do
|
||||
FastImage.stubs(:size)
|
||||
expect(reply.image_url).to eq(nil)
|
||||
cpp.post_process
|
||||
reply.reload
|
||||
expect(reply.image_url).to be_present
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
context "post image" do
|
||||
let(:reply) { Fabricate(:post_with_uploaded_image, post_number: 2) }
|
||||
let(:cpp) { CookedPostProcessor.new(reply) }
|
||||
|
||||
it "adds a post image if there's one in the post" do
|
||||
FastImage.stubs(:size)
|
||||
expect(reply.image_url).to eq(nil)
|
||||
cpp.update_post_image
|
||||
reply.reload
|
||||
expect(reply.image_url).to be_present
|
||||
end
|
||||
end
|
||||
|
||||
end
|
||||
|
||||
context "#extract_images" do
|
||||
|
@ -867,9 +862,7 @@ describe CookedPostProcessor do
|
|||
post.save_custom_fields
|
||||
|
||||
cpp = CookedPostProcessor.new(post, invalidate_oneboxes: true)
|
||||
cpp.post_process_oneboxes
|
||||
cpp.post_process_images
|
||||
cpp.optimize_urls
|
||||
cpp.post_process
|
||||
|
||||
expect(cpp.doc.to_s).to match(/<div class="large-image-placeholder">/)
|
||||
end
|
||||
|
|
Loading…
Reference in New Issue