You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
84 lines
2.2 KiB
Lua
84 lines
2.2 KiB
Lua
local cqueues = require'cqueues'
|
|
local socket = require'cqueues.socket'
|
|
local openssl_context = require'openssl.ssl.context'
|
|
local base64 = require'base64'
|
|
|
|
|
|
|
|
local get_default_ehlo_host = function()
|
|
return 'debian' -- TODO read from /etc/hosts
|
|
end
|
|
|
|
local send_auth_plain = function(opts)
|
|
if opts.host==nil or opts.from==nil or opts.to==nil then error('`host`, `from`, and `to` are required.') end
|
|
|
|
local host = opts.host
|
|
local port = opts.port or 25 --587
|
|
local username = opts.username
|
|
local password = opts.password
|
|
|
|
local ehlo_host = opts.ehlo_host or get_default_ehlo_host()
|
|
|
|
local from = opts.from
|
|
local to = opts.to
|
|
-- `message` includes Subject and other headers. Use stmp-message.lua to construct a message string.
|
|
local message = opts.message or 'Subject: \r\n\r\n\r\n.\r\n'
|
|
--local subject = opts.subject or ''
|
|
--local body = opts.body or ''
|
|
|
|
local connection = socket.connect(host, port)
|
|
connection:settimeout(5)
|
|
|
|
local read = function()
|
|
local m = connection:read('*l') or ''
|
|
print('<-- '..m)
|
|
return m
|
|
end
|
|
|
|
local read_until = function(code_desired, substring)
|
|
local substring_needed = (substring ~= nil)
|
|
local code, line
|
|
repeat
|
|
line = read()
|
|
code = string.sub(line,1,3)
|
|
until code == code_desired and (not substring_needed or line:find(substring) ~= nil)
|
|
end
|
|
|
|
local write = function(m)
|
|
print('--> '..m)
|
|
connection:write(m)
|
|
end
|
|
|
|
read_until('220')
|
|
write('STARTTLS\r\n')
|
|
|
|
read_until('220')
|
|
local ctx = openssl_context.new('TLSv1_2', false)
|
|
|
|
local ok, err = connection:starttls(ctx)
|
|
if not ok then print('starttls error', err) end
|
|
|
|
write('EHLO '..ehlo_host..'\r\n')
|
|
read_until('250','PLAIN')
|
|
|
|
write('AUTH PLAIN '..base64.encode(username..'\0'..username..'\0'..password)..'\r\n')
|
|
|
|
read_until('235') -- auth successful
|
|
write('MAIL FROM:<'..from..'>\r\n')
|
|
read_until('250')
|
|
write('RCPT TO:<'..to..'>\r\n')
|
|
read_until('250')
|
|
write('DATA\r\n')
|
|
read_until('354')
|
|
write(message)
|
|
--write('Subject: '..subject..'\r\n\r\n')
|
|
--write(body..'\r\n')
|
|
write('\r\n.\r\n')
|
|
read_until('250')
|
|
write('QUIT')
|
|
--read_until('221')
|
|
connection:close()
|
|
end
|
|
|
|
return send_auth_plain
|