Skip to content

Commit

Permalink
♻️ SASL LOGIN: Add "#done?" [🚧 WIP]
Browse files Browse the repository at this point in the history
The client should raise an error if the command completes successfully
but "done?" returns false.

Also move to sasl dir and SASL module.
  • Loading branch information
nevans committed Jul 25, 2023
1 parent 619247a commit b6fdf18
Show file tree
Hide file tree
Showing 4 changed files with 64 additions and 49 deletions.
45 changes: 0 additions & 45 deletions lib/net/imap/authenticators/login.rb

This file was deleted.

5 changes: 2 additions & 3 deletions lib/net/imap/sasl.rb
Original file line number Diff line number Diff line change
Expand Up @@ -67,13 +67,14 @@ module SASL

autoload :CramMD5Authenticator, "#{sasl_dir}/cram_md5_authenticator"
autoload :DigestMD5Authenticator, "#{sasl_dir}/digest_md5_authenticator"
autoload :LoginAuthenticator, "#{sasl_dir}/login_authenticator"

# Authenticators are all lazy loaded
def self.authenticators
@authenticators ||= SASL::Authenticators.new.tap do |registry|
registry.add_authenticator "Plain"
registry.add_authenticator "XOAuth2"
registry.add_authenticator "Login", LoginAuthenticator # deprecated
registry.add_authenticator "Login" # deprecated
registry.add_authenticator "Cram-MD5" # deprecated
registry.add_authenticator "Digest-MD5" # deprecated
end
Expand Down Expand Up @@ -105,5 +106,3 @@ def saslprep(string, **opts)
end
end
end

require_relative "authenticators/login"
61 changes: 61 additions & 0 deletions lib/net/imap/sasl/login_authenticator.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,61 @@
# frozen_string_literal: true

module Net
class IMAP < Protocol
module SASL

# Authenticator for the "+LOGIN+" SASL mechanism. See Net::IMAP#authenticate.
#
# +LOGIN+ authentication sends the password in cleartext.
# RFC3501[https://tools.ietf.org/html/rfc3501] encourages servers to disable
# cleartext authentication until after TLS has been negotiated.
# RFC8314[https://tools.ietf.org/html/rfc8314] recommends TLS version 1.2 or
# greater be used for all traffic, and deprecate cleartext access ASAP. +LOGIN+
# can be secured by TLS encryption.
#
# == Deprecated
#
# The {SASL mechanisms
# registry}[https://www.iana.org/assignments/sasl-mechanisms/sasl-mechanisms.xhtml]
# marks "LOGIN" as obsoleted in favor of "PLAIN". It is included here for
# compatibility with existing servers. See
# {draft-murchison-sasl-login}[https://www.iana.org/go/draft-murchison-sasl-login]
# for both specification and deprecation.
class LoginAuthenticator

STATE_USER = :USER
STATE_PASSWORD = :PASSWORD
STATE_DONE = :DONE
private_constant :STATE_USER, :STATE_PASSWORD, :STATE_DONE

def initialize(user, password, warn_deprecation: true, **_ignored)
if warn_deprecation
warn "WARNING: LOGIN SASL mechanism is deprecated. Use PLAIN instead."
end
@user = user
@password = password
@state = STATE_USER
end

def process(data)
case @state
when STATE_USER
@state = STATE_PASSWORD
@user
when STATE_PASSWORD
@state = STATE_DONE
@password
when STATE_DONE
raise ResponseParseError, data
end
end

def done?; @state == STATE_DONE end
end
end

LoginAuthenticator = SASL::LoginAuthenticator # :nodoc:
deprecate_constant :LoginAuthenticator

end
end
2 changes: 1 addition & 1 deletion test/net/imap/test_imap_authenticators.rb
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ def login(*args, warn_deprecation: false, **kwargs, &block)
end

def test_login_authenticator_matches_mechanism
assert_kind_of(Net::IMAP::LoginAuthenticator, login("n", "p"))
assert_kind_of(Net::IMAP::SASL::LoginAuthenticator, login("n", "p"))
end

def test_login_authenticator_deprecated
Expand Down

0 comments on commit b6fdf18

Please sign in to comment.