Browse Source

Added schema validation to emails namespace

master
Stephen Starkey 2 years ago
parent
commit
9a08c7c2db
  1. 23
      src/clj/email_counter/emails.clj
  2. 11
      test/clj/email_counter/test/emails.clj
  3. 7
      test/clj/email_counter/test/handler.clj

23
src/clj/email_counter/emails.clj

@ -1,19 +1,20 @@
(ns email-counter.emails
(:require [clojure.string :as str])
(:require [clojure.string :as str]
[schema.core :as s])
(:import (javax.mail.internet AddressException InternetAddress)))
(defn parse-email
(s/defn parse-email :- (s/maybe s/Str)
"Attempt to get the address portion of an assumed rfc822-compliant email
address. If we can't, we return nil."
[s]
[email :- (s/maybe s/Str)]
(try
(when s (-> s InternetAddress. .getAddress))
(when email (-> email InternetAddress. .getAddress))
(catch AddressException _)))
(defn parse-for-gmail
(s/defn parse-for-gmail :- (s/maybe s/Str)
"Given a valid email address, strip any periods and any content after a +
from the name portion. If the email is nil, we will simply return nil"
[email]
[email :- (s/maybe s/Str)]
(let [email (parse-email email)
[_ n d] (when email (re-matches #"^(.*?)(@[^@]+$)" email))]
(some-> n
@ -21,18 +22,18 @@
(str/replace #"\+.*" "")
(str d))))
(defn unique-gmail-parsed-emails
(s/defn unique-gmail-parsed-set :- #{s/Str}
"Given a bunch of email addresses, strip out the bits Gmail would have
stripped out, lower-case them, and then add them to a hash set"
[emails]
[emails :- [(s/maybe s/Str)]]
(->> emails
(map parse-for-gmail)
(remove nil?)
(map str/lower-case)
(into #{})))
(defn count-unique
(s/defn count-unique :- s/Int
"Given a bunch of email addresses, count the number of unique ones, given
Gmail's special parsing rules."
[emails]
(count (unique-gmail-parsed-emails emails)))
[emails :- [(s/maybe s/Str)]]
(count (unique-gmail-parsed-set emails)))

11
test/clj/email_counter/test/emails.clj

@ -1,6 +1,11 @@
(ns email-counter.test.emails
(:require [clojure.test :refer :all]
[email-counter.emails :refer :all]))
[email-counter.emails :refer :all]
[schema.core :as s]))
(use-fixtures
:once
(fn [f] (s/with-fn-validation (f))))
(deftest parse-email-test
(are [expected given] (= expected (parse-email given))
@ -21,10 +26,10 @@
"me@here.com" "me+you+another-person@here.com"
"me@here.com" "Me <me@here.com>"))
(deftest unique-gmail-parsed-emails-test
(deftest unique-gmail-parsed-set-test
(is (= #{"me@here.com"
"you@there.com"}
(unique-gmail-parsed-emails
(unique-gmail-parsed-set
["me@here.com"
"m.e@here.com"
"Me <me@here.com>"

7
test/clj/email_counter/test/handler.clj

@ -6,14 +6,17 @@
[email-counter.handler :refer :all]
[muuntaja.core :as m]
[mount.core :as mount]
[ring.mock.request :refer :all]))
[ring.mock.request :refer :all]
[schema.core :as s]))
(use-fixtures
:once
(fn [f]
(mount/start #'email-counter.config/env
#'email-counter.handler/app-routes)
(try (f) (finally (mount/stop)))))
(try
(s/with-fn-validation (f))
(finally (mount/stop)))))
(defn decode-response-body [{{:strs [Content-Type]} :headers :as response}]
(case (first (str/split Content-Type #";"))

Loading…
Cancel
Save