Class: Banzai::Filter::UserReferenceFilter

Inherits:
ReferenceFilter
  • Object
show all
Defined in:
lib/banzai/filter/user_reference_filter.rb

Overview

HTML filter that replaces user or group references with links.

A special `@all` reference is also supported.

Class Method Summary collapse

Instance Method Summary collapse

Methods inherited from ReferenceFilter

call, #call_and_update_nodes, #data_attribute, #each_node, #element_node?, #group, #ignore_ancestor_query, #initialize, #nodes, #project, #reference_class, #replace_link_node_with_href, #replace_link_node_with_text, #replace_text_when_pattern_matches, #skip_project_check?, #text_node?, #user, #validate, #yield_valid_link

Methods included from OutputSafety

#escape_once

Methods included from RequestStoreReferenceCache

#cached_call, #get_or_set_cache

Constructor Details

This class inherits a constructor from Banzai::Filter::ReferenceFilter

Class Method Details

.references_in(text) ⇒ Object

Public: Find `@user` user references in text

UserReferenceFilter.references_in(text) do |match, username|
  "<a href=...>@#{user}</a>"
end

text - String text to search.

Yields the String match, and the String user name.

Returns a String replaced with the return of the block.


22
23
24
25
26
# File 'lib/banzai/filter/user_reference_filter.rb', line 22

def self.references_in(text)
  text.gsub(User.reference_pattern) do |match|
    yield match, $~[:user]
  end
end

Instance Method Details

#callObject


28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
# File 'lib/banzai/filter/user_reference_filter.rb', line 28

def call
  return doc if project.nil? && group.nil? && !skip_project_check?

  ref_pattern = User.reference_pattern
  ref_pattern_start = /\A#{ref_pattern}\z/

  nodes.each_with_index do |node, index|
    if text_node?(node)
      replace_text_when_pattern_matches(node, index, ref_pattern) do |content|
        user_link_filter(content)
      end
    elsif element_node?(node)
      yield_valid_link(node) do |link, inner_html|
        if link =~ ref_pattern_start
          replace_link_node_with_href(node, index, link) do
            user_link_filter(link, link_content: inner_html)
          end
        end
      end
    end
  end

  doc
end

#namespacesObject

Returns a Hash containing all Namespace objects for the username references in the current document.

The keys of this Hash are the namespace paths, the values the corresponding Namespace objects.


82
83
84
85
86
87
# File 'lib/banzai/filter/user_reference_filter.rb', line 82

def namespaces
  @namespaces ||= Namespace.eager_load(:owner, :route)
                           .where_full_path_in(usernames)
                           .index_by(&:full_path)
                           .transform_keys(&:downcase)
end

Replace `@user` user references in text with links to the referenced user's profile page.

text - String text to replace references in. link_content - Original content of the link being replaced.

Returns a String with `@user` references replaced with links. All links have `gfm` and `gfm-project_member` class names attached for styling.


61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
# File 'lib/banzai/filter/user_reference_filter.rb', line 61

def user_link_filter(text, link_content: nil)
  self.class.references_in(text) do |match, username|
    if username == 'all' && !skip_project_check?
      link_to_all(link_content: link_content)
    else
      cached_call(:banzai_url_for_object, match, path: [User, username.downcase]) do
        if namespace = namespaces[username.downcase]
          link_to_namespace(namespace, link_content: link_content) || match
        else
          match
        end
      end
    end
  end
end

#usernamesObject

Returns all usernames referenced in the current document.


90
91
92
93
94
95
96
97
98
99
100
# File 'lib/banzai/filter/user_reference_filter.rb', line 90

def usernames
  refs = Set.new

  nodes.each do |node|
    node.to_html.scan(User.reference_pattern) do
      refs << $~[:user]
    end
  end

  refs.to_a
end