Added x-header support and unit tests.
This commit is contained in:
parent
00cc1ff6ce
commit
04123e3359
4 changed files with 156 additions and 19 deletions
|
@ -78,18 +78,39 @@ class Channel::EmailParser
|
||||||
def process(channel, msg)
|
def process(channel, msg)
|
||||||
mail = parse( msg )
|
mail = parse( msg )
|
||||||
|
|
||||||
|
# check if trust x-headers
|
||||||
|
if !channel[:trusted]
|
||||||
|
mail.each {|key, value|
|
||||||
|
if key =~ /^x-zammad/i
|
||||||
|
mail.delete(key)
|
||||||
|
end
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
|
# check ignore header
|
||||||
|
return true if mail[ 'x-zammad-ignore'.to_sym ] == 'true' || mail[ 'x-zammad-ignore'.to_sym ] == true
|
||||||
|
|
||||||
|
ticket = nil
|
||||||
|
article = nil
|
||||||
|
user = nil
|
||||||
|
|
||||||
# use transaction
|
# use transaction
|
||||||
ActiveRecord::Base.transaction do
|
ActiveRecord::Base.transaction do
|
||||||
|
|
||||||
user = User.where( :email => mail[:from_email] ).first
|
if mail[ 'x-zammad-customer-login'.to_sym ]
|
||||||
if !user then
|
user = User.where( :login => mail[ 'x-zammad-customer-login'.to_sym ] ).first
|
||||||
|
end
|
||||||
|
if !user
|
||||||
|
user = User.where( :email => mail[ 'x-zammad-customer-email'.to_sym ] || mail[:from_email] ).first
|
||||||
|
end
|
||||||
|
if !user
|
||||||
puts 'create user...'
|
puts 'create user...'
|
||||||
roles = Role.where( :name => 'Customer' )
|
roles = Role.where( :name => 'Customer' )
|
||||||
user = User.create(
|
user = User.create(
|
||||||
:login => mail[:from_email],
|
:login => mail[ 'x-zammad-customer-login'.to_sym ] || mail[ 'x-zammad-customer-email'.to_sym ] || mail[:from_email],
|
||||||
:firstname => mail[:from_display_name],
|
:firstname => mail[ 'x-zammad-customer-firstname'.to_sym ] || mail[:from_display_name],
|
||||||
:lastname => '',
|
:lastname => mail[ 'x-zammad-customer-lastname'.to_sym ],
|
||||||
:email => mail[:from_email],
|
:email => mail[ 'x-zammad-customer-email'.to_sym ] || mail[:from_email],
|
||||||
:password => '',
|
:password => '',
|
||||||
:active => true,
|
:active => true,
|
||||||
:roles => roles,
|
:roles => roles,
|
||||||
|
@ -114,19 +135,45 @@ class Channel::EmailParser
|
||||||
end
|
end
|
||||||
|
|
||||||
# create new ticket
|
# create new ticket
|
||||||
if !ticket then
|
if !ticket
|
||||||
ticket = Ticket.create(
|
|
||||||
|
# set attributes
|
||||||
|
ticket_attributes = {
|
||||||
:group_id => channel[:group_id] || 1,
|
:group_id => channel[:group_id] || 1,
|
||||||
:customer_id => user.id,
|
:customer_id => user.id,
|
||||||
:title => mail[:subject],
|
:title => mail[:subject],
|
||||||
:ticket_state_id => Ticket::State.where( :name => 'new' ).first.id,
|
:ticket_state_id => Ticket::State.where( :name => 'new' ).first.id,
|
||||||
:ticket_priority_id => Ticket::Priority.where( :name => '2 normal' ).first.id,
|
:ticket_priority_id => Ticket::Priority.where( :name => '2 normal' ).first.id,
|
||||||
:created_by_id => user.id
|
:created_by_id => user.id,
|
||||||
)
|
}
|
||||||
|
|
||||||
|
# x-headers lookup
|
||||||
|
map = [
|
||||||
|
[ 'x-zammad-group', Group, 'group_id', 'name' ],
|
||||||
|
[ 'x-zammad-state', Ticket::State, 'ticket_state_id', 'name' ],
|
||||||
|
[ 'x-zammad-priority', Ticket::Priority, 'ticket_priority_id', 'name' ],
|
||||||
|
[ 'x-zammad-owner', User, 'owner_id', 'login' ],
|
||||||
|
]
|
||||||
|
map.each { |item|
|
||||||
|
if mail[ item[0].to_sym ]
|
||||||
|
if item[1].where( item[3].to_sym => mail[ item[0].to_sym ] ).first
|
||||||
|
ticket_attributes[ item[2].to_sym ] = item[1].where( item[3].to_sym => mail[ item[0].to_sym ] ).first.id
|
||||||
|
end
|
||||||
|
end
|
||||||
|
}
|
||||||
|
|
||||||
|
# create ticket
|
||||||
|
ticket = Ticket.create( ticket_attributes )
|
||||||
end
|
end
|
||||||
|
|
||||||
# import mail
|
# import mail
|
||||||
article = Ticket::Article.create(
|
|
||||||
|
# set attributes
|
||||||
|
internal = false
|
||||||
|
if mail[ 'X-Zammad-Article-Visability'.to_sym ] && mail[ 'X-Zammad-Article-Visability'.to_sym ] == 'internal'
|
||||||
|
internal = true
|
||||||
|
end
|
||||||
|
article_attributes = {
|
||||||
:created_by_id => user.id,
|
:created_by_id => user.id,
|
||||||
:ticket_id => ticket.id,
|
:ticket_id => ticket.id,
|
||||||
:ticket_article_type_id => Ticket::Article::Type.where( :name => 'email' ).first.id,
|
:ticket_article_type_id => Ticket::Article::Type.where( :name => 'email' ).first.id,
|
||||||
|
@ -137,8 +184,24 @@ class Channel::EmailParser
|
||||||
:cc => mail[:cc],
|
:cc => mail[:cc],
|
||||||
:subject => mail[:subject],
|
:subject => mail[:subject],
|
||||||
:message_id => mail[:message_id],
|
:message_id => mail[:message_id],
|
||||||
:internal => false
|
:internal => internal,
|
||||||
)
|
}
|
||||||
|
|
||||||
|
# x-headers lookup
|
||||||
|
map = [
|
||||||
|
[ 'x-zammad-article-type', Ticket::Article::Type, 'ticket_article_type_id', 'name' ],
|
||||||
|
[ 'x-zammad-article-sender', Ticket::Article::Sender, 'ticket_article_sender_id', 'name' ],
|
||||||
|
]
|
||||||
|
map.each { |item|
|
||||||
|
if mail[ item[0].to_sym ]
|
||||||
|
if item[1].where( item[3].to_sym => mail[ item[0].to_sym ] ).first
|
||||||
|
article_attributes[ item[2].to_sym ] = item[1].where( item[3].to_sym => mail[ item[0].to_sym ] ).first.id
|
||||||
|
end
|
||||||
|
end
|
||||||
|
}
|
||||||
|
|
||||||
|
# create article
|
||||||
|
article = Ticket::Article.create(article_attributes)
|
||||||
|
|
||||||
# store mail plain
|
# store mail plain
|
||||||
Store.add(
|
Store.add(
|
||||||
|
@ -161,10 +224,12 @@ class Channel::EmailParser
|
||||||
)
|
)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
return ticket, article, user
|
|
||||||
end
|
end
|
||||||
|
|
||||||
# execute ticket events
|
# execute ticket events
|
||||||
Ticket::Observer::Notification.transaction
|
Ticket::Observer::Notification.transaction
|
||||||
|
|
||||||
|
# return new objects
|
||||||
|
return ticket, article, user
|
||||||
end
|
end
|
||||||
end
|
end
|
|
@ -9,5 +9,8 @@ class ActiveSupport::TestCase
|
||||||
# -- they do not yet inherit this setting
|
# -- they do not yet inherit this setting
|
||||||
fixtures :all
|
fixtures :all
|
||||||
|
|
||||||
|
# load seeds
|
||||||
|
load "#{Rails.root}/db/seeds.rb"
|
||||||
|
|
||||||
# Add more helper methods to be used by all tests here...
|
# Add more helper methods to be used by all tests here...
|
||||||
end
|
end
|
||||||
|
|
|
@ -45,7 +45,7 @@ class EmailParserTest < ActiveSupport::TestCase
|
||||||
# check body
|
# check body
|
||||||
md5 = Digest::MD5.hexdigest( data[:plain_part] )
|
md5 = Digest::MD5.hexdigest( data[:plain_part] )
|
||||||
assert_equal( file[:body_md5], md5 )
|
assert_equal( file[:body_md5], md5 )
|
||||||
puts data[:from]
|
|
||||||
# check params
|
# check params
|
||||||
file[:params].each { |key, value|
|
file[:params].each { |key, value|
|
||||||
if key.to_s == 'plain_part'
|
if key.to_s == 'plain_part'
|
||||||
|
|
69
test/unit/email_process_test.rb
Normal file
69
test/unit/email_process_test.rb
Normal file
|
@ -0,0 +1,69 @@
|
||||||
|
# encoding: utf-8
|
||||||
|
require 'test_helper'
|
||||||
|
|
||||||
|
class EmailProcessTest < ActiveSupport::TestCase
|
||||||
|
test 'process' do
|
||||||
|
files = [
|
||||||
|
{
|
||||||
|
:data => 'From: me@example.com
|
||||||
|
To: customer@example.com
|
||||||
|
Subject: some subject
|
||||||
|
|
||||||
|
Some Text',
|
||||||
|
:success => true,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
:data => 'From: me@example.com
|
||||||
|
To: customer@example.com
|
||||||
|
Subject: some subject
|
||||||
|
X-Zammad-Ignore: true
|
||||||
|
|
||||||
|
Some Text',
|
||||||
|
:success => false,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
:data => 'From: me@example.com
|
||||||
|
To: customer@example.com
|
||||||
|
Subject: some subject
|
||||||
|
X-Zammad-Priority: 3 high
|
||||||
|
X-Zammad-Article-Sender: system
|
||||||
|
x-Zammad-Article-Type: phone
|
||||||
|
|
||||||
|
Some Text',
|
||||||
|
:success => true,
|
||||||
|
:result => {
|
||||||
|
0 => {
|
||||||
|
:ticket_priority => '3 high',
|
||||||
|
},
|
||||||
|
1 => {
|
||||||
|
:ticket_article_sender => 'System',
|
||||||
|
:ticket_article_type => 'phone',
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
]
|
||||||
|
|
||||||
|
files.each { |file|
|
||||||
|
parser = Channel::EmailParser.new
|
||||||
|
result = parser.process( { :trusted => true }, file[:data] )
|
||||||
|
if file[:success] && result[1]
|
||||||
|
assert( true )
|
||||||
|
if file[:result]
|
||||||
|
[ 0, 1, 2 ].each { |level|
|
||||||
|
if file[:result][level]
|
||||||
|
file[:result][level].each { |key, value|
|
||||||
|
assert_equal( result[level].send(key).name, value.to_s)
|
||||||
|
}
|
||||||
|
end
|
||||||
|
}
|
||||||
|
end
|
||||||
|
elsif !file[:success] && result == true
|
||||||
|
assert( true )
|
||||||
|
elsif !file[:success] && result[1]
|
||||||
|
assert( false, 'ticket should not be created' )
|
||||||
|
else
|
||||||
|
assert( false, 'UNKNOWN!' )
|
||||||
|
end
|
||||||
|
}
|
||||||
|
end
|
||||||
|
end
|
Loading…
Reference in a new issue