bridgetown-core 0.14.1 → 0.15.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/Rakefile +3 -1
- data/bin/bridgetown +9 -23
- data/bridgetown-core.gemspec +3 -1
- data/lib/bridgetown-core.rb +9 -2
- data/lib/bridgetown-core/commands/apply.rb +73 -0
- data/lib/bridgetown-core/commands/base.rb +45 -0
- data/lib/bridgetown-core/commands/build.rb +91 -86
- data/lib/bridgetown-core/commands/clean.rb +30 -29
- data/lib/bridgetown-core/commands/concerns/actions.rb +128 -0
- data/lib/bridgetown-core/commands/concerns/build_options.rb +76 -0
- data/lib/bridgetown-core/commands/concerns/configuration_overridable.rb +18 -0
- data/lib/bridgetown-core/commands/concerns/summarizable.rb +13 -0
- data/lib/bridgetown-core/commands/console.rb +57 -39
- data/lib/bridgetown-core/commands/doctor.rb +126 -126
- data/lib/bridgetown-core/commands/new.rb +120 -155
- data/lib/bridgetown-core/commands/plugins.rb +167 -130
- data/lib/bridgetown-core/commands/registrations.rb +16 -0
- data/lib/bridgetown-core/commands/serve.rb +219 -215
- data/lib/bridgetown-core/concerns/convertible.rb +1 -4
- data/lib/bridgetown-core/concerns/site/renderable.rb +1 -2
- data/lib/bridgetown-core/drops/document_drop.rb +9 -1
- data/lib/bridgetown-core/drops/page_drop.rb +1 -1
- data/lib/bridgetown-core/excerpt.rb +4 -1
- data/lib/bridgetown-core/generators/prototype_generator.rb +2 -0
- data/lib/bridgetown-core/liquid_renderer.rb +1 -0
- data/lib/bridgetown-core/liquid_renderer/file.rb +1 -4
- data/lib/bridgetown-core/liquid_renderer/file_system.rb +3 -1
- data/lib/bridgetown-core/page.rb +3 -18
- data/lib/bridgetown-core/plugin_manager.rb +31 -17
- data/lib/bridgetown-core/renderer.rb +31 -18
- data/lib/bridgetown-core/tags/include.rb +14 -0
- data/lib/bridgetown-core/tags/render_content.rb +39 -16
- data/lib/bridgetown-core/tags/with.rb +15 -0
- data/lib/bridgetown-core/utils.rb +44 -0
- data/lib/bridgetown-core/version.rb +2 -2
- data/lib/bridgetown-core/watcher.rb +17 -10
- data/lib/site_template/Gemfile.erb +19 -0
- data/lib/site_template/bridgetown.config.yml +5 -3
- data/lib/site_template/package.json +1 -0
- data/lib/site_template/src/_components/footer.liquid +3 -0
- data/lib/site_template/src/_components/head.liquid +9 -0
- data/lib/site_template/src/{_includes/navbar.html → _components/navbar.liquid} +0 -0
- data/lib/site_template/src/_layouts/default.html +3 -3
- data/lib/site_template/start.js +1 -1
- data/lib/site_template/webpack.config.js +3 -3
- metadata +53 -19
- data/lib/bridgetown-core/command.rb +0 -112
- data/lib/bridgetown-core/commands/help.rb +0 -34
- data/lib/site_template/src/_components/.keep +0 -0
- data/lib/site_template/src/_includes/footer.html +0 -3
- data/lib/site_template/src/_includes/head.html +0 -9
@@ -188,13 +188,10 @@ module Bridgetown
|
|
188
188
|
#
|
189
189
|
# Returns nothing.
|
190
190
|
def do_layout(payload, layouts)
|
191
|
-
|
191
|
+
_renderer.tap do |renderer|
|
192
192
|
renderer.layouts = layouts
|
193
193
|
renderer.payload = payload
|
194
194
|
end.run
|
195
|
-
|
196
|
-
Bridgetown.logger.debug "Post-Render Hooks:", relative_path
|
197
|
-
Bridgetown::Hooks.trigger hook_owner, :post_render, self
|
198
195
|
ensure
|
199
196
|
@_renderer = nil # this will allow the modifications above to disappear
|
200
197
|
end
|
@@ -43,8 +43,7 @@ module Bridgetown
|
|
43
43
|
def render_regenerated(document, payload)
|
44
44
|
return unless regenerator.regenerate?(document)
|
45
45
|
|
46
|
-
|
47
|
-
document.trigger_hooks(:post_render)
|
46
|
+
Bridgetown::Renderer.new(self, document, payload).run
|
48
47
|
end
|
49
48
|
end
|
50
49
|
end
|
@@ -12,7 +12,15 @@ module Bridgetown
|
|
12
12
|
mutable false
|
13
13
|
|
14
14
|
def_delegator :@obj, :relative_path, :path
|
15
|
-
def_delegators :@obj,
|
15
|
+
def_delegators :@obj,
|
16
|
+
:id,
|
17
|
+
:output,
|
18
|
+
:content,
|
19
|
+
:to_s,
|
20
|
+
:relative_path,
|
21
|
+
:url,
|
22
|
+
:date,
|
23
|
+
:related_posts
|
16
24
|
|
17
25
|
private def_delegator :@obj, :data, :fallback_data
|
18
26
|
|
@@ -63,6 +63,8 @@ module Bridgetown
|
|
63
63
|
new_page
|
64
64
|
end
|
65
65
|
|
66
|
+
# TODO: this would be a great use of .try
|
67
|
+
# document.try(:collection).try(:label) == @configured_collection
|
66
68
|
def terms_matching_pages(search_term)
|
67
69
|
selected_docs = @site.documents.select do |document|
|
68
70
|
document.respond_to?(:collection) && document.collection.label == @configured_collection
|
@@ -10,11 +10,8 @@ module Bridgetown
|
|
10
10
|
|
11
11
|
def parse(content)
|
12
12
|
measure_time do
|
13
|
-
# Remove extraneous indentation for rendercontent tags
|
14
|
-
processed_content = content.gsub(%r!^[ \t]+{%-? rendercontent!, "{% rendercontent")
|
15
|
-
|
16
13
|
@renderer.cache[@filename] ||= Liquid::Template.parse(
|
17
|
-
|
14
|
+
content, line_numbers: true
|
18
15
|
)
|
19
16
|
end
|
20
17
|
@template = @renderer.cache[@filename]
|
@@ -31,7 +31,9 @@ module Bridgetown
|
|
31
31
|
raise Liquid::FileSystemError, "No such template '#{template_path}'" if found_paths.empty?
|
32
32
|
|
33
33
|
# Last path in the list wins
|
34
|
-
|
34
|
+
LiquidComponent.parse(
|
35
|
+
::File.read(found_paths.last, site.file_read_opts)
|
36
|
+
).content
|
35
37
|
end
|
36
38
|
end
|
37
39
|
end
|
data/lib/bridgetown-core/page.rb
CHANGED
@@ -73,18 +73,6 @@ module Bridgetown
|
|
73
73
|
end
|
74
74
|
end
|
75
75
|
|
76
|
-
# For backwards-compatibility in subclasses that do not redefine
|
77
|
-
# the `:to_liquid` method, stash existing definition under a new name
|
78
|
-
#
|
79
|
-
# TODO: Remove in Bridgetown 5.0
|
80
|
-
alias_method :legacy_to_liquid, :to_liquid
|
81
|
-
private :legacy_to_liquid
|
82
|
-
|
83
|
-
# Private
|
84
|
-
# Subclasses can choose to optimize their `:to_liquid` method by wrapping
|
85
|
-
# it around this definition.
|
86
|
-
#
|
87
|
-
# TODO: Remove in Bridgetown 5.0
|
88
76
|
def liquid_drop
|
89
77
|
@liquid_drop ||= begin
|
90
78
|
defaults = site.frontmatter_defaults.all(relative_path, type)
|
@@ -94,15 +82,12 @@ module Bridgetown
|
|
94
82
|
Drops::PageDrop.new(self)
|
95
83
|
end
|
96
84
|
end
|
97
|
-
private :liquid_drop
|
98
85
|
|
99
86
|
# Public
|
100
87
|
#
|
101
88
|
# Liquid representation of current page
|
102
|
-
|
103
|
-
|
104
|
-
def to_liquid(attrs = nil)
|
105
|
-
self.class == Bridgetown::Page ? liquid_drop : legacy_to_liquid(attrs)
|
89
|
+
def to_liquid
|
90
|
+
liquid_drop
|
106
91
|
end
|
107
92
|
|
108
93
|
# The full path and filename of the post. Defined in the YAML of the post
|
@@ -180,7 +165,7 @@ module Bridgetown
|
|
180
165
|
|
181
166
|
# The path to the page source file, relative to the site source
|
182
167
|
def relative_path
|
183
|
-
@relative_path ||= File.join(*[@dir, @name].map(&:to_s).reject(&:empty?)).
|
168
|
+
@relative_path ||= File.join(*[@dir, @name].map(&:to_s).reject(&:empty?)).delete_prefix("/")
|
184
169
|
end
|
185
170
|
|
186
171
|
# Obtain destination path.
|
@@ -2,6 +2,9 @@
|
|
2
2
|
|
3
3
|
module Bridgetown
|
4
4
|
class PluginManager
|
5
|
+
PLUGINS_GROUP = :bridgetown_plugins
|
6
|
+
YARN_DEPENDENCY_REGEXP = %r!(.+)@([^@]*)$!.freeze
|
7
|
+
|
5
8
|
attr_reader :site
|
6
9
|
|
7
10
|
@source_manifests = Set.new
|
@@ -40,11 +43,9 @@ module Bridgetown
|
|
40
43
|
if !ENV["BRIDGETOWN_NO_BUNDLER_REQUIRE"] && File.file?("Gemfile")
|
41
44
|
require "bundler"
|
42
45
|
|
43
|
-
|
44
|
-
|
45
|
-
required_gems = Bundler.require group_name
|
46
|
+
required_gems = Bundler.require PLUGINS_GROUP
|
46
47
|
required_gems.select! do |dep|
|
47
|
-
(dep.groups & [
|
48
|
+
(dep.groups & [PLUGINS_GROUP]).any? && dep.should_include?
|
48
49
|
end
|
49
50
|
|
50
51
|
install_yarn_dependencies(required_gems)
|
@@ -67,30 +68,43 @@ module Bridgetown
|
|
67
68
|
# If that exact package hasn't been installed, execute yarn add
|
68
69
|
#
|
69
70
|
# Returns nothing.
|
70
|
-
# rubocop:disable Metrics/AbcSize, Metrics/CyclomaticComplexity
|
71
71
|
def self.install_yarn_dependencies(required_gems)
|
72
72
|
return unless File.exist?("package.json")
|
73
73
|
|
74
74
|
package_json = JSON.parse(File.read("package.json"))
|
75
75
|
|
76
76
|
required_gems.each do |loaded_gem|
|
77
|
-
|
78
|
-
|
79
|
-
yarn_add_dependency = loaded_gem.to_spec.metadata["yarn-add"].split("@")
|
80
|
-
next unless yarn_add_dependency.length == 2
|
81
|
-
|
82
|
-
# check matching version number is see if it's already installed
|
83
|
-
if package_json["dependencies"]
|
84
|
-
current_package = package_json["dependencies"].dig(yarn_add_dependency.first)
|
85
|
-
next unless current_package.nil? || current_package != yarn_add_dependency.last
|
86
|
-
end
|
77
|
+
yarn_dependency = find_yarn_dependency(loaded_gem)
|
78
|
+
next unless add_yarn_dependency?(yarn_dependency, package_json)
|
87
79
|
|
88
80
|
# all right, time to install the package
|
89
|
-
cmd = "yarn add #{
|
81
|
+
cmd = "yarn add #{yarn_dependency.join("@")}"
|
90
82
|
system cmd
|
91
83
|
end
|
92
84
|
end
|
93
|
-
|
85
|
+
|
86
|
+
def self.find_yarn_dependency(loaded_gem)
|
87
|
+
yarn_dependency = loaded_gem.to_spec&.metadata&.dig("yarn-add")&.match(YARN_DEPENDENCY_REGEXP)
|
88
|
+
return nil if yarn_dependency&.length != 3 || yarn_dependency[2] == ""
|
89
|
+
|
90
|
+
yarn_dependency[1..2]
|
91
|
+
end
|
92
|
+
|
93
|
+
def self.add_yarn_dependency?(yarn_dependency, package_json)
|
94
|
+
return false if yarn_dependency.nil?
|
95
|
+
|
96
|
+
# check matching version number is see if it's already installed
|
97
|
+
if package_json["dependencies"]
|
98
|
+
current_version = package_json["dependencies"].dig(yarn_dependency.first)
|
99
|
+
package_requires_updating?(current_version, yarn_dependency.last)
|
100
|
+
else
|
101
|
+
true
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
def self.package_requires_updating?(current_version, dep_version)
|
106
|
+
current_version.nil? || current_version != dep_version && !current_version.include?("/")
|
107
|
+
end
|
94
108
|
|
95
109
|
# Require all .rb files
|
96
110
|
#
|
@@ -5,11 +5,16 @@ module Bridgetown
|
|
5
5
|
attr_reader :document, :site
|
6
6
|
attr_writer :layouts, :payload
|
7
7
|
|
8
|
+
class << self
|
9
|
+
attr_accessor :cached_partials
|
10
|
+
end
|
11
|
+
|
8
12
|
def initialize(site, document, site_payload = nil)
|
9
13
|
@site = site
|
10
14
|
@document = document
|
11
15
|
@payload = site_payload
|
12
16
|
@layouts = nil
|
17
|
+
self.class.cached_partials ||= {}
|
13
18
|
end
|
14
19
|
|
15
20
|
# Fetches the payload used in Liquid rendering.
|
@@ -48,7 +53,7 @@ module Bridgetown
|
|
48
53
|
|
49
54
|
# Prepare payload and render the document
|
50
55
|
#
|
51
|
-
# Returns
|
56
|
+
# Returns nothing
|
52
57
|
def run
|
53
58
|
Bridgetown.logger.debug "Rendering:", document.relative_path
|
54
59
|
|
@@ -58,8 +63,8 @@ module Bridgetown
|
|
58
63
|
assign_layout_data!
|
59
64
|
|
60
65
|
document.trigger_hooks(:pre_render, payload)
|
61
|
-
|
62
|
-
|
66
|
+
document.output = render_document
|
67
|
+
document.trigger_hooks(:post_render)
|
63
68
|
end
|
64
69
|
|
65
70
|
# Render the document.
|
@@ -67,18 +72,14 @@ module Bridgetown
|
|
67
72
|
# Returns String rendered document output
|
68
73
|
# rubocop: disable Metrics/AbcSize
|
69
74
|
def render_document
|
70
|
-
|
71
|
-
registers: { site: site, page: payload["page"] },
|
72
|
-
strict_filters: liquid_options["strict_filters"],
|
73
|
-
strict_variables: liquid_options["strict_variables"],
|
74
|
-
}
|
75
|
+
liquid_context = provide_liquid_context
|
75
76
|
|
76
77
|
execute_inline_ruby!
|
77
78
|
|
78
79
|
output = document.content
|
79
80
|
if document.render_with_liquid?
|
80
81
|
Bridgetown.logger.debug "Rendering Liquid:", document.relative_path
|
81
|
-
output = render_liquid(output, payload,
|
82
|
+
output = render_liquid(output, payload, liquid_context, document.path)
|
82
83
|
end
|
83
84
|
|
84
85
|
Bridgetown.logger.debug "Rendering Markup:", document.relative_path
|
@@ -87,12 +88,24 @@ module Bridgetown
|
|
87
88
|
|
88
89
|
if document.place_in_layout?
|
89
90
|
Bridgetown.logger.debug "Rendering Layout:", document.relative_path
|
90
|
-
output = place_in_layouts(output, payload,
|
91
|
+
output = place_in_layouts(output, payload, liquid_context)
|
91
92
|
end
|
92
93
|
|
93
94
|
output
|
94
95
|
end
|
95
96
|
|
97
|
+
def provide_liquid_context
|
98
|
+
{
|
99
|
+
registers: {
|
100
|
+
site: site,
|
101
|
+
page: payload["page"],
|
102
|
+
cached_partials: self.class.cached_partials,
|
103
|
+
},
|
104
|
+
strict_filters: liquid_options["strict_filters"],
|
105
|
+
strict_variables: liquid_options["strict_variables"],
|
106
|
+
}
|
107
|
+
end
|
108
|
+
|
96
109
|
def execute_inline_ruby!
|
97
110
|
return unless site.config.should_execute_inline_ruby?
|
98
111
|
|
@@ -101,21 +114,21 @@ module Bridgetown
|
|
101
114
|
|
102
115
|
# rubocop: enable Metrics/AbcSize
|
103
116
|
|
104
|
-
# Render the given content with the payload and
|
117
|
+
# Render the given content with the payload and context
|
105
118
|
#
|
106
119
|
# content -
|
107
120
|
# payload -
|
108
|
-
#
|
121
|
+
# context -
|
109
122
|
# path - (optional) the path to the file, for use in ex
|
110
123
|
#
|
111
124
|
# Returns String the content, rendered by Liquid.
|
112
|
-
def render_liquid(content, payload,
|
125
|
+
def render_liquid(content, payload, liquid_context, path = nil)
|
113
126
|
template = site.liquid_renderer.file(path).parse(content)
|
114
127
|
template.warnings.each do |e|
|
115
128
|
Bridgetown.logger.warn "Liquid Warning:",
|
116
129
|
LiquidRenderer.format_error(e, path || document.relative_path)
|
117
130
|
end
|
118
|
-
template.render!(payload,
|
131
|
+
template.render!(payload, liquid_context)
|
119
132
|
# rubocop: disable Lint/RescueException
|
120
133
|
rescue Exception => e
|
121
134
|
Bridgetown.logger.error "Liquid Exception:",
|
@@ -151,7 +164,7 @@ module Bridgetown
|
|
151
164
|
# Render layouts and place document content inside.
|
152
165
|
#
|
153
166
|
# Returns String rendered content
|
154
|
-
def place_in_layouts(content, payload,
|
167
|
+
def place_in_layouts(content, payload, liquid_context)
|
155
168
|
output = content.dup
|
156
169
|
layout = layouts[document.data["layout"].to_s]
|
157
170
|
validate_layout(layout)
|
@@ -162,7 +175,7 @@ module Bridgetown
|
|
162
175
|
payload["layout"] = nil
|
163
176
|
|
164
177
|
while layout
|
165
|
-
output = render_layout(output, layout,
|
178
|
+
output = render_layout(output, layout, liquid_context)
|
166
179
|
add_regenerator_dependencies(layout)
|
167
180
|
|
168
181
|
next unless (layout = site.layouts[layout.data["layout"]])
|
@@ -189,14 +202,14 @@ module Bridgetown
|
|
189
202
|
# Render layout content into document.output
|
190
203
|
#
|
191
204
|
# Returns String rendered content
|
192
|
-
def render_layout(output, layout,
|
205
|
+
def render_layout(output, layout, liquid_context)
|
193
206
|
payload["content"] = output
|
194
207
|
payload["layout"] = Utils.deep_merge_hashes(layout.data, payload["layout"] || {})
|
195
208
|
|
196
209
|
render_liquid(
|
197
210
|
layout.content,
|
198
211
|
payload,
|
199
|
-
|
212
|
+
liquid_context,
|
200
213
|
layout.path
|
201
214
|
)
|
202
215
|
end
|
@@ -3,6 +3,10 @@
|
|
3
3
|
module Bridgetown
|
4
4
|
module Tags
|
5
5
|
class IncludeTag < Liquid::Tag
|
6
|
+
class << self
|
7
|
+
attr_accessor :deprecation_message_shown
|
8
|
+
end
|
9
|
+
|
6
10
|
VALID_SYNTAX = %r!
|
7
11
|
([\w-]+)\s*=\s*
|
8
12
|
(?:"([^"\\]*(?:\\.[^"\\]*)*)"|'([^'\\]*(?:\\.[^'\\]*)*)'|([\w\.-]+))
|
@@ -18,6 +22,14 @@ module Bridgetown
|
|
18
22
|
|
19
23
|
def initialize(tag_name, markup, tokens)
|
20
24
|
super
|
25
|
+
|
26
|
+
unless self.class.deprecation_message_shown
|
27
|
+
Bridgetown.logger.warn "NOTICE: the {% include %} tag is deprecated and" \
|
28
|
+
" will be removed in Bridgetown 1.0. You should" \
|
29
|
+
" use the {% render %} tag instead."
|
30
|
+
self.class.deprecation_message_shown = true
|
31
|
+
end
|
32
|
+
|
21
33
|
matched = markup.strip.match(VARIABLE_SYNTAX)
|
22
34
|
if matched
|
23
35
|
@file = matched["variable"].strip
|
@@ -200,7 +212,9 @@ module Bridgetown
|
|
200
212
|
else
|
201
213
|
File.join(site.config["collections_dir"], page_payload["path"])
|
202
214
|
end
|
215
|
+
# rubocop:disable Performance/DeleteSuffix
|
203
216
|
resource_path.sub!(%r!/#excerpt\z!, "")
|
217
|
+
# rubocop:enable Performance/DeleteSuffix
|
204
218
|
site.in_source_dir File.dirname(resource_path)
|
205
219
|
end
|
206
220
|
end
|
@@ -3,28 +3,51 @@
|
|
3
3
|
module Bridgetown
|
4
4
|
module Tags
|
5
5
|
class BlockRenderTag < Liquid::Block
|
6
|
-
|
7
|
-
|
6
|
+
# rubocop:disable Metrics/AbcSize, Metrics/MethodLength
|
7
|
+
def render(context)
|
8
|
+
context.stack({}) do
|
9
|
+
# unindent the incoming text
|
10
|
+
content = Bridgetown::Utils.reindent_for_markdown(super)
|
8
11
|
|
9
|
-
|
10
|
-
@markup = markup
|
11
|
-
@options = options
|
12
|
-
end
|
12
|
+
regions = gather_content_regions(context)
|
13
13
|
|
14
|
-
|
15
|
-
|
14
|
+
site = context.registers[:site]
|
15
|
+
converter = site.find_converter_instance(Bridgetown::Converters::Markdown)
|
16
|
+
markdownified_content = converter.convert(content)
|
17
|
+
context["processed_component_content"] = markdownified_content
|
16
18
|
|
17
|
-
|
18
|
-
|
19
|
-
|
19
|
+
render_params = [@markup, "content: processed_component_content"]
|
20
|
+
unless regions.empty?
|
21
|
+
regions.each do |region_name, region_content|
|
22
|
+
region_name = region_name.sub("content_with_region_", "")
|
20
23
|
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
24
|
+
if region_name.end_with? ":markdown"
|
25
|
+
region_name.sub!(%r!:markdown$!, "")
|
26
|
+
context[region_name] = converter.convert(
|
27
|
+
Bridgetown::Utils.reindent_for_markdown(region_content)
|
28
|
+
)
|
29
|
+
else
|
30
|
+
context[region_name] = region_content
|
31
|
+
end
|
32
|
+
render_params.push "#{region_name}: #{region_name}"
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
Liquid::Render.parse("render", render_params.join(","), nil, @parse_context)
|
37
|
+
.render_tag(context, +"")
|
26
38
|
end
|
27
39
|
end
|
40
|
+
# rubocop:enable Metrics/AbcSize, Metrics/MethodLength
|
41
|
+
|
42
|
+
private
|
43
|
+
|
44
|
+
def gather_content_regions(context)
|
45
|
+
unless context.scopes[0].keys.find { |k| k.to_s.start_with? "content_with_region_" }
|
46
|
+
return {}
|
47
|
+
end
|
48
|
+
|
49
|
+
context.scopes[0].select { |k| k.to_s.start_with? "content_with_region_" }
|
50
|
+
end
|
28
51
|
end
|
29
52
|
end
|
30
53
|
end
|