docyard 0.5.0 → 0.7.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.rubocop.yml +1 -1
- data/CHANGELOG.md +34 -1
- data/lib/docyard/build/static_generator.rb +3 -44
- data/lib/docyard/builder.rb +14 -4
- data/lib/docyard/cli.rb +6 -3
- data/lib/docyard/components/aliases.rb +29 -0
- data/lib/docyard/components/base_processor.rb +6 -0
- data/lib/docyard/components/processors/callout_processor.rb +124 -0
- data/lib/docyard/components/processors/code_block_diff_preprocessor.rb +106 -0
- data/lib/docyard/components/processors/code_block_focus_preprocessor.rb +79 -0
- data/lib/docyard/components/processors/code_block_options_preprocessor.rb +78 -0
- data/lib/docyard/components/processors/code_block_processor.rb +175 -0
- data/lib/docyard/components/processors/code_snippet_import_preprocessor.rb +127 -0
- data/lib/docyard/components/processors/heading_anchor_processor.rb +39 -0
- data/lib/docyard/components/processors/icon_processor.rb +53 -0
- data/lib/docyard/components/processors/table_of_contents_processor.rb +68 -0
- data/lib/docyard/components/processors/table_wrapper_processor.rb +22 -0
- data/lib/docyard/components/processors/tabs_processor.rb +48 -0
- data/lib/docyard/components/registry.rb +4 -4
- data/lib/docyard/components/support/code_block/feature_extractor.rb +117 -0
- data/lib/docyard/components/support/code_block/icon_detector.rb +44 -0
- data/lib/docyard/components/support/code_block/line_parser.rb +84 -0
- data/lib/docyard/components/support/code_block/line_wrapper.rb +50 -0
- data/lib/docyard/components/support/code_block/patterns.rb +55 -0
- data/lib/docyard/components/support/code_detector.rb +61 -0
- data/lib/docyard/components/support/tabs/icon_detector.rb +62 -0
- data/lib/docyard/components/support/tabs/parser.rb +195 -0
- data/lib/docyard/components/support/tabs/range_finder.rb +46 -0
- data/lib/docyard/config/branding_resolver.rb +74 -0
- data/lib/docyard/{constants.rb → config/constants.rb} +1 -0
- data/lib/docyard/config/validator.rb +8 -0
- data/lib/docyard/config.rb +17 -1
- data/lib/docyard/{prev_next_builder.rb → navigation/prev_next_builder.rb} +2 -2
- data/lib/docyard/{sidebar → navigation/sidebar}/renderer.rb +3 -14
- data/lib/docyard/{sidebar → navigation/sidebar}/tree_builder.rb +9 -2
- data/lib/docyard/{sidebar_builder.rb → navigation/sidebar_builder.rb} +3 -15
- data/lib/docyard/{icons → rendering/icons}/file_types.rb +0 -13
- data/lib/docyard/{icons → rendering/icons}/phosphor.rb +4 -1
- data/lib/docyard/{markdown.rb → rendering/markdown.rb} +23 -14
- data/lib/docyard/{renderer.rb → rendering/renderer.rb} +24 -20
- data/lib/docyard/search/build_indexer.rb +74 -0
- data/lib/docyard/search/dev_indexer.rb +110 -0
- data/lib/docyard/search/pagefind_support.rb +31 -0
- data/lib/docyard/{asset_handler.rb → server/asset_handler.rb} +1 -1
- data/lib/docyard/{server.rb → server/dev_server.rb} +32 -9
- data/lib/docyard/{preview_server.rb → server/preview_server.rb} +1 -1
- data/lib/docyard/{rack_application.rb → server/rack_application.rb} +53 -50
- data/lib/docyard/server/resolution_result.rb +29 -0
- data/lib/docyard/{router.rb → server/router.rb} +4 -4
- data/lib/docyard/templates/assets/css/code.css +12 -4
- data/lib/docyard/templates/assets/css/components/code-block.css +427 -24
- data/lib/docyard/templates/assets/css/components/navigation.css +12 -9
- data/lib/docyard/templates/assets/css/components/search.css +549 -0
- data/lib/docyard/templates/assets/css/components/tabs.css +50 -44
- data/lib/docyard/templates/assets/css/layout.css +15 -1
- data/lib/docyard/templates/assets/css/variables.css +44 -0
- data/lib/docyard/templates/assets/js/components/search.js +685 -0
- data/lib/docyard/templates/layouts/default.html.erb +14 -2
- data/lib/docyard/templates/partials/_code_block.html.erb +50 -2
- data/lib/docyard/templates/partials/_heading_anchor.html.erb +1 -1
- data/lib/docyard/templates/partials/_prev_next.html.erb +1 -1
- data/lib/docyard/templates/partials/_search_modal.html.erb +45 -0
- data/lib/docyard/templates/partials/_search_trigger.html.erb +22 -0
- data/lib/docyard/utils/html_helpers.rb +14 -0
- data/lib/docyard/utils/path_resolver.rb +2 -1
- data/lib/docyard/utils/url_helpers.rb +20 -0
- data/lib/docyard/version.rb +1 -1
- data/lib/docyard.rb +22 -15
- metadata +57 -36
- data/lib/docyard/components/callout_processor.rb +0 -121
- data/lib/docyard/components/code_block_processor.rb +0 -55
- data/lib/docyard/components/code_detector.rb +0 -59
- data/lib/docyard/components/heading_anchor_processor.rb +0 -34
- data/lib/docyard/components/icon_detector.rb +0 -57
- data/lib/docyard/components/icon_processor.rb +0 -51
- data/lib/docyard/components/table_of_contents_processor.rb +0 -64
- data/lib/docyard/components/table_wrapper_processor.rb +0 -18
- data/lib/docyard/components/tabs_parser.rb +0 -60
- data/lib/docyard/components/tabs_processor.rb +0 -44
- data/lib/docyard/routing/resolution_result.rb +0 -31
- /data/lib/docyard/{sidebar → navigation/sidebar}/config_parser.rb +0 -0
- /data/lib/docyard/{sidebar → navigation/sidebar}/file_system_scanner.rb +0 -0
- /data/lib/docyard/{sidebar → navigation/sidebar}/item.rb +0 -0
- /data/lib/docyard/{sidebar → navigation/sidebar}/title_extractor.rb +0 -0
- /data/lib/docyard/{icons → rendering/icons}/LICENSE.phosphor +0 -0
- /data/lib/docyard/{icons.rb → rendering/icons.rb} +0 -0
- /data/lib/docyard/{language_mapping.rb → rendering/language_mapping.rb} +0 -0
- /data/lib/docyard/{file_watcher.rb → server/file_watcher.rb} +0 -0
- /data/lib/docyard/{errors.rb → utils/errors.rb} +0 -0
- /data/lib/docyard/{logging.rb → utils/logging.rb} +0 -0
|
@@ -1,59 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require_relative "../language_mapping"
|
|
4
|
-
|
|
5
|
-
module Docyard
|
|
6
|
-
module Components
|
|
7
|
-
class CodeDetector
|
|
8
|
-
def self.detect(content)
|
|
9
|
-
new(content).detect
|
|
10
|
-
end
|
|
11
|
-
|
|
12
|
-
def initialize(content)
|
|
13
|
-
@content = content
|
|
14
|
-
end
|
|
15
|
-
|
|
16
|
-
def detect
|
|
17
|
-
return nil unless code_only?
|
|
18
|
-
|
|
19
|
-
language = extract_language
|
|
20
|
-
return nil unless language
|
|
21
|
-
|
|
22
|
-
icon_for_language(language)
|
|
23
|
-
end
|
|
24
|
-
|
|
25
|
-
private
|
|
26
|
-
|
|
27
|
-
attr_reader :content
|
|
28
|
-
|
|
29
|
-
def code_only?
|
|
30
|
-
stripped = content.strip
|
|
31
|
-
return false unless stripped.start_with?("```") && stripped.end_with?("```")
|
|
32
|
-
|
|
33
|
-
parts = stripped.split("```")
|
|
34
|
-
parts.length == 2 && parts[0].empty?
|
|
35
|
-
end
|
|
36
|
-
|
|
37
|
-
def extract_language
|
|
38
|
-
parts = content.strip.split("```")
|
|
39
|
-
return nil unless parts[1]
|
|
40
|
-
|
|
41
|
-
lines = parts[1].split("\n", 2)
|
|
42
|
-
lang_line = lines[0].strip
|
|
43
|
-
return nil if lang_line.empty? || lang_line.include?(" ")
|
|
44
|
-
|
|
45
|
-
lang_line.downcase
|
|
46
|
-
end
|
|
47
|
-
|
|
48
|
-
def icon_for_language(language)
|
|
49
|
-
if LanguageMapping.terminal_language?(language)
|
|
50
|
-
{ icon: "terminal-window", source: "phosphor" }
|
|
51
|
-
elsif (extension = LanguageMapping.extension_for(language))
|
|
52
|
-
{ icon: extension, source: "file-extension" }
|
|
53
|
-
else
|
|
54
|
-
{ icon: "file", source: "phosphor" }
|
|
55
|
-
end
|
|
56
|
-
end
|
|
57
|
-
end
|
|
58
|
-
end
|
|
59
|
-
end
|
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Docyard
|
|
4
|
-
module Components
|
|
5
|
-
class HeadingAnchorProcessor < BaseProcessor
|
|
6
|
-
self.priority = 30
|
|
7
|
-
|
|
8
|
-
def postprocess(html)
|
|
9
|
-
add_anchor_links(html)
|
|
10
|
-
end
|
|
11
|
-
|
|
12
|
-
private
|
|
13
|
-
|
|
14
|
-
def add_anchor_links(html)
|
|
15
|
-
html.gsub(%r{<(h[2-6])\s+id="([^"]+)">(.*?)</\1>}m) do |_match|
|
|
16
|
-
tag = Regexp.last_match(1)
|
|
17
|
-
id = Regexp.last_match(2)
|
|
18
|
-
content = Regexp.last_match(3)
|
|
19
|
-
|
|
20
|
-
anchor_html = render_anchor_link(id)
|
|
21
|
-
|
|
22
|
-
"<#{tag} id=\"#{id}\">#{content}#{anchor_html}</#{tag}>"
|
|
23
|
-
end
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
def render_anchor_link(id)
|
|
27
|
-
renderer = Renderer.new
|
|
28
|
-
renderer.render_partial("_heading_anchor", {
|
|
29
|
-
id: id
|
|
30
|
-
})
|
|
31
|
-
end
|
|
32
|
-
end
|
|
33
|
-
end
|
|
34
|
-
end
|
|
@@ -1,57 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require_relative "code_detector"
|
|
4
|
-
|
|
5
|
-
module Docyard
|
|
6
|
-
module Components
|
|
7
|
-
class IconDetector
|
|
8
|
-
MANUAL_ICON_PATTERN = /^:([a-z0-9-]+):\s*(.+)$/i
|
|
9
|
-
|
|
10
|
-
def self.detect(tab_name, tab_content)
|
|
11
|
-
new(tab_name, tab_content).detect
|
|
12
|
-
end
|
|
13
|
-
|
|
14
|
-
def initialize(tab_name, tab_content)
|
|
15
|
-
@tab_name = tab_name
|
|
16
|
-
@tab_content = tab_content
|
|
17
|
-
end
|
|
18
|
-
|
|
19
|
-
def detect
|
|
20
|
-
manual_icon || auto_detected_icon || no_icon
|
|
21
|
-
end
|
|
22
|
-
|
|
23
|
-
private
|
|
24
|
-
|
|
25
|
-
attr_reader :tab_name, :tab_content
|
|
26
|
-
|
|
27
|
-
def manual_icon
|
|
28
|
-
return nil unless tab_name.match(MANUAL_ICON_PATTERN)
|
|
29
|
-
|
|
30
|
-
{
|
|
31
|
-
name: Regexp.last_match(2).strip,
|
|
32
|
-
icon: Regexp.last_match(1),
|
|
33
|
-
icon_source: "phosphor"
|
|
34
|
-
}
|
|
35
|
-
end
|
|
36
|
-
|
|
37
|
-
def auto_detected_icon
|
|
38
|
-
detected = CodeDetector.detect(tab_content)
|
|
39
|
-
return nil unless detected
|
|
40
|
-
|
|
41
|
-
{
|
|
42
|
-
name: tab_name,
|
|
43
|
-
icon: detected[:icon],
|
|
44
|
-
icon_source: detected[:source]
|
|
45
|
-
}
|
|
46
|
-
end
|
|
47
|
-
|
|
48
|
-
def no_icon
|
|
49
|
-
{
|
|
50
|
-
name: tab_name,
|
|
51
|
-
icon: nil,
|
|
52
|
-
icon_source: nil
|
|
53
|
-
}
|
|
54
|
-
end
|
|
55
|
-
end
|
|
56
|
-
end
|
|
57
|
-
end
|
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require_relative "../icons"
|
|
4
|
-
require_relative "base_processor"
|
|
5
|
-
|
|
6
|
-
module Docyard
|
|
7
|
-
module Components
|
|
8
|
-
class IconProcessor < BaseProcessor
|
|
9
|
-
self.priority = 20
|
|
10
|
-
|
|
11
|
-
ICON_PATTERN = /:([a-z][a-z0-9-]*):(?:([a-z]+):)?/i
|
|
12
|
-
|
|
13
|
-
def postprocess(html)
|
|
14
|
-
segments = split_preserving_code_blocks(html)
|
|
15
|
-
|
|
16
|
-
segments.map do |segment|
|
|
17
|
-
segment[:type] == :code ? segment[:content] : process_segment(segment[:content])
|
|
18
|
-
end.join
|
|
19
|
-
end
|
|
20
|
-
|
|
21
|
-
private
|
|
22
|
-
|
|
23
|
-
def split_preserving_code_blocks(html)
|
|
24
|
-
segments = []
|
|
25
|
-
current_pos = 0
|
|
26
|
-
|
|
27
|
-
html.scan(%r{<(code|pre)[^>]*>.*?</\1>}m) do
|
|
28
|
-
match_start = Regexp.last_match.begin(0)
|
|
29
|
-
match_end = Regexp.last_match.end(0)
|
|
30
|
-
|
|
31
|
-
segments << { type: :text, content: html[current_pos...match_start] } if match_start > current_pos
|
|
32
|
-
segments << { type: :code, content: html[match_start...match_end] }
|
|
33
|
-
|
|
34
|
-
current_pos = match_end
|
|
35
|
-
end
|
|
36
|
-
|
|
37
|
-
segments << { type: :text, content: html[current_pos..] } if current_pos < html.length
|
|
38
|
-
|
|
39
|
-
segments.empty? ? [{ type: :text, content: html }] : segments
|
|
40
|
-
end
|
|
41
|
-
|
|
42
|
-
def process_segment(content)
|
|
43
|
-
content.gsub(ICON_PATTERN) do
|
|
44
|
-
icon_name = Regexp.last_match(1)
|
|
45
|
-
weight = Regexp.last_match(2) || "regular"
|
|
46
|
-
Icons.render(icon_name, weight) || Regexp.last_match(0)
|
|
47
|
-
end
|
|
48
|
-
end
|
|
49
|
-
end
|
|
50
|
-
end
|
|
51
|
-
end
|
|
@@ -1,64 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Docyard
|
|
4
|
-
module Components
|
|
5
|
-
class TableOfContentsProcessor < BaseProcessor
|
|
6
|
-
self.priority = 35
|
|
7
|
-
|
|
8
|
-
def postprocess(html)
|
|
9
|
-
headings = extract_headings(html)
|
|
10
|
-
Thread.current[:docyard_toc] = headings
|
|
11
|
-
html
|
|
12
|
-
end
|
|
13
|
-
|
|
14
|
-
private
|
|
15
|
-
|
|
16
|
-
def extract_headings(html)
|
|
17
|
-
headings = []
|
|
18
|
-
|
|
19
|
-
html.scan(%r{<(h[2-4])\s+id="([^"]+)">(.*?)</\1>}m) do
|
|
20
|
-
level = Regexp.last_match(1)[1].to_i
|
|
21
|
-
id = Regexp.last_match(2)
|
|
22
|
-
text = strip_html(Regexp.last_match(3))
|
|
23
|
-
|
|
24
|
-
headings << {
|
|
25
|
-
level: level,
|
|
26
|
-
id: id,
|
|
27
|
-
text: text
|
|
28
|
-
}
|
|
29
|
-
end
|
|
30
|
-
|
|
31
|
-
build_hierarchy(headings)
|
|
32
|
-
end
|
|
33
|
-
|
|
34
|
-
def build_hierarchy(headings)
|
|
35
|
-
return [] if headings.empty?
|
|
36
|
-
|
|
37
|
-
root = []
|
|
38
|
-
stack = []
|
|
39
|
-
|
|
40
|
-
headings.each do |heading|
|
|
41
|
-
heading[:children] = []
|
|
42
|
-
|
|
43
|
-
stack.pop while stack.any? && stack.last[:level] >= heading[:level]
|
|
44
|
-
|
|
45
|
-
if stack.empty?
|
|
46
|
-
root << heading
|
|
47
|
-
else
|
|
48
|
-
stack.last[:children] << heading
|
|
49
|
-
end
|
|
50
|
-
|
|
51
|
-
stack << heading
|
|
52
|
-
end
|
|
53
|
-
|
|
54
|
-
root
|
|
55
|
-
end
|
|
56
|
-
|
|
57
|
-
def strip_html(text)
|
|
58
|
-
text.gsub(%r{<a[^>]*class="heading-anchor"[^>]*>.*?</a>}, "")
|
|
59
|
-
.gsub(/<[^>]+>/, "")
|
|
60
|
-
.strip
|
|
61
|
-
end
|
|
62
|
-
end
|
|
63
|
-
end
|
|
64
|
-
end
|
|
@@ -1,18 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Docyard
|
|
4
|
-
module Components
|
|
5
|
-
class TableWrapperProcessor < BaseProcessor
|
|
6
|
-
self.priority = 100
|
|
7
|
-
|
|
8
|
-
def postprocess(html)
|
|
9
|
-
wrapped = html.gsub(/<table([^>]*)>/) do
|
|
10
|
-
attributes = Regexp.last_match(1)
|
|
11
|
-
"<div class=\"table-wrapper\"><table#{attributes}>"
|
|
12
|
-
end
|
|
13
|
-
|
|
14
|
-
wrapped.gsub("</table>", "</table></div>")
|
|
15
|
-
end
|
|
16
|
-
end
|
|
17
|
-
end
|
|
18
|
-
end
|
|
@@ -1,60 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require_relative "icon_detector"
|
|
4
|
-
require "kramdown"
|
|
5
|
-
require "kramdown-parser-gfm"
|
|
6
|
-
|
|
7
|
-
module Docyard
|
|
8
|
-
module Components
|
|
9
|
-
class TabsParser
|
|
10
|
-
def self.parse(content)
|
|
11
|
-
new(content).parse
|
|
12
|
-
end
|
|
13
|
-
|
|
14
|
-
def initialize(content)
|
|
15
|
-
@content = content
|
|
16
|
-
end
|
|
17
|
-
|
|
18
|
-
def parse
|
|
19
|
-
sections.filter_map { |section| parse_section(section) }
|
|
20
|
-
end
|
|
21
|
-
|
|
22
|
-
private
|
|
23
|
-
|
|
24
|
-
attr_reader :content
|
|
25
|
-
|
|
26
|
-
def sections
|
|
27
|
-
content.split(/^==[ \t]+/)
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
def parse_section(section)
|
|
31
|
-
return nil if section.strip.empty?
|
|
32
|
-
|
|
33
|
-
parts = section.split("\n", 2)
|
|
34
|
-
tab_name = parts[0]&.strip
|
|
35
|
-
return nil if tab_name.nil? || tab_name.empty?
|
|
36
|
-
|
|
37
|
-
tab_content = parts[1]&.strip || ""
|
|
38
|
-
icon_data = IconDetector.detect(tab_name, tab_content)
|
|
39
|
-
|
|
40
|
-
{
|
|
41
|
-
name: icon_data[:name],
|
|
42
|
-
content: render_markdown(tab_content),
|
|
43
|
-
icon: icon_data[:icon],
|
|
44
|
-
icon_source: icon_data[:icon_source]
|
|
45
|
-
}
|
|
46
|
-
end
|
|
47
|
-
|
|
48
|
-
def render_markdown(markdown_content)
|
|
49
|
-
return "" if markdown_content.empty?
|
|
50
|
-
|
|
51
|
-
Kramdown::Document.new(
|
|
52
|
-
markdown_content,
|
|
53
|
-
input: "GFM",
|
|
54
|
-
hard_wrap: false,
|
|
55
|
-
syntax_highlighter: "rouge"
|
|
56
|
-
).to_html
|
|
57
|
-
end
|
|
58
|
-
end
|
|
59
|
-
end
|
|
60
|
-
end
|
|
@@ -1,44 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
require_relative "../renderer"
|
|
4
|
-
require_relative "base_processor"
|
|
5
|
-
require_relative "tabs_parser"
|
|
6
|
-
require "securerandom"
|
|
7
|
-
|
|
8
|
-
module Docyard
|
|
9
|
-
module Components
|
|
10
|
-
class TabsProcessor < BaseProcessor
|
|
11
|
-
self.priority = 15
|
|
12
|
-
|
|
13
|
-
def preprocess(content)
|
|
14
|
-
return content unless content.include?(":::tabs")
|
|
15
|
-
|
|
16
|
-
content.gsub(/^:::[ \t]*tabs[ \t]*\n(.*?)^:::[ \t]*$/m) do
|
|
17
|
-
process_tabs_block(Regexp.last_match(1))
|
|
18
|
-
end
|
|
19
|
-
end
|
|
20
|
-
|
|
21
|
-
private
|
|
22
|
-
|
|
23
|
-
def process_tabs_block(tabs_content)
|
|
24
|
-
tabs = TabsParser.parse(tabs_content)
|
|
25
|
-
return "" if tabs.empty?
|
|
26
|
-
|
|
27
|
-
wrap_in_nomarkdown(render_tabs(tabs))
|
|
28
|
-
end
|
|
29
|
-
|
|
30
|
-
def render_tabs(tabs)
|
|
31
|
-
Renderer.new.render_partial(
|
|
32
|
-
"_tabs", {
|
|
33
|
-
tabs: tabs,
|
|
34
|
-
group_id: SecureRandom.hex(4)
|
|
35
|
-
}
|
|
36
|
-
)
|
|
37
|
-
end
|
|
38
|
-
|
|
39
|
-
def wrap_in_nomarkdown(html)
|
|
40
|
-
"{::nomarkdown}\n#{html}\n{:/nomarkdown}"
|
|
41
|
-
end
|
|
42
|
-
end
|
|
43
|
-
end
|
|
44
|
-
end
|
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
# frozen_string_literal: true
|
|
2
|
-
|
|
3
|
-
module Docyard
|
|
4
|
-
module Routing
|
|
5
|
-
class ResolutionResult
|
|
6
|
-
attr_reader :file_path, :status
|
|
7
|
-
|
|
8
|
-
def self.found(file_path)
|
|
9
|
-
new(file_path: file_path, status: :found)
|
|
10
|
-
end
|
|
11
|
-
|
|
12
|
-
def self.not_found
|
|
13
|
-
new(file_path: nil, status: :not_found)
|
|
14
|
-
end
|
|
15
|
-
|
|
16
|
-
def initialize(file_path:, status:)
|
|
17
|
-
@file_path = file_path
|
|
18
|
-
@status = status
|
|
19
|
-
freeze
|
|
20
|
-
end
|
|
21
|
-
|
|
22
|
-
def found?
|
|
23
|
-
status == :found
|
|
24
|
-
end
|
|
25
|
-
|
|
26
|
-
def not_found?
|
|
27
|
-
status == :not_found
|
|
28
|
-
end
|
|
29
|
-
end
|
|
30
|
-
end
|
|
31
|
-
end
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|