Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Replace deprecated Network usage #25

Merged
merged 5 commits into from
Jun 19, 2019

Conversation

shulhi
Copy link
Contributor

@shulhi shulhi commented May 24, 2019

This PR removes the use of deprecated Network module (from network). Unfortunately there are breaking changes but they are pretty easy to fix (only change of types).

It is still work in progress but I like to get an early feedback if this is the way going forward. I am using this at work, so preferably we like to get this merged at some point when this PR is ready (should be soon).

Copy link
Collaborator

@parsonsmatt parsonsmatt left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks good so far! I'd prefer if the indentation style was kept consistent to 4 space. I've got a few questions and comments, but I think this should be good to get merged when done.

Network/Mail/SMTP.hs Outdated Show resolved Hide resolved
Network/Mail/SMTP.hs Outdated Show resolved Hide resolved
smtp-mail.cabal Outdated Show resolved Hide resolved
smtp-mail.cabal Outdated Show resolved Hide resolved
@@ -137,8 +137,14 @@ parseResponse conn = do
(code, bdy) <- readLines
return (read $ B8.unpack code, B8.unlines bdy)
where
getLines c acc = do
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@parsonsmatt I need some help with this as I am not sure if this is right or should I just stick with connectionGetLine. Having to specify max bytes per line seems a little off to me.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thinking out loud here:

  • This function is replacing B8.hGetLine :: Handle -> IO ByteString. Implementation linked.
  • This function reads from the bytestring until it either finds a \n character or the end-of-file. (figuring this out exactly took me a long time, dang the bytestring internals are tough)
  • connectionGetLine doesn't work in exactly the same way. The Int parameter is to prevent DoS attacks, so it'd be a security improvement to have it for sure - no idea what typical line length limit might be safe here 🤷‍♂️ .
  • The bigger problem with connectionGetLine is that it throws isEOFError exception on end of input. Except, it says "An end of file will be considered as a line terminator too, if line is not empty." - Looking at the source... well, it's a bit confusing, but I think I've worked out what is going on.

I think we're fine with connectionGetLine, we just need to pick a suitable line length.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I did a quick Google and got this StackOverflow post re line lengths in mail.

I think 1000 is a reasonable pick. The standard says lines MUST be no more than 998 characters.

@@ -309,27 +318,19 @@ simpleMail from to cc bcc subject parts =

-- | Construct a plain text 'Part'
plainTextPart :: TL.Text -> Part
plainTextPart = Part "text/plain; charset=utf-8"
QuotedPrintableText Nothing [] . TL.encodeUtf8
plainTextPart body = Part "text/plain; charset=utf-8"
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@parsonsmatt mime-mail has plainPart, htmlPart, and filePart. Should I just remove these and prefer ones from mime-mail instead?

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This PR is a breaking change to the type of exposed functions, and thus a major version bump. I think it'd be fine to write DEPRECATED pragmas for these functions, point users to the relevant mime-mail replacements, and we'll remove in another major version bump.

@shulhi
Copy link
Contributor Author

shulhi commented Jun 18, 2019

@parsonsmatt What do you think about these changes? Are there anything you like me to change in order to get this PR in?

@parsonsmatt parsonsmatt self-assigned this Jun 18, 2019
Copy link
Collaborator

@parsonsmatt parsonsmatt left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's use connectionGetLine 1000 instead of the getLines function and we'll be all set. Sorry for sitting on this so long!

@@ -309,27 +318,19 @@ simpleMail from to cc bcc subject parts =

-- | Construct a plain text 'Part'
plainTextPart :: TL.Text -> Part
plainTextPart = Part "text/plain; charset=utf-8"
QuotedPrintableText Nothing [] . TL.encodeUtf8
plainTextPart body = Part "text/plain; charset=utf-8"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This PR is a breaking change to the type of exposed functions, and thus a major version bump. I think it'd be fine to write DEPRECATED pragmas for these functions, point users to the relevant mime-mail replacements, and we'll remove in another major version bump.

@@ -137,8 +137,14 @@ parseResponse conn = do
(code, bdy) <- readLines
return (read $ B8.unpack code, B8.unlines bdy)
where
getLines c acc = do
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

thinking out loud here:

  • This function is replacing B8.hGetLine :: Handle -> IO ByteString. Implementation linked.
  • This function reads from the bytestring until it either finds a \n character or the end-of-file. (figuring this out exactly took me a long time, dang the bytestring internals are tough)
  • connectionGetLine doesn't work in exactly the same way. The Int parameter is to prevent DoS attacks, so it'd be a security improvement to have it for sure - no idea what typical line length limit might be safe here 🤷‍♂️ .
  • The bigger problem with connectionGetLine is that it throws isEOFError exception on end of input. Except, it says "An end of file will be considered as a line terminator too, if line is not empty." - Looking at the source... well, it's a bit confusing, but I think I've worked out what is going on.

I think we're fine with connectionGetLine, we just need to pick a suitable line length.

res <- Conn.connectionGetChunk c
if B8.null res
then return acc
else getLines c $ B8.append acc res
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This current implementation does not return a line, but instead returns the entire contents of the connection. Replacing it with connectionGetLine will fix it.

@@ -137,8 +137,14 @@ parseResponse conn = do
(code, bdy) <- readLines
return (read $ B8.unpack code, B8.unlines bdy)
where
getLines c acc = do
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I did a quick Google and got this StackOverflow post re line lengths in mail.

I think 1000 is a reasonable pick. The standard says lines MUST be no more than 998 characters.

@shulhi
Copy link
Contributor Author

shulhi commented Jun 19, 2019

@parsonsmatt I resolved all feedbacks. Let's get it merge if you think it's okay now 😃

@parsonsmatt parsonsmatt merged commit 1807a03 into jhickner:master Jun 19, 2019
@shulhi shulhi deleted the shulhi-ghc86-upgrade branch June 20, 2019 00:48
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants