Files
danbooru/app/logical/sources/strategies/moebooru.rb
evazion b4aea72d04 sources: remove preview_urls method from base strategy.
Remove the `preview_urls` method from strategies. The only place this was used was
when doing IQDB searches, to download the thumbnail image from the source instead of
the full image.

This wasn't worth it for a few reasons:

* Thumbnails on other sites are sometimes not the size we want, which could affect
  IQDB results.
* Grabbing thumbnails is complex for some sites. You can't always just rewrite the
  image URL. Sometimes it requires extra API calls, which can be slower than just
  grabbing the full image.
* For videos and animations, thumbnails from other sites don't always match our
  thumbnails. We do smart thumbnail generation to try to avoid blank thumbnails, which
  means we don't always pick the first frame, which could affect IQDB results.

API changes:

* /iqdb_queries?search[file_url] now downloads the URL as is without any modification.
  Before it tried to change thumbnail and sample size image URLs to the full version.

* /iqdb_queries?search[url] now returns an error if the URL is for a HTML page that
  contains multiple images. Before it would grab only the first image and silently
  ignore the rest.
2022-03-11 03:22:23 -06:00

112 lines
3.3 KiB
Ruby

# frozen_string_literal: true
# @see Source::URL::Moebooru
module Sources
module Strategies
class Moebooru < Base
delegate :artist_name, :profile_url, :tag_name, :artist_commentary_title, :artist_commentary_desc, :dtext_artist_commentary_title, :dtext_artist_commentary_desc, to: :sub_strategy, allow_nil: true
delegate :site_name, :domain, to: :parsed_url
def match?
Source::URL::Moebooru === parsed_url
end
def image_urls
return [] if post_md5.blank? || file_ext.blank?
[Source::URL::Moebooru.full_image_url(site_name, post_md5, file_ext, post_id)]
end
def page_url
return nil if post_id.blank?
"https://#{domain}/post/show/#{post_id}"
end
def canonical_url
image_urls.first
end
def normalize_for_source
id = post_id_from_url
md5 = post_md5_from_url
if id.present?
"https://#{domain}/post/show/#{id}"
elsif md5.present?
"https://#{domain}/post?tags=md5:#{md5}"
end
end
def tags
api_response[:tags].to_s.split.map do |tag|
[tag, "https://#{domain}/post?tags=#{CGI.escape(tag)}"]
end
end
# XXX the base strategy excludes artist tags from the translated tags; we don't want that for moebooru.
def translated_tags
tags.map(&:first).flat_map(&method(:translate_tag)).uniq.sort
end
# Moebooru returns an empty array when doing an md5:<hash> search for a
# deleted post. Because of this, api_response may be empty in some cases.
def api_response
if post_id_from_url.present?
params = { tags: "id:#{post_id_from_url}" }
elsif post_md5_from_url.present?
params = { tags: "md5:#{post_md5_from_url}" }
else
return {}
end
response = http.cache(1.minute).get("https://#{domain}/post.json", params: params)
post = response.parse.first&.with_indifferent_access
post || {}
end
memoize :api_response
concerning :HelperMethods do
def sub_strategy
@sub_strategy ||= Sources::Strategies.find(api_response[:source], default: nil)
end
def file_ext
if parsed_url.original_file_ext.present?
parsed_url.original_file_ext
# file_ext is not present in konachan's api (only on yande.re)
elsif api_response[:file_ext].present?
api_response[:file_ext]
# file_url is not present in yande.re's api on deleted posts
elsif api_response[:file_url].present?
api_response[:file_url][/\.(jpg|jpeg|png|gif)\z/i, 1]
# the api_response wasn't available because it's a deleted post.
elsif post_md5.present?
%w[jpg png gif].find { |ext| http_exists?("https://#{domain}/image/#{post_md5}.#{ext}") }
else
nil
end
end
def post_id_from_url
parsed_url.work_id || parsed_referer&.work_id
end
def post_md5_from_url
parsed_url.md5 || parsed_referer&.md5
end
def post_id
post_id_from_url || api_response[:id]
end
def post_md5
post_md5_from_url || api_response[:md5]
end
end
end
end
end