Home > database >  Haskell function that parses an email address
Haskell function that parses an email address

Time:11-23

Is there a Haskell function that parses an email address in a standard format? For example:

parseEmailAddress "Jon Doe<[email protected]>"

would return something like:

Address (Just "Jon Doe") "[email protected]"

I could not find a function that does this in the mime-mail package.

CodePudding user response:

Would something like this work:

parseEmailAddress xs =
  case break (== '<') of
    (mail, "") -> Address Nothing mail
    (name, mail) -> Address (Just name) (init (tail mail))

This assumes that the name does not include the < character.

CodePudding user response:

Okay. Here is what I wrote.

{-# LANGUAGE NamedFieldPuns #-}

module Email (parseEmailAddress) where

import           Text.Parsec (parse)
import           Text.Parsec.Rfc2822 (NameAddr(..), name_addr)
import           Network.Mail.Mime (Address(..))
import           Data.Text (pack)
import           Data.List (elem)

mapMaybe :: (a -> b) -> Maybe a -> Maybe b
mapMaybe _ Nothing = Nothing
mapMaybe f (Just a) = Just (f a)

-- | Given a string email address, spits out an Address record
parseEmailAddress :: String -> Maybe Address
parseEmailAddress str =
  case parse name_addr "" addr of
    Left _ ->
      Nothing
    Right (NameAddr { nameAddr_name, nameAddr_addr }) ->
      Just (Address (mapMaybe pack nameAddr_name) (pack nameAddr_addr))
  where
    -- Standardize the email address
    addr = if '<' `elem` str then str else "<"    str    ">"

Then, the function would work as follows:

parseEmailAddress "[email protected]"  -- Just (Address Nothing "[email protected]")

parseEmailAddress "John Doe <[email protected]>" -- Just (Address (Just "John Doe") "[email protected]")

parseEmailAddress "johndoe" -- Nothing
  • Related