Parent

Included Modules

Class Index [+]

Quicksearch

Webgen::SourceHandler::Main

This class is used by Website to do the actual rendering of the website. It

Public Instance Methods

render() click to toggle source

Render the current website. Before the actual rendering is done, the sources are checked for changes, i.e. nodes for deleted sources are deleted, nodes for new and changed sources are updated.

    # File lib/webgen/sourcehandler.rb, line 54
54:       def render
55:         begin
56:           website.logger.mark_new_cycle if website.logger
57: 
58:           puts "Updating tree..."
59:           time = Benchmark.measure do
60:             website.cache.reset_volatile_cache
61:             update_tree
62:           end
63:           puts "...done in " + ('%2.4f' % time.real) + ' seconds'
64: 
65:           if !website.tree.root
66:             puts 'No source files found - maybe not a webgen website?'
67:             return nil
68:           end
69: 
70:           puts "Writing changed nodes..."
71:           time = Benchmark.measure do
72:             write_tree
73:           end
74:           puts "...done in " + ('%2.4f' % time.real) + ' seconds'
75:         end while website.tree.node_access[:alcn].any? {|name,node| node.flagged?(:created) || node.flagged?(:reinit)}
76:         :success
77:       rescue Webgen::Error
78:         raise
79:       rescue Exception => e
80:         raise Webgen::Error.new(e)
81:       end

Private Instance Methods

create_nodes(path, source_handler) click to toggle source

Prepare everything to create from the path using the source_handler. If a block is given, the actual creation of the nodes is deferred to it. Otherwise the # method of the source_handler is used. After the nodes are created, it is also checked if they have all needed properties.

     # File lib/webgen/sourcehandler.rb, line 233
233:       def create_nodes(path, source_handler) #:yields: path
234:         path = path.dup
235:         path.meta_info = default_meta_info(path, source_handler.class.name)
236:         (website.cache[:sourcehandler_path_mi] ||= {})[[path.path, source_handler.class.name]] = path.meta_info.dup
237:         website.blackboard.dispatch_msg(:before_node_created, path)
238:         *nodes = if block_given?
239:                    yield(path)
240:                  else
241:                    source_handler.create_node(path)
242:                  end
243:         nodes = nodes.flatten.compact
244:         nodes.each {|node| website.blackboard.dispatch_msg(:after_node_created, node)}
245:         nodes
246:       rescue Webgen::Error => e
247:         e.alcn = path unless e.alcn
248:         raise
249:       rescue Exception => e
250:         raise Webgen::NodeCreationError.new(e, source_handler.class.name, path)
251:       end
create_nodes_from_paths(paths) click to toggle source

Use the source handlers to create nodes for the paths in the website.tree and return the nodes that have been created.

     # File lib/webgen/sourcehandler.rb, line 212
212:       def create_nodes_from_paths(paths)
213:         nodes = Set.new
214:         website.config['sourcehandler.invoke'].sort.each do |priority, shns|
215:           shns.each do |shn|
216:             sh = website.cache.instance(shn)
217:             handler_paths = paths_for_handler(shn, paths)
218:             handler_paths.sort {|a,b| a.path.length <=> b.path.length}.each do |path|
219:               if !website.tree[path.parent_path]
220:                 nodes.merge(create_nodes_from_paths([path.parent_path]))
221:               end
222:               nodes += create_nodes(path, sh)
223:             end
224:           end
225:         end
226:         nodes
227:       end
default_meta_info(path, sh_name) click to toggle source

Return the default meta info for the pair of path and sh_name.

     # File lib/webgen/sourcehandler.rb, line 254
254:       def default_meta_info(path, sh_name)
255:         path.meta_info.merge(website.config['sourcehandler.default_meta_info'][:all]).
256:           merge(website.config['sourcehandler.default_meta_info'][sh_name] || {})
257:       end
find_all_source_paths() click to toggle source

Return a hash with all source paths.

     # File lib/webgen/sourcehandler.rb, line 176
176:       def find_all_source_paths
177:         if !defined?(@paths)
178:           active_source = Webgen::Source::Stacked.new(website.config['sources'].collect do |mp, name, *args|
179:                                                         [mp, Webgen::Common.const_for_name(name).new(*args)]
180:                                                       end)
181:           passive_source = Webgen::Source::Stacked.new(website.config['passive_sources'].collect do |mp, name, *args|
182:                                                          [mp, Webgen::Common.const_for_name(name).new(*args)]
183:                                                        end, true)
184:           passive_source.paths.each {|path| path.passive = true }
185:           source = Webgen::Source::Stacked.new([['/', active_source], ['/', passive_source]])
186: 
187:           @paths = {}
188:           source.paths.each do |path|
189:             if !(website.config['sourcehandler.ignore'].any? {|pat| File.fnmatch(pat, path, File::FNM_CASEFOLD|File::FNM_DOTMATCH)})
190:               @paths[path.source_path] = path
191:             end
192:           end
193:         end
194:         @paths
195:       end
meta_info_changed?(node) click to toggle source

Check if the default meta information for node has changed since the last run. But don’t take the node’s path’s modified_at meta information into account since that changes on every path change.

     # File lib/webgen/sourcehandler.rb, line 262
