dtext links: add table for tracking links between wikis.

Add a dtext_links table for tracking links between wiki pages. This is
to allow for broken link detection and "what links here" searches, among
other uses.
This commit is contained in:
evazion
2019-10-23 14:23:03 -05:00
parent f54885b72e
commit 9f0ecf7247
7 changed files with 178 additions and 1 deletions

View File

@@ -77,6 +77,21 @@ class DText
title = WikiPage.normalize_title(title)
title
end
titles.uniq
end
def self.parse_external_links(text)
html = DTextRagel.parse(text)
fragment = Nokogiri::HTML.fragment(html)
links = fragment.css("a.dtext-external-link").map { |node| node["href"] }
links.uniq
end
def self.dtext_links_differ?(a, b)
Set.new(parse_wiki_titles(a)) != Set.new(parse_wiki_titles(b)) ||
Set.new(parse_external_links(a)) != Set.new(parse_external_links(b))
end
def self.strip_blocks(string, tag)

27
app/models/dtext_link.rb Normal file
View File

@@ -0,0 +1,27 @@
class DtextLink < ApplicationRecord
belongs_to :model, polymorphic: true
enum link_type: [:wiki_link, :external_link]
before_validation :normalize_link_target
validates :link_target, uniqueness: { scope: [:model_type, :model_id] }
def self.new_from_dtext(dtext)
links = []
links += DText.parse_wiki_titles(dtext).map do |link|
DtextLink.new(link_type: :wiki_link, link_target: link)
end
links += DText.parse_external_links(dtext).map do |link|
DtextLink.new(link_type: :external_link, link_target: link)
end
links
end
def normalize_link_target
if wiki_link?
self.link_target = WikiPage.normalize_title(link_target)
end
end
end

View File

@@ -5,6 +5,7 @@ class WikiPage < ApplicationRecord
before_save :normalize_title
before_save :normalize_other_names
before_save :update_dtext_links, if: :dtext_links_changed?
after_save :create_version
validates_uniqueness_of :title, :case_sensitive => false
validates_presence_of :title
@@ -19,6 +20,7 @@ class WikiPage < ApplicationRecord
has_one :tag, :foreign_key => "name", :primary_key => "title"
has_one :artist, -> {where(:is_active => true)}, :foreign_key => "name", :primary_key => "title"
has_many :versions, -> {order("wiki_page_versions.id ASC")}, :class_name => "WikiPageVersion", :dependent => :destroy
has_many :dtext_links, as: :model, dependent: :destroy
api_attributes including: [:creator_name, :category_name]
@@ -197,6 +199,14 @@ class WikiPage < ApplicationRecord
end
end
def dtext_links_changed?
body_changed? && DText.dtext_links_differ?(body, body_was)
end
def update_dtext_links
self.dtext_links = DtextLink.new_from_dtext(body)
end
def post_set
@post_set ||= PostSets::WikiPage.new(title, 1, 4)
end