blob: 30b32808d1331d923de162dcc0b1880a15754f29 [file] [log] [blame]
#
# File an additional ICLA:
# - [optional] move existing ICLA into a directory
# - add files to (new) documents/iclas dirctory
# - modify officers/iclas.txt entry
# - respond to original email
#
# extract message
message = Mailbox.find(@message)
# find person
person = ASF::Person.find(@id)
# extract file extension
fileext = File.extname(@selected).downcase if @signature.empty?
# obtain per-user information
_personalize_email(env.user)
########################################################################
# move existing document #
########################################################################
@filename.untaint if @filename =~ /\A\w[-.\w]*\z/
if not ASF::ICLAFiles.Dir? @filename
# Assumes there is a single matching file
@existing = ASF::ICLAFiles.matchStem(@filename).first
task "svn mv #@existing #@filename/icla#{File.extname(@existing)}" do
form do
_input value: @existing, name: 'existing'
end
complete do |dir|
# checkout empty iclas directory
svn 'checkout', '--depth', 'empty',
'https://svn.apache.org/repos/private/documents/iclas', "#{dir}/iclas"
# update file to be moved
svn 'update', "#{dir}/iclas/#{@existing}"
# create target directory
FileUtils.mkdir "#{dir}/iclas/#{@filename}"
svn 'add', "#{dir}/iclas/#{@filename}"
# update file to be moved
svn 'mv', "#{dir}/iclas/#{@existing}",
"#{dir}/iclas/#@filename/icla#{File.extname(@existing)}"
# commit changes
svn 'commit', "#{dir}/iclas", '-m', "move previous ICLA from #{@pubname}"
end
end
end
########################################################################
# file new document #
########################################################################
# determine what the counter is likely to be by querying the server
# Notes:
# - ASF::SVN.list returns
# - a string with "\n" separators
# - If there is an error ASF::SVN.list returns an array with nil
# as the first entry.
# - Converting the results to an array, extracting the first entry,
# coorsing it to a string, and then splitting it will result in an array
# - calling .max on an empty array returns nil. Treat it as one as there
# is an existing document that will be moved into this directory.
# - If all else fails, set count to "N"
count = (Array(ASF::SVN.list(ASF::SVN.svnurl('iclas') + '/' + @filename.untaint)).
first.to_s.split.
map {|name| name[/.*(\d+)\./, 1] || 1}.
map(&:to_i).max || 1) + 1 rescue 'N'
# write attachment (+ signature, if present) to the documents/iclas directory
task "svn commit documents/iclas/#@filename/iclaN#{count}{fileext}" do
form do
_input value: @selected, name: 'selected'
if @signature and not @signature.empty?
_input value: @signature, name: 'signature'
end
end
complete do |dir|
# checkout directory
svn 'checkout',
"https://svn.apache.org/repos/private/documents/iclas/#@filename",
"#{dir}/#@filename"
# determine numeric suffix for the new ICLA
count = Dir["#{dir}/#@filename/*"].
map {|name| name[/.*(\d+)\./, 1] || 1}.map(&:to_i).max + 1
# create/add file(s)
files = {@selected => "icla#{count}#{fileext}"}
files[@signature] = "icla#{count}pdf.asc" unless @signature.to_s.empty?
message.write_svn(dir, @filename, files)
# Show files to be added
svn 'status', "#{dir}/#@filename"
# commit changes
svn 'commit',
*files.values.map {|name| "#{dir}/#@filename/#{@name}"},
'-m', "additional ICLA from #{@pubname}"
end
end
########################################################################
# officers/iclas.txt #
########################################################################
# insert line into iclas.txt
task "svn commit foundation/officers/iclas.txt" do
icla = ASF::ICLA.find_by_id(@id) || ASF::ICLA.find_by_email(@oldemail)
unless icla and icla.id == @id and icla.email == @oldemail
raise ArgumentError.new("ICLA not found for #@id:#@oldemail")
end
# construct line to be inserted
@iclaline ||= [
@id,
icla.legal_name,
@pubname.strip,
@email.strip,
icla.form
].join(':')
form do
_input value: @iclaline, name: 'iclaline'
end
complete do |dir|
# checkout empty officers directory
svn 'checkout', '--depth', 'empty',
'https://svn.apache.org/repos/private/foundation/officers',
"#{dir}/officers"
# retrieve iclas.txt
dest = "#{dir}/officers/iclas.txt"
svn 'update', dest
# update iclas.txt
iclas_txt = File.read(dest)
iclas_txt[/^#{@id}:.*:#{@oldemail}:.*/] = @iclaline
File.write dest, ASF::ICLA.sort(iclas_txt)
# show the changes
svn 'diff', dest
# commit changes
svn 'commit', dest, '-m', "ICLA for #{@pubname}"
end
end
########################################################################
# update public name in LDAP #
########################################################################
if person.public_name != @pubname and @id != 'notinavail'
task "change public name in LDAP" do
form do
_input value: @pubname, name: 'pubname'
end
complete do
ldap = ASF.init_ldap(true)
ldap.bind("uid=#{env.user.untaint},ou=people,dc=apache,dc=org",
env.password.untaint)
ldap.modify person.dn, [ASF::Base.mod_replace('cn', @pubname.strip)]
log = ["LDAP modify: #{ldap.err2string(ldap.err)} (#{ldap.err})"]
if ldap.err == 0
_transcript log
else
_backtrace log
end
ldap.unbind
end
end
end
########################################################################
# email submitter #
########################################################################
# send confirmation email
task "email #@email" do
cc = person.all_mail.map {|email| "#{@pubname.inspect} <#{email}>"}
cc << 'secretary@apache.org'
# build mail from template
mail = message.reply(
subject: "ICLA for #{@pubname}",
from: @from,
to: "#{@pubname.inspect} <#{@email}>",
cc: cc,
body: template('icla2.erb')
)
# echo email
form do
_message mail.to_s
end
# deliver mail
complete do
mail.deliver!
end
end
########################################################################
# update email address in LDAP #
########################################################################
if @id != 'notinavail'
task "change email address in LDAP" do
form do
_input value: @email, name: 'email'
end
complete do
ldap = ASF.init_ldap(true)
ldap.bind("uid=#{env.user.untaint},ou=people,dc=apache,dc=org",
env.password.untaint)
ldap.modify person.dn, [ASF::Base.mod_replace('mail', @email.strip)]
log = ["LDAP modify: #{ldap.err2string(ldap.err)} (#{ldap.err})"]
if ldap.err == 0
_transcript log
else
_backtrace log
end
ldap.unbind
end
end
end