ruhoh 2.5 → 2.6
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.
- data/Gemfile +1 -1
- data/bin/ruhoh +10 -3
- data/features/_root.feature +11 -0
- data/features/data.feature +78 -0
- data/features/javascripts.feature +36 -0
- data/features/permalinks.feature +23 -0
- data/features/plugins.feature +84 -0
- data/features/sort_order.feature +121 -0
- data/features/step_defs.rb +3 -3
- data/features/support/helpers.rb +3 -5
- data/history.json +21 -0
- data/lib/ruhoh.rb +28 -123
- data/lib/ruhoh/base/collectable.rb +273 -0
- data/lib/ruhoh/base/compilable.rb +30 -0
- data/lib/ruhoh/base/compilable_asset.rb +30 -0
- data/lib/ruhoh/base/model_viewable.rb +30 -0
- data/lib/ruhoh/base/modelable.rb +44 -0
- data/lib/ruhoh/base/page_like.rb +111 -0
- data/lib/ruhoh/base/page_viewable.rb +92 -0
- data/lib/ruhoh/base/routable.rb +20 -0
- data/lib/ruhoh/base/watchable.rb +18 -0
- data/lib/ruhoh/cascade.rb +93 -0
- data/lib/ruhoh/client.rb +1 -3
- data/lib/ruhoh/collections.rb +2 -1
- data/lib/ruhoh/config.rb +67 -0
- data/lib/ruhoh/console_methods.rb +0 -2
- data/lib/ruhoh/parse.rb +7 -5
- data/lib/ruhoh/plugins/initializer.rb +24 -0
- data/lib/ruhoh/plugins/local_plugins_plugin.rb +10 -0
- data/lib/ruhoh/plugins/plugin.rb +27 -0
- data/lib/ruhoh/programs/compile.rb +2 -6
- data/lib/ruhoh/programs/preview.rb +5 -2
- data/lib/ruhoh/programs/watch.rb +4 -6
- data/lib/ruhoh/publish/rsync.rb +2 -2
- data/lib/ruhoh/resources/_base/collection.rb +6 -0
- data/lib/ruhoh/resources/_base/compiler.rb +3 -0
- data/lib/ruhoh/resources/_base/model.rb +3 -0
- data/lib/ruhoh/resources/_base/model_view.rb +3 -0
- data/lib/ruhoh/resources/_base/watcher.rb +4 -0
- data/lib/ruhoh/resources/data/collection.rb +30 -9
- data/lib/ruhoh/resources/javascripts/collection_view.rb +5 -1
- data/lib/ruhoh/resources/javascripts/model_view.rb +15 -0
- data/lib/ruhoh/resources/layouts/client.rb +1 -1
- data/lib/ruhoh/resources/pages/client.rb +2 -2
- data/lib/ruhoh/resources/pages/collection.rb +2 -21
- data/lib/ruhoh/resources/theme/compiler.rb +2 -2
- data/lib/ruhoh/resources/widgets/collection.rb +2 -2
- data/lib/ruhoh/routes.rb +1 -1
- data/lib/ruhoh/summarizer.rb +2 -2
- data/lib/ruhoh/ui/dashboard.rb +13 -0
- data/lib/ruhoh/ui/page_not_found.rb +3 -2
- data/lib/ruhoh/url_slug.rb +23 -9
- data/lib/ruhoh/version.rb +1 -1
- data/lib/ruhoh/views/master_view.rb +1 -1
- data/spec/lib/ruhoh/plugins/initializer_spec.rb +43 -0
- data/spec/lib/ruhoh/plugins/plugin_spec.rb +40 -0
- data/spec/spec_helper.rb +1 -0
- data/system/config.json +21 -0
- data/system/{dash/index.html → dashboard.html} +1 -1
- data/{lib/ruhoh/ui → system}/page_not_found.html +0 -0
- data/system/plugins/sprockets/compiler.rb +1 -0
- data/system/widgets/comments/disqus.html +1 -1
- metadata +34 -15
- data/lib/ruhoh/base/collection.rb +0 -284
- data/lib/ruhoh/base/compiler.rb +0 -67
- data/lib/ruhoh/base/model.rb +0 -161
- data/lib/ruhoh/base/model_view.rb +0 -129
- data/lib/ruhoh/base/watcher.rb +0 -25
- data/lib/ruhoh/resources/dash/collection.rb +0 -10
- data/lib/ruhoh/resources/dash/model.rb +0 -5
- data/lib/ruhoh/resources/dash/model_view.rb +0 -5
- data/lib/ruhoh/resources/dash/previewer.rb +0 -13
data/features/support/helpers.rb
CHANGED
@@ -2,17 +2,15 @@
|
|
2
2
|
SampleSitePath = File.expand_path(File.join(File.dirname(__FILE__), '..', '..', '__tmp'))
|
3
3
|
|
4
4
|
def start
|
5
|
-
@ruhoh = Ruhoh.new
|
6
|
-
@ruhoh.setup(:source => SampleSitePath)
|
5
|
+
@ruhoh = Ruhoh.new(:source => SampleSitePath)
|
7
6
|
@ruhoh.env = :test
|
8
|
-
@ruhoh.setup_paths
|
9
7
|
@ruhoh.setup_plugins
|
10
8
|
end
|
11
9
|
|
12
10
|
def compile
|
13
11
|
start
|
14
12
|
@ruhoh.env = 'production'
|
15
|
-
@ruhoh.
|
13
|
+
@ruhoh.config['compiled_path'] = File.join(SampleSitePath, 'compiled')
|
16
14
|
@ruhoh.compile
|
17
15
|
end
|
18
16
|
|
@@ -55,7 +53,7 @@ TEXT
|
|
55
53
|
end
|
56
54
|
|
57
55
|
def get_compiled_file(path)
|
58
|
-
FileUtils.cd(@ruhoh.
|
56
|
+
FileUtils.cd(@ruhoh.config['compiled_path']) {
|
59
57
|
File.open(path, 'r:UTF-8') { |f|
|
60
58
|
return f.read }
|
61
59
|
}
|
data/history.json
CHANGED
@@ -1,4 +1,25 @@
|
|
1
1
|
[
|
2
|
+
{
|
3
|
+
"version" : "2.6",
|
4
|
+
"date" : "13.12.2013",
|
5
|
+
"changes" : [
|
6
|
+
"config['compiled'] is now config['compiled_path'] and compiled folder is collection ignored.",
|
7
|
+
"Dash is no longer a collection, it is tracked on the root blog level and may be overloaded as normal."
|
8
|
+
],
|
9
|
+
"features" : [
|
10
|
+
"config file now deep merges itself down the cascade.",
|
11
|
+
"data file now deep merges itself down the cascade.",
|
12
|
+
"page_not_found UI can now be overloaded via the cascade.",
|
13
|
+
"Any page metatdata attribute can be used in custom permalink",
|
14
|
+
"@nicolaracco adds ability to load plugins from gems."
|
15
|
+
],
|
16
|
+
"bugs" : [
|
17
|
+
"@mudasobwa fix for non-ASCII summaries",
|
18
|
+
"custo data collections now work as expected as per the collection API.",
|
19
|
+
"@richtera enables ?to_javascripts to work with needed fingerpinting inclusion."
|
20
|
+
]
|
21
|
+
}
|
22
|
+
,
|
2
23
|
{
|
3
24
|
"version" : "2.5",
|
4
25
|
"date" : "22.09.2013",
|
data/lib/ruhoh.rb
CHANGED
@@ -18,6 +18,8 @@ require 'ruhoh/utils'
|
|
18
18
|
require 'ruhoh/friend'
|
19
19
|
require 'ruhoh/parse'
|
20
20
|
|
21
|
+
require 'ruhoh/config'
|
22
|
+
require 'ruhoh/cascade'
|
21
23
|
require 'ruhoh/converter'
|
22
24
|
require 'ruhoh/views/master_view'
|
23
25
|
require 'ruhoh/collections'
|
@@ -26,21 +28,24 @@ require 'ruhoh/routes'
|
|
26
28
|
require 'ruhoh/string_format'
|
27
29
|
require 'ruhoh/url_slug'
|
28
30
|
require 'ruhoh/programs/preview'
|
31
|
+
require 'ruhoh/plugins/plugin'
|
29
32
|
|
30
33
|
class Ruhoh
|
31
34
|
class << self
|
32
35
|
attr_accessor :log
|
33
|
-
attr_reader :
|
36
|
+
attr_reader :root
|
34
37
|
end
|
35
38
|
|
36
39
|
attr_accessor :log, :env
|
37
|
-
attr_reader :
|
40
|
+
attr_reader :root, :cache, :collections, :routes
|
38
41
|
|
39
42
|
Root = File.expand_path(File.join(File.dirname(__FILE__), '..'))
|
40
43
|
@log = Ruhoh::Logger.new
|
41
44
|
@root = Root
|
42
45
|
|
43
|
-
def initialize
|
46
|
+
def initialize(opts={})
|
47
|
+
self.class.log.log_file = opts[:log_file] if opts[:log_file] #todo
|
48
|
+
@base = opts[:source] ? opts[:source] : Dir.getwd
|
44
49
|
@collections = Ruhoh::Collections.new(self)
|
45
50
|
@cache = Ruhoh::Cache.new(self)
|
46
51
|
@routes = Ruhoh::Routes.new(self)
|
@@ -50,119 +55,55 @@ class Ruhoh
|
|
50
55
|
Ruhoh::Views::MasterView.new(self, pointer)
|
51
56
|
end
|
52
57
|
|
53
|
-
# Public: Setup Ruhoh utilities relative to the current application directory.
|
54
|
-
# Returns boolean on success/failure
|
55
|
-
def setup(opts={})
|
56
|
-
self.class.log.log_file = opts[:log_file] if opts[:log_file] #todo
|
57
|
-
@base = opts[:source] ? opts[:source] : Dir.getwd
|
58
|
-
!!config
|
59
|
-
end
|
60
|
-
|
61
58
|
def collection(resource)
|
62
59
|
@collections.load(resource)
|
63
60
|
end
|
64
61
|
|
65
|
-
def config
|
66
|
-
return @config
|
67
|
-
|
68
|
-
config
|
69
|
-
config['compiled'] = config['compiled'] ? File.expand_path(config['compiled']) : "compiled"
|
70
|
-
|
71
|
-
config['_root'] ||= {}
|
72
|
-
config['_root']['permalink'] ||= "/:relative_path/:filename"
|
73
|
-
config['_root']['paginator'] ||= {}
|
74
|
-
config['_root']['paginator']['url'] ||= "/index/"
|
75
|
-
config['_root']['rss'] ||= {}
|
76
|
-
config['_root']['rss']['url'] ||= "/"
|
77
|
-
|
78
|
-
config['base_path'] = config['base_path'].to_s.strip
|
79
|
-
if config['base_path'].empty?
|
80
|
-
config['base_path'] = '/'
|
81
|
-
else
|
82
|
-
config['base_path'] += "/" unless config['base_path'][-1] == '/'
|
83
|
-
end
|
84
|
-
|
85
|
-
Time.default_format = config['date_format'] || "%Y-%m-%d"
|
86
|
-
|
87
|
-
@config = config
|
88
|
-
end
|
89
|
-
|
90
|
-
Paths = Struct.new(:base, :theme, :system, :compiled)
|
91
|
-
def setup_paths
|
92
|
-
@paths = Paths.new
|
93
|
-
@paths.base = @base
|
94
|
-
@paths.system = File.join(Ruhoh::Root, "system")
|
95
|
-
@paths.compiled = @config["compiled"]
|
96
|
-
|
97
|
-
theme = @config.find { |resource, data| data.is_a?(Hash) && data['use'] == "theme" }
|
98
|
-
if theme
|
99
|
-
Ruhoh::Friend.say { plain "Using theme: \"#{theme[0]}\""}
|
100
|
-
@paths.theme = File.join(@base, theme[0])
|
101
|
-
end
|
102
|
-
|
103
|
-
@paths
|
62
|
+
def config
|
63
|
+
return @config if @config
|
64
|
+
@config = Ruhoh::Config.new(self)
|
65
|
+
@config.touch
|
104
66
|
end
|
105
67
|
|
106
|
-
# Default paths to the 3 levels of the cascade.
|
107
68
|
def cascade
|
108
|
-
|
109
|
-
{
|
110
|
-
"name" => "system",
|
111
|
-
"path" => paths.system
|
112
|
-
},
|
113
|
-
{
|
114
|
-
"name" => "base",
|
115
|
-
"path" => paths.base
|
116
|
-
}
|
117
|
-
]
|
118
|
-
a << {
|
119
|
-
"name" => "theme",
|
120
|
-
"path" => paths.theme
|
121
|
-
} if paths.theme
|
69
|
+
return @cascade if @cascade
|
122
70
|
|
123
|
-
|
71
|
+
@cascade = Ruhoh::Cascade.new(config)
|
72
|
+
@cascade.base = @base
|
73
|
+
config.touch
|
74
|
+
|
75
|
+
@cascade
|
124
76
|
end
|
125
77
|
|
126
78
|
def setup_plugins
|
127
|
-
|
128
|
-
|
129
|
-
enable_sprockets = @config['asset_pipeline']['enable'] rescue false
|
79
|
+
enable_sprockets = config['asset_pipeline']['enable'] rescue false
|
130
80
|
if enable_sprockets
|
131
81
|
Ruhoh::Friend.say { green "=> Oh boy! Asset pipeline enabled by way of sprockets =D" }
|
132
|
-
sprockets = Dir[File.join(
|
82
|
+
sprockets = Dir[File.join(cascade.system, "plugins", "sprockets", "**/*.rb")]
|
133
83
|
sprockets.each {|f| require f }
|
134
84
|
end
|
85
|
+
require 'ruhoh/plugins/local_plugins_plugin'
|
135
86
|
|
136
|
-
|
137
|
-
plugins.each {|f| require f } unless plugins.empty?
|
87
|
+
Ruhoh::Plugins::Plugin.run_all self
|
138
88
|
end
|
139
89
|
|
140
90
|
def env
|
141
91
|
@env || 'development'
|
142
92
|
end
|
143
93
|
|
144
|
-
def base_path
|
145
|
-
return '/' unless (env == 'production')
|
146
|
-
|
147
|
-
string = config['base_path'].chomp('/').reverse.chomp('/').reverse
|
148
|
-
return '/' if string.empty? || string == '/'
|
149
|
-
"/#{ string }/"
|
150
|
-
end
|
151
|
-
|
152
94
|
def compiled_path(url)
|
153
95
|
if config['compile_as_root']
|
154
|
-
url = url.gsub(/^#{ base_path.chomp('/') }\/?/, '')
|
96
|
+
url = url.gsub(/^#{ config.base_path.chomp('/') }\/?/, '')
|
155
97
|
end
|
156
98
|
|
157
|
-
path = File.expand_path(File.join(
|
99
|
+
path = File.expand_path(File.join(config['compiled_path'], url)).gsub(/\/{2,}/, '/')
|
158
100
|
CGI.unescape(path)
|
159
101
|
end
|
160
102
|
|
161
|
-
# @config['base_path'] is assumed to be well-formed.
|
162
103
|
# Always remove trailing slash.
|
163
104
|
# Returns String - normalized url with prepended base_path
|
164
105
|
def to_url(*args)
|
165
|
-
url = base_path + args.join('/')
|
106
|
+
url = config.base_path + args.join('/')
|
166
107
|
url = url.gsub(/\/{2,}/, '/')
|
167
108
|
(url == "/") ? url : url.chomp('/')
|
168
109
|
end
|
@@ -196,10 +137,9 @@ class Ruhoh
|
|
196
137
|
# end
|
197
138
|
# end
|
198
139
|
def compile
|
199
|
-
ensure_paths
|
200
140
|
Ruhoh::Friend.say { plain "Compiling for environment: '#{@env}'" }
|
201
|
-
FileUtils.rm_r
|
202
|
-
FileUtils.mkdir_p
|
141
|
+
FileUtils.rm_r config['compiled_path'] if File.exist?(config['compiled_path'])
|
142
|
+
FileUtils.mkdir_p config['compiled_path']
|
203
143
|
|
204
144
|
# Run the resource compilers
|
205
145
|
compilers = @collections.all
|
@@ -209,6 +149,7 @@ class Ruhoh
|
|
209
149
|
compilers.delete('javascripts')
|
210
150
|
compilers.unshift('javascripts')
|
211
151
|
|
152
|
+
|
212
153
|
compilers.each do |name|
|
213
154
|
collection = collection(name)
|
214
155
|
next unless collection.compiler?
|
@@ -229,42 +170,6 @@ class Ruhoh
|
|
229
170
|
true
|
230
171
|
end
|
231
172
|
|
232
|
-
# Find a file in the base cascade directories
|
233
|
-
# @return[Hash, nil] a single file pointer
|
234
|
-
def find_file(key)
|
235
|
-
dict = _all_files
|
236
|
-
dict[key] || dict.values.find{ |a| key == a['id'].gsub(/.[^.]+$/, '') }
|
237
|
-
end
|
238
|
-
|
239
|
-
# Collect all files from the base cascade directories.
|
240
|
-
# @return[Hash] dictionary of file pointers
|
241
|
-
def _all_files
|
242
|
-
dict = {}
|
243
|
-
cascade.map{ |a| a['path'] }.each do |path|
|
244
|
-
FileUtils.cd(path) {
|
245
|
-
Dir["*"].each { |id|
|
246
|
-
next unless File.exist?(id) && FileTest.file?(id)
|
247
|
-
dict[id] = {
|
248
|
-
"id" => id,
|
249
|
-
"realpath" => File.realpath(id),
|
250
|
-
}
|
251
|
-
}
|
252
|
-
}
|
253
|
-
end
|
254
|
-
|
255
|
-
dict
|
256
|
-
end
|
257
|
-
|
258
|
-
def ensure_setup
|
259
|
-
return if @config && @paths
|
260
|
-
raise 'Ruhoh has not been fully setup. Please call: Ruhoh.setup'
|
261
|
-
end
|
262
|
-
|
263
|
-
def ensure_paths
|
264
|
-
return if @config && @paths
|
265
|
-
raise 'Ruhoh has not setup paths. Please call: Ruhoh.setup'
|
266
|
-
end
|
267
|
-
|
268
173
|
def self.collection(resource)
|
269
174
|
Collections.load(resource)
|
270
175
|
end
|
@@ -0,0 +1,273 @@
|
|
1
|
+
module Ruhoh::Base::Collectable
|
2
|
+
def self.included(klass)
|
3
|
+
klass.__send__(:attr_accessor, :resource_name, :master)
|
4
|
+
klass.__send__(:attr_reader, :ruhoh)
|
5
|
+
end
|
6
|
+
|
7
|
+
def initialize(ruhoh)
|
8
|
+
@ruhoh = ruhoh
|
9
|
+
end
|
10
|
+
|
11
|
+
# Public API for finding a resource from this collection
|
12
|
+
# @param name_or_pointer [String, Hash]
|
13
|
+
# Hash - File pointer
|
14
|
+
# String - id (filename) with full extension, e.g: about-me.md
|
15
|
+
# String - name (filename) without the extension e.g: about-me
|
16
|
+
# Returns the first matched filename.
|
17
|
+
# See implementation for how match is determined.
|
18
|
+
# @param opts [Hash] Optional options
|
19
|
+
# opts[:all] - true to search all files as some may be invalid as resources
|
20
|
+
#
|
21
|
+
# @return[model, nil] the model is always wrapped in its view.
|
22
|
+
def find(name_or_pointer, opts={})
|
23
|
+
pointer = find_file(name_or_pointer, opts)
|
24
|
+
return nil unless pointer
|
25
|
+
|
26
|
+
@ruhoh.cache.get(pointer['realpath']) ||
|
27
|
+
@ruhoh.cache.set(pointer['realpath'], load_model_view(pointer))
|
28
|
+
end
|
29
|
+
|
30
|
+
# Public API
|
31
|
+
# @return[Hash] dictionary of models { "id" => Model }
|
32
|
+
def dictionary
|
33
|
+
dict = {}
|
34
|
+
files.values.each { |pointer|
|
35
|
+
dict.merge!({
|
36
|
+
pointer['id'] => find(pointer)
|
37
|
+
})
|
38
|
+
}
|
39
|
+
dict
|
40
|
+
end
|
41
|
+
|
42
|
+
def resource_name
|
43
|
+
@resource_name ||= self.class.name.split("::").pop
|
44
|
+
end
|
45
|
+
|
46
|
+
# Implemented via Observable module
|
47
|
+
# See http://ruby-doc.org/stdlib-1.9.3/libdoc/observer/rdoc/Observable.html
|
48
|
+
# Collection subscribes to its child models.
|
49
|
+
# #update is called on model #process.
|
50
|
+
# noop
|
51
|
+
def update(model_data)
|
52
|
+
end
|
53
|
+
|
54
|
+
# The default glob for finding files.
|
55
|
+
# Every file in all child directories.
|
56
|
+
def glob
|
57
|
+
"**/*"
|
58
|
+
end
|
59
|
+
|
60
|
+
# Default paths to the 3 levels of the cascade.
|
61
|
+
def paths
|
62
|
+
Array(@ruhoh.cascade.paths.map{|h| h["path"]}).map { |path|
|
63
|
+
collection_path = File.join(path, resource_name)
|
64
|
+
next unless File.directory?(collection_path)
|
65
|
+
|
66
|
+
collection_path
|
67
|
+
}.compact
|
68
|
+
end
|
69
|
+
|
70
|
+
# Does this resource have any valid paths to process?
|
71
|
+
# A valid path may exist on any of the cascade levels.
|
72
|
+
# False means there are no directories on any cascade level.
|
73
|
+
# @returns[Boolean]
|
74
|
+
def paths?
|
75
|
+
!paths.empty?
|
76
|
+
end
|
77
|
+
|
78
|
+
def config
|
79
|
+
config = @ruhoh.config[resource_name] || {}
|
80
|
+
unless config.is_a?(Hash)
|
81
|
+
Ruhoh.log.error("'#{resource_name}' config key in config" +
|
82
|
+
" is a #{config.class}; it needs to be a Hash (object).")
|
83
|
+
end
|
84
|
+
config
|
85
|
+
end
|
86
|
+
|
87
|
+
# NOOP
|
88
|
+
# touch a model.
|
89
|
+
# Used to perform custom regeneration logic against a model.
|
90
|
+
def touch(name_or_pointer)
|
91
|
+
end
|
92
|
+
|
93
|
+
# @param key [String, Hash]
|
94
|
+
# String - id (filename) with full extension, e.g: about-me.md
|
95
|
+
# String - name (filename) without the extension e.g: about-me
|
96
|
+
# Returns the first matched filename.
|
97
|
+
# See implementation for how match is determined.
|
98
|
+
# Hash - File pointer
|
99
|
+
#
|
100
|
+
# @param opts [Hash] Optional options
|
101
|
+
# opts[:all] - true to search all files as some may be invalid as resources
|
102
|
+
#
|
103
|
+
# @return [pointer, nil]
|
104
|
+
def find_file(key, opts={})
|
105
|
+
return key if key.is_a?(Hash) # assume valid pointer
|
106
|
+
|
107
|
+
dict = opts[:all] ? _all_files : files
|
108
|
+
|
109
|
+
dict[key] || dict.values.find{ |a| key == a['id'].gsub(/.[^.]+$/, '') }
|
110
|
+
end
|
111
|
+
|
112
|
+
# Collect all files (as mapped by data resources) for this data endpoint.
|
113
|
+
# Each resource can have 3 file references, one per each cascade level.
|
114
|
+
# The file hashes are collected in order
|
115
|
+
# so they will overwrite eachother if found.
|
116
|
+
|
117
|
+
# @param id [String, Array] Optional.
|
118
|
+
# Collect all files for a single data resource.
|
119
|
+
# Can be many files due to the cascade.
|
120
|
+
# @param [block] Optional.
|
121
|
+
# Implement custom validation logic by passing in a block.
|
122
|
+
# The block is given (id, self) as args.
|
123
|
+
# Return true/false for whether the file is valid/invalid.
|
124
|
+
#
|
125
|
+
# @return[Hash] dictionary of pointers.
|
126
|
+
def files(id=nil, &block)
|
127
|
+
return @ruhoh.cache.get(files_cache_key) if @ruhoh.cache.get(files_cache_key)
|
128
|
+
|
129
|
+
dict = _all_files
|
130
|
+
dict.keep_if do |id, pointer|
|
131
|
+
block_given? ? yield(id, self) : valid_file?(id)
|
132
|
+
end
|
133
|
+
|
134
|
+
@ruhoh.cache.set(files_cache_key, dict)
|
135
|
+
dict
|
136
|
+
end
|
137
|
+
|
138
|
+
# Collect all files within this collection, valid or otherwise.
|
139
|
+
# Each resource can have 3 file references, one per each cascade level.
|
140
|
+
# The file hashes are collected in order and overwrite eachother if found.
|
141
|
+
# This is a low-level method, see #files for the public interface.
|
142
|
+
#
|
143
|
+
# @return[Hash] dictionary of pointers.
|
144
|
+
def _all_files
|
145
|
+
dict = {}
|
146
|
+
paths.each do |path|
|
147
|
+
FileUtils.cd(path) {
|
148
|
+
Dir[glob].each { |id|
|
149
|
+
next unless File.exist?(id) && FileTest.file?(id)
|
150
|
+
dict[id] = {
|
151
|
+
"id" => id,
|
152
|
+
"realpath" => File.realpath(id),
|
153
|
+
"resource" => resource_name,
|
154
|
+
}
|
155
|
+
}
|
156
|
+
}
|
157
|
+
end
|
158
|
+
|
159
|
+
dict
|
160
|
+
end
|
161
|
+
|
162
|
+
def valid_file?(filepath)
|
163
|
+
return false if filepath.start_with?('.')
|
164
|
+
return false if filepath.start_with?('_')
|
165
|
+
return false if %w{ config.json config.yaml config.yml }.include?(filepath)
|
166
|
+
excludes = Array(config['exclude']).map { |node| Regexp.new(node) }
|
167
|
+
excludes.each { |regex| return false if filepath =~ regex }
|
168
|
+
true
|
169
|
+
end
|
170
|
+
|
171
|
+
%w{
|
172
|
+
collection_view
|
173
|
+
model
|
174
|
+
model_view
|
175
|
+
client
|
176
|
+
compiler
|
177
|
+
watcher
|
178
|
+
previewer
|
179
|
+
}.each do |method_name|
|
180
|
+
define_method(method_name) do
|
181
|
+
get_module_namespace.const_get(camelize(method_name).to_sym)
|
182
|
+
end
|
183
|
+
|
184
|
+
define_method("#{method_name}?") do
|
185
|
+
get_module_namespace.const_defined?(camelize(method_name).to_sym)
|
186
|
+
end
|
187
|
+
end
|
188
|
+
|
189
|
+
def load_collection_view
|
190
|
+
@_collection_view ||= collection_view? ?
|
191
|
+
collection_view.new(self) :
|
192
|
+
self
|
193
|
+
end
|
194
|
+
|
195
|
+
def load_model(pointer)
|
196
|
+
_model = model? ?
|
197
|
+
model.new(@ruhoh, pointer) :
|
198
|
+
Ruhoh::Base::Model.new(@ruhoh, pointer)
|
199
|
+
_model.add_observer(self)
|
200
|
+
_model
|
201
|
+
end
|
202
|
+
|
203
|
+
def load_model_view(pointer)
|
204
|
+
model_view? ?
|
205
|
+
model_view.new(load_model(pointer)) :
|
206
|
+
Ruhoh::Base::ModelView.new(load_model(pointer))
|
207
|
+
end
|
208
|
+
|
209
|
+
def load_client(opts)
|
210
|
+
@_client ||= client.new(load_collection_view, opts)
|
211
|
+
end
|
212
|
+
|
213
|
+
def load_compiler
|
214
|
+
@_compiler ||= compiler.new(load_collection_view)
|
215
|
+
end
|
216
|
+
|
217
|
+
def load_watcher(*args)
|
218
|
+
@_watcher ||= watcher? ?
|
219
|
+
watcher.new(load_collection_view) :
|
220
|
+
Ruhoh::Base::Watcher.new(load_collection_view)
|
221
|
+
end
|
222
|
+
|
223
|
+
def load_previewer(*args)
|
224
|
+
@_previewer ||= previewer.new(@ruhoh)
|
225
|
+
end
|
226
|
+
|
227
|
+
def files_cache_key
|
228
|
+
"#{ resource_name }-files"
|
229
|
+
end
|
230
|
+
|
231
|
+
def scaffold
|
232
|
+
pointer = find_file('_scaffold', all: true) || @ruhoh.cascade.find_file('_scaffold')
|
233
|
+
return '' unless pointer
|
234
|
+
|
235
|
+
File.open(pointer['realpath'], 'r:UTF-8') { |f| f.read }
|
236
|
+
end
|
237
|
+
|
238
|
+
def compiled_path
|
239
|
+
@compiled_path ||= @ruhoh.compiled_path(@ruhoh.to_url(url_endpoint))
|
240
|
+
end
|
241
|
+
|
242
|
+
protected
|
243
|
+
|
244
|
+
# Load the registered resource else default to Pages if not configured.
|
245
|
+
# @returns[Constant] the resource's module namespace
|
246
|
+
def get_module_namespace
|
247
|
+
type = @ruhoh.config[resource_name]["use"] rescue nil
|
248
|
+
if type
|
249
|
+
if @ruhoh.collections.registered.include?(type)
|
250
|
+
Ruhoh::Resources.const_get(camelize(type))
|
251
|
+
elsif @ruhoh.collections.base.include?(type)
|
252
|
+
Ruhoh::Base.const_get(camelize(type))
|
253
|
+
else
|
254
|
+
klass = camelize(type)
|
255
|
+
Friend.say {
|
256
|
+
red "#{resource_name} resource set to use:'#{type}' in config" +
|
257
|
+
" but Ruhoh::Resources::#{klass} does not exist."
|
258
|
+
}
|
259
|
+
abort
|
260
|
+
end
|
261
|
+
else
|
262
|
+
if @ruhoh.collections.registered.include?(resource_name)
|
263
|
+
Ruhoh::Resources.const_get(camelize(resource_name))
|
264
|
+
else
|
265
|
+
Ruhoh::Resources.const_get(:Pages)
|
266
|
+
end
|
267
|
+
end
|
268
|
+
end
|
269
|
+
|
270
|
+
def camelize(name)
|
271
|
+
name.to_s.split('_').map { |a| a.capitalize }.join
|
272
|
+
end
|
273
|
+
end
|