gryphon_nest 1.0.0 → 1.1.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/gryphon_nest/renderer.rb +55 -0
- data/lib/gryphon_nest/version.rb +1 -1
- data/lib/gryphon_nest.rb +114 -109
- metadata +3 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 773f8de17a88d769b28ca4a19a9f7f0f1a916b865d3363262515cee758be13d3
|
4
|
+
data.tar.gz: e597a97c55f7f34ab8aa2498d608eb1b18e8363bb866549fa5cd514303f8ef1e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 70b4641bc1e84078c37edf1ba0f1c06cda9ec0252133c7a05ac52264a76789c9c8cacfca2e930c631eaa938ce325c3f1a293815685ead2ee70265060e535928c
|
7
|
+
data.tar.gz: 4989b444b40a22778a4b308637bca2b3630ded3ec4a87deb65ec4a231c0d3dead50f3fe5511a73d723a069907ebb85c221106b024f0b9592446003c7bddcd64a
|
@@ -0,0 +1,55 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'htmlbeautifier'
|
4
|
+
require 'mustache'
|
5
|
+
|
6
|
+
module GryphonNest
|
7
|
+
# Renders mustache templates to html
|
8
|
+
class Renderer
|
9
|
+
# @param layouts [Array]
|
10
|
+
def initialize
|
11
|
+
@layouts = {}
|
12
|
+
end
|
13
|
+
|
14
|
+
# @param template [String]
|
15
|
+
# @param layout [String]
|
16
|
+
# @param context [Hash]
|
17
|
+
# @return [String]
|
18
|
+
def render(template, layout, context)
|
19
|
+
File.open(template) do |f|
|
20
|
+
content = render_template(f.read, context)
|
21
|
+
layout = get_template_layout(layout)
|
22
|
+
|
23
|
+
unless layout.nil?
|
24
|
+
context[:yield] = content
|
25
|
+
content = render_template(layout, context)
|
26
|
+
end
|
27
|
+
|
28
|
+
HtmlBeautifier.beautify(content)
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
private
|
33
|
+
|
34
|
+
# @param content [String]
|
35
|
+
# @param context [Hash]
|
36
|
+
# @return [String]
|
37
|
+
def render_template(content, context)
|
38
|
+
Mustache.render(content, context)
|
39
|
+
end
|
40
|
+
|
41
|
+
# @param path [String]
|
42
|
+
# @return [String|null]
|
43
|
+
def get_template_layout(path)
|
44
|
+
return @layouts[path] if @layouts.key?(path)
|
45
|
+
|
46
|
+
return unless File.exist?(path)
|
47
|
+
|
48
|
+
File.open(path) do |file|
|
49
|
+
content = file.read
|
50
|
+
@layouts[path] = content
|
51
|
+
return content
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
data/lib/gryphon_nest/version.rb
CHANGED
data/lib/gryphon_nest.rb
CHANGED
@@ -1,13 +1,12 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
3
|
require 'fileutils'
|
4
|
-
require 'htmlbeautifier'
|
5
|
-
require 'mustache'
|
6
4
|
require 'pathname'
|
7
5
|
require 'webrick'
|
8
6
|
require 'yaml'
|
9
7
|
|
10
8
|
module GryphonNest
|
9
|
+
autoload :Renderer, 'gryphon_nest/renderer'
|
11
10
|
autoload :VERSION, 'gryphon_nest/version'
|
12
11
|
|
13
12
|
class << self
|
@@ -18,6 +17,32 @@ module GryphonNest
|
|
18
17
|
LAYOUT_DIR = 'layouts'
|
19
18
|
TEMPLATE_EXT = '.mustache'
|
20
19
|
|
20
|
+
def build_website
|
21
|
+
raise "Content directory doesn't exist" unless Dir.exist?(CONTENT_DIR)
|
22
|
+
|
23
|
+
existing_files = []
|
24
|
+
if Dir.exist?(BUILD_DIR)
|
25
|
+
existing_files = filter_glob("#{BUILD_DIR}/**/*")
|
26
|
+
else
|
27
|
+
Dir.mkdir(BUILD_DIR)
|
28
|
+
end
|
29
|
+
|
30
|
+
existing_files = existing_files.difference(process_content)
|
31
|
+
existing_files = existing_files.difference(copy_assets)
|
32
|
+
cleanup(existing_files)
|
33
|
+
end
|
34
|
+
|
35
|
+
# @param port [Integer]
|
36
|
+
def serve_website(port)
|
37
|
+
puts "Running local server on #{port}"
|
38
|
+
server = WEBrick::HTTPServer.new(Port: port, DocumentRoot: BUILD_DIR)
|
39
|
+
# Trap ctrl c so we don't get the horrible stack trace
|
40
|
+
trap('INT') { server.shutdown }
|
41
|
+
server.start
|
42
|
+
end
|
43
|
+
|
44
|
+
private
|
45
|
+
|
21
46
|
# @param template_name [String]
|
22
47
|
# @return [String]
|
23
48
|
def get_output_name(template_name)
|
@@ -33,51 +58,100 @@ module GryphonNest
|
|
33
58
|
path.to_s
|
34
59
|
end
|
35
60
|
|
36
|
-
# @
|
37
|
-
# @
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
61
|
+
# @params path [String]
|
62
|
+
# @return [Array]
|
63
|
+
def filter_glob(path)
|
64
|
+
Dir.glob(path).reject do |p|
|
65
|
+
File.directory?(p)
|
66
|
+
end
|
67
|
+
end
|
43
68
|
|
44
|
-
|
69
|
+
# @param path [String]
|
70
|
+
# @param content [String]
|
71
|
+
def save_html_file(path, content)
|
72
|
+
dir = File.dirname(path)
|
45
73
|
|
46
|
-
|
47
|
-
|
48
|
-
|
74
|
+
unless Dir.exist?(dir)
|
75
|
+
puts "Creating #{dir}"
|
76
|
+
Dir.mkdir(dir)
|
77
|
+
end
|
78
|
+
|
79
|
+
puts "Creating #{path}"
|
80
|
+
File.write(path, content)
|
81
|
+
end
|
82
|
+
|
83
|
+
# @param src [String]
|
84
|
+
# @param dest [String]
|
85
|
+
# @param layout_file [String]
|
86
|
+
# @param context_file [String]
|
87
|
+
# @return [Boolean]
|
88
|
+
def can_create_html_file?(src, dest, layout_file, context_file)
|
89
|
+
return true unless File.exist?(dest)
|
90
|
+
|
91
|
+
src_mtime = File.mtime(src)
|
92
|
+
dest_mtime = File.mtime(dest)
|
93
|
+
|
94
|
+
return true if src_mtime > dest_mtime
|
95
|
+
|
96
|
+
if File.exist?(layout_file)
|
97
|
+
layout_mtime = File.mtime(layout_file)
|
98
|
+
return true if layout_mtime > dest_mtime
|
99
|
+
end
|
100
|
+
|
101
|
+
if File.exist?(context_file)
|
102
|
+
context_mtime = File.mtime(context_file)
|
103
|
+
return true if context_mtime > dest_mtime
|
49
104
|
end
|
105
|
+
|
106
|
+
false
|
50
107
|
end
|
51
108
|
|
52
109
|
# @param name [String]
|
53
|
-
# @param
|
54
|
-
# @param layouts [Hash]
|
55
|
-
# @param data [Hash]
|
110
|
+
# @param context [Hash]
|
56
111
|
# @return [String]
|
57
|
-
def
|
58
|
-
|
59
|
-
|
112
|
+
def get_layout_file(name, context)
|
113
|
+
path = Pathname.new(LAYOUT_DIR)
|
114
|
+
|
115
|
+
if context.key?('layout')
|
116
|
+
layout = context['layout']
|
117
|
+
path = path.join(layout)
|
60
118
|
|
61
|
-
|
119
|
+
raise "#{name} requires layout file #{layout} but it doesn't exist or can't be read" unless File.exist?(path)
|
62
120
|
|
63
|
-
|
64
|
-
|
65
|
-
|
121
|
+
return path.to_s
|
122
|
+
end
|
123
|
+
|
124
|
+
path.join('main.mustache').to_s
|
66
125
|
end
|
67
126
|
|
68
|
-
# @
|
69
|
-
# @return [
|
70
|
-
def
|
71
|
-
|
72
|
-
|
127
|
+
# @param path [String]
|
128
|
+
# @return [Hash]
|
129
|
+
def read_context_file(path)
|
130
|
+
return {} if path == ''
|
131
|
+
|
132
|
+
return {} unless File.exist?(path)
|
133
|
+
|
134
|
+
File.open(path) do |yaml|
|
135
|
+
YAML.safe_load(yaml)
|
73
136
|
end
|
74
137
|
end
|
75
138
|
|
76
|
-
# @param
|
77
|
-
# @
|
139
|
+
# @param name [String]
|
140
|
+
# @return [String]
|
141
|
+
def get_context_file(name)
|
142
|
+
basename = File.basename(name, TEMPLATE_EXT)
|
143
|
+
|
144
|
+
Dir.glob("#{DATA_DIR}/#{basename}.{yaml,yml}") do |f|
|
145
|
+
return f
|
146
|
+
end
|
147
|
+
|
148
|
+
''
|
149
|
+
end
|
150
|
+
|
78
151
|
# @return [Array]
|
79
|
-
def process_content
|
152
|
+
def process_content
|
80
153
|
created_files = []
|
154
|
+
renderer = Renderer.new
|
81
155
|
|
82
156
|
filter_glob("#{CONTENT_DIR}/**/*").each do |template|
|
83
157
|
if File.extname(template) != TEMPLATE_EXT
|
@@ -85,23 +159,16 @@ module GryphonNest
|
|
85
159
|
next
|
86
160
|
end
|
87
161
|
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
dir = File.dirname(html_file)
|
162
|
+
dest_file = get_output_name(template)
|
163
|
+
context_file = get_context_file(template)
|
164
|
+
context = read_context_file(context_file)
|
165
|
+
layout_file = get_layout_file(template, context)
|
94
166
|
|
95
|
-
|
96
|
-
|
97
|
-
Dir.mkdir(dir)
|
98
|
-
end
|
167
|
+
created_files << dest_file
|
168
|
+
next unless can_create_html_file?(template, dest_file, layout_file, context_file)
|
99
169
|
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
created_files << html_file
|
104
|
-
end
|
170
|
+
content = renderer.render(template, layout_file, context)
|
171
|
+
save_html_file(dest_file, content)
|
105
172
|
end
|
106
173
|
|
107
174
|
created_files
|
@@ -128,51 +195,15 @@ module GryphonNest
|
|
128
195
|
|
129
196
|
next unless can_copy_asset?(asset, dest)
|
130
197
|
|
198
|
+
puts "Copying #{asset} to #{dest}"
|
131
199
|
dest_dir = File.dirname(dest)
|
132
200
|
FileUtils.makedirs(dest_dir)
|
133
201
|
FileUtils.copy_file(asset, dest)
|
134
|
-
puts "Copying #{asset} to #{dest}"
|
135
202
|
end
|
136
203
|
|
137
204
|
copied_files
|
138
205
|
end
|
139
206
|
|
140
|
-
# @return [Hash]
|
141
|
-
def read_layout_files
|
142
|
-
return {} unless Dir.exist?(LAYOUT_DIR)
|
143
|
-
|
144
|
-
layouts = {}
|
145
|
-
|
146
|
-
Dir.glob("#{LAYOUT_DIR}/*#{TEMPLATE_EXT}") do |f|
|
147
|
-
key = File.basename(f, TEMPLATE_EXT)
|
148
|
-
layouts[key] = File.read(f)
|
149
|
-
end
|
150
|
-
|
151
|
-
layouts
|
152
|
-
end
|
153
|
-
|
154
|
-
# @param file [String]
|
155
|
-
# @return [Hash]
|
156
|
-
def read_yaml(file)
|
157
|
-
File.open(file) do |yaml|
|
158
|
-
YAML.safe_load(yaml)
|
159
|
-
end
|
160
|
-
end
|
161
|
-
|
162
|
-
# @return [Hash]
|
163
|
-
def read_data_files
|
164
|
-
return {} unless Dir.exist?(DATA_DIR)
|
165
|
-
|
166
|
-
data = {}
|
167
|
-
|
168
|
-
Dir.glob("#{DATA_DIR}/*.{yaml,yml}") do |f|
|
169
|
-
key = File.basename(f, '.*')
|
170
|
-
data[key] = read_yaml(f)
|
171
|
-
end
|
172
|
-
|
173
|
-
data
|
174
|
-
end
|
175
|
-
|
176
207
|
# @param junk_files [Array]
|
177
208
|
def cleanup(junk_files)
|
178
209
|
junk_files.each do |f|
|
@@ -180,31 +211,5 @@ module GryphonNest
|
|
180
211
|
FileUtils.remove_file(f)
|
181
212
|
end
|
182
213
|
end
|
183
|
-
|
184
|
-
def build_website
|
185
|
-
raise "Content directory doesn't exist" unless Dir.exist?(CONTENT_DIR)
|
186
|
-
|
187
|
-
existing_files = []
|
188
|
-
if Dir.exist?(BUILD_DIR)
|
189
|
-
existing_files = filter_glob("#{BUILD_DIR}/**/*")
|
190
|
-
else
|
191
|
-
Dir.mkdir(BUILD_DIR)
|
192
|
-
end
|
193
|
-
|
194
|
-
data = read_data_files
|
195
|
-
layouts = read_layout_files
|
196
|
-
existing_files = existing_files.difference(process_content(layouts, data))
|
197
|
-
existing_files = existing_files.difference(copy_assets)
|
198
|
-
cleanup(existing_files)
|
199
|
-
end
|
200
|
-
|
201
|
-
# @param port [Integer]
|
202
|
-
def serve_website(port)
|
203
|
-
put "Running local server on #{port}"
|
204
|
-
server = WEBrick::HTTPServer.new(Port: port, DocumentRoot: BUILD_DIR)
|
205
|
-
# Trap ctrl c so we don't get the horrible stack trace
|
206
|
-
trap('INT') { server.shutdown }
|
207
|
-
server.start
|
208
|
-
end
|
209
214
|
end
|
210
215
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: gryphon_nest
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.
|
4
|
+
version: 1.1.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Christopher Birmingham
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-04-
|
11
|
+
date: 2023-04-22 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: htmlbeautifier
|
@@ -92,6 +92,7 @@ files:
|
|
92
92
|
- LICENSE
|
93
93
|
- bin/nest
|
94
94
|
- lib/gryphon_nest.rb
|
95
|
+
- lib/gryphon_nest/renderer.rb
|
95
96
|
- lib/gryphon_nest/version.rb
|
96
97
|
homepage: https://github.com/chrisBirmingham/gryphon_nest
|
97
98
|
licenses:
|