app/models/web.rb in Pimki-1.7.092 vs app/models/web.rb in Pimki-1.8.092

- old
+ new

@@ -1,317 +1,315 @@ -require "cgi" -require "page" -require "page_set" -require "wiki_words" -require "zip/zip" - -class Web - attr_accessor :pages, :name, :address, :password, :menu_type, :menu_content, :rendered_menu, :menu_limit, :menu_category - attr_accessor :markup, :color, :safe_mode, :additional_style, :published, :default_to_published, :brackets_only, :count_pages - attr_accessor :mind_map_size, :symbols_map, :links_map, :enable_dclick_edit, :check_pass_on_edit, :enable_menu - - # Mind Map defaults - attr_accessor :mm_prog, :mm_graph_type, :mm_show_missing, :mm_show_authors, :mm_show_leaves, :mm_selected_categories - - @@BLIKI_TEMPLATE = "Try a weekly worksheet:\n\n| / | *Morning* | *Afternoon* |\n" + - "| *Mon* | - | - |\n| *Tue* | - | - |\n| *Wed* | - | - |\n" + - "| *Thu* | - | - |\n| *Fri* | - | - |\n" - - def bliki - @bliki ||= Hash.new - end - - def initialize(name, address, password = nil) - @name, @address, @password, @safe_mode = name, address, password, false - @pages = {} - end - - def add_page(page) - @pages[page.name] = page - end - - def remove_pages(pages_to_be_removed) - pages.delete_if { |page_name, page| pages_to_be_removed.include?(page) } - end - - def revised_on - pages.values.sort_by { |page| [page.created_at] }.reverse.first.created_at - end - - def select(&accept) - PageSet.new(self, @pages.values, accept) - end - - def select_bliki(&accept) - PageSet.new(self, bliki.values, accept) - end - - def revised_on - select.most_recent_revision - end - - def authors - select.authors - end - - def categories - select.map { |page| page.categories }.flatten.uniq.sort - end - - # Create a link for the given page name and link text based - # on the render mode in options and whether the page exists - # in the this web. - def make_link(name, text = nil, options = {}) - page = pages[name] - text = text || WikiWords.separate(name) - link = CGI.escape(name) - - case options[:mode] - when :export - if page then "<a class=\"existingWikiWord\" href=\"#{link}.html\">#{text}</a>" - else "<span class=\"newWikiWord\">#{text}</span>" end - when :publish - if page then "<a class=\"existingWikiWord\" href=\"../published/#{link}\">#{text}</a>" - else "<span class=\"newWikiWord\">#{text}</span>" end - else - if page then "<a class=\"existingWikiWord\" href=\"../show/#{link}\">#{text}</a>" - else "<span class=\"newWikiWord\">#{text}<a href=\"../show/#{link}\">?</a></span>" end - end - end - - - # Clears the display cache for all the pages with references to - def refresh_pages_with_references(page_name) - select.pages_that_reference(page_name).each { |page| - page.revisions.each { |revision| revision.clear_display_cache } - } - end - - def refresh_revisions - select.each { |page| page.revisions.each { |revision| revision.clear_display_cache } } - select_bliki.each { |page| page.revisions.each { |revision| revision.clear_display_cache } } - end - - # Default values - def markup() @markup || :textile end - def color() @color || "008B26" end - def brackets_only() @brackets_only || false end - def count_pages() @count_pages || false end - def enable_menu() @enable_menu || true end - def menu_content() @menu_content || nil end - def menu_limit() @menu_limit || 20 end - def default_to_published() @default_to_published || false end - def menu_type() - (@menu_type.nil? || @menu_type.empty?) ? 'linkers' : @menu_type - end - def mind_map_size() (@mind_map_size == '0,0' ? '6,5' : @mind_map_size) end - def mm_prog() @mm_prog || 'neato' end - def mm_graph_type() @mm_graph_type || 'normal' end - def mm_show_missing() @mm_show_missing || false end - def mm_show_authors() @mm_show_authors || false end - def mm_show_leaves() @mm_show_leaves || true end - def mm_selected_categories() @mm_selected_categories || [] end - - # create a Mind Map graph and return the PNG and HTML map files generated - def create_mind_map(prog, missing, show_authors, show_leaves, selected_categories, mm_size) - dotFile = File.expand_path("#{WikiService.storage_path}/graph.dot") - mapFile = File.expand_path("#{WikiService.storage_path}/graph.map") - pngFile = File.expand_path("#{WikiService.storage_path}/map.png") - - File.open(dotFile, "w") do |file| - - # Graph properties: - output_graph_header_to file, mm_size - - # Links and node properties: - nodes = filter_categories(pages.values, selected_categories) - auths = authors # avoid repeated selects - unless show_authors - nodes.delete_if { |entry| - auths.include? entry.name - } - end - unless show_leaves - nodes.delete_if { |page| - (page.wiki_words - [missing].flatten).size == 0 - } - end - - # Page Special nodes properties: - file.puts %{"Home Page" [color=\"##{color}\",style=bold];} if nodes.map{ |p| p.name }.include? "HomePage" - - nodes.each do |page| - file.puts %{"#{page.plain_name}" [URL=\"../show/#{page.name}\"];} - page.references.each do |referer| - unless page.name == referer.name or not nodes.include? referer - unless !show_authors and auths.include? referer.name - file.puts %{"#{referer.plain_name}" -> "#{page.plain_name}";} - end - end - end - end - - # find missing pages: - if missing - shown_missing = [] - nodes.each do |page| - missing.each do |wanted| - if page.content =~ /#{wanted}/ - file.puts %{"#{page.plain_name}" -> "#{WikiWords.separate wanted}";} - shown_missing << wanted - end - end - end - shown_missing.each do |wanted| - file.puts %{"#{WikiWords.separate wanted}" [URL="/#{@address}/show/#{wanted}", fontsize=10,style=filled,color=grey];} - end - end - - output_graph_footer_to file - end - - call_graphviz(prog, dotFile, mapFile, pngFile) - - [pngFile, mapFile] - end - - def create_author_graph(prog, selected_categories, mm_size) - dotFile = File.expand_path("#{WikiService.storage_path}/graph.dot") - mapFile = File.expand_path("#{WikiService.storage_path}/graph.map") - pngFile = File.expand_path("#{WikiService.storage_path}/map.png") - - File.open(dotFile, "w") do |file| - - # Graph properties: - output_graph_header_to file, mm_size - - # Links and node properties: - auths = authors # avoid repeated selects - auths.each do |auth| - file.puts %{"#{auth}" [style=filled,color=grey,URL="../show/#{auth}"];} - end - - nodes = pages.values.reject { |entry| auths.include? entry.name } - nodes = filter_categories(nodes, selected_categories) - nodes.each do |page| - file.puts %{"#{page.plain_name}" [URL="../show/#{page.name}"];} - page.authors.each do |auth| - file.puts %{"#{auth}" -> "#{page.plain_name}";} - end - end - - output_graph_footer_to file - end - - call_graphviz(prog, dotFile, mapFile, pngFile) - - [pngFile, mapFile] - end - - def create_category_graph(prog, show_authors, selected_categories, mm_size) #{{{ - dotFile = File.expand_path("#{WikiService.storage_path}/graph.dot") - mapFile = File.expand_path("#{WikiService.storage_path}/graph.map") - pngFile = File.expand_path("#{WikiService.storage_path}/map.png") - - File.open(dotFile, "w") do |file| - # Graph properties: - output_graph_header_to file, mm_size - - # Page Special nodes properties: - categs = selected_categories.empty? ? categories : selected_categories - categs.each do |category| - file.puts %{"#{category}" [fontsize=20,style=filled,color=grey,comment="#{category}",URL="../list/?category=#{category}"];} - end - - # Links and node properties: - nodes = filter_categories(pages.values, selected_categories) - auths = authors # avoid repeated selects - unless show_authors - nodes.delete_if { |entry| - auths.include? entry.name - } - end - nodes.each do |page| - file.puts %{"#{page.plain_name}" [URL=\"../show/#{page.name}\"];} - page.categories.each do |category| - file.puts %{"#{category}" -> "#{page.plain_name}";} - end - end - - output_graph_footer_to file - end - - call_graphviz(prog, dotFile, mapFile, pngFile) - - [pngFile, mapFile] - end #}}} - - def output_graph_header_to file, mm_size - file.puts "digraph G {" - file.puts "size=\"#{mm_size}\";" if mm_size - file.puts 'ratio=fill;' - file.puts 'concentrate=true;' - file.puts 'node [fontsize=10,fontname="Tahoma"];' - file.puts 'edge [len=1.5];' - end - - def output_graph_footer_to file - file.puts "}" - end - - def filter_categories(pages, selected_categories) #{{{ - nodes = pages - unless selected_categories.empty? - nodes = pages.reject { |page| (page.categories & selected_categories).empty? } - if selected_categories.include? 'none' - nodes += pages.select { |page| page.categories.empty? } - end - end - nodes - end #}}} - - def call_graphviz(prog, dotFile, mapFile, pngFile) - system("#{prog} -Tcmap \"#{dotFile}\" -o \"#{mapFile}\"") - system("#{prog} -Tpng \"#{dotFile}\" -o \"#{pngFile}\"") - end - - ## Bliki methods - - def add_bliki_entry(page) - bliki[page.name] = page - end - - def bliki_entries_by_date - bliki.values.sort_by { |page| page.revisions.first.created_at }.reverse - end - - def bliki_entries_by_name - pages.values.sort_by { |page| [page.name] } - end - - def bliki_entries_that_match(regexp) - bliki.values.select { |page| page.content =~ /#{regexp}/i } - end - - def bliki_entries_that_reference(page_name) - bliki.values.select { |page| page.wiki_words.include?(page_name) } - end - - def bliki_entries_authored_by(author) - bliki.values.select { |page| page.authors.include?(author) } - end - - ## End bliki methods - - private - # Returns an array of all the wiki words in any current revision - def wiki_words - pages.values.inject([]) { |wiki_words, page| wiki_words << page.wiki_words }.flatten.uniq - end - - # Returns an array of all the page names on this web - def page_names - pages.keys - end -end - +require "cgi" +require "page" +require "page_set" +require "wiki_words" +require "zip/zip" + +class Web + attr_accessor :pages, :name, :address, :password, :menu_type, :menu_content, :rendered_menu, :menu_limit, :menu_category + attr_accessor :markup, :color, :safe_mode, :additional_style, :published, :default_to_published, :brackets_only, :count_pages + attr_accessor :mind_map_size, :symbols_map, :links_map, :enable_dclick_edit, :check_pass_on_edit, :enable_menu + + # Mind Map defaults + attr_accessor :mm_prog, :mm_graph_type, :mm_show_missing, :mm_show_authors, :mm_show_leaves, :mm_selected_categories + + @@BLIKI_TEMPLATE = "Try a weekly worksheet:\n\n| / | *Morning* | *Afternoon* |\n" + + "| *Mon* | - | - |\n| *Tue* | - | - |\n| *Wed* | - | - |\n" + + "| *Thu* | - | - |\n| *Fri* | - | - |\n" + + def bliki + @bliki ||= Hash.new + end + + def initialize(name, address, password = nil) + @name, @address, @password, @safe_mode = name, address, password, false + @pages = {} + end + + def add_page(page) + @pages[page.name] = page + end + + def remove_pages(pages_to_be_removed) + pages.delete_if { |page_name, page| pages_to_be_removed.include?(page) } + end + + def revised_on + pages.values.sort_by { |page| [page.created_at] }.reverse.first.created_at + end + + def select(&accept) + PageSet.new(self, @pages.values, accept) + end + + def select_bliki(&accept) + PageSet.new(self, bliki.values, accept) + end + + def revised_on + select.most_recent_revision + end + + def authors + select.authors + end + + def categories + select.map { |page| page.categories }.flatten.uniq.sort + end + + # Create a link for the given page name and link text based + # on the render mode in options and whether the page exists + # in the this web. + def make_link(name, text = nil, options = {}) + page = pages[name] + text = text || WikiWords.separate(name) + link = CGI.escape(name) + + case options[:mode] + when :export + if page then "<a class=\"existingWikiWord\" href=\"#{link}.html\">#{text}</a>" + else "<span class=\"newWikiWord\">#{text}</span>" end + when :publish + if page then "<a class=\"existingWikiWord\" href=\"../published/#{link}\">#{text}</a>" + else "<span class=\"newWikiWord\">#{text}</span>" end + else + if page then "<a class=\"existingWikiWord\" href=\"../show/#{link}\">#{text}</a>" + else "<span class=\"newWikiWord\">#{text}<a href=\"../show/#{link}\">?</a></span>" end + end + end + + + # Clears the display cache for all the pages with references to + def refresh_pages_with_references(page_name) + select.pages_that_reference(page_name).each { |page| + page.revisions.each { |revision| revision.clear_display_cache } + } + end + + def refresh_revisions + select.each { |page| page.revisions.each { |revision| revision.clear_display_cache } } + select_bliki.each { |page| page.revisions.each { |revision| revision.clear_display_cache } } + end + + # Default values + def markup() @markup || :textile end + def color() @color || "008B26" end + def brackets_only() @brackets_only || false end + def count_pages() @count_pages || false end + def menu_content() @menu_content || nil end + def menu_limit() @menu_limit || 20 end + def default_to_published() @default_to_published || false end + def menu_type() + (@menu_type.nil? || @menu_type.empty?) ? 'linkers' : @menu_type + end + def mind_map_size() (@mind_map_size == '0,0' ? '6,5' : @mind_map_size) end + def mm_prog() @mm_prog || 'neato' end + def mm_graph_type() @mm_graph_type || 'normal' end + def mm_show_missing() @mm_show_missing || false end + def mm_show_authors() @mm_show_authors || false end + def mm_selected_categories() @mm_selected_categories || [] end + + # create a Mind Map graph and return the PNG and HTML map files generated + def create_mind_map(prog, missing, show_authors, show_leaves, selected_categories, mm_size) + dotFile = File.expand_path("#{WikiService.storage_path}/graph.dot") + mapFile = File.expand_path("#{WikiService.storage_path}/graph.map") + pngFile = File.expand_path("#{WikiService.storage_path}/map.png") + + File.open(dotFile, "w") do |file| + + # Graph properties: + output_graph_header_to file, mm_size + + # Links and node properties: + nodes = filter_categories(pages.values, selected_categories) + auths = authors # avoid repeated selects + unless show_authors + nodes.delete_if { |entry| + auths.include? entry.name + } + end + unless show_leaves + nodes.delete_if { |page| + (page.wiki_words - [missing].flatten).size == 0 + } + end + + # Page Special nodes properties: + file.puts %{"Home Page" [color=\"##{color}\",style=bold];} if nodes.map{ |p| p.name }.include? "HomePage" + + nodes.each do |page| + file.puts %{"#{page.plain_name}" [URL=\"../show/#{page.name}\"];} + page.references.each do |referer| + unless page.name == referer.name or not nodes.include? referer + unless !show_authors and auths.include? referer.name + file.puts %{"#{referer.plain_name}" -> "#{page.plain_name}";} + end + end + end + end + + # find missing pages: + if missing + shown_missing = [] + nodes.each do |page| + missing.each do |wanted| + if page.content =~ /#{wanted}/ + file.puts %{"#{page.plain_name}" -> "#{WikiWords.separate wanted}";} + shown_missing << wanted + end + end + end + shown_missing.each do |wanted| + file.puts %{"#{WikiWords.separate wanted}" [URL="/#{@address}/show/#{wanted}", fontsize=10,style=filled,color=grey];} + end + end + + output_graph_footer_to file + end + + call_graphviz(prog, dotFile, mapFile, pngFile) + + [pngFile, mapFile] + end + + def create_author_graph(prog, selected_categories, mm_size) + dotFile = File.expand_path("#{WikiService.storage_path}/graph.dot") + mapFile = File.expand_path("#{WikiService.storage_path}/graph.map") + pngFile = File.expand_path("#{WikiService.storage_path}/map.png") + + File.open(dotFile, "w") do |file| + + # Graph properties: + output_graph_header_to file, mm_size + + # Links and node properties: + auths = authors # avoid repeated selects + auths.each do |auth| + file.puts %{"#{auth}" [style=filled,color=grey,URL="../show/#{auth}"];} + end + + nodes = pages.values.reject { |entry| auths.include? entry.name } + nodes = filter_categories(nodes, selected_categories) + nodes.each do |page| + file.puts %{"#{page.plain_name}" [URL="../show/#{page.name}"];} + page.authors.each do |auth| + file.puts %{"#{auth}" -> "#{page.plain_name}";} + end + end + + output_graph_footer_to file + end + + call_graphviz(prog, dotFile, mapFile, pngFile) + + [pngFile, mapFile] + end + + def create_category_graph(prog, show_authors, selected_categories, mm_size) #{{{ + dotFile = File.expand_path("#{WikiService.storage_path}/graph.dot") + mapFile = File.expand_path("#{WikiService.storage_path}/graph.map") + pngFile = File.expand_path("#{WikiService.storage_path}/map.png") + + File.open(dotFile, "w") do |file| + # Graph properties: + output_graph_header_to file, mm_size + + # Page Special nodes properties: + categs = selected_categories.empty? ? categories : selected_categories + categs.each do |category| + file.puts %{"#{category}" [fontsize=20,style=filled,color=grey,comment="#{category}",URL="../list/?category=#{category}"];} + end + + # Links and node properties: + nodes = filter_categories(pages.values, selected_categories) + auths = authors # avoid repeated selects + unless show_authors + nodes.delete_if { |entry| + auths.include? entry.name + } + end + nodes.each do |page| + file.puts %{"#{page.plain_name}" [URL=\"../show/#{page.name}\"];} + page.categories.each do |category| + file.puts %{"#{category}" -> "#{page.plain_name}";} + end + end + + output_graph_footer_to file + end + + call_graphviz(prog, dotFile, mapFile, pngFile) + + [pngFile, mapFile] + end #}}} + + def output_graph_header_to file, mm_size + file.puts "digraph G {" + file.puts "size=\"#{mm_size}\";" if mm_size + file.puts 'ratio=fill;' + file.puts 'concentrate=true;' + file.puts 'node [fontsize=10,fontname="Tahoma"];' + file.puts 'edge [len=1.5];' + end + + def output_graph_footer_to file + file.puts "}" + end + + def filter_categories(pages, selected_categories) #{{{ + nodes = pages + unless selected_categories.empty? + nodes = pages.reject { |page| (page.categories & selected_categories).empty? } + if selected_categories.include? 'none' + nodes += pages.select { |page| page.categories.empty? } + end + end + nodes + end #}}} + + def call_graphviz(prog, dotFile, mapFile, pngFile) + system("#{prog} -Tcmap \"#{dotFile}\" -o \"#{mapFile}\"") + system("#{prog} -Tpng \"#{dotFile}\" -o \"#{pngFile}\"") + end + + ## Bliki methods + + def add_bliki_entry(page) + bliki[page.name] = page + end + + def bliki_entries_by_date + bliki.values.sort_by { |page| page.revisions.first.created_at }.reverse + end + + def bliki_entries_by_name + pages.values.sort_by { |page| [page.name] } + end + + def bliki_entries_that_match(regexp) + bliki.values.select { |page| page.content =~ /#{regexp}/i } + end + + def bliki_entries_that_reference(page_name) + bliki.values.select { |page| page.wiki_words.include?(page_name) } + end + + def bliki_entries_authored_by(author) + bliki.values.select { |page| page.authors.include?(author) } + end + + ## End bliki methods + + private + # Returns an array of all the wiki words in any current revision + def wiki_words + pages.values.inject([]) { |wiki_words, page| wiki_words << page.wiki_words }.flatten.uniq + end + + # Returns an array of all the page names on this web + def page_names + pages.keys + end +end + # jEdit :folding=indent:collapseFolds=1: \ No newline at end of file