Module: Primer::Static::GenerateInfoArch

Defined in:
lib/primer/static/generate_info_arch.rb

Overview

:nodoc:

Constant Summary collapse

SKIP_METHODS =
%i[call before_render].freeze

Class Method Summary collapse

Class Method Details

.callObject

[View source]

15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
# File 'lib/primer/static/generate_info_arch.rb', line 15

def call
  components = Primer::Component.descendants.sort_by(&:name) - [Primer::BaseComponent]

  component_docs = components.each_with_object({}) do |component, memo|
    docs = registry.find(component)

    preview_data = previews.find do |preview|
      preview["component"] == docs.[:title] &&
        preview["status"] == component.status.to_s
    end

    arg_data = args.find do |component_args|
      component_args["component"] == docs.[:title] &&
        component_args["status"] == component.status.to_s
    end

    slot_docs = docs.slot_methods.map do |slot_method|
      param_tags = slot_method.tags(:param)

      {
        "name" => slot_method.name,
        "description" =>
          if slot_method.base_docstring.to_s.present?
            render_erb_ignoring_markdown_code_fences(slot_method.base_docstring)
          end,
        "parameters" => serialize_params(param_tags, component)
      }
    end

    mtds = docs.non_slot_methods.select do |mtd|
      next false if mtd.base_docstring.to_s.blank?
      next false if SKIP_METHODS.include?(mtd.name)

      method_location, = mtd.files.first
      class_location, = docs.docs.files.first

      method_location == class_location
    end

    method_docs = mtds.map do |mtd|
      param_tags = mtd.tags(:param)
      return_tag = mtd.tags(:return)

      {
        "name" => mtd.name,
        "description" => render_erb_ignoring_markdown_code_fences(mtd.base_docstring),
        "parameters" => serialize_params(param_tags, component),
        "return_types" => return_tag.first&.types || [],
      }
    end

    description =
      if component == Primer::BaseComponent
        docs.base_docstring
      else
        render_erb_ignoring_markdown_code_fences(docs.base_docstring)
      end

    accessibility_docs =
      if (accessibility_tag_text = docs.tags(:accessibility)&.first&.text)
        render_erb_ignoring_markdown_code_fences(accessibility_tag_text)
      end

    memo[component] = {
      "fully_qualified_name" => component.name,
      "description" => description,
      "accessibility_docs" => accessibility_docs,
      "is_form_component" => docs.manifest_entry.form_component?,
      "is_published" => docs.manifest_entry.published?,
      "requires_js" => docs.manifest_entry.requires_js?,
      **arg_data,
      "slots" => slot_docs,
      "methods" => method_docs,
      "previews" => (preview_data || {}).fetch("examples", []),
      "subcomponents" => []
    }
  end

  statuses = Primer::Status::Dsl::STATUSES.keys.map { |k| k.to_s.capitalize }

  Primer::Component.descendants.each do |component|
    fq_class = component.name.to_s.split("::")
    fq_class.shift # remove Primer::
    status = fq_class.shift if statuses.include?(fq_class.first) # remove Status::

    parent, *child = *fq_class

    next if child.empty?

    parent_class = Primer
    parent_class = parent_class.const_get(status) if status
    parent_class = parent_class.const_get(parent)

    parent_docs = component_docs[parent_class]
    next unless parent_docs

    if (child_docs = component_docs.delete(component))
      parent_docs["subcomponents"] << child_docs
    end
  end

  component_docs.values + [system_args_docs]
end