@@ -76,79 +76,74 @@ module Mail
76
76
class SMTP
77
77
attr_accessor :settings
78
78
79
+ DEFAULTS = {
80
+ :address => 'localhost' ,
81
+ :port => 25 ,
82
+ :domain => 'localhost.localdomain' ,
83
+ :user_name => nil ,
84
+ :password => nil ,
85
+ :authentication => nil ,
86
+ :enable_starttls => nil ,
87
+ :enable_starttls_auto => true ,
88
+ :openssl_verify_mode => nil ,
89
+ :ssl => nil ,
90
+ :tls => nil ,
91
+ :open_timeout => nil ,
92
+ :read_timeout => nil
93
+ }
94
+
79
95
def initialize ( values )
80
- self . settings = { :address => "localhost" ,
81
- :port => 25 ,
82
- :domain => 'localhost.localdomain' ,
83
- :user_name => nil ,
84
- :password => nil ,
85
- :authentication => nil ,
86
- :enable_starttls => nil ,
87
- :enable_starttls_auto => true ,
88
- :openssl_verify_mode => nil ,
89
- :ssl => nil ,
90
- :tls => nil ,
91
- :open_timeout => nil ,
92
- :read_timeout => nil
93
- } . merge! ( values )
96
+ self . settings = DEFAULTS . merge ( values )
94
97
end
95
98
96
- # Send the message via SMTP.
97
- # The from and to attributes are optional. If not set, they are retrieve from the Message.
98
99
def deliver! ( mail )
99
- smtp_from , smtp_to , message = Mail ::CheckDeliveryParams . check ( mail )
100
-
101
- smtp = Net ::SMTP . new ( settings [ :address ] , settings [ :port ] )
102
- if settings [ :tls ] || settings [ :ssl ]
103
- if smtp . respond_to? ( :enable_tls )
104
- smtp . enable_tls ( ssl_context )
105
- end
106
- elsif settings [ :enable_starttls ]
107
- if smtp . respond_to? ( :enable_starttls )
108
- smtp . enable_starttls ( ssl_context )
109
- end
110
- elsif settings [ :enable_starttls_auto ]
111
- if smtp . respond_to? ( :enable_starttls_auto )
112
- smtp . enable_starttls_auto ( ssl_context )
113
- end
100
+ response = start_smtp_session do |smtp |
101
+ Mail ::SMTPConnection . new ( :connection => smtp , :return_response => true ) . deliver! ( mail )
114
102
end
115
- smtp . open_timeout = settings [ :open_timeout ] if settings [ :open_timeout ]
116
- smtp . read_timeout = settings [ :read_timeout ] if settings [ :read_timeout ]
117
103
118
- response = nil
119
- smtp . start ( settings [ :domain ] , settings [ :user_name ] , settings [ :password ] , settings [ :authentication ] ) do |smtp_obj |
120
- response = smtp_obj . sendmail ( dot_stuff ( message ) , smtp_from , smtp_to )
121
- end
122
-
123
- if settings [ :return_response ]
124
- response
125
- else
126
- self
127
- end
104
+ settings [ :return_response ] ? response : self
128
105
end
129
106
130
107
private
108
+ def start_smtp_session ( &block )
109
+ build_smtp_session . start ( settings [ :domain ] , settings [ :user_name ] , settings [ :password ] , settings [ :authentication ] , &block )
110
+ end
131
111
132
- # This is Net::SMTP's job, but before Ruby 2.x it does not dot-stuff
133
- # an unterminated last line: https://bugs.ruby-lang.org/issues/9627
134
- def dot_stuff ( message )
135
- message . gsub ( /(\r \n \. )(\r \n |$)/ , '\1.\2' )
136
- end
137
-
138
- # Allow SSL context to be configured via settings, for Ruby >= 1.9
139
- # Just returns openssl verify mode for Ruby 1.8.x
140
- def ssl_context
141
- openssl_verify_mode = settings [ :openssl_verify_mode ]
112
+ def build_smtp_session
113
+ Net ::SMTP . new ( settings [ :address ] , settings [ :port ] ) . tap do |smtp |
114
+ if settings [ :tls ] || settings [ :ssl ]
115
+ if smtp . respond_to? ( :enable_tls )
116
+ smtp . enable_tls ( ssl_context )
117
+ end
118
+ elsif settings [ :enable_starttls ]
119
+ if smtp . respond_to? ( :enable_starttls )
120
+ smtp . enable_starttls ( ssl_context )
121
+ end
122
+ elsif settings [ :enable_starttls_auto ]
123
+ if smtp . respond_to? ( :enable_starttls_auto )
124
+ smtp . enable_starttls_auto ( ssl_context )
125
+ end
126
+ end
142
127
143
- if openssl_verify_mode . kind_of? ( String )
144
- openssl_verify_mode = OpenSSL ::SSL . const_get ( "VERIFY_#{ openssl_verify_mode . upcase } " )
128
+ smtp . open_timeout = settings [ :open_timeout ] if settings [ :open_timeout ]
129
+ smtp . read_timeout = settings [ :read_timeout ] if settings [ :read_timeout ]
130
+ end
145
131
end
146
132
147
- context = Net ::SMTP . default_ssl_context
148
- context . verify_mode = openssl_verify_mode if openssl_verify_mode
149
- context . ca_path = settings [ :ca_path ] if settings [ :ca_path ]
150
- context . ca_file = settings [ :ca_file ] if settings [ :ca_file ]
151
- context
152
- end
133
+ # Allow SSL context to be configured via settings, for Ruby >= 1.9
134
+ # Just returns openssl verify mode for Ruby 1.8.x
135
+ def ssl_context
136
+ openssl_verify_mode = settings [ :openssl_verify_mode ]
137
+
138
+ if openssl_verify_mode . kind_of? ( String )
139
+ openssl_verify_mode = OpenSSL ::SSL . const_get ( "VERIFY_#{ openssl_verify_mode . upcase } " )
140
+ end
141
+
142
+ context = Net ::SMTP . default_ssl_context
143
+ context . verify_mode = openssl_verify_mode if openssl_verify_mode
144
+ context . ca_path = settings [ :ca_path ] if settings [ :ca_path ]
145
+ context . ca_file = settings [ :ca_file ] if settings [ :ca_file ]
146
+ context
147
+ end
153
148
end
154
149
end
0 commit comments