From be2e2b480540bcc38aaf75f1767dfff1b8199097 Mon Sep 17 00:00:00 2001 From: Hiroshi SHIBATA Date: Wed, 26 May 2021 15:58:26 +0900 Subject: Promote net-smtp to the bundled gems --- test/net/smtp/test_response.rb | 100 ------------- test/net/smtp/test_smtp.rb | 302 --------------------------------------- test/net/smtp/test_ssl_socket.rb | 99 ------------- test/net/smtp/test_sslcontext.rb | 129 ----------------- test/net/smtp/test_starttls.rb | 122 ---------------- 5 files changed, 752 deletions(-) delete mode 100644 test/net/smtp/test_response.rb delete mode 100644 test/net/smtp/test_smtp.rb delete mode 100644 test/net/smtp/test_ssl_socket.rb delete mode 100644 test/net/smtp/test_sslcontext.rb delete mode 100644 test/net/smtp/test_starttls.rb (limited to 'test/net/smtp') diff --git a/test/net/smtp/test_response.rb b/test/net/smtp/test_response.rb deleted file mode 100644 index 3cf909a762..0000000000 --- a/test/net/smtp/test_response.rb +++ /dev/null @@ -1,100 +0,0 @@ -# frozen_string_literal: true -require 'net/smtp' -require 'test/unit' - -module Net - class SMTP - class TestResponse < Test::Unit::TestCase - def test_capabilities - res = Response.parse("250-ubuntu-desktop\n250-PIPELINING\n250-SIZE 10240000\n250-VRFY\n250-ETRN\n250-STARTTLS\n250-ENHANCEDSTATUSCODES\n250 DSN\n") - - capabilities = res.capabilities - %w{ PIPELINING SIZE VRFY STARTTLS ENHANCEDSTATUSCODES DSN}.each do |str| - assert capabilities.key?(str), str - end - end - - def test_capabilities_default - res = Response.parse("250-ubuntu-desktop\n250-PIPELINING\n250 DSN\n") - assert_equal [], res.capabilities['PIPELINING'] - end - - def test_capabilities_value - res = Response.parse("250-ubuntu-desktop\n250-SIZE 1234\n250 DSN\n") - assert_equal ['1234'], res.capabilities['SIZE'] - end - - def test_capabilities_multi - res = Response.parse("250-ubuntu-desktop\n250-SIZE 1 2 3\n250 DSN\n") - assert_equal %w{1 2 3}, res.capabilities['SIZE'] - end - - def test_bad_string - res = Response.parse("badstring") - assert_equal({}, res.capabilities) - end - - def test_success? - res = Response.parse("250-ubuntu-desktop\n250-SIZE 1 2 3\n250 DSN\n") - assert res.success? - assert !res.continue? - end - - # RFC 2821, Section 4.2.1 - def test_continue? - res = Response.parse("3yz-ubuntu-desktop\n250-SIZE 1 2 3\n250 DSN\n") - assert !res.success? - assert res.continue? - end - - def test_status_type_char - res = Response.parse("3yz-ubuntu-desktop\n250-SIZE 1 2 3\n250 DSN\n") - assert_equal '3', res.status_type_char - - res = Response.parse("250-ubuntu-desktop\n250-SIZE 1 2 3\n250 DSN\n") - assert_equal '2', res.status_type_char - end - - def test_message - res = Response.parse("250-ubuntu-desktop\n250-SIZE 1 2 3\n250 DSN\n") - assert_equal "250-ubuntu-desktop\n", res.message - end - - def test_server_busy_exception - res = Response.parse("400 omg busy") - assert_equal Net::SMTPServerBusy, res.exception_class - res = Response.parse("410 omg busy") - assert_equal Net::SMTPServerBusy, res.exception_class - end - - def test_syntax_error_exception - res = Response.parse("500 omg syntax error") - assert_equal Net::SMTPSyntaxError, res.exception_class - - res = Response.parse("501 omg syntax error") - assert_equal Net::SMTPSyntaxError, res.exception_class - end - - def test_authentication_exception - res = Response.parse("530 omg auth error") - assert_equal Net::SMTPAuthenticationError, res.exception_class - - res = Response.parse("531 omg auth error") - assert_equal Net::SMTPAuthenticationError, res.exception_class - end - - def test_fatal_error - res = Response.parse("510 omg fatal error") - assert_equal Net::SMTPFatalError, res.exception_class - - res = Response.parse("511 omg fatal error") - assert_equal Net::SMTPFatalError, res.exception_class - end - - def test_default_exception - res = Response.parse("250 omg fatal error") - assert_equal Net::SMTPUnknownError, res.exception_class - end - end - end -end diff --git a/test/net/smtp/test_smtp.rb b/test/net/smtp/test_smtp.rb deleted file mode 100644 index 91974d4dfe..0000000000 --- a/test/net/smtp/test_smtp.rb +++ /dev/null @@ -1,302 +0,0 @@ -# frozen_string_literal: true -require 'net/smtp' -require 'stringio' -require 'test/unit' - -module Net - class TestSMTP < Test::Unit::TestCase - CA_FILE = File.expand_path("../fixtures/cacert.pem", __dir__) - SERVER_KEY = File.expand_path("../fixtures/server.key", __dir__) - SERVER_CERT = File.expand_path("../fixtures/server.crt", __dir__) - - class FakeSocket - attr_reader :write_io - - def initialize out = "250 OK\n" - @write_io = StringIO.new - @read_io = StringIO.new out - end - - def writeline line - @write_io.write "#{line}\r\n" - end - - def readline - line = @read_io.gets - raise 'ran out of input' unless line - line.chop - end - end - - def setup - # Avoid hanging at fake_server_start's IO.select on --jit-wait CI like http://ci.rvm.jp/results/trunk-mjit-wait@phosphorus-docker/3302796 - # Unfortunately there's no way to configure read_timeout for Net::SMTP.start. - if defined?(RubyVM::JIT) && RubyVM::JIT.enabled? - Net::SMTP.prepend Module.new { - def initialize(*) - super - @read_timeout *= 5 - end - } - end - - @server_threads = [] - end - - def teardown - @server_threads.each {|th| th.join } - end - - def test_critical - smtp = Net::SMTP.new 'localhost', 25 - - assert_raise RuntimeError do - smtp.send :critical do - raise 'fail on purpose' - end - end - - assert_kind_of Net::SMTP::Response, smtp.send(:critical), - '[Bug #9125]' - end - - def test_esmtp - smtp = Net::SMTP.new 'localhost', 25 - assert smtp.esmtp - assert smtp.esmtp? - - smtp.esmtp = 'omg' - assert_equal 'omg', smtp.esmtp - assert_equal 'omg', smtp.esmtp? - end - - def test_rset - smtp = Net::SMTP.new 'localhost', 25 - smtp.instance_variable_set :@socket, FakeSocket.new - - assert smtp.rset - end - - def test_mailfrom - sock = FakeSocket.new - smtp = Net::SMTP.new 'localhost', 25 - smtp.instance_variable_set :@socket, sock - assert smtp.mailfrom("foo@example.com").success? - assert_equal "MAIL FROM:\r\n", sock.write_io.string - end - - def test_rcptto - sock = FakeSocket.new - smtp = Net::SMTP.new 'localhost', 25 - smtp.instance_variable_set :@socket, sock - assert smtp.rcptto("foo@example.com").success? - assert_equal "RCPT TO:\r\n", sock.write_io.string - end - - def test_auth_plain - sock = FakeSocket.new - smtp = Net::SMTP.new 'localhost', 25 - smtp.instance_variable_set :@socket, sock - assert smtp.auth_plain("foo", "bar").success? - assert_equal "AUTH PLAIN AGZvbwBiYXI=\r\n", sock.write_io.string - end - - def test_crlf_injection - smtp = Net::SMTP.new 'localhost', 25 - smtp.instance_variable_set :@socket, FakeSocket.new - - assert_raise(ArgumentError) do - smtp.mailfrom("foo\r\nbar") - end - - assert_raise(ArgumentError) do - smtp.mailfrom("foo\rbar") - end - - assert_raise(ArgumentError) do - smtp.mailfrom("foo\nbar") - end - - assert_raise(ArgumentError) do - smtp.rcptto("foo\r\nbar") - end - end - - def test_tls_connect - servers = Socket.tcp_server_sockets("localhost", 0) - ctx = OpenSSL::SSL::SSLContext.new - ctx.ca_file = CA_FILE - ctx.key = File.open(SERVER_KEY) { |f| - OpenSSL::PKey::RSA.new(f) - } - ctx.cert = File.open(SERVER_CERT) { |f| - OpenSSL::X509::Certificate.new(f) - } - begin - sock = nil - Thread.start do - s = accept(servers) - sock = OpenSSL::SSL::SSLSocket.new(s, ctx) - sock.sync_close = true - sock.accept - sock.write("220 localhost Service ready\r\n") - sock.gets - sock.write("250 localhost\r\n") - sock.gets - sock.write("221 localhost Service closing transmission channel\r\n") - end - smtp = Net::SMTP.new("localhost", servers[0].local_address.ip_port) - smtp.enable_tls - smtp.open_timeout = 1 - smtp.start(tls_verify: false) do - end - ensure - sock.close if sock - servers.each(&:close) - end - rescue LoadError - # skip (require openssl) - end - - def test_tls_connect_timeout - servers = Socket.tcp_server_sockets("localhost", 0) - begin - sock = nil - Thread.start do - sock = accept(servers) - end - smtp = Net::SMTP.new("localhost", servers[0].local_address.ip_port) - smtp.enable_tls - smtp.open_timeout = 0.1 - assert_raise(Net::OpenTimeout) do - smtp.start do - end - end - rescue LoadError - # skip (require openssl) - ensure - sock.close if sock - servers.each(&:close) - end - end - - def test_eof_error_backtrace - bug13018 = '[ruby-core:78550] [Bug #13018]' - servers = Socket.tcp_server_sockets("localhost", 0) - begin - sock = nil - t = Thread.start do - sock = accept(servers) - sleep 0.1 - sock.close - end - smtp = Net::SMTP.new("localhost", servers[0].local_address.ip_port) - e = assert_raise(EOFError, bug13018) do - smtp.start do - end - end - assert_equal(EOFError, e.class, bug13018) - assert(e.backtrace.grep(%r"\bnet/smtp\.rb:").size > 0, bug13018) - ensure - sock.close if sock - servers.each(&:close) - t.join - end - end - - def test_start - port = fake_server_start - smtp = Net::SMTP.start('localhost', port) - smtp.finish - end - - def test_start_with_position_argument - port = fake_server_start(helo: 'myname', user: 'account', password: 'password') - smtp = Net::SMTP.start('localhost', port, 'myname', 'account', 'password', :plain) - smtp.finish - end - - def test_start_with_keyword_argument - port = fake_server_start(helo: 'myname', user: 'account', password: 'password') - smtp = Net::SMTP.start('localhost', port, helo: 'myname', user: 'account', secret: 'password', authtype: :plain) - smtp.finish - end - - def test_start_password_is_secret - port = fake_server_start(helo: 'myname', user: 'account', password: 'password') - smtp = Net::SMTP.start('localhost', port, helo: 'myname', user: 'account', password: 'password', authtype: :plain) - smtp.finish - end - - def test_start_invalid_number_of_arguments - err = assert_raise ArgumentError do - Net::SMTP.start('localhost', 25, 'myname', 'account', 'password', :plain, :invalid_arg) - end - assert_equal('wrong number of arguments (given 7, expected 1..6)', err.message) - end - - def test_start_instance - port = fake_server_start - smtp = Net::SMTP.new('localhost', port) - smtp.start - smtp.finish - end - - def test_start_instance_with_position_argument - port = fake_server_start(helo: 'myname', user: 'account', password: 'password') - smtp = Net::SMTP.new('localhost', port) - smtp.start('myname', 'account', 'password', :plain) - smtp.finish - end - - def test_start_instance_with_keyword_argument - port = fake_server_start(helo: 'myname', user: 'account', password: 'password') - smtp = Net::SMTP.new('localhost', port) - smtp.start(helo: 'myname', user: 'account', secret: 'password', authtype: :plain) - smtp.finish - end - - def test_start_instance_password_is_secret - port = fake_server_start(helo: 'myname', user: 'account', password: 'password') - smtp = Net::SMTP.new('localhost', port) - smtp.start(helo: 'myname', user: 'account', password: 'password', authtype: :plain) - smtp.finish - end - - def test_start_instance_invalid_number_of_arguments - smtp = Net::SMTP.new('localhost') - err = assert_raise ArgumentError do - smtp.start('myname', 'account', 'password', :plain, :invalid_arg) - end - assert_equal('wrong number of arguments (given 5, expected 0..4)', err.message) - end - - private - - def accept(servers) - Socket.accept_loop(servers) { |s, _| break s } - end - - def fake_server_start(helo: 'localhost', user: nil, password: nil) - servers = Socket.tcp_server_sockets('localhost', 0) - @server_threads << Thread.start do - Thread.current.abort_on_exception = true - sock = accept(servers) - sock.puts "220 ready\r\n" - assert_equal("EHLO #{helo}\r\n", sock.gets) - sock.puts "220-servername\r\n220 AUTH PLAIN\r\n" - if user - credential = ["\0#{user}\0#{password}"].pack('m0') - assert_equal("AUTH PLAIN #{credential}\r\n", sock.gets) - sock.puts "235 2.7.0 Authentication successful\r\n" - end - assert_equal("QUIT\r\n", sock.gets) - sock.puts "221 2.0.0 Bye\r\n" - sock.close - servers.each(&:close) - end - port = servers[0].local_address.ip_port - return port - end - end -end diff --git a/test/net/smtp/test_ssl_socket.rb b/test/net/smtp/test_ssl_socket.rb deleted file mode 100644 index dd9529f25e..0000000000 --- a/test/net/smtp/test_ssl_socket.rb +++ /dev/null @@ -1,99 +0,0 @@ -# frozen_string_literal: true -require 'net/smtp' -require 'test/unit' - -module Net - class TestSSLSocket < Test::Unit::TestCase - class MySMTP < SMTP - attr_accessor :fake_tcp, :fake_ssl - - def initialize(*args) - super(*args) - @open_timeout = nil - end - - def tcp_socket address, port - fake_tcp - end - - def ssl_socket socket, context - fake_ssl - end - end - - require 'stringio' - class SSLSocket < StringIO - attr_accessor :sync_close, :connected, :closed - - def initialize(*args) - @connected = false - @closed = true - super - end - - def connect - self.connected = true - self.closed = false - end - - def close - self.closed = true - end - - def post_connection_check omg - end - end - - def test_ssl_socket_close_on_post_connection_check_fail - tcp_socket = StringIO.new success_response - - ssl_socket = SSLSocket.new.extend Module.new { - def post_connection_check omg - raise OpenSSL::SSL::SSLError, 'hostname was not match with the server certificate' - end - } - - ssl_context = OpenSSL::SSL::SSLContext.new - ssl_context.verify_mode = OpenSSL::SSL::VERIFY_PEER - connection = MySMTP.new('localhost', 25) - connection.enable_starttls_auto(ssl_context) - connection.fake_tcp = tcp_socket - connection.fake_ssl = ssl_socket - - assert_raise(OpenSSL::SSL::SSLError) do - connection.start - end - assert_equal true, ssl_socket.closed - end - - def test_ssl_socket_open_on_post_connection_check_success - tcp_socket = StringIO.new success_response - - ssl_socket = SSLSocket.new success_response - - connection = MySMTP.new('localhost', 25) - connection.enable_starttls_auto - connection.fake_tcp = tcp_socket - connection.fake_ssl = ssl_socket - - connection.start - assert_equal false, ssl_socket.closed - end - - def success_response - [ - '220 smtp.example.com ESMTP Postfix', - "250-ubuntu-desktop", - "250-PIPELINING", - "250-SIZE 10240000", - "250-VRFY", - "250-ETRN", - "250-STARTTLS", - "250-ENHANCEDSTATUSCODES", - "250-8BITMIME", - "250 DSN", - "220 2.0.0 Ready to start TLS", - ].join("\r\n") + "\r\n" - end - end -end if defined?(OpenSSL) diff --git a/test/net/smtp/test_sslcontext.rb b/test/net/smtp/test_sslcontext.rb deleted file mode 100644 index 4f1dcfe669..0000000000 --- a/test/net/smtp/test_sslcontext.rb +++ /dev/null @@ -1,129 +0,0 @@ -require 'net/smtp' -require 'test/unit' - -module Net - class TestSSLContext < Test::Unit::TestCase - class MySMTP < SMTP - attr_reader :__ssl_context, :__tls_hostname - - def initialize(socket) - @fake_socket = socket - super("smtp.example.com") - end - - def tcp_socket(*) - @fake_socket - end - - def ssl_socket_connect(*) - end - - def tlsconnect(*) - super - @fake_socket - end - - def ssl_socket(socket, context) - @__ssl_context = context - s = super - hostname = @__tls_hostname = '' - s.define_singleton_method(:post_connection_check){ |name| hostname.replace(name) } - s - end - end - - def teardown - @server_thread&.exit&.join - @server_socket&.close - @client_socket&.close - end - - def start_smtpd(starttls) - @server_socket, @client_socket = Object.const_defined?(:UNIXSocket) ? - UNIXSocket.pair : Socket.pair(:INET, :STREAM, 0) - @starttls_executed = false - @server_thread = Thread.new(@server_socket) do |s| - s.puts "220 fakeserver\r\n" - while cmd = s.gets&.chomp - case cmd - when /\AEHLO / - s.puts "250-fakeserver\r\n" - s.puts "250-STARTTLS\r\n" if starttls - s.puts "250 8BITMIME\r\n" - when /\ASTARTTLS/ - @starttls_executed = true - s.puts "220 2.0.0 Ready to start TLS\r\n" - else - raise "unsupported command: #{cmd}" - end - end - end - @client_socket - end - - def test_default - smtp = MySMTP.new(start_smtpd(true)) - smtp.start - assert_equal(OpenSSL::SSL::VERIFY_PEER, smtp.__ssl_context.verify_mode) - end - - def test_enable_tls - smtp = MySMTP.new(start_smtpd(true)) - context = OpenSSL::SSL::SSLContext.new - smtp.enable_tls(context) - smtp.start - assert_equal(context, smtp.__ssl_context) - end - - def test_enable_tls_before_disable_starttls - smtp = MySMTP.new(start_smtpd(true)) - context = OpenSSL::SSL::SSLContext.new - smtp.enable_tls(context) - smtp.disable_starttls - smtp.start - assert_equal(context, smtp.__ssl_context) - end - - def test_enable_starttls - smtp = MySMTP.new(start_smtpd(true)) - context = OpenSSL::SSL::SSLContext.new - smtp.enable_starttls(context) - smtp.start - assert_equal(context, smtp.__ssl_context) - end - - def test_enable_starttls_before_disable_tls - smtp = MySMTP.new(start_smtpd(true)) - context = OpenSSL::SSL::SSLContext.new - smtp.enable_starttls(context) - smtp.disable_tls - smtp.start - assert_equal(context, smtp.__ssl_context) - end - - def test_start_with_tls_verify_true - smtp = MySMTP.new(start_smtpd(true)) - smtp.start(tls_verify: true) - assert_equal(OpenSSL::SSL::VERIFY_PEER, smtp.__ssl_context.verify_mode) - end - - def test_start_with_tls_verify_false - smtp = MySMTP.new(start_smtpd(true)) - smtp.start(tls_verify: false) - assert_equal(OpenSSL::SSL::VERIFY_NONE, smtp.__ssl_context.verify_mode) - end - - def test_start_with_tls_hostname - smtp = MySMTP.new(start_smtpd(true)) - smtp.start(tls_hostname: "localhost") - assert_equal("localhost", smtp.__tls_hostname) - end - - def test_start_without_tls_hostname - smtp = MySMTP.new(start_smtpd(true)) - smtp.start - assert_equal("smtp.example.com", smtp.__tls_hostname) - end - - end -end diff --git a/test/net/smtp/test_starttls.rb b/test/net/smtp/test_starttls.rb deleted file mode 100644 index 4a29fa6d70..0000000000 --- a/test/net/smtp/test_starttls.rb +++ /dev/null @@ -1,122 +0,0 @@ -require 'net/smtp' -require 'test/unit' - -module Net - class TestStarttls < Test::Unit::TestCase - class MySMTP < SMTP - def initialize(socket) - @fake_socket = socket - super("smtp.example.com") - end - - def tcp_socket(*) - @fake_socket - end - - def tlsconnect(*) - @fake_socket - end - end - - def teardown - @server_thread&.exit&.join - @server_socket&.close - @client_socket&.close - end - - def start_smtpd(starttls) - @server_socket, @client_socket = Object.const_defined?(:UNIXSocket) ? - UNIXSocket.pair : Socket.pair(:INET, :STREAM, 0) - @starttls_executed = false - @server_thread = Thread.new(@server_socket) do |s| - s.puts "220 fakeserver\r\n" - while cmd = s.gets&.chomp - case cmd - when /\AEHLO / - s.puts "250-fakeserver\r\n" - s.puts "250-STARTTLS\r\n" if starttls - s.puts "250 8BITMIME\r\n" - when /\ASTARTTLS/ - @starttls_executed = true - s.puts "220 2.0.0 Ready to start TLS\r\n" - else - raise "unsupported command: #{cmd}" - end - end - end - @client_socket - end - - def test_default_with_starttls_capable - smtp = MySMTP.new(start_smtpd(true)) - smtp.start - assert(@starttls_executed) - end - - def test_default_without_starttls_capable - smtp = MySMTP.new(start_smtpd(false)) - smtp.start - assert(!@starttls_executed) - end - - def test_enable_starttls_with_starttls_capable - smtp = MySMTP.new(start_smtpd(true)) - smtp.enable_starttls - smtp.start - assert(@starttls_executed) - end - - def test_enable_starttls_without_starttls_capable - smtp = MySMTP.new(start_smtpd(false)) - smtp.enable_starttls - err = assert_raise(Net::SMTPUnsupportedCommand) { smtp.start } - assert_equal("STARTTLS is not supported on this server", err.message) - end - - def test_enable_starttls_auto_with_starttls_capable - smtp = MySMTP.new(start_smtpd(true)) - smtp.enable_starttls_auto - smtp.start - assert(@starttls_executed) - end - - def test_tls_with_starttls_capable - smtp = MySMTP.new(start_smtpd(true)) - smtp.enable_tls - smtp.start - assert(!@starttls_executed) - end - - def test_tls_without_starttls_capable - smtp = MySMTP.new(start_smtpd(false)) - smtp.enable_tls - end - - def test_disable_starttls - smtp = MySMTP.new(start_smtpd(true)) - smtp.disable_starttls - smtp.start - assert(!@starttls_executed) - end - - def test_enable_tls_and_enable_starttls - smtp = MySMTP.new(start_smtpd(true)) - smtp.enable_tls - err = assert_raise(ArgumentError) { smtp.enable_starttls } - assert_equal("SMTPS and STARTTLS is exclusive", err.message) - end - - def test_enable_tls_and_enable_starttls_auto - smtp = MySMTP.new(start_smtpd(true)) - smtp.enable_tls - err = assert_raise(ArgumentError) { smtp.enable_starttls_auto } - assert_equal("SMTPS and STARTTLS is exclusive", err.message) - end - - def test_enable_starttls_and_enable_starttls_auto - smtp = MySMTP.new(start_smtpd(true)) - smtp.enable_starttls - assert_nothing_raised { smtp.enable_starttls_auto } - end - end -end -- cgit v1.2.3