Wiki: allows single section edit (#2222).
git-svn-id: svn+ssh://rubyforge.org/var/svn/redmine/trunk@7829 e93f8b46-1217-0410-a6f0-8f06a7374b81
This commit is contained in:
@@ -17,6 +17,8 @@
|
||||
|
||||
module Redmine
|
||||
module WikiFormatting
|
||||
class StaleSectionError < Exception; end
|
||||
|
||||
@@formatters = {}
|
||||
|
||||
class << self
|
||||
@@ -29,6 +31,10 @@ module Redmine
|
||||
@@formatters[name.to_s] = {:formatter => formatter, :helper => helper}
|
||||
end
|
||||
|
||||
def formatter
|
||||
formatter_for(Setting.text_formatting)
|
||||
end
|
||||
|
||||
def formatter_for(name)
|
||||
entry = @@formatters[name.to_s]
|
||||
(entry && entry[:formatter]) || Redmine::WikiFormatting::NullFormatter::Formatter
|
||||
@@ -43,7 +49,7 @@ module Redmine
|
||||
@@formatters.keys.map
|
||||
end
|
||||
|
||||
def to_html(format, text, options = {}, &block)
|
||||
def to_html(format, text, options = {})
|
||||
text = if Setting.cache_formatted_text? && text.size > 2.kilobyte && cache_store && cache_key = cache_key_for(format, options[:object], options[:attribute])
|
||||
# Text retrieved from the cache store may be frozen
|
||||
# We need to dup it so we can do in-place substitutions with gsub!
|
||||
@@ -53,9 +59,6 @@ module Redmine
|
||||
else
|
||||
formatter_for(format).new(text).to_html
|
||||
end
|
||||
if block_given?
|
||||
execute_macros(text, block)
|
||||
end
|
||||
text
|
||||
end
|
||||
|
||||
@@ -70,33 +73,6 @@ module Redmine
|
||||
def cache_store
|
||||
ActionController::Base.cache_store
|
||||
end
|
||||
|
||||
MACROS_RE = /
|
||||
(!)? # escaping
|
||||
(
|
||||
\{\{ # opening tag
|
||||
([\w]+) # macro name
|
||||
(\(([^\}]*)\))? # optional arguments
|
||||
\}\} # closing tag
|
||||
)
|
||||
/x unless const_defined?(:MACROS_RE)
|
||||
|
||||
# Macros substitution
|
||||
def execute_macros(text, macros_runner)
|
||||
text.gsub!(MACROS_RE) do
|
||||
esc, all, macro = $1, $2, $3.downcase
|
||||
args = ($5 || '').split(',').each(&:strip)
|
||||
if esc.nil?
|
||||
begin
|
||||
macros_runner.call(macro, args)
|
||||
rescue => e
|
||||
"<div class=\"flash error\">Error executing the <strong>#{macro}</strong> macro (#{e})</div>"
|
||||
end || all
|
||||
else
|
||||
all
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
# Default formatter module
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
require 'redcloth3'
|
||||
require 'digest/md5'
|
||||
|
||||
module Redmine
|
||||
module WikiFormatting
|
||||
@@ -38,6 +39,68 @@ module Redmine
|
||||
super(*RULES).to_s
|
||||
end
|
||||
|
||||
def get_section(index)
|
||||
section = extract_sections(index)[1]
|
||||
hash = Digest::MD5.hexdigest(section)
|
||||
return section, hash
|
||||
end
|
||||
|
||||
def update_section(index, update, hash=nil)
|
||||
t = extract_sections(index)
|
||||
if hash.present? && hash != Digest::MD5.hexdigest(t[1])
|
||||
raise Redmine::WikiFormatting::StaleSectionError
|
||||
end
|
||||
t[1] = update unless t[1].blank?
|
||||
t.reject(&:blank?).join "\n\n"
|
||||
end
|
||||
|
||||
def extract_sections(index)
|
||||
@pre_list = []
|
||||
text = self.dup
|
||||
rip_offtags text
|
||||
before = ''
|
||||
s = ''
|
||||
after = ''
|
||||
i = 0
|
||||
l = 1
|
||||
started = false
|
||||
ended = false
|
||||
text.scan(/(((?:.*?)(\A|\r?\n\r?\n))(h(\d+)(#{A}#{C})\.(?::(\S+))? (.*?)$)|.*)/m).each do |all, content, lf, heading, level|
|
||||
if heading.nil?
|
||||
if ended
|
||||
after << all
|
||||
elsif started
|
||||
s << all
|
||||
else
|
||||
before << all
|
||||
end
|
||||
break
|
||||
end
|
||||
i += 1
|
||||
if ended
|
||||
after << all
|
||||
elsif i == index
|
||||
l = level.to_i
|
||||
before << content
|
||||
s << heading
|
||||
started = true
|
||||
elsif i > index
|
||||
s << content
|
||||
if level.to_i > l
|
||||
s << heading
|
||||
else
|
||||
after << heading
|
||||
ended = true
|
||||
end
|
||||
else
|
||||
before << all
|
||||
end
|
||||
end
|
||||
sections = [before.strip, s.strip, after.strip]
|
||||
sections.each {|section| smooth_offtags section}
|
||||
sections
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
# Patch for RedCloth. Fixed in RedCloth r128 but _why hasn't released it yet.
|
||||
|
||||
Reference in New Issue
Block a user