Skip to content

Instantly share code, notes, and snippets.

@javazquez
Last active December 3, 2017 17:45
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save javazquez/9fb1e5d2a8104ae1e6900789b817565c to your computer and use it in GitHub Desktop.
Save javazquez/9fb1e5d2a8104ae1e6900789b817565c to your computer and use it in GitHub Desktop.
Clojurescript Gmail API example ran with lumo. Converted Nodejs example from https://developers.google.com/gmail/api/quickstart/nodejs
;; Juan Vazquez
;; javazquez.com
;; https://github.com/javazquez
;; example converted from https://developers.google.com/gmail/api/quickstart/nodejs
(ns gmail-client.gapi
(:require [fs ]
[readline]
[googleapis :as google]
[google-auth-library :as googleAuth]
[goog.object]))
;; If modifying these scopes, delete your previously saved credentials
;; at ~/.credentials/gmail-nodejs-quickstart.json
(def SCOPES ["https://www.googleapis.com/auth/gmail.readonly"]);
(def TOKEN_DIR (str (or js/process.env.HOME
js/process.env.HOMEPATH
js/process.env.USERPROFILE)
"/.credentials/"))
(def TOKEN_PATH (str TOKEN_DIR "gmail-nodejs-quickstart.json"))
(defn list-labels
" * Lists the labels in the user's account.
*
* @param {google.auth.OAuth2} auth An authorized OAuth2 client."
[auth]
(let [gmail (.gmail google "v1") ]
(.list gmail.users.labels
(clj->js {:auth auth
:userId "me"})
(fn [err, response]
(if err
(js/console.log "The API return error: " err)
(let [labels (goog.object/get response "labels") ]
(if (< 0
(count (js->clj labels)))
(js/console.log "No Labels found." labels)
(run! #(js/console.log (.name %))
labels))))))))
(defn store-token
"Store token to disk be used in later program executions.
@param {Object} token The token to store to disk."
[token]
(try
(.mkdirSync fs TOKEN_DIR)
(catch :default err
(if (not= "EEXIST"
(.code err ))
(throw err))))
(.writeFile fs
TOKEN_PATH
(js/JSON.stringify token))
(js/console.log "Token stored to " TOKEN_PATH))
(defn get-new-token
"Get and store new token after prompting for user authorization, and then
execute the given callback with the authorized OAuth2 client.
@param {google.auth.OAuth2} oauth2Client The OAuth2 client to get token for.
@param {getEventsCallback} callback The callback to call with the authorized
client."
[oauth2-client callback]
(let [auth-url (.generateAuthUrl oauth2-client
(clj->js {:access_type "offline"
:scope SCOPES}))
rl (.createInterface readline
#js {:input js/process.stdin
:output js/process.stdout})]
(js/console.log "Authorize this app by visiting this url" auth-url)
(.question rl
"Enter the code from the page here:"
(fn [code]
(js/console.log "Calling inner function")
(.close rl)
(.getToken oauth2-client
code
(fn [err token]
(if err
(js/console.log "Error while trying to get access token" err)
(do
(goog.object/set oauth2-client
"credentials"
token)
(store-token token)
(callback oauth2-client)))))))))
(defn authorize
"Create an OAuth2 client with the given credentials, and then execute the
given callback function.
@param {Object} credentials The authorization client credentials.
@param {function} callback The callback to call with the authorized client."
[credentials callback]
(let [client-secret (goog.object/getValueByKeys credentials
"installed"
"client_secret")
client-id (goog.object/getValueByKeys credentials
"installed"
"client_id")
redirect-url (first (goog.object/getValueByKeys credentials
"installed"
"redirect_uris"))
auth (googleAuth.)
oauth2-client (auth.OAuth2.
client-id
client-secret
redirect-url)]
(.readFile fs
TOKEN_PATH
(fn [err token]
(if err
(get-new-token oauth2-client
callback)
(do (goog.object/set oauth2-client
"credentials"
(js/JSON.parse token))
(callback oauth2-client)) )))))
(defn process-client-secrets
"Authorize a client with the loaded credentials, then call the
Gmail API."
[err, content]
(if err
(js/console.log "Error loading client secret file:" err)
(authorize (js/JSON.parse content)
list-labels)))
;; Load client secrets from a local file.
(.readFile fs "client_secret.json"
process-client-secrets)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment