Project

General

Profile

« Previous | Next » 

Revision 3d7bbe55

Added by Marc Dequènes over 14 years ago

  • ID 3d7bbe55cb6110cbe884ce7c45db045849a2be38

[evol] improved Order classes a lot (closes #101)

View differences:

bin/postman
return true
end
order = MailOrder.parse(report.user, report.message)
mail_parser = MailOrderParser.new(report.user)
order = mail_parser.parse(report.message)
result_tag = order.valid? ? "SUCCESS" : "FAILURE"
result_msg = "Processing result: #{result_tag}"
result_msg += " (#{order.error.untranslated})" unless order.valid?
lib/cyborghood/command_runner.rb
end
srv_dns = Services::DNS.new(zone)
zone_content = srv_dns.read_zone
zone_content = srv_dns.read_zone
result.ok = true
result.message = _("Requested zone content attached.")
......
srv_dns = Services::DNS.new(zone)
return if cmdline.empty?
content_ref = cmdline.shift
ref, part = Order.dereference_param(shared_parameters, content_ref)
unless part.content_type == "text/plain"
result.message = _("Attachment has wrong content-type.")
zone_data = cmdline.shift
unless zone_data.content_type == "text/plain"
result.message = _("Zone data has wrong content-type.")
return result
end
f = Tempfile.new(zone)
f.write(part.content)
f.write(zone_data.content)
f.close
logger.debug "Created temporary zone file '#{f.path}'"
lib/cyborghood/mail_order.rb
require 'cyborghood/order'
module CyborgHood
class MailOrder < Order
def self.parse(user, message)
class MailOrderParser < OrderParser
def parse(message)
logger.debug "Parsing Mail"
# analyse mail parts
order_txt = nil
shared_parameters = nil
if message.multipart?
if message.parts[0].content_type == "text/plain"
order_txt = message.parts[0].body
shared_parameters = {}
i = -1
message.parts.each do |part|
i += 1
next if i == 0
next if i == 0
shared_parameters[i] = SharedParameter.new(part.body, part.content_type)
filename = part.header['content-disposition'].params['filename'] || part.header['content-type'].params['name']
@shared_parameters[i] = CommandParameter.new(part.body, part.content_type)
shared_parameters[filename] = ParameterReference.new(i) if filename
filename = part.header['content-disposition'].params['filename'] || part.header['content-type'].params['name']
@shared_parameters[filename] = CommandParameterRef.new(i) if filename
end
end
else
order_txt = message.body if message.content_type == "text/plain"
shared_parameters = {}
end
return new(:error => _("Mail does not contain a proper text part for commands."), :user => user) if order_txt.nil?
return Order.new(:error => _("Mail does not contain a proper text part for commands."), :user => @user) if order_txt.nil?
# find command lines
command_lines = order_txt.split("\n")
# remove message signature
signature_pos = command_lines.index("-- ")
command_lines.slice!(signature_pos..-1) if signature_pos
super(user, command_lines, shared_parameters) do |word, errors, used_refs|
# generic parsing
super(command_lines) do |word, errors|
if word =~ /^@([a-zA-Z0-9._-]+)$/
ref = $1
param = ParameterReference.new(ref)
d_ref, d_param = dereference_param(shared_parameters, param)
ref = ref.is_numeric? ? ref.to_i : ref
d_ref, d_param = deref_param(ref)
if d_ref.nil?
errors << _("Attachment '%{ref}' not found.", :ref => ref)
d_param = nil
else
used_refs << d_ref
@used_refs << d_ref
end
d_param
else
word
CommandParameter.new(word, 'text/plain')
end
end
end
lib/cyborghood/order.rb
end
end
class SharedParameter
attr_reader :content_type, :content
class CommandParameter < String
attr_reader :content_type
def initialize(content, content_type = nil)
@content = content
super(content)
@content_type = content_type
end
def content
to_s
end
end
class ParameterReference
class CommandParameterRef
attr_reader :reference
def initialize(reference)
......
@shared_parameters = params[:shared_parameters]
end
def self.parse(user, command_lines, shared_parameters)
def valid?
@error.nil? and @user and not @commands.empty?
end
end
class OrderParser
include I18nTranslation
def initialize(user)
@user = user
@commands = []
@shared_parameters = {}
@used_refs = []
end
def parse(command_lines)
logger.debug "Parsing Order"
used_refs = []
commands = []
command_lines.each do |line|
line.strip!
# skip empty lines and comments
......
raw_cmd_parts = []
end
cmd_parts = raw_cmd_parts.collect do |word|
yield word, errors, used_refs
yield word, errors
end
commands << Command.new(line, cmd_parts, errors)
@commands << Command.new(line, cmd_parts, errors)
end
# remove references to unused parameters
shared_parameters.delete_if{|ref, param| not used_refs.include?(ref) }
@shared_parameters.delete_if{|ref, param| not @used_refs.include?(ref) }
logger.debug "Order is OK"
new(:user => user, :commands => commands, :shared_parameters => shared_parameters)
Order.new(:user => @user, :commands => @commands, :shared_parameters => @shared_parameters)
end
def self.dereference_param(shared_parameters, param, ref = nil)
if param.is_a? SharedParameter
[ref, param]
elsif param.is_a? ParameterReference
d_ref = param.reference
d_param = shared_parameters[d_ref]
return dereference_param(shared_parameters, d_param, d_ref)
def deref_param(param, old_ref = nil)
if param.is_a? CommandParameterRef
return deref_param(@shared_parameters[param.reference], param.reference)
elsif param.is_a? CommandParameter
return old_ref, param
elsif param.is_a? String or param.is_a? Fixnum
return deref_param(@shared_parameters[param], param)
else
nil
end
end
def valid?
@error.nil? and @user and not @commands.empty?
end
end
end

Also available in: Unified diff