Performs an authentication attempt using the PLAIN mechanism.

        Protocol:

            1. Format the username and password in a suitable way ;
            2. The formatted string is base64-encoded ;
            3. The string 'AUTH PLAIN' and a space character are prepended to
               the base64-encoded username and password and sent to the
               server ;
            4. If the server replies with a 235 return code, user is
               authenticated.

        Args:
            username (str): Identifier of the user trying to authenticate.
            password (str): Password for the user.

        Raises:
            ConnectionResetError: If the connection with the server is
                unexpectedely lost.
            SMTPAuthenticationError: If the authentication attempt fails.

        Returns:
            (int, str): A (code, message) 2-tuple containing the server
                response.

async def _auth_plain(self, username, password):
        """
        Performs an authentication attempt using the PLAIN mechanism.

        Protocol:

            1. Format the username and password in a suitable way ;
            2. The formatted string is base64-encoded ;
            3. The string 'AUTH PLAIN' and a space character are prepended to
               the base64-encoded username and password and sent to the
               server ;
            4. If the server replies with a 235 return code, user is
               authenticated.

        Args:
            username (str): Identifier of the user trying to authenticate.
            password (str): Password for the user.

        Raises:
            ConnectionResetError: If the connection with the server is
                unexpectedely lost.
            SMTPAuthenticationError: If the authentication attempt fails.

        Returns:
            (int, str): A (code, message) 2-tuple containing the server
                response.
        """
        mechanism = "PLAIN"

        credentials = "\0{}\0{}".format(username, password)
        encoded_credentials = SMTP.b64enc(credentials)

        try:
            code, message = await self.do_cmd(
                "AUTH", mechanism, encoded_credentials, success=(235, 503)
            )
        except SMTPCommandFailedError as e:
            raise SMTPAuthenticationError(e.code, e.message, mechanism)

        return code, message