262:       def meta_info_changed?(node)
263:         path = node.node_info[:creation_path]
264:         old_mi = website.cache[:sourcehandler_path_mi][[path, node.node_info[:processor]]]
265:         old_mi.delete('modified_at')
266:         new_mi = default_meta_info(@paths[path] || Webgen::Path.new(path), node.node_info[:processor])
267:         new_mi.delete('modified_at')
268:         node.flag(:dirty_meta_info) if !old_mi || old_mi != new_mi
269:       end
paths_for_handler(name, paths) click to toggle source

Return only the subset of paths which are handled by the source handler name.

     # File lib/webgen/sourcehandler.rb, line 198
198:       def paths_for_handler(name, paths)
199:         patterns = website.config['sourcehandler.patterns'][name]
200:         return [] if patterns.nil?
201: 
202:         options = (website.config['sourcehandler.casefold'] ? File::FNM_CASEFOLD : 0) |
203:           (website.config['sourcehandler.use_hidden_files'] ? File::FNM_DOTMATCH : 0) |
204:           File::FNM_PATHNAME
205:         find_all_source_paths.values_at(*paths).compact.select do |path|
206:           patterns.any? {|pat| File.fnmatch(pat, path, options)}
207:         end
208:       end
update_tree() click to toggle source

Update the website.tree by creating/reinitializing all needed nodes.

     # File lib/webgen/sourcehandler.rb, line 88
 88:       def update_tree
 89:         unused_paths = Set.new
 90:         referenced_nodes = Set.new
 91:         all_but_passive_paths = Set.new(find_all_source_paths.select {|name, path| !path.passive?}.collect {|name, path| name})
 92:         begin
 93:           used_paths = all_but_passive_paths - unused_paths
 94:           paths_to_use = Set.new
 95:           nodes_to_delete = Set.new
 96:           passive_nodes = Set.new
 97: 
 98:           website.tree.node_access[:alcn].each do |alcn, node|
 99:             next if node == website.tree.dummy_root
100: 
101:             begin
102:               used_paths.delete(node.node_info[:src])
103: 
104:               src_path = find_all_source_paths[node.node_info[:src]]
105:               if !src_path
106:                 nodes_to_delete << node
107:               elsif (!node.flagged?(:created) && src_path.changed?) || node.meta_info_changed?
108:                 node.flag(:reinit)
109:                 paths_to_use << node.node_info[:src]
110:               elsif node.changed?
111:                 # nothing to be done here but method node.changed? has to be called
112:               end
113: 
114:               if src_path && src_path.passive?
115:                 passive_nodes << node
116:               elsif src_path
117:                 referenced_nodes += node.node_info[:used_meta_info_nodes] + node.node_info[:used_nodes]
118:               end
119:             rescue Webgen::Error => e
120:               e.alcn = node.alcn unless e.alcn
121:               raise
122:             rescue Exception => e
123:               raise Webgen::Error.new(e, nil, node)
124:             end
125:           end
126: 
127:           # add unused passive nodes to node_to_delete set
128:           unreferenced_passive_nodes, other_passive_nodes = passive_nodes.partition do |pnode|
129:             !referenced_nodes.include?(pnode.alcn)
130:           end
131:           refs = other_passive_nodes.collect {|n| (n.node_info[:used_meta_info_nodes] + n.node_info[:used_nodes]).to_a}.flatten
132:           unreferenced_passive_nodes.each {|n| nodes_to_delete << n if !refs.include?(n.alcn)}
133: 
134:           nodes_to_delete.each {|node| website.tree.delete_node(node)}
135:           used_paths.merge(paths_to_use)
136:           paths = create_nodes_from_paths(used_paths).collect {|n| n.node_info[:src]}
137:           unused_paths.merge(used_paths - paths)
138:           website.tree.node_access[:alcn].each {|name, node| website.tree.delete_node(node) if node.flagged?(:reinit)}
139:           website.cache.reset_volatile_cache
140:         end until used_paths.empty?
141:       end
write_tree() click to toggle source

Write out all changed nodes of the website.tree.

     # File lib/webgen/sourcehandler.rb, line 144
144:       def write_tree
145:         output = website.blackboard.invoke(:output_instance)
146: 
147:         website.tree.node_access[:alcn].select do |name, node|
148:           use_node = (node != website.tree.dummy_root && node.flagged?(:dirty))
149:           node.unflag(:dirty_meta_info)
150:           node.unflag(:created)
151:           node.unflag(:dirty)
152:           use_node
153:         end.sort.each do |name, node|
154:           begin
155:             next if node['no_output'] || !(content = node.content)
156: 
157:             puts " "*4 + name, :verbose
158:             type = if node.is_directory?
159:                      :directory
160:                    elsif node.is_fragment?
161:                      :fragment
162:                    else
163:                      :file
164:                    end
165:             output.write(node.path, content, type)
166:           rescue Webgen::Error => e
167:             e.alcn = node.alcn unless e.alcn
168:             raise
169:           rescue Exception => e
170:             raise Webgen::RenderError.new(e, nil, node)
171:           end
172:         end
173:       end

Disabled; run with --debug to generate this.

[Validate]

Generated with the Darkfish Rdoc Generator 1.1.6